@@ -232,7 +232,7 @@ func (s *service) GetBalance(ctx context.Context, input GetBalanceServiceInput)
232232
233233 // Pending balance remains a current projection from open charges.
234234 // Historical cursor/as-of filtering only affects the booked/settled side for now.
235- impacts , err := s .getChargePendingBalanceImpacts (ctx , input .CustomerID , input .Currency )
235+ impacts , err := s .getChargePendingBalanceImpacts (ctx , input .CustomerID , input .Currency , normalizeFeatureFilter ( input . FeatureFilter ) )
236236 if err != nil {
237237 return nil , fmt .Errorf ("get charge pending balance impacts: %w" , err )
238238 }
@@ -275,7 +275,7 @@ func (s *service) GetFBOCurrencies(ctx context.Context, customerID customer.Cust
275275 return codes , nil
276276}
277277
278- func (s * service ) getChargePendingBalanceImpacts (ctx context.Context , customerID customer.CustomerID , currency currencyx.Code ) ([]Impact , error ) {
278+ func (s * service ) getChargePendingBalanceImpacts (ctx context.Context , customerID customer.CustomerID , currency currencyx.Code , featureFilter mo. Option [creditpurchase. FeatureFilters ] ) ([]Impact , error ) {
279279 items , err := pagination .CollectAll (
280280 ctx ,
281281 pagination .NewPaginator (func (ctx context.Context , page pagination.Page ) (pagination.Result [charges.Charge ], error ) {
@@ -299,7 +299,7 @@ func (s *service) getChargePendingBalanceImpacts(ctx context.Context, customerID
299299
300300 impacts := make ([]Impact , 0 , len (items ))
301301 for _ , charge := range items {
302- impact , err := s .getChargePendingBalanceImpact (ctx , charge , currency )
302+ impact , err := s .getChargePendingBalanceImpact (ctx , charge , currency , featureFilter )
303303 if err != nil {
304304 return nil , err
305305 }
@@ -314,22 +314,22 @@ func (s *service) getChargePendingBalanceImpacts(ctx context.Context, customerID
314314 return impacts , nil
315315}
316316
317- func (s * service ) getChargePendingBalanceImpact (ctx context.Context , charge charges.Charge , currency currencyx.Code ) (* Impact , error ) {
317+ func (s * service ) getChargePendingBalanceImpact (ctx context.Context , charge charges.Charge , currency currencyx.Code , featureFilter mo. Option [creditpurchase. FeatureFilters ] ) (* Impact , error ) {
318318 if ! chargeHasStarted (charge ) {
319319 return nil , nil
320320 }
321321
322322 switch charge .Type () {
323323 case meta .ChargeTypeFlatFee :
324- return getFlatFeeChargePendingBalanceImpact (charge , currency )
324+ return getFlatFeeChargePendingBalanceImpact (charge , currency , featureFilter )
325325 case meta .ChargeTypeUsageBased :
326- return s .getUsageBasedChargePendingBalanceImpact (ctx , charge , currency )
326+ return s .getUsageBasedChargePendingBalanceImpact (ctx , charge , currency , featureFilter )
327327 default :
328328 return nil , nil
329329 }
330330}
331331
332- func getFlatFeeChargePendingBalanceImpact (charge charges.Charge , currency currencyx.Code ) (* Impact , error ) {
332+ func getFlatFeeChargePendingBalanceImpact (charge charges.Charge , currency currencyx.Code , featureFilter mo. Option [creditpurchase. FeatureFilters ] ) (* Impact , error ) {
333333 flatFeeCharge , err := charge .AsFlatFeeCharge ()
334334 if err != nil {
335335 return nil , fmt .Errorf ("map flat fee charge: %w" , err )
@@ -339,10 +339,14 @@ func getFlatFeeChargePendingBalanceImpact(charge charges.Charge, currency curren
339339 return nil , nil
340340 }
341341
342+ if ! featureFilterMatchesChargeFeatureKey (featureFilter , flatFeeCharge .Intent .FeatureKey ) {
343+ return nil , nil
344+ }
345+
342346 return newImpactOrNil (charge , flatFeeCharge .State .AmountAfterProration )
343347}
344348
345- func (s * service ) getUsageBasedChargePendingBalanceImpact (ctx context.Context , charge charges.Charge , currency currencyx.Code ) (* Impact , error ) {
349+ func (s * service ) getUsageBasedChargePendingBalanceImpact (ctx context.Context , charge charges.Charge , currency currencyx.Code , featureFilter mo. Option [creditpurchase. FeatureFilters ] ) (* Impact , error ) {
346350 usageBasedCharge , err := charge .AsUsageBasedCharge ()
347351 if err != nil {
348352 return nil , fmt .Errorf ("map usage based charge: %w" , err )
@@ -352,6 +356,10 @@ func (s *service) getUsageBasedChargePendingBalanceImpact(ctx context.Context, c
352356 return nil , nil
353357 }
354358
359+ if ! featureFilterMatchesChargeFeatureKey (featureFilter , usageBasedCharge .Intent .FeatureKey ) {
360+ return nil , nil
361+ }
362+
355363 currentTotals , err := s .UsageBasedService .GetCurrentTotals (ctx , usagebased.GetCurrentTotalsInput {
356364 ChargeID : usageBasedCharge .GetChargeID (),
357365 })
@@ -362,6 +370,23 @@ func (s *service) getUsageBasedChargePendingBalanceImpact(ctx context.Context, c
362370 return newImpactOrNil (charges .NewCharge (currentTotals .Charge ), currentTotals .DueTotals .Total )
363371}
364372
373+ func featureFilterMatchesChargeFeatureKey (featureFilter mo.Option [creditpurchase.FeatureFilters ], featureKey string ) bool {
374+ if featureFilter .IsAbsent () {
375+ return true
376+ }
377+
378+ features := featureFilter .OrEmpty ()
379+ if features == nil {
380+ return featureKey == ""
381+ }
382+
383+ if featureKey == "" {
384+ return true
385+ }
386+
387+ return len (features ) == 1 && features [0 ] == featureKey
388+ }
389+
365390func chargeHasStarted (charge charges.Charge ) bool {
366391 now := clock .Now ()
367392
0 commit comments