From 114e5102ff1477dabec2ae10643d8f25b6848e67 Mon Sep 17 00:00:00 2001 From: Rowan Seymour Date: Mon, 9 May 2022 16:01:22 -0500 Subject: [PATCH] Record ticket daily counts when opening tickets --- core/handlers/ticket_opened_test.go | 4 ++- core/hooks/insert_tickets.go | 2 +- core/models/tickets.go | 43 +++++++++++++++++++++++++++-- core/models/tickets_test.go | 7 ++++- go.mod | 2 +- go.sum | 4 +-- services/tickets/utils_test.go | 7 ++--- testsuite/testsuite.go | 1 + 8 files changed, 58 insertions(+), 12 deletions(-) diff --git a/core/handlers/ticket_opened_test.go b/core/handlers/ticket_opened_test.go index 376c79f93..da57129c9 100644 --- a/core/handlers/ticket_opened_test.go +++ b/core/handlers/ticket_opened_test.go @@ -44,9 +44,11 @@ func TestTicketOpened(t *testing.T) { }, })) + oa := testdata.Org1.Load(rt) + // an existing ticket cathyTicket := models.NewTicket(flows.TicketUUID(uuids.New()), testdata.Org1.ID, testdata.Cathy.ID, testdata.Mailgun.ID, "748363", testdata.DefaultTopic.ID, "Who?", models.NilUserID, nil) - err := models.InsertTickets(ctx, db, []*models.Ticket{cathyTicket}) + err := models.InsertTickets(ctx, db, oa, []*models.Ticket{cathyTicket}) require.NoError(t, err) tcs := []handlers.TestCase{ diff --git a/core/hooks/insert_tickets.go b/core/hooks/insert_tickets.go index 3acf2606b..ee93baf5e 100644 --- a/core/hooks/insert_tickets.go +++ b/core/hooks/insert_tickets.go @@ -27,7 +27,7 @@ func (h *insertTicketsHook) Apply(ctx context.Context, rt *runtime.Runtime, tx * } // insert the tickets - err := models.InsertTickets(ctx, tx, tickets) + err := models.InsertTickets(ctx, tx, oa, tickets) if err != nil { return errors.Wrapf(err, "error inserting tickets") } diff --git a/core/models/tickets.go b/core/models/tickets.go index b75a81a6f..db6771da5 100644 --- a/core/models/tickets.go +++ b/core/models/tickets.go @@ -4,6 +4,7 @@ import ( "context" "database/sql" "database/sql/driver" + "fmt" "net/http" "time" @@ -51,10 +52,15 @@ func (i *TicketID) Scan(value interface{}) error { type TicketerID null.Int type TicketStatus string +type TicketDailyCountType string const ( TicketStatusOpen = TicketStatus("O") TicketStatusClosed = TicketStatus("C") + + TicketDailyCountOpening = TicketDailyCountType("O") + TicketDailyCountAssignment = TicketDailyCountType("A") + TicketDailyCountReply = TicketDailyCountType("R") ) // Register a ticket service factory with the engine @@ -334,7 +340,7 @@ RETURNING ` // InsertTickets inserts the passed in tickets returning any errors encountered -func InsertTickets(ctx context.Context, tx Queryer, tickets []*Ticket) error { +func InsertTickets(ctx context.Context, tx Queryer, oa *OrgAssets, tickets []*Ticket) error { if len(tickets) == 0 { return nil } @@ -344,7 +350,40 @@ func InsertTickets(ctx context.Context, tx Queryer, tickets []*Ticket) error { ts[i] = &tickets[i].t } - return BulkQuery(ctx, "inserted tickets", tx, sqlInsertTicket, ts) + if err := BulkQuery(ctx, "inserted tickets", tx, sqlInsertTicket, ts); err != nil { + return err + } + + return insertTicketDailyCounts(ctx, tx, TicketDailyCountOpening, oa.Org().Timezone(), map[string]int{ + fmt.Sprintf("o:%d", oa.OrgID()): len(tickets), + }) +} + +const sqlInsertTicketDailyCount = ` +INSERT INTO tickets_ticketdailycount(count_type, scope, count, day, is_squashed) + VALUES(:count_type, :scope, :count, :day, FALSE)` + +func insertTicketDailyCounts(ctx context.Context, tx Queryer, countType TicketDailyCountType, tz *time.Location, scopeCounts map[string]int) error { + type dailyCount struct { + CountType TicketDailyCountType `db:"count_type"` + Scope string `db:"scope"` + Count int `db:"count"` + Day dates.Date `db:"day"` + } + + day := dates.ExtractDate(dates.Now().In(tz)) + + counts := make([]*dailyCount, 0, len(scopeCounts)) + for scope, count := range scopeCounts { + counts = append(counts, &dailyCount{ + CountType: countType, + Scope: scope, + Count: count, + Day: day, + }) + } + + return BulkQuery(ctx, "inserted ticket daily counts", tx, sqlInsertTicketDailyCount, counts) } // UpdateTicketExternalID updates the external ID of the given ticket diff --git a/core/models/tickets_test.go b/core/models/tickets_test.go index c541de906..f0fd516f9 100644 --- a/core/models/tickets_test.go +++ b/core/models/tickets_test.go @@ -62,6 +62,8 @@ func TestTickets(t *testing.T) { defer testsuite.Reset(testsuite.ResetData) + oa := testdata.Org1.Load(rt) + ticket1 := models.NewTicket( "2ef57efc-d85f-4291-b330-e4afe68af5fe", testdata.Org1.ID, @@ -108,12 +110,15 @@ func TestTickets(t *testing.T) { assert.Equal(t, testdata.Admin.ID, ticket1.AssigneeID()) assert.Equal(t, "", ticket1.Config("xyz")) - err := models.InsertTickets(ctx, db, []*models.Ticket{ticket1, ticket2, ticket3}) + err := models.InsertTickets(ctx, db, oa, []*models.Ticket{ticket1, ticket2, ticket3}) assert.NoError(t, err) // check all tickets were created assertdb.Query(t, db, `SELECT count(*) FROM tickets_ticket WHERE status = 'O' AND closed_on IS NULL`).Returns(3) + // check the opened count was added + assertdb.Query(t, db, `SELECT SUM(count) FROM tickets_ticketdailycount WHERE count_type = 'O' AND scope = CONCAT('o:', $1::text)`, testdata.Org1.ID).Returns(3) + // can lookup a ticket by UUID tk1, err := models.LookupTicketByUUID(ctx, db, "2ef57efc-d85f-4291-b330-e4afe68af5fe") assert.NoError(t, err) diff --git a/go.mod b/go.mod index 4302715e2..bcd30d22c 100644 --- a/go.mod +++ b/go.mod @@ -16,7 +16,7 @@ require ( github.com/jmoiron/sqlx v1.3.4 github.com/lib/pq v1.10.4 github.com/nyaruka/ezconf v0.2.1 - github.com/nyaruka/gocommon v1.19.1 + github.com/nyaruka/gocommon v1.20.0 github.com/nyaruka/goflow v0.158.1 github.com/nyaruka/librato v1.0.0 github.com/nyaruka/logrus_sentry v0.8.2-0.20190129182604-c2962b80ba7d diff --git a/go.sum b/go.sum index 8fdc07e0c..28cd62b10 100644 --- a/go.sum +++ b/go.sum @@ -129,8 +129,8 @@ github.com/naoina/toml v0.1.1 h1:PT/lllxVVN0gzzSqSlHEmP8MJB4MY2U7STGxiouV4X8= github.com/naoina/toml v0.1.1/go.mod h1:NBIhNtsFMo3G2szEBne+bO4gS192HuIYRqfvOWb4i1E= github.com/nyaruka/ezconf v0.2.1 h1:TDXWoqjqYya1uhou1mAJZg7rgFYL98EB0Tb3+BWtUh0= github.com/nyaruka/ezconf v0.2.1/go.mod h1:ey182kYkw2MIi4XiWe1FR/mzI33WCmTWuceDYYxgnQw= -github.com/nyaruka/gocommon v1.19.1 h1:miVSFCqSEe1pKAID/PWqwRBtdvPnw6kQZC/Bz9tYVgQ= -github.com/nyaruka/gocommon v1.19.1/go.mod h1:JrQSLAPo9ezSy1AzsJ1zDr1HW0/eu+aipICJkN/+kpg= +github.com/nyaruka/gocommon v1.20.0 h1:qbxRsBBPvpfGbuBq08jlQGxa5t+UZX/YGV7+kR+/moM= +github.com/nyaruka/gocommon v1.20.0/go.mod h1:JrQSLAPo9ezSy1AzsJ1zDr1HW0/eu+aipICJkN/+kpg= github.com/nyaruka/goflow v0.158.1 h1:Q6zrf55f8XqsC3WFRD/Gcpp/RwLXnHdY7UslT32TI7o= github.com/nyaruka/goflow v0.158.1/go.mod h1:J+FJ0iw1cjivEziBGpVPtTl9fuOz+ib558MCBdKLC8M= github.com/nyaruka/librato v1.0.0 h1:Vznj9WCeC1yZXbBYyYp40KnbmXLbEkjKmHesV/v2SR0= diff --git a/services/tickets/utils_test.go b/services/tickets/utils_test.go index 4e082b960..fd8fd1e8b 100644 --- a/services/tickets/utils_test.go +++ b/services/tickets/utils_test.go @@ -158,6 +158,8 @@ func TestCloseTicket(t *testing.T) { }, })) + oa := testdata.Org1.Load(rt) + // create an open ticket ticket1 := models.NewTicket( "2ef57efc-d85f-4291-b330-e4afe68af5fe", @@ -172,15 +174,12 @@ func TestCloseTicket(t *testing.T) { "contact-display": "Cathy", }, ) - err := models.InsertTickets(ctx, db, []*models.Ticket{ticket1}) + err := models.InsertTickets(ctx, db, oa, []*models.Ticket{ticket1}) require.NoError(t, err) // create a close ticket trigger testdata.InsertTicketClosedTrigger(db, testdata.Org1, testdata.Favorites) - oa, err := models.GetOrgAssets(ctx, rt, testdata.Org1.ID) - require.NoError(t, err) - logger := &models.HTTPLogger{} err = tickets.Close(ctx, rt, oa, ticket1, true, logger) diff --git a/testsuite/testsuite.go b/testsuite/testsuite.go index b68055c84..493717efc 100644 --- a/testsuite/testsuite.go +++ b/testsuite/testsuite.go @@ -184,6 +184,7 @@ UPDATE contacts_contact SET current_flow_id = NULL; DELETE FROM notifications_notification; DELETE FROM notifications_incident; DELETE FROM request_logs_httplog; +DELETE FROM tickets_ticketdailycount; DELETE FROM tickets_ticketevent; DELETE FROM tickets_ticket; DELETE FROM triggers_trigger_contacts WHERE trigger_id >= 30000;