Skip to content

Commit

Permalink
Cancel event on conflict
Browse files Browse the repository at this point in the history
  • Loading branch information
zdevaty committed Apr 23, 2024
1 parent 73398ab commit 57bc6e2
Show file tree
Hide file tree
Showing 3 changed files with 43 additions and 16 deletions.
23 changes: 18 additions & 5 deletions app.go
Original file line number Diff line number Diff line change
Expand Up @@ -234,7 +234,7 @@ func collectResources(config apiserver.Configuration) error {
log.Error("Booking", "updating bookings: %v", err)
}

if err := bc.Cancel(cancelledBookings); err != nil {
if err := bc.CancelSlice(cancelledBookings); err != nil {
log.Error("Booking", "cancelling bookings: %v", err)
}

Expand Down Expand Up @@ -307,15 +307,28 @@ func bookInEWS(book model.Booking, config apiserver.Configuration) {
Location: asset.ProviderID,
Attendees: []string{asset.ProviderID},
}
booking, err := ewsHelper.CreateAppointment(app)
if err != nil {
a, err := ewsHelper.CreateAppointment(app)
book.ExchangeUID = a.ExchangeUID
book.ExchangeIDInResourceMailbox = a.ExchangeIDInResourceMailbox
if errors.Is(err, ews.ErrDeclined) {
bc := booking.NewClient(*config.BookingAppURL)
if err := ewsHelper.CancelEvent(book); err != nil {
log.Error("ews", "cancelling conflicting event: %v", err)
return
}
if err := bc.Cancel(book.ElionaID, "conflict"); err != nil {
log.Error("booking", "cancelling conflicting appointment: %v", err)
return
}
log.Debug("ews", "booking for %v was conflicting; cancelled", book.OrganizerEmail)
} else if err != nil {
log.Error("ews", "creating appointment: %v", err)
return
}
log.Debug("ews", "created a booking for %v", book.OrganizerEmail)
b := appdb.Booking{
ExchangeID: null.StringFrom(booking.ExchangeIDInResourceMailbox),
ExchangeUID: null.StringFrom(booking.ExchangeUID),
ExchangeID: null.StringFrom(book.ExchangeIDInResourceMailbox),
ExchangeUID: null.StringFrom(book.ExchangeUID),
BookingID: null.Int32From(book.ElionaID),
}
if err := conf.UpsertBooking(b); err != nil {
Expand Down
8 changes: 4 additions & 4 deletions booking/booking.go
Original file line number Diff line number Diff line change
Expand Up @@ -98,18 +98,18 @@ func (c *client) book(bookings bookingRequest) (bookingResponse, error) {
return respBody, nil
}

func (c *client) Cancel(bookings []model.Booking) error {
func (c *client) CancelSlice(bookings []model.Booking) error {
for _, b := range bookings {
err := c.cancel(b.ElionaID)
err := c.Cancel(b.ElionaID, "cancelled")
if err != nil {
return err
}
}
return nil
}

func (c *client) cancel(elionaID int32) error {
req, err := http.NewRequest(http.MethodDelete, fmt.Sprintf("%s/sync/bookings/%v", c.BaseURL, elionaID), nil)
func (c *client) Cancel(elionaID int32, reason string) error {
req, err := http.NewRequest(http.MethodDelete, fmt.Sprintf("%s/sync/bookings/%v?reason=%v", c.BaseURL, elionaID, reason), nil)
if err != nil {
return err
}
Expand Down
28 changes: 21 additions & 7 deletions ews/ews.go
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ import (
"encoding/base64"
"encoding/hex"
"encoding/xml"
"errors"
"ews/apiserver"
"ews/model"
"fmt"
Expand All @@ -33,6 +34,10 @@ import (
"golang.org/x/oauth2/clientcredentials"
)

var ErrDeclined = errors.New("resource has declined invitation")

var errNotFound = errors.New("entity not found")

type EWSHelper struct {
Client *http.Client
EwsURL string
Expand Down Expand Up @@ -431,15 +436,24 @@ func (h *EWSHelper) CreateAppointment(appointment Appointment) (booking model.Bo
if err != nil {
return model.Booking{}, fmt.Errorf("getting UID from ItemID: %v", err)
}
booking.ExchangeUID = uid

// Let's give the server some time to process the invitation. Sometimes it's
// instant, sometimes 2 seconds aren't enough. This should be long enough
// time.
time.Sleep(15 * time.Second)

resourceEventID, _, err := h.findEventUIDInMailbox(appointment.Location, uid)
if err != nil {
return model.Booking{}, fmt.Errorf("finding resource event ID: %v", err)
if errors.Is(err, errNotFound) {
// The resource has probably declined the invitation.
return booking, ErrDeclined
} else if err != nil {
return booking, fmt.Errorf("finding resource event ID: %v", err)
}

return model.Booking{
ExchangeIDInResourceMailbox: resourceEventID,
ExchangeUID: uid,
}, nil
booking.ExchangeIDInResourceMailbox = resourceEventID

return booking, nil
}

func formatAttendees(attendees []string) string {
Expand Down Expand Up @@ -701,7 +715,7 @@ func (h *EWSHelper) findEventUIDInMailbox(mailbox, uid string) (itemID string, c
}

if len(response.Body.FindItemResponse.ResponseMessages.FindItemResponseMessage.RootFolder.Items.CalendarItem) == 0 {
return "", "", fmt.Errorf("event not found. response: %v", string(respBody))
return "", "", errNotFound
}

item := response.Body.FindItemResponse.ResponseMessages.FindItemResponseMessage.RootFolder.Items.CalendarItem[0].ItemId
Expand Down

0 comments on commit 57bc6e2

Please sign in to comment.