func TestPrefixedSchemaName(t *testing.T) { const prefix = "SomePrefix" origSchemaNameForType := SchemaNameForType defer func() { SchemaNameForType = origSchemaNameForType }() SchemaNameForType = func(t reflect.Type) string { return prefix + t.Name() } d := createDescriptor(t) for name := range d.Descriptor.Schemas { if !strings.HasPrefix(name, prefix) { t.Errorf("HasPrefix(%q, %q) = false", name, prefix) } } for mname, meth := range d.Descriptor.Methods { if meth.Request != nil { if !strings.HasPrefix(meth.Request.Ref, prefix) { t.Errorf("HasPrefix(%q, %q) = false; request of %q", meth.Request.Ref, prefix, mname) } } if meth.Response != nil { if !strings.HasPrefix(meth.Response.Ref, prefix) { t.Errorf("HasPrefix(%q, %q) = false; response of %q", meth.Response.Ref, prefix, mname) } } } }
func TestGrammar(t *testing.T) { bnf0 := GenerateBnf0Grammar() g := GetIndexedGrammar(bnf0) idxIf, err := g.GetIndex(GrammarIndexTypeTerm) if err != nil { t.Error(err) return } termIndex := idxIf.(TermGrammarIndex) for _, ntn := range termIndex.GetNonterminalNames() { nt, _ := termIndex.GetNonterminal(ntn) fmt.Printf("%d: <%s>\n", nt.Id(), nt.Name()) } for _, tn := range termIndex.GetTerminalNames() { t, _ := termIndex.GetTerminal(tn) fmt.Printf("%d: %s\n", t.Id(), t.Name()) } }
func TestTaskQueue(t *testing.T) { t.Parallel() Convey("TaskQueue", t, func() { now := time.Date(2000, time.January, 1, 1, 1, 1, 1, time.UTC) c, tc := testclock.UseTime(context.Background(), now) c = mathrand.Set(c, rand.New(rand.NewSource(clock.Now(c).UnixNano()))) c = Use(c) tq := tqS.Get(c) tqt := tq.Testable() So(tqt, ShouldNotBeNil) So(tq, ShouldNotBeNil) Convey("implements TQMultiReadWriter", func() { Convey("Add", func() { t := tq.NewTask("/hello/world") Convey("works", func() { t.Delay = 4 * time.Second t.Header = http.Header{} t.Header.Add("Cat", "tabby") t.Payload = []byte("watwatwat") t.RetryOptions = &tqS.RetryOptions{AgeLimit: 7 * time.Second} So(tq.Add(t, ""), ShouldBeNil) name := "Z_UjshxM9ecyMQfGbZmUGOEcgxWU0_5CGLl_-RntudwAw2DqQ5-58bzJiWQN4OKzeuUb9O4JrPkUw2rOvk2Ax46THojnQ6avBQgZdrKcJmrwQ6o4qKfJdiyUbGXvy691yRfzLeQhs6cBhWrgf3wH-VPMcA4SC-zlbJ2U8An7I0zJQA5nBFnMNoMgT-2peGoay3rCSbj4z9VFFm9kS_i6JCaQH518ujLDSNCYdjTq6B6lcWrZAh0U_q3a1S2nXEwrKiw_t9MTNQFgAQZWyGBbvZQPmeRYtu8SPaWzTfd25v_YWgBuVL2rRSPSMvlDwE04nNdtvVzE8vNNiA1zRimmdzKeqATQF9_ReUvj4D7U8dcS703DZWfKMBLgBffY9jqCassOOOw77V72Oq5EVauUw3Qw0L6bBsfM9FtahTKUdabzRZjXUoze3EK4KXPt3-wdidau-8JrVf2XFocjjZbwHoxcGvbtT3b4nGLDlgwdC00bwaFBZWff" So(tqt.GetScheduledTasks()["default"][name], ShouldResemble, &tqS.Task{ ETA: now.Add(4 * time.Second), Header: http.Header{"Cat": []string{"tabby"}}, Method: "POST", Name: name, Path: "/hello/world", Payload: []byte("watwatwat"), RetryOptions: &tqS.RetryOptions{AgeLimit: 7 * time.Second}, }) }) Convey("picks up namespace", func() { c, err := info.Get(c).Namespace("coolNamespace") So(err, ShouldBeNil) tq = tqS.Get(c) t := tq.NewTask("") So(tq.Add(t, ""), ShouldBeNil) So(t.Header, ShouldResemble, http.Header{ "X-Appengine-Current-Namespace": {"coolNamespace"}, }) }) Convey("cannot add to bad queues", func() { So(tq.Add(nil, "waaat").Error(), ShouldContainSubstring, "UNKNOWN_QUEUE") Convey("but you can add Queues when testing", func() { tqt.CreateQueue("waaat") So(tq.Add(t, "waaat"), ShouldBeNil) Convey("you just can't add them twice", func() { So(func() { tqt.CreateQueue("waaat") }, ShouldPanic) }) }) }) Convey("supplies a URL if it's missing", func() { t.Path = "" So(tq.Add(t, ""), ShouldBeNil) So(t.Path, ShouldEqual, "/_ah/queue/default") }) Convey("cannot add twice", func() { t.Name = "bob" So(tq.Add(t, ""), ShouldBeNil) // can't add the same one twice! So(tq.Add(t, ""), ShouldEqual, tqS.ErrTaskAlreadyAdded) }) Convey("cannot add deleted task", func() { t.Name = "bob" So(tq.Add(t, ""), ShouldBeNil) So(tq.Delete(t, ""), ShouldBeNil) // can't add a deleted task! So(tq.Add(t, ""), ShouldEqual, tqS.ErrTaskAlreadyAdded) }) Convey("cannot set ETA+Delay", func() { t.ETA = clock.Now(c).Add(time.Hour) tc.Add(time.Second) t.Delay = time.Hour So(func() { So(tq.Add(t, ""), ShouldBeNil) }, ShouldPanic) }) Convey("must use a reasonable method", func() { t.Method = "Crystal" So(tq.Add(t, "").Error(), ShouldContainSubstring, "bad method") }) Convey("payload gets dumped for non POST/PUT methods", func() { t.Method = "HEAD" t.Payload = []byte("coool") So(tq.Add(t, ""), ShouldBeNil) So(t.Payload, ShouldBeNil) }) Convey("invalid names are rejected", func() { t.Name = "happy times" So(tq.Add(t, "").Error(), ShouldContainSubstring, "INVALID_TASK_NAME") }) Convey("AddMulti also works", func() { t2 := t.Duplicate() t2.Path = "/hi/city" expect := []*tqS.Task{t, t2} So(tq.AddMulti(expect, "default"), ShouldBeNil) So(len(expect), ShouldEqual, 2) So(len(tqt.GetScheduledTasks()["default"]), ShouldEqual, 2) for i := range expect { Convey(fmt.Sprintf("task %d: %s", i, expect[i].Path), func() { So(expect[i].Method, ShouldEqual, "POST") So(expect[i].ETA, ShouldHappenOnOrBefore, now) So(len(expect[i].Name), ShouldEqual, 500) }) } Convey("stats work too", func() { delay := -time.Second * 400 t := tq.NewTask("/somewhere") t.Delay = delay So(tq.Add(t, ""), ShouldBeNil) stats, err := tq.Stats("") So(err, ShouldBeNil) So(stats[0].Tasks, ShouldEqual, 3) So(stats[0].OldestETA, ShouldHappenOnOrBefore, clock.Now(c).Add(delay)) _, err = tq.Stats("noexist") So(err.Error(), ShouldContainSubstring, "UNKNOWN_QUEUE") }) Convey("can purge all tasks", func() { So(tq.Add(&tqS.Task{Path: "/wut/nerbs"}, ""), ShouldBeNil) So(tq.Purge(""), ShouldBeNil) So(len(tqt.GetScheduledTasks()["default"]), ShouldEqual, 0) So(len(tqt.GetTombstonedTasks()["default"]), ShouldEqual, 0) So(len(tqt.GetTransactionTasks()["default"]), ShouldEqual, 0) Convey("purging a queue which DNE fails", func() { So(tq.Purge("noexist").Error(), ShouldContainSubstring, "UNKNOWN_QUEUE") }) }) }) }) Convey("Delete", func() { t := &tqS.Task{Path: "/hello/world"} So(tq.Add(t, ""), ShouldBeNil) Convey("works", func() { err := tq.Delete(t, "") So(err, ShouldBeNil) So(len(tqt.GetScheduledTasks()["default"]), ShouldEqual, 0) So(len(tqt.GetTombstonedTasks()["default"]), ShouldEqual, 1) So(tqt.GetTombstonedTasks()["default"][t.Name], ShouldResemble, t) }) Convey("cannot delete a task twice", func() { So(tq.Delete(t, ""), ShouldBeNil) So(tq.Delete(t, "").Error(), ShouldContainSubstring, "TOMBSTONED_TASK") Convey("but you can if you do a reset", func() { tqt.ResetTasks() So(tq.Add(t, ""), ShouldBeNil) So(tq.Delete(t, ""), ShouldBeNil) }) }) Convey("cannot delete from bogus queues", func() { err := tq.Delete(t, "wat") So(err.Error(), ShouldContainSubstring, "UNKNOWN_QUEUE") }) Convey("cannot delete a missing task", func() { t.Name = "tarntioarenstyw" err := tq.Delete(t, "") So(err.Error(), ShouldContainSubstring, "UNKNOWN_TASK") }) Convey("DeleteMulti also works", func() { t2 := t.Duplicate() t2.Name = "" t2.Path = "/hi/city" So(tq.Add(t2, ""), ShouldBeNil) Convey("usually works", func() { So(tq.DeleteMulti([]*tqS.Task{t, t2}, ""), ShouldBeNil) So(len(tqt.GetScheduledTasks()["default"]), ShouldEqual, 0) So(len(tqt.GetTombstonedTasks()["default"]), ShouldEqual, 2) }) }) }) }) Convey("works with transactions", func() { t := &tqS.Task{Path: "/hello/world"} So(tq.Add(t, ""), ShouldBeNil) t2 := &tqS.Task{Path: "/hi/city"} So(tq.Add(t2, ""), ShouldBeNil) So(tq.Delete(t2, ""), ShouldBeNil) Convey("can view regular tasks", func() { So(dsS.Get(c).RunInTransaction(func(c context.Context) error { tqt := tqS.GetRaw(c).Testable() So(tqt.GetScheduledTasks()["default"][t.Name], ShouldResemble, t) So(tqt.GetTombstonedTasks()["default"][t2.Name], ShouldResemble, t2) So(tqt.GetTransactionTasks()["default"], ShouldBeNil) return nil }, nil), ShouldBeNil) }) Convey("can add a new task", func() { t3 := &tqS.Task{Path: "/sandwitch/victory"} err := dsS.Get(c).RunInTransaction(func(c context.Context) error { tq := tqS.Get(c) tqt := tq.Testable() So(tq.Add(t3, ""), ShouldBeNil) So(t3.Name, ShouldEqual, "") So(tqt.GetScheduledTasks()["default"][t.Name], ShouldResemble, t) So(tqt.GetTombstonedTasks()["default"][t2.Name], ShouldResemble, t2) So(tqt.GetTransactionTasks()["default"][0], ShouldResemble, t3) return nil }, nil) So(err, ShouldBeNil) for _, tsk := range tqt.GetScheduledTasks()["default"] { if tsk.Name == t.Name { So(tsk, ShouldResemble, t) } else { tsk.Name = "" So(tsk, ShouldResemble, t3) } } So(tqt.GetTombstonedTasks()["default"][t2.Name], ShouldResemble, t2) So(tqt.GetTransactionTasks()["default"], ShouldBeNil) }) Convey("can add a new task (but reset the state in a test)", func() { t3 := &tqS.Task{Path: "/sandwitch/victory"} ttq := tqS.Interface(nil) So(dsS.Get(c).RunInTransaction(func(c context.Context) error { ttq = tqS.Get(c) tqt := ttq.Testable() So(ttq.Add(t3, ""), ShouldBeNil) So(tqt.GetScheduledTasks()["default"][t.Name], ShouldResemble, t) So(tqt.GetTombstonedTasks()["default"][t2.Name], ShouldResemble, t2) So(tqt.GetTransactionTasks()["default"][0], ShouldResemble, t3) tqt.ResetTasks() So(len(tqt.GetScheduledTasks()["default"]), ShouldEqual, 0) So(len(tqt.GetTombstonedTasks()["default"]), ShouldEqual, 0) So(len(tqt.GetTransactionTasks()["default"]), ShouldEqual, 0) return nil }, nil), ShouldBeNil) So(len(tqt.GetScheduledTasks()["default"]), ShouldEqual, 0) So(len(tqt.GetTombstonedTasks()["default"]), ShouldEqual, 0) So(len(tqt.GetTransactionTasks()["default"]), ShouldEqual, 0) Convey("and reusing a closed context is bad times", func() { So(ttq.Add(nil, "").Error(), ShouldContainSubstring, "expired") }) }) Convey("you can AddMulti as well", func() { So(dsS.Get(c).RunInTransaction(func(c context.Context) error { tq := tqS.Get(c) tqt := tq.Testable() t.Name = "" tasks := []*tqS.Task{t.Duplicate(), t.Duplicate(), t.Duplicate()} So(tq.AddMulti(tasks, ""), ShouldBeNil) So(len(tqt.GetScheduledTasks()["default"]), ShouldEqual, 1) So(len(tqt.GetTransactionTasks()["default"]), ShouldEqual, 3) return nil }, nil), ShouldBeNil) So(len(tqt.GetScheduledTasks()["default"]), ShouldEqual, 4) So(len(tqt.GetTransactionTasks()["default"]), ShouldEqual, 0) }) Convey("unless you add too many things", func() { So(dsS.Get(c).RunInTransaction(func(c context.Context) error { for i := 0; i < 5; i++ { So(tqS.Get(c).Add(t.Duplicate(), ""), ShouldBeNil) } So(tqS.Get(c).Add(t, "").Error(), ShouldContainSubstring, "BAD_REQUEST") return nil }, nil), ShouldBeNil) }) Convey("unless you Add to a bad queue", func() { So(dsS.Get(c).RunInTransaction(func(c context.Context) error { So(tqS.Get(c).Add(t, "meat").Error(), ShouldContainSubstring, "UNKNOWN_QUEUE") Convey("unless you add it!", func() { tqS.GetRaw(c).Testable().CreateQueue("meat") So(tqS.Get(c).Add(t, "meat"), ShouldBeNil) }) return nil }, nil), ShouldBeNil) }) Convey("No other features are available, however", func() { So(dsS.Get(c).RunInTransaction(func(c context.Context) error { So(tqS.Get(c).Delete(t, "").Error(), ShouldContainSubstring, "cannot DeleteMulti from a transaction") So(tqS.Get(c).Purge("").Error(), ShouldContainSubstring, "cannot Purge from a transaction") _, err := tqS.Get(c).Stats("") So(err.Error(), ShouldContainSubstring, "cannot Stats from a transaction") return nil }, nil), ShouldBeNil) }) Convey("can get the non-transactional taskqueue context though", func() { So(dsS.Get(c).RunInTransaction(func(c context.Context) error { So(tqS.GetNoTxn(c).Delete(t, ""), ShouldBeNil) So(tqS.GetNoTxn(c).Purge(""), ShouldBeNil) _, err := tqS.GetNoTxn(c).Stats("") So(err, ShouldBeNil) return nil }, nil), ShouldBeNil) }) Convey("adding a new task only happens if we don't errout", func() { So(dsS.Get(c).RunInTransaction(func(c context.Context) error { t3 := tq.NewTask("/sandwitch/victory") So(tqS.Get(c).Add(t3, ""), ShouldBeNil) return fmt.Errorf("nooooo") }, nil), ShouldErrLike, "nooooo") So(tqt.GetScheduledTasks()["default"][t.Name], ShouldResemble, t) So(tqt.GetTombstonedTasks()["default"][t2.Name], ShouldResemble, t2) So(tqt.GetTransactionTasks()["default"], ShouldBeNil) }) Convey("likewise, a panic doesn't schedule anything", func() { func() { defer func() { _ = recover() }() So(dsS.Get(c).RunInTransaction(func(c context.Context) error { tq := tqS.Get(c) So(tq.Add(tq.NewTask("/sandwitch/victory"), ""), ShouldBeNil) panic(fmt.Errorf("nooooo")) }, nil), ShouldBeNil) }() So(tqt.GetScheduledTasks()["default"][t.Name], ShouldResemble, t) So(tqt.GetTombstonedTasks()["default"][t2.Name], ShouldResemble, t2) So(tqt.GetTransactionTasks()["default"], ShouldBeNil) }) }) }) }
func TestFindTypeCycles(t *testing.T) { tests := []struct { desc string typ TypeSpec msgs []string }{ { desc: "self-referential typedef", typ: withTypedef(func(t *TypedefSpec) { t.Name = "foo" t.Target = t }), msgs: []string{ "found a type reference cycle", " foo", "-> foo", }, }, { desc: "mutually recursive references", typ: withTypedef(func(x *TypedefSpec) { x.Name = "foo" x.Target = &TypedefSpec{ Name: "bar", File: "test.thrift", Target: x, } }), msgs: []string{ "found a type reference cycle", " foo", "-> bar", "-> foo", }, }, { desc: "recurse from map", typ: withTypedef(func(t *TypedefSpec) { t.Name = "foo" t.Target = &MapSpec{ KeySpec: &StringSpec{}, ValueSpec: t, } }), msgs: []string{ "found a type reference cycle", " foo", "-> map<string, foo>", "-> foo", }, }, { desc: "recurse from list", typ: withTypedef(func(t *TypedefSpec) { t.Name = "foo" t.Target = &ListSpec{ValueSpec: t} }), msgs: []string{ "found a type reference cycle", " foo", "-> list<foo>", "-> foo", }, }, { desc: "recurse from set", typ: withTypedef(func(t *TypedefSpec) { t.Name = "foo" t.Target = &SetSpec{ValueSpec: t} }), msgs: []string{ "found a type reference cycle", " foo", "-> set<foo>", "-> foo", }, }, { desc: "recurse from struct", typ: withTypedef(func(t *TypedefSpec) { t.Name = "foo" t.Target = &StructSpec{ Name: "bar", File: "test.thrift", Type: ast.StructType, Fields: FieldGroup{ { ID: 1, Name: "foo", Type: t, Required: true, }, }, } }), }, } for _, tt := range tests { typ := mustLink(t, tt.typ, defaultScope) err := findTypeCycles(typ) if len(tt.msgs) > 0 { if assert.Error(t, err, tt.desc) { for _, msg := range tt.msgs { assert.Contains(t, err.Error(), msg) } } } else { assert.NoError(t, err, tt.desc) } } }
func TestApiClient(t *testing.T) { done := make(chan struct{}) defer func() { close(done) time.Sleep(time.Second) }() url := startApi(done) agentCount := 1 metricsCount := 2 taskCount := 0 Convey("Client should exist", t, func() { c, cerr := New(url, adminKey, false) So(cerr, ShouldBeNil) Convey("When calling the api heartbeat method", func() { ok, hErr := c.Heartbeat() So(hErr, ShouldBeNil) So(ok, ShouldBeTrue) }) Convey("when adding a new Agent", func() { agentCount++ pre := time.Now() a := model.AgentDTO{ Name: fmt.Sprintf("demo%d", agentCount), Enabled: true, Public: false, Tags: []string{"demo", "private"}, } aErr := c.AddAgent(&a) So(aErr, ShouldBeNil) So(a.Id, ShouldNotBeEmpty) So(a.Name, ShouldEqual, fmt.Sprintf("demo%d", agentCount)) So(a.Enabled, ShouldEqual, true) So(a.Public, ShouldEqual, false) So(a.Created, ShouldHappenBefore, time.Now()) So(a.Created, ShouldHappenAfter, pre) So(a.Created.Unix(), ShouldEqual, a.Updated.Unix()) Convey("when getting an agent by id", func() { agent, err := c.GetAgentById(a.Id) So(err, ShouldBeNil) So(agent, ShouldNotBeNil) So(agent, ShouldHaveSameTypeAs, &model.AgentDTO{}) So(agent.Id, ShouldEqual, a.Id) So(agent.Created.Unix(), ShouldEqual, a.Created.Unix()) Convey("when updating an Agent", func() { a := new(model.AgentDTO) *a = *agent a.Name = "test1" pre := time.Now() err := c.UpdateAgent(a) So(err, ShouldBeNil) So(a.Id, ShouldNotBeEmpty) So(a.Name, ShouldEqual, "test1") So(a.Enabled, ShouldEqual, true) So(a.Public, ShouldEqual, false) So(a.Created, ShouldHappenBefore, pre) So(a.Updated, ShouldHappenAfter, pre) }) Convey("When deleting an agent", func() { err := c.DeleteAgent(&a) So(err, ShouldBeNil) agentCount-- Convey("When searching for agent by name", func() { query := model.GetAgentsQuery{Name: a.Name} agents, err := c.GetAgents(&query) So(err, ShouldBeNil) So(len(agents), ShouldEqual, 0) }) }) }) Convey("When getting the list of Agents", func() { query := model.GetAgentsQuery{} agents, err := c.GetAgents(&query) So(err, ShouldBeNil) So(len(agents), ShouldEqual, agentCount) }) }) Convey("When getting list of public agenst", func() { query := model.GetAgentsQuery{Public: "true"} agents, err := c.GetAgents(&query) So(err, ShouldBeNil) So(len(agents), ShouldEqual, 1) So(agents[0].Id, ShouldEqual, 1) Convey("When updating tags of public agent", func() { a := new(model.AgentDTO) *a = *agents[0] a.Tags = []string{"foo", "demo"} err := c.UpdateAgent(a) So(err, ShouldBeNil) So(a.Id, ShouldNotBeEmpty) So(a.Name, ShouldEqual, "publicTest") So(a.Enabled, ShouldEqual, true) So(a.Public, ShouldEqual, true) So(len(a.Tags), ShouldEqual, 2) }) }) // Metric Tests Convey("When getting metrics list", func() { query := &model.GetMetricsQuery{} metrics, err := c.GetMetrics(query) So(err, ShouldBeNil) So(metrics, ShouldNotBeNil) So(metrics, ShouldHaveSameTypeAs, []*model.Metric{}) So(len(metrics), ShouldEqual, metricsCount) agent, err := c.GetAgentById(2) if err != nil { panic(err) } addTestMetrics(agent) metricsCount = 3 Convey("When getting metrics for Agent", func() { metrics, err := c.GetAgentMetrics(agent.Id) So(err, ShouldBeNil) So(metrics, ShouldNotBeNil) So(metrics, ShouldHaveSameTypeAs, []*model.Metric{}) So(len(metrics), ShouldEqual, 2) }) Convey("When getting agent with Metric", func() { q := &model.GetAgentsQuery{ Metric: "/testing/demo/demo1", } agentsWithMetric, err := c.GetAgents(q) So(err, ShouldBeNil) So(agentsWithMetric, ShouldNotBeNil) So(agentsWithMetric, ShouldHaveSameTypeAs, []*model.AgentDTO{}) So(len(agentsWithMetric), ShouldEqual, 1) So(agentsWithMetric[0].Id, ShouldEqual, agent.Id) }) Convey("When getting agent with Metric wildcard", func() { q := &model.GetAgentsQuery{ Metric: "/testing/public/*", } agentsWithMetric, err := c.GetAgents(q) So(err, ShouldBeNil) So(agentsWithMetric, ShouldNotBeNil) So(agentsWithMetric, ShouldHaveSameTypeAs, []*model.AgentDTO{}) So(len(agentsWithMetric), ShouldEqual, 1) So(agentsWithMetric[0].Id, ShouldEqual, 1) }) Convey("When getting agent with Metric wildcard that doesnt match", func() { q := &model.GetAgentsQuery{ Metric: "/not-found/demo/*", } agentsWithMetric, err := c.GetAgents(q) So(err, ShouldBeNil) So(agentsWithMetric, ShouldNotBeNil) So(agentsWithMetric, ShouldHaveSameTypeAs, []*model.AgentDTO{}) So(len(agentsWithMetric), ShouldEqual, 0) }) }) Convey("When getting list of tasks", func() { query := model.GetTasksQuery{} tasks, err := c.GetTasks(&query) So(err, ShouldBeNil) So(tasks, ShouldNotBeNil) So(len(tasks), ShouldEqual, taskCount) So(tasks, ShouldHaveSameTypeAs, []*model.TaskDTO{}) Convey("When Adding new Task", func() { pre := time.Now() taskCount++ t := &model.TaskDTO{ Name: fmt.Sprintf("test Task%d", taskCount), Interval: 60, Config: map[string]map[string]interface{}{"/": { "user": "******", "passwd": "test", }}, Metrics: map[string]int64{"/testing/demo/demo1": 0}, Route: &model.TaskRoute{ Type: "any", }, Enabled: true, } err := c.AddTask(t) So(err, ShouldBeNil) So(t.Id, ShouldNotBeEmpty) So(t.Name, ShouldEqual, fmt.Sprintf("test Task%d", taskCount)) So(t.Created, ShouldHappenBefore, time.Now()) So(t.Created, ShouldHappenAfter, pre) So(t.Created.Unix(), ShouldEqual, t.Updated.Unix()) Convey("When adding first task", func() { So(len(tasks), ShouldEqual, 0) }) Convey("When adding second task", func() { So(len(tasks), ShouldEqual, 1) }) }) Convey("when updating task", func() { pre := time.Now() t := new(model.TaskDTO) *t = *tasks[0] t.Name = "demo" err := c.UpdateTask(t) So(err, ShouldBeNil) So(t.Id, ShouldEqual, tasks[0].Id) So(t.Name, ShouldEqual, "demo") So(t.Created, ShouldHappenBefore, pre) So(t.Updated, ShouldHappenAfter, pre) So(t.Updated, ShouldHappenAfter, t.Created) }) Convey("When Adding new Task with route by tag", func() { t := &model.TaskDTO{ Name: "task route by tags", Interval: 60, Config: map[string]map[string]interface{}{"/": { "user": "******", "passwd": "test", }}, Metrics: map[string]int64{"/testing/demo2/demo": 0}, Route: &model.TaskRoute{ Type: model.RouteByTags, Config: map[string]interface{}{"tags": []string{"demo"}}, }, Enabled: true, } taskCount++ err = c.AddTask(t) So(err, ShouldBeNil) Convey("When getting agentTasks", func() { tasks, err := sqlstore.GetAgentTasks(&model.AgentDTO{Id: 1, OrgId: 1000}) So(err, ShouldBeNil) So(len(tasks), ShouldEqual, 1) So(tasks[0].Name, ShouldEqual, "task route by tags") tasks, err = sqlstore.GetAgentTasks(&model.AgentDTO{Id: 2, OrgId: 1}) So(err, ShouldBeNil) So(len(tasks), ShouldEqual, 3) }) }) Convey("When Adding new Task with route by tag matching only private probes", func() { t := &model.TaskDTO{ Name: "task route by tags2", Interval: 60, Config: map[string]map[string]interface{}{"/": { "user": "******", "passwd": "test", }}, Metrics: map[string]int64{"/testing/demo2/demo": 0}, Route: &model.TaskRoute{ Type: model.RouteByTags, Config: map[string]interface{}{"tags": []string{"private"}}, }, Enabled: true, } taskCount++ err = c.AddTask(t) So(err, ShouldBeNil) Convey("When getting agentTasks", func() { tasks, err := sqlstore.GetAgentTasks(&model.AgentDTO{Id: 1, OrgId: 1000}) So(err, ShouldBeNil) So(len(tasks), ShouldEqual, 1) So(tasks[0].Name, ShouldEqual, "task route by tags") tasks, err = sqlstore.GetAgentTasks(&model.AgentDTO{Id: 2, OrgId: 1}) So(err, ShouldBeNil) So(len(tasks), ShouldEqual, 4) }) }) Convey("When Adding new Task with no valid agents", func() { err := sqlstore.DeleteAgentSessionsByServer("localhost") So(err, ShouldBeNil) t := &model.TaskDTO{ Name: "task should fail", Interval: 60, Config: map[string]map[string]interface{}{"/": { "user": "******", "passwd": "test", }}, Metrics: map[string]int64{"/testing/demo/demo1": 0}, Route: &model.TaskRoute{ Type: "any", }, Enabled: true, } err = c.AddTask(t) So(err, ShouldNotBeNil) So(err.Error(), ShouldEqual, "400: No agent found that can provide all requested metrics.") }) }) }) }