Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

gql: add field "assignedSchedules" to type "User" #3231

Merged
merged 22 commits into from
Oct 27, 2023
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
69 changes: 69 additions & 0 deletions graphql2/generated.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions graphql2/schema.graphql
Original file line number Diff line number Diff line change
Expand Up @@ -864,6 +864,7 @@ type OnCallShift {
start: ISOTimestamp!
end: ISOTimestamp!
truncated: Boolean!
target: Target!
}

type ScheduleTarget {
Expand Down
30 changes: 21 additions & 9 deletions oncall/state.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ type ResolvedRotation struct {
}

type state struct {
schedule schedule.Schedule
tempScheds []schedule.TemporarySchedule
rules []ResolvedRule
overrides []override.UserOverride
Expand Down Expand Up @@ -124,33 +125,44 @@ func (s *state) CalculateShifts(start, end time.Time) []Shift {
isOnCall := make(map[string]*Shift)
stillOnCall := make(map[string]bool)

setOnCall := func(userIDs []string) {
setOnCall := func(userIDs []string, shiftType assignment.TargetType) {
// reset map
for id := range stillOnCall {
delete(stillOnCall, id)
}
now := time.Unix(t.Unix(), 0)
for _, id := range userIDs {
stillOnCall[id] = true
s := isOnCall[id]
if s != nil {
o := isOnCall[id]
if o != nil {
continue
}
Forfold marked this conversation as resolved.
Show resolved Hide resolved

isOnCall[id] = &Shift{
Start: now,
UserID: id,
Target: assignment.RawTarget{
Type: shiftType,
ID: s.schedule.ID,
Name: s.schedule.Name,
},
}
}
for id, s := range isOnCall {
for id, shift := range isOnCall {
if stillOnCall[id] {
continue
}

shift.Target = assignment.RawTarget{
Type: shiftType,
ID: s.schedule.ID,
Name: s.schedule.Name,
}

// no longer on call
if now.After(start) {
s.End = now
shifts = append(shifts, *s)
shift.End = now
shifts = append(shifts, *shift)
}
delete(isOnCall, id)
}
Expand All @@ -159,18 +171,18 @@ func (s *state) CalculateShifts(start, end time.Time) []Shift {
for t.Next() {
if time.Unix(t.Unix(), 0).Before(historyCutoff) {
// use history if in the past
setOnCall(hist.ActiveUsers())
setOnCall(hist.ActiveUsers(), assignment.TargetTypeSchedule)
continue
}

if tempScheds.Active() {
// use TemporarySchedule if one is active
setOnCall(tempScheds.ActiveUsers())
setOnCall(tempScheds.ActiveUsers(), assignment.TargetTypeSchedule)
continue
}

// apply any overrides
setOnCall(overrides.MapUsers(rules.ActiveUsers()))
setOnCall(overrides.MapUsers(rules.ActiveUsers()), assignment.TargetTypeUserOverride)
}

// remaining shifts are truncated
Expand Down
23 changes: 18 additions & 5 deletions oncall/store.go
Original file line number Diff line number Diff line change
Expand Up @@ -36,10 +36,11 @@ type ServiceOnCallUser struct {
// the time the user stopped being on call, instead it indicates
// they were still on-call at that time.
type Shift struct {
UserID string `json:"user_id"`
Start time.Time `json:"start_time"`
End time.Time `json:"end_time"`
Truncated bool `json:"truncated"`
UserID string `json:"user_id"`
Start time.Time `json:"start_time"`
End time.Time `json:"end_time"`
Truncated bool `json:"truncated"`
Target assignment.RawTarget `json:"target"`
}

// Store allows retrieving and calculating on-call information.
Expand All @@ -51,6 +52,7 @@ type Store struct {
schedOverrides *sql.Stmt

schedOnCall *sql.Stmt
schedName *sql.Stmt
schedTZ *sql.Stmt
schedRot *sql.Stmt
rotParts *sql.Stmt
Expand Down Expand Up @@ -107,7 +109,8 @@ func NewStore(ctx context.Context, db *sql.DB, ruleStore *rule.Store, schedStore
tstzrange($2, $3) && tstzrange(start_time, end_time) and
(end_time isnull or (end_time - start_time) > '1 minute'::interval)
`),
schedTZ: p.P(`select time_zone, now() from schedules where id = $1`),
schedName: p.P(`select name from schedules where id = $1`),
schedTZ: p.P(`select time_zone, now() from schedules where id = $1`),
schedRot: p.P(`
select distinct
rot.id,
Expand Down Expand Up @@ -211,6 +214,12 @@ func (s *Store) HistoryBySchedule(ctx context.Context, scheduleID string, start,
}
defer sqlutil.Rollback(ctx, "oncall: fetch schedule history", tx)

var schedName string
err = tx.StmtContext(ctx, s.schedName).QueryRowContext(ctx, scheduleID).Scan(&schedName)
if err != nil {
return nil, errors.Wrap(err, "lookup schedule name")
}

var schedTZ string
var now time.Time
err = tx.StmtContext(ctx, s.schedTZ).QueryRowContext(ctx, scheduleID).Scan(&schedTZ, &now)
Expand Down Expand Up @@ -325,6 +334,10 @@ func (s *Store) HistoryBySchedule(ctx context.Context, scheduleID string, start,
return nil, errors.Wrap(err, "load time zone info")
}
st := state{
schedule: schedule.Schedule{
ID: scheduleID,
Name: schedName,
},
rules: rules,
overrides: overrides,
history: userHistory,
Expand Down
1 change: 1 addition & 0 deletions web/src/schema.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -678,6 +678,7 @@ export interface OnCallShift {
start: ISOTimestamp
end: ISOTimestamp
truncated: boolean
target: Target
}

export interface ScheduleTarget {
Expand Down