diff --git a/components/dropdown.vue b/components/dropdown.vue
index cfb6085..1dff597 100644
--- a/components/dropdown.vue
+++ b/components/dropdown.vue
@@ -17,6 +17,7 @@
     margin-top: 5px;
     z-index: 3;
     border: 1px solid black;
+    top: 100%;
   }
   
   .entry {
diff --git a/components/estimate-test.vue b/components/estimate-test.vue
index ce1d0b4..e0117f9 100644
--- a/components/estimate-test.vue
+++ b/components/estimate-test.vue
@@ -1,5 +1,6 @@
 <template>
 <div id="pdf-doc" ref="doc" v-if="estimate">
+<div class="disclaimer"><p>Actual costs may vary from estimates after approval. Get an official quote before choosing a loan.</p></div>
 
 <header class="heading">
 
@@ -11,14 +12,18 @@
 <h4>{{user.firstName + " " + user.lastName}}</h4>
 <span>{{user.email}}</span>
 <span>{{user.phone}}</span>
-<small>{{user.phone}}</small>
+<small>{{user.address.street}}</small>
+<small>
+{{`${user.address.city}, ${user.address.region} ${user.address.zip}`}}
+</small>
 </div>
 <img :src="avatar"/>
 </div>
 
 </header>
 
-<button @click="makePDF">Generate</button>
+<button @click="getPdf">Generate</button>
+<a :href="pdfLink" v-if="pdfLink" download="estimate.pdf">download </a>
 </div>
 </template>
 
@@ -30,6 +35,7 @@ const doc = ref(null)
 const props = defineProps(['token', 'estimate', 'user'])
 const estimate = ref(null)
 const estimates = ref(null)
+const pdfLink = ref('')
 
 const letterhead = computed(() => {
     if (!props.user.letterhead) return null
@@ -43,7 +49,11 @@ const avatar = computed(() => {
 })
 
 function makePDF() {
-  html2pdf(doc.value)
+    var opt = {
+        image: { type: 'png', quality: 1 },
+    }
+
+  html2pdf(doc.value, opt)
 }
 
 
@@ -65,18 +75,62 @@ function getEstimates() {
 	})
 }
 
+function getPdf() {
+	fetch(`/api/pdf`,
+		{method: 'GET',
+    		headers: {
+        	"Accept": "application/json",
+        	"Authorization": `Bearer ${props.token}`,
+    		},
+	}).then(response => {
+		if (response.ok) { return response.blob() }
+		else {
+		    return null
+		}
+	}).then (result => {
+		if (!result) return
+		pdfLink.value = URL.createObjectURL(result)
+	})
+}
+
 onMounted(() => {
     getEstimates().then(() => estimate.value = estimates.value[0])
 })
 </script>
 
 <style scoped>
+#pdf-doc {
+    margin: 4px 30px;
+}
+
+.disclaimer {
+    font-weight: bold;
+    border-bottom: 1px solid lightgrey;
+    margin-bottom: 20px;
+    color: var(--text);
+}
+
+.disclaimer p {
+    margin: 5px 0;
+}
+
+h4 {
+    margin: 4px 0;
+}
+
 header.heading {
     display: flex;
+    justify-content: space-between;
 }
 
 .user-info {
     display: flex;
     flex-flow: column;
 }
+
+#pdf-doc header.heading > div {
+    display: flex;
+    gap: 8px;
+    text-align: right;
+}
 </style>
diff --git a/components/settings.vue b/components/settings.vue
index fc48171..b966e7f 100644
--- a/components/settings.vue
+++ b/components/settings.vue
@@ -31,7 +31,7 @@
 <label for="">NMLS ID</label>
 <input type="text">
 <label for="">Branch ID</label>
-<input type="text" :value="user.branchId">
+<input type="text" :value="user.branchId" disabled>
 
 <select id="" name="" :value="user.country">
 	<option value="USA">USA</option>
@@ -288,5 +288,6 @@ watch(props.user, (u) => {
     div.address-entry {
         display: flex;
         flex-flow: column;
+        position: relative;
     }
 </style>
diff --git a/skouter.go b/skouter.go
index 56d22a2..753f521 100644
--- a/skouter.go
+++ b/skouter.go
@@ -2,6 +2,7 @@ package main
 
 import (
 		"os"
+		"os/exec"
 		"net/http"
 		"net/mail"
 		"log"
@@ -12,6 +13,7 @@ import (
 		_ "github.com/go-sql-driver/mysql"
 		"fmt"
 		"encoding/json"
+		"encoding/base64"
 		"strconv"
 		"bytes"
 		"time"
@@ -811,7 +813,8 @@ func queryUsers(db *sql.DB, id int) ( []User, error ) {
 	u.status,
 	u.verified,
 	u.role,
-	u.address
+	u.address,
+	u.phone
 	FROM user u WHERE u.id = CASE @e := ? WHEN 0 THEN u.id ELSE @e END
 	`
 	rows, err = db.Query(query, id)
@@ -838,6 +841,7 @@ func queryUsers(db *sql.DB, id int) ( []User, error ) {
 			&user.Verified,
 			&user.Role,
 			&user.Address.Id,
+			&user.Phone,
 			)
 		err != nil {
 			return users, err
@@ -1807,7 +1811,7 @@ func showPDF(w http.ResponseWriter, r *http.Request) {
 
 	// p := r.URL.Path
 	db, err := sql.Open("mysql",
-		fmt.Sprintf("%s:%s@tcp(127.0.0.1:3306)/skouter",
+		fmt.Sprintf("%s:%s@tcp(127.0.0.1:3306)/skouter_dev",
 			os.Getenv("DBUser"),
 			os.Getenv("DBPass")))
 
@@ -1829,18 +1833,102 @@ func showPDF(w http.ResponseWriter, r *http.Request) {
 	info := struct {
 		Title string
 		Name string
+		Avatar string
+		Letterhead string
 		User User
 	}{
 		Title: "test PDF",
 		Name: "idk-random-name",
 		User: users[0],
 	}
+	avatar, err := fetchAvatar(db, info.User.Id)
+	letterhead, err := fetchLetterhead(db, info.User.Id)
+	info.Avatar =
+	base64.StdEncoding.EncodeToString(avatar)
+	info.Letterhead =
+	base64.StdEncoding.EncodeToString(letterhead)
 	
 	err = pa.Execute(w, info)
 	if err != nil {fmt.Println(err)}
 
 }
 
+func getPdf(w http.ResponseWriter, db *sql.DB, r *http.Request) {
+	var err error
+	cmd := exec.Command("wkhtmltopdf", "-", "-")
+	
+	stdout, err := cmd.StdoutPipe()
+	if err != nil {
+		w.WriteHeader(500);
+		log.Println(err)
+		return
+	}
+	
+	stdin, err := cmd.StdinPipe()
+	if err != nil {
+		w.WriteHeader(500);
+		log.Println(err)
+		return
+	}
+
+	if err := cmd.Start(); err != nil {
+		log.Fatal(err)
+	}
+	
+	var pa = template.Must(template.ParseFiles("views/pdf.tpl",
+	"views/test.tpl"))
+	
+	// claims, err := getClaims(r)
+	if err != nil {
+		w.WriteHeader(500);
+		log.Println(err)
+		return
+	}
+	users, err := queryUsers(db, 1)
+	
+	info := struct {
+		Title string
+		Name string
+		Avatar string
+		Letterhead string
+		User User
+	}{
+		Title: "test PDF",
+		Name: "idk-random-name",
+		User: users[0],
+	}
+	avatar, err := fetchAvatar(db, info.User.Id)
+	letterhead, err := fetchLetterhead(db, info.User.Id)
+	info.Avatar =
+	base64.StdEncoding.EncodeToString(avatar)
+	info.Letterhead =
+	base64.StdEncoding.EncodeToString(letterhead)
+	
+	
+	err = pa.Execute(stdin, info)
+	if err != nil {
+		w.WriteHeader(500);
+		log.Println(err)
+		return
+	}
+	stdin.Close()
+	
+	buf, err := io.ReadAll(stdout)
+	
+	if _, err := w.Write(buf); err != nil {
+		w.WriteHeader(500);
+		log.Println(err)
+		return
+	}
+	
+	if err := cmd.Wait(); err != nil {
+		// w.WriteHeader(500)
+		log.Println(err)
+		return
+	}
+	
+}
+
 func clipLetterhead(w http.ResponseWriter, db *sql.DB, r *http.Request) {
 	var validTypes []string = []string{"image/png", "image/jpeg"}
 	var isValidType bool
@@ -1966,6 +2054,10 @@ func api(w http.ResponseWriter, r *http.Request) {
 	r.Method == http.MethodPost &&
 	guard(r, 1):
 		summarize(w, db, r)
+	case match(p, "/api/pdf", &args) &&
+	r.Method == http.MethodGet &&
+	guard(r, 1):
+		getPdf(w, db, r)
 	default:
 		http.Error(w, "Invalid route or token", 404)
 	}
diff --git a/views/pdf.tpl b/views/pdf.tpl
new file mode 100644
index 0000000..cc695d4
--- /dev/null
+++ b/views/pdf.tpl
@@ -0,0 +1,14 @@
+<!DOCTYPE html>
+<head>
+	<meta charset='utf-8'>
+    <meta name="viewport"
+	content="width=device-width, initial-scale=1, shrink-to-fit=no">
+	<link rel="stylesheet" href="">
+</head>
+
+<body>
+{{block "header" .}}
+{{end}}
+
+{{template "main" .}}
+</body>
diff --git a/views/test.tpl b/views/test.tpl
index 2daecca..55cbe25 100644
--- a/views/test.tpl
+++ b/views/test.tpl
@@ -4,8 +4,67 @@
 {{end}}
 
 {{define "main"}}
-<main class='fade-in-2'>
-<div>hello world {{.User.Title}}</div>
-<section>TESTING</section>
-</main>
+<div id="pdf-doc" ref="doc" v-if="estimate">
+<div class="disclaimer"><p>Actual costs may vary from estimates after approval. Get an official quote before choosing a loan.</p></div>
+
+<header class="heading">
+
+<img src="data:image/png;base64,{{.Letterhead}}" />
+
+<div>
+<div class="user-info">
+<h4>{{.User.FirstName}} {{.User.LastName}}</h4>
+<span>{{.User.Email}}</span>
+<span>{{.User.Phone}}</span>
+<small>{{.User.Address.Street}}</small>
+<small>
+{{.User.Address.City}}, {{.User.Address.Region}} {{.User.Address.Zip}}
+</small>
+</div>
+<img src="data:image/png;base64,{{.Avatar}}" />
+</div>
+
+</header>
+
+<style scoped>
+#pdf-doc {
+    margin: 4px 30px;
+}
+
+.disclaimer {
+    font-weight: bold;
+    border-bottom: 1px solid lightgrey;
+    margin-bottom: 20px;
+    color: var(--text);
+}
+
+.disclaimer p {
+    margin: 5px 0;
+}
+
+h4 {
+    margin: 4px 0;
+}
+
+header.heading {
+    display: flex;
+    justify-content: space-between;
+}
+
+.user-info {
+    display: flex;
+    flex-flow: column;
+}
+
+#pdf-doc header.heading > div {
+    display: flex;
+    text-align: right;
+}
+
+header.heading .user-info {
+  margin-right: 8px;
+}
+</style>
 {{end}}
+
+