Skip to content

Instantly share code, notes, and snippets.

@jordanorelli
Last active December 20, 2015 22:48
Show Gist options
  • Select an option

  • Save jordanorelli/6207698 to your computer and use it in GitHub Desktop.

Select an option

Save jordanorelli/6207698 to your computer and use it in GitHub Desktop.
diff --git a/go/src/hello/hello.go b/go/src/hello/hello.go
index 5f54709..b843e19 100644
--- a/go/src/hello/hello.go
+++ b/go/src/hello/hello.go
@@ -10,6 +10,7 @@ import (
"runtime"
"sort"
"strconv"
+ "sync"
_ "github.com/go-sql-driver/mysql"
)
@@ -52,12 +53,15 @@ var (
updateStatement *sql.Stmt
helloWorldBytes = []byte(helloWorldString)
+ db *sql.DB
+ queryChan chan (*queryRequest)
)
func main() {
runtime.GOMAXPROCS(runtime.NumCPU())
- db, err := sql.Open("mysql", connectionString)
+ var err error
+ db, err = sql.Open("mysql", connectionString)
if err != nil {
log.Fatalf("Error opening database: %v", err)
}
@@ -75,6 +79,12 @@ func main() {
log.Fatal(err)
}
+ queryChan = make(chan *queryRequest)
+ numQueryRunners := runtime.NumCPU() * 2
+ for i := 0; i < numQueryRunners; i++ {
+ go queryRunner(queryChan)
+ }
+
http.HandleFunc("/db", dbHandler)
http.HandleFunc("/queries", queriesHandler)
http.HandleFunc("/json", jsonHandler)
@@ -102,6 +112,38 @@ func dbHandler(w http.ResponseWriter, r *http.Request) {
json.NewEncoder(w).Encode(&world)
}
+type queryRequest struct {
+ n int
+ wg *sync.WaitGroup
+ result World
+ err error
+}
+
+func setupQueryRequest(r *queryRequest, wg *sync.WaitGroup) {
+ r.n = rand.Intn(worldRowCount) + 1
+ r.wg = wg
+}
+
+func (q *queryRequest) MarshalJSON() ([]byte, error) {
+ return json.Marshal(q.result)
+}
+
+func (r *queryRequest) runQuery(stmt *sql.Stmt) {
+ defer r.wg.Done()
+ r.err = stmt.QueryRow(r.n).Scan(&r.result.Id, &r.result.RandomNumber)
+}
+
+func queryRunner(c chan *queryRequest) {
+ stmt, err := db.Prepare(worldSelect)
+ if err != nil {
+ log.Fatal(err)
+ }
+ defer stmt.Close()
+ for r := range c {
+ r.runQuery(stmt)
+ }
+}
+
// Test 3: Multiple database queries
func queriesHandler(w http.ResponseWriter, r *http.Request) {
n := 1
@@ -114,16 +156,23 @@ func queriesHandler(w http.ResponseWriter, r *http.Request) {
return
}
- world := make([]World, n)
+ var wg sync.WaitGroup
+ queries := make([]queryRequest, n)
+ wg.Add(n)
for i := 0; i < n; i++ {
- err := worldStatement.QueryRow(rand.Intn(worldRowCount)+1).Scan(&world[i].Id, &world[
- if err != nil {
- log.Fatalf("Error scanning world row: %s", err.Error())
+ setupQueryRequest(&queries[i], &wg)
+ queryChan <- &queries[i]
+ }
+ wg.Wait()
+
+ for i := range queries {
+ if queries[i].err != nil {
+ log.Fatalf("Error scanning world row: %d %s", queries[i].n, queries[i].err.Er
}
}
w.Header().Set("Content-Type", "application/json")
- json.NewEncoder(w).Encode(world)
+ json.NewEncoder(w).Encode(queries)
}
// Test 4: Fortunes
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment