From a4e96e0cc6192f714e24be54ca319f5b173bfd3b Mon Sep 17 00:00:00 2001 From: Daniel Fischer Date: Wed, 6 May 2026 13:17:30 +1000 Subject: [PATCH] feat: Add Subscription support Add subscription functionality to the Octopus GO Client. --- pkg/constants/constants_parameters.go | 1 + pkg/subscriptions/subscription.go | 84 +++++++++++++++++++++++ pkg/subscriptions/subscription_service.go | 41 +++++++++++ 3 files changed, 126 insertions(+) create mode 100644 pkg/subscriptions/subscription.go diff --git a/pkg/constants/constants_parameters.go b/pkg/constants/constants_parameters.go index b63bf578..13bd37c3 100644 --- a/pkg/constants/constants_parameters.go +++ b/pkg/constants/constants_parameters.go @@ -41,6 +41,7 @@ const ( ParameterSecretKey string = "secretKey" ParameterSling string = "sling" ParameterSpace string = "space" + ParameterSubscription string = "subscription" ParameterTagSet string = "tagSet" ParameterTask string = "task" ParameterTeam string = "team" diff --git a/pkg/subscriptions/subscription.go b/pkg/subscriptions/subscription.go new file mode 100644 index 00000000..9962fd25 --- /dev/null +++ b/pkg/subscriptions/subscription.go @@ -0,0 +1,84 @@ +package subscriptions + +import ( + "time" + + "github.com/OctopusDeploy/go-octopusdeploy/v2/pkg/resources" + "github.com/go-playground/validator/v10" +) + +type EventNotificationSubscriptionFilter struct { + DocumentTypes []string `json:"DocumentTypes"` + EventAgents []string `json:"EventAgents"` + EventCategories []string `json:"EventCategories"` + EventGroups []string `json:"EventGroups"` + Environments []string `json:"Environments"` + ProjectGroups []string `json:"ProjectGroups"` + Projects []string `json:"Projects"` + Tags []string `json:"Tags"` + Tenants []string `json:"Tenants"` + Users []string `json:"Users"` +} + +type EventNotificationSubscription struct { + EmailDigestLastProcessed *time.Time `json:"EmailDigestLastProcessed,omitempty"` + EmailDigestLastProcessedEventAutoId *int64 `json:"EmailDigestLastProcessedEventAutoId,omitempty"` + EmailFrequencyPeriod string `json:"EmailFrequencyPeriod"` + EmailPriority string `json:"EmailPriority"` + EmailShowDatesInTimeZoneId string `json:"EmailShowDatesInTimeZoneId"` + EmailTeams []string `json:"EmailTeams"` + Filter *EventNotificationSubscriptionFilter `json:"Filter"` + WebhookHeaderKey string `json:"WebhookHeaderKey"` + WebhookHeaderValue string `json:"WebhookHeaderValue"` + WebhookLastProcessed *time.Time `json:"WebhookLastProcessed,omitempty"` + WebhookLastProcessedEventAutoId *int64 `json:"WebhookLastProcessedEventAutoId,omitempty"` + WebhookTeams []string `json:"WebhookTeams"` + WebhookTimeout string `json:"WebhookTimeout"` + WebhookURI string `json:"WebhookURI"` +} + +type Subscription struct { + EventNotificationSubscription *EventNotificationSubscription `json:"EventNotificationSubscription"` + IsDisabled bool `json:"IsDisabled"` + Name string `json:"Name" validate:"required"` + SpaceID string `json:"SpaceId,omitempty"` + Type string `json:"Type,omitempty"` + + resources.Resource +} + +func NewSubscription(name string) *Subscription { + return &Subscription{ + Name: name, + Resource: *resources.NewResource(), + EventNotificationSubscription: &EventNotificationSubscription{ + EmailFrequencyPeriod: "01:00:00", + EmailPriority: "Normal", + EmailShowDatesInTimeZoneId: "UTC", + EmailTeams: []string{}, + WebhookTeams: []string{}, + WebhookTimeout: "00:00:10", + Filter: &EventNotificationSubscriptionFilter{ + DocumentTypes: []string{}, + EventAgents: []string{}, + EventCategories: []string{}, + EventGroups: []string{}, + Environments: []string{}, + ProjectGroups: []string{}, + Projects: []string{}, + Tags: []string{}, + Tenants: []string{}, + Users: []string{}, + }, + }, + } +} + +func (s *Subscription) GetName() string { return s.Name } +func (s *Subscription) SetName(name string) { s.Name = name } + +func (s *Subscription) Validate() error { + return validator.New().Struct(s) +} + +var _ resources.IHasName = &Subscription{} diff --git a/pkg/subscriptions/subscription_service.go b/pkg/subscriptions/subscription_service.go index ec5f42b5..3be504a6 100644 --- a/pkg/subscriptions/subscription_service.go +++ b/pkg/subscriptions/subscription_service.go @@ -1,7 +1,10 @@ package subscriptions import ( + "github.com/OctopusDeploy/go-octopusdeploy/v2/internal" "github.com/OctopusDeploy/go-octopusdeploy/v2/pkg/constants" + "github.com/OctopusDeploy/go-octopusdeploy/v2/pkg/newclient" + "github.com/OctopusDeploy/go-octopusdeploy/v2/pkg/resources" "github.com/OctopusDeploy/go-octopusdeploy/v2/pkg/services" "github.com/dghubble/sling" ) @@ -17,3 +20,41 @@ func NewSubscriptionService(sling *sling.Sling, uriTemplate string) *Subscriptio }, } } + +const template = "/api/{spaceId}/subscriptions{/id}{?skip,take,ids,partialName,spaces}" + +// Add creates a new subscription. +func Add(client newclient.Client, spaceID string, subscription *Subscription) (*Subscription, error) { + if subscription == nil { + return nil, internal.CreateInvalidParameterError(constants.OperationAdd, constants.ParameterSubscription) + } + return newclient.Add[Subscription](client, template, spaceID, subscription) +} + +// GetByID returns the subscription that matches the input ID. +func GetByID(client newclient.Client, spaceID string, id string) (*Subscription, error) { + return newclient.GetByID[Subscription](client, template, spaceID, id) +} + +// Update modifies a subscription based on the one provided as input. +func Update(client newclient.Client, spaceID string, subscription *Subscription) (*Subscription, error) { + if subscription == nil { + return nil, internal.CreateInvalidParameterError(constants.OperationUpdate, constants.ParameterSubscription) + } + return newclient.Update[Subscription](client, template, spaceID, subscription.ID, subscription) +} + +// DeleteByID deletes the subscription that matches the input ID. +func DeleteByID(client newclient.Client, spaceID string, id string) error { + return newclient.DeleteByID(client, template, spaceID, id) +} + +// GetAll returns all subscriptions for the given space. +func GetAll(client newclient.Client, spaceID string) ([]*Subscription, error) { + return newclient.GetAll[Subscription](client, template, spaceID) +} + +// Get returns a collection of subscriptions based on the criteria defined by its input query parameter. +func Get(client newclient.Client, spaceID string, query SubscriptionsQuery) (*resources.Resources[*Subscription], error) { + return newclient.GetByQuery[Subscription](client, template, spaceID, query) +}