Ejemplo n.º 1
0
func main() {
	// Print action
	if steps > 0 {
		log.Printf("applying migrations...")
	} else if steps == -1 {
		log.Printf("rolling back by 1...")
	} else if steps < 0 {
		log.Printf("reset. rolling back all migrations...")
	}

	// Parse migrations
	stamps := []int{}
	ups := map[int]reflect.Method{}
	downs := map[int]reflect.Method{}

	structVal := reflect.ValueOf(&M{})
	for i := 0; i < structVal.NumMethod(); i++ {
		method := structVal.Type().Method(i)
		if c := strings.Split(method.Name, "_"); len(c) >= 3 {
			stamp, _ := strconv.Atoi(c[len(c)-2])
			if c[len(c)-1] == "Up" {
				ups[stamp] = method
				stamps = append(stamps, stamp)
			} else {
				downs[stamp] = method
			}
		}
	}

	sort.Ints(stamps)

	// Open hood
	hd, err := hood.Open(driver, source)
	if err != nil {
		panic(err)
	}
	hd.Log = true

	// Create migration table if necessary
	tx := hd.Begin()
	tx.CreateTableIfNotExists(&Migrations{})
	err = tx.Commit()
	if err != nil {
		panic(err)
	}

	// Check if any previous migrations have been run
	var rows []Migrations
	err = hd.Find(&rows)
	if err != nil {
		panic(err)
	}
	if len(rows) > 1 {
		panic("invalid migrations table")
	}
	info := Migrations{}
	if len(rows) > 0 {
		info = rows[0]
	}

	// Apply
	cur := 0
	count := 0
	if steps > 0 {
		for _, stamp := range stamps {
			if stamp > info.Current {
				if cur++; cur <= steps {
					apply(stamp, stamp, &count, hd, &info, structVal, ups[stamp])
				}
			}
		}
	} else if steps < 0 {
		for i := len(stamps) - 1; i >= 0; i-- {
			stamp := stamps[i]
			next := 0
			if i > 0 {
				next = stamps[i-1]
			}
			if stamp <= info.Current {
				if cur--; cur >= steps {
					apply(stamp, next, &count, hd, &info, structVal, downs[stamp])
				}
			}
		}
	}

	if steps > 0 {
		log.Printf("applied %d migrations", count)
	} else if steps < 0 {
		log.Printf("rolled back %d migrations", count)
	}

	log.Printf("generating new schema... %s", schemaPath)

	dry := hood.Dry()
	for _, ts := range stamps {
		if ts <= info.Current {
			method := ups[ts]
			method.Func.Call([]reflect.Value{structVal, reflect.ValueOf(dry)})
		}
	}
	err = ioutil.WriteFile(schemaPath, []byte(dry.GoSchema()), 0666)
	if err != nil {
		panic(err)
	}
	err = exec.Command("go", "fmt", schemaPath).Run()
	if err != nil {
		panic(err)
	}
	log.Printf("wrote schema %s", schemaPath)
	log.Printf("done.")
}
Ejemplo n.º 2
0
func TestTagApi(t *testing.T) {

	tests := []TestTagStruct{
		{
			First: &TestTag{
				Request: "GET",
				Url:     "http://localhost/api/tags",
				Status:  200,
				Body:    `[]`,
			},
		},
		{
			First: &TestTag{
				Request: "POST",
				Url:     "http://localhost/api/tags",
				Input: &map[string]string{
					"name": "a",
				},
				Status: 200,
			},
			Last: &TestTag{
				Request: "GET",
				Url:     "http://localhost/api/tags",
				Input:   nil,
				Status:  200,
				Result: &api.Tag{
					Name:   "a",
					Weight: 20,
				},
			},
		},
	}

	// db, err := sql.Open(dbconf.Driver, dbconf.Source)
	db, err := hood.Open("postgres", "user=postgres dbname=indata_test host=192.168.0.10 sslmode=disable")
	if err != nil {
		log.Fatal(err)
	}

	serviceApi := api.Api{Db: db}
	rapi := rest.NewApi()
	rapi.Use(rest.DefaultCommonStack...)
	// rapi.Use(&rest.AccessLogApacheMiddleware{})
	// rapi.Use(&rest.GzipMiddleware{})
	rapi.Use(&rest.ContentTypeCheckerMiddleware{})

	router, err := rest.MakeRouter(
		rest.Get("/tags", serviceApi.GetAllTags),
		rest.Post("/tags", serviceApi.PostTag),
		rest.Get("/tags/:name", serviceApi.GetTag),
		rest.Post("/tags/:name", serviceApi.UpdateTag),
		rest.Delete("/tags/:name", serviceApi.DeleteTag),
	)
	if err != nil {
		log.Fatal(err)
	}
	rapi.SetApp(router)

	for _, testVars := range tests {
		// Start a transaction
		tx := db.Begin()

		tx.DropTableIfExists(api.Tag{})
		tx.DropTableIfExists(api.Contact{})
		tx.DropTableIfExists(api.TagContact{})

		tx.CreateTableIfNotExists(api.Tag{})
		tx.CreateTableIfNotExists(api.Contact{})
		tx.CreateTableIfNotExists(api.TagContact{})

		// Commit changes
		err = tx.Commit()
		if err != nil {
			log.Println(err)
		}
		hndl := rapi.MakeHandler()
		handler := http.StripPrefix("/api", hndl)

		// recorded := test.RunRequest(t, handler, test.MakeSimpleRequest("GET", "http://localhost/api/tags/notfound", nil))
		// recorded.CodeIs(404)
		// recorded.ContentTypeIsJson()
		// recorded.BodyIs("{\n  \"Error\": \"Resource not found\"\n}")

		// recorded = test.RunRequest(t, &handler, test.MakeSimpleRequest("GET", "http://1.2.3.4/user-notfound", nil))
		// recorded.CodeIs(404)
		// recorded.ContentTypeIsJson()
		// recorded.BodyIs(`{"Error":"Resource not found"}`)

		log.Printf("%s request to %s ", testVars.First.Request, testVars.First.Url)
		recorded := test.RunRequest(t, handler, test.MakeSimpleRequest(testVars.First.Request, testVars.First.Url, testVars.First.Input))
		recorded.CodeIs(testVars.First.Status)
		recorded.ContentTypeIsJson()
		// recorded.ContentEncodingIsGzip()
		log.Printf("body %#v", recorded.Recorder.Body.String())
		if testVars.First.Body != "" {
			recorded.BodyIs(testVars.First.Body)
		}

		if testVars.Last != nil {
			log.Printf("%s request to %s ", testVars.Last.Request, testVars.Last.Url)

			recorded := test.RunRequest(t, handler, test.MakeSimpleRequest(testVars.Last.Request, testVars.Last.Url, testVars.Last.Input))
			recorded.CodeIs(testVars.Last.Status)
			recorded.ContentTypeIsJson()
			// recorded.ContentEncodingIsGzip()

			if testVars.Last.Result != nil {
				var tags []api.Tag
				err = recorded.DecodeJsonPayload(&tags)

				log.Printf("tags %#v", tags)
				if len(tags) != 1 {
					t.Errorf(`Expected one element and got %d`, len(tags))
				}

				if testVars.Last.Result.Name != "" {
					if tags[0].Name != testVars.Last.Result.Name {
						t.Errorf(`Expected tag name "%s"`, testVars.Last.Result.Name)
					}
				}

				// if ok := testVars.Last.Result.Weight; ok {
				// if testVars.Last.Result.Weight {
				if tags[0].Weight != testVars.Last.Result.Weight {
					t.Errorf(`Expected tag weight "%s"`, testVars.Last.Result.Weight)
				}
				// }
				// }
			}
		}

	}
	//
	// recorded = test.RunRequest(t, handler, test.MakeSimpleRequest("GET", "http://localhost/api/tags", nil))
	// recorded.CodeIs(200)
	// recorded.ContentTypeIsJson()
	// // recorded.ContentEncodingIsGzip()
	//
	// var tags []api.Tag
	// err = recorded.DecodeJsonPayload(&tags)
	//
	// if len(tags) != 1 {
	// 	t.Errorf(`Expected one element and got %d`, len(tags))
	// }
	//
	// if tags[0].Name != "a" {
	// 	t.Error(`Expected tag name "a"`)
	// }
	//
	// recorded = test.RunRequest(t, handler, test.MakeSimpleRequest("DELETE", "http://localhost/api/tags/"+tags[0].Name, nil))
	// recorded.CodeIs(200)
	// recorded.ContentTypeIsJson()
	//
	// recorded = test.RunRequest(t, handler, test.MakeSimpleRequest("GET", "http://localhost/api/tags", nil))
	// recorded.CodeIs(200)
	// recorded.ContentTypeIsJson()
	// // recorded.ContentEncodingIsGzip()
	// recorded.BodyIs(`[]`)
}
Ejemplo n.º 3
0
func main() {

	flag.Parse()

	p, err := osext.ExecutableFolder()
	if err != nil {
		log.Fatal(err)
	}

	dbconf, err := load(path.Join(p, "db", "config.json"), *flagEnv)
	if err != nil {
		log.Fatal(err)
	}

	// db, err := sql.Open(dbconf.Driver, dbconf.Source)
	db, err := hood.Open(dbconf.Driver, dbconf.Source)
	if err != nil {
		log.Fatal(err)
	}

	// svmw := semVerMiddleware{
	// 	MinVersion: "1.0.0",
	// 	MaxVersion: "1.0.0",
	// }
	serviceApi := api.Api{Db: db}
	rapi := rest.NewApi()
	rapi.Use(rest.DefaultDevStack...)
	router, err := rest.MakeRouter(

		rest.Get("/tags", serviceApi.GetAllTags),
		rest.Post("/tags", serviceApi.PostTag),
		rest.Get("/tags/:name", serviceApi.GetTag),
		rest.Post("/tags/:name", serviceApi.UpdateTag),
		rest.Delete("/tags/:name", serviceApi.DeleteTag),

		rest.Get("/contacts", serviceApi.GetAllContacts),
		rest.Post("/contacts", serviceApi.PostContact),
		rest.Get("/contacts/:name", serviceApi.GetContact),
		rest.Post("/contacts/:name", serviceApi.UpdateContact),
		rest.Delete("/contacts/:name", serviceApi.DeleteContact),

		// rest.Get("/#version/message", svmw.MiddlewareFunc(
		// 	func(w rest.ResponseWriter, req *rest.Request) {
		// 		version := req.Env["VERSION"].(*semver.Version)
		// 		if version.Major == 2 {
		// 			// http://en.wikipedia.org/wiki/Second-system_effect
		// 			w.WriteJson(map[string]string{
		// 				"Body": "Hello broken World!",
		// 			})
		// 		} else {
		// 			w.WriteJson(map[string]string{
		// 				"Body": "Hello World!",
		// 			})
		// 		}
		// 	},
		// )),
	)
	if err != nil {
		log.Fatal(err)
	}
	rapi.SetApp(router)
	http.Handle("/api/", http.StripPrefix("/api", rapi.MakeHandler()))

	log.Println("Started")
	log.Fatal(http.ListenAndServe(":8080", nil))
}
Ejemplo n.º 4
0
func TestContactApi(t *testing.T) {

	// db, err := sql.Open(dbconf.Driver, dbconf.Source)
	db, err := hood.Open("postgres", "user=postgres dbname=indata_test host=192.168.0.10 sslmode=disable")
	if err != nil {
		log.Fatal(err)
	}

	serviceApi := api.Api{Db: db}
	rapi := rest.NewApi()
	rapi.Use(rest.DefaultDevStack...)
	router, err := rest.MakeRouter(
		rest.Get("/contacts", serviceApi.GetAllContacts),
		rest.Post("/contacts", serviceApi.PostContact),
		rest.Get("/contacts/:name", serviceApi.GetContact),
		rest.Post("/contacts/:name", serviceApi.UpdateContact),
		rest.Delete("/contacts/:name", serviceApi.DeleteContact),
	)
	if err != nil {
		log.Fatal(err)
	}
	rapi.SetApp(router)

	// Start a transaction
	tx := db.Begin()

	tx.DropTableIfExists(api.Tag{})
	tx.DropTableIfExists(api.Contact{})
	tx.DropTableIfExists(api.TagContact{})

	tx.CreateTableIfNotExists(api.Tag{})
	tx.CreateTableIfNotExists(api.Contact{})
	tx.CreateTableIfNotExists(api.TagContact{})

	// Commit changes
	err = tx.Commit()
	if err != nil {
		log.Println(err)
	}

	handler := http.StripPrefix("/api", rapi.MakeHandler())

	recorded := test.RunRequest(t, handler, test.MakeSimpleRequest("GET", "http://localhost/api/contacts", nil))
	recorded.CodeIs(200)
	recorded.ContentTypeIsJson()
	// recorded.ContentEncodingIsGzip()
	recorded.BodyIs(`[]`)

	recorded = test.RunRequest(t, handler, test.MakeSimpleRequest("POST", "http://localhost/api/contacts",
		&map[string]string{
			"name":        "a",
			"title":       "a",
			"description": "a",
		}))
	recorded.CodeIs(200)
	recorded.ContentTypeIsJson()
	// recorded.ContentEncodingIsGzip()

	recorded = test.RunRequest(t, handler, test.MakeSimpleRequest("GET", "http://localhost/api/contacts", nil))
	recorded.CodeIs(200)
	recorded.ContentTypeIsJson()
	// recorded.ContentEncodingIsGzip()

	var contacts []api.Contact
	err = recorded.DecodeJsonPayload(&contacts)

	if len(contacts) != 1 {
		t.Errorf(`Expected one element and got %d`, len(contacts))
	}

	if contacts[0].Name != "a" {
		t.Error(`Expected contact name "a"`)
	}

	spew.Dump(contacts)
	recorded = test.RunRequest(t, handler, test.MakeSimpleRequest("DELETE", "http://localhost/api/contacts/"+contacts[0].Name, nil))
	recorded.CodeIs(200)
	recorded.ContentTypeIsJson()

	recorded = test.RunRequest(t, handler, test.MakeSimpleRequest("GET", "http://localhost/api/contacts", nil))
	recorded.CodeIs(200)
	recorded.ContentTypeIsJson()
	// recorded.ContentEncodingIsGzip()
	recorded.BodyIs(`[]`)
}