package oci import ( "context" "fmt" "time" "github.com/oracle/oci-go-sdk/v65/common" "github.com/oracle/oci-go-sdk/v65/tenantmanagercontrolplane" ) // SubscriptionInfo 是租户订阅的摘要信息。 type SubscriptionInfo struct { ID string `json:"id"` ServiceName string `json:"serviceName"` TimeCreated *time.Time `json:"timeCreated"` TimeUpdated *time.Time `json:"timeUpdated"` } // PromotionInfo 是订阅下的一条促销记录。 type PromotionInfo struct { Duration int `json:"duration"` DurationUnit string `json:"durationUnit"` Amount float32 `json:"amount"` Status string `json:"status"` IsIntentToPay bool `json:"isIntentToPay"` CurrencyUnit string `json:"currencyUnit"` TimeStarted *time.Time `json:"timeStarted"` TimeExpired *time.Time `json:"timeExpired"` } // SubscriptionDetail 是单个订阅的完整信息(Classic v1 订阅)。 type SubscriptionDetail struct { ID string `json:"id"` ServiceName string `json:"serviceName"` ClassicSubscriptionID string `json:"classicSubscriptionId"` PaymentModel string `json:"paymentModel"` SubscriptionTier string `json:"subscriptionTier"` LifecycleState string `json:"lifecycleState"` ProgramType string `json:"programType"` CustomerCountryCode string `json:"customerCountryCode"` CloudAmountCurrency string `json:"cloudAmountCurrency"` CsiNumber string `json:"csiNumber"` RegionAssignment string `json:"regionAssignment"` IsGovernmentSubscription bool `json:"isGovernmentSubscription"` Promotions []PromotionInfo `json:"promotions"` StartDate *time.Time `json:"startDate"` EndDate *time.Time `json:"endDate"` TimeCreated *time.Time `json:"timeCreated"` TimeUpdated *time.Time `json:"timeUpdated"` } // ListSubscriptions 实现 Client:分页列出租户全部订阅摘要。 func (c *RealClient) ListSubscriptions(ctx context.Context, cred Credentials) ([]SubscriptionInfo, error) { sc, err := tenantmanagercontrolplane.NewSubscriptionClientWithConfigurationProvider(provider(cred)) if err != nil { return nil, fmt.Errorf("new subscription client: %w", err) } applyProxy(&sc.BaseClient, cred) var subs []SubscriptionInfo var page *string for { resp, err := sc.ListSubscriptions(ctx, tenantmanagercontrolplane.ListSubscriptionsRequest{ CompartmentId: &cred.TenancyOCID, Page: page, }) if err != nil { return nil, fmt.Errorf("list subscriptions: %w", err) } for _, item := range resp.Items { subs = append(subs, SubscriptionInfo{ ID: deref(item.GetId()), ServiceName: deref(item.GetServiceName()), TimeCreated: sdkTime(item.GetTimeCreated()), TimeUpdated: sdkTime(item.GetTimeUpdated()), }) } if resp.OpcNextPage == nil { return orEmpty(subs), nil } page = resp.OpcNextPage } } // GetSubscription 实现 Client:查询单个订阅的完整信息。 func (c *RealClient) GetSubscription(ctx context.Context, cred Credentials, subscriptionID string) (SubscriptionDetail, error) { sc, err := tenantmanagercontrolplane.NewSubscriptionClientWithConfigurationProvider(provider(cred)) if err != nil { return SubscriptionDetail{}, fmt.Errorf("new subscription client: %w", err) } applyProxy(&sc.BaseClient, cred) resp, err := sc.GetSubscription(ctx, tenantmanagercontrolplane.GetSubscriptionRequest{ SubscriptionId: &subscriptionID, }) if err != nil { return SubscriptionDetail{}, fmt.Errorf("get subscription %s: %w", subscriptionID, err) } switch sub := resp.Subscription.(type) { case tenantmanagercontrolplane.ClassicSubscription: return toSubscriptionDetail(sub), nil case *tenantmanagercontrolplane.ClassicSubscription: return toSubscriptionDetail(*sub), nil default: return SubscriptionDetail{}, fmt.Errorf("get subscription %s: unexpected type %T", subscriptionID, resp.Subscription) } } func toSubscriptionDetail(sub tenantmanagercontrolplane.ClassicSubscription) SubscriptionDetail { detail := SubscriptionDetail{ ID: deref(sub.Id), ServiceName: deref(sub.ServiceName), ClassicSubscriptionID: deref(sub.ClassicSubscriptionId), PaymentModel: deref(sub.PaymentModel), SubscriptionTier: deref(sub.SubscriptionTier), LifecycleState: string(sub.LifecycleState), ProgramType: deref(sub.ProgramType), CustomerCountryCode: deref(sub.CustomerCountryCode), CloudAmountCurrency: deref(sub.CloudAmountCurrency), CsiNumber: deref(sub.CsiNumber), RegionAssignment: deref(sub.RegionAssignment), IsGovernmentSubscription: sub.IsGovernmentSubscription != nil && *sub.IsGovernmentSubscription, StartDate: sdkTime(sub.StartDate), EndDate: sdkTime(sub.EndDate), TimeCreated: sdkTime(sub.TimeCreated), TimeUpdated: sdkTime(sub.TimeUpdated), } detail.Promotions = make([]PromotionInfo, 0, len(sub.Promotion)) for _, p := range sub.Promotion { detail.Promotions = append(detail.Promotions, toPromotionInfo(p)) } return detail } func toPromotionInfo(p tenantmanagercontrolplane.Promotion) PromotionInfo { info := PromotionInfo{ Status: string(p.Status), DurationUnit: deref(p.DurationUnit), CurrencyUnit: deref(p.CurrencyUnit), TimeStarted: sdkTime(p.TimeStarted), TimeExpired: sdkTime(p.TimeExpired), } if p.Duration != nil { info.Duration = *p.Duration } if p.Amount != nil { info.Amount = *p.Amount } if p.IsIntentToPay != nil { info.IsIntentToPay = *p.IsIntentToPay } return info } func sdkTime(t *common.SDKTime) *time.Time { if t == nil { return nil } return &t.Time }