package db import ( "context" ) func (r *PGRepository) GetSubscriptionSnapshot(ctx context.Context, tenantID string) (BillingSnapshotRecord, error) { var record BillingSnapshotRecord err := r.pool.QueryRow(ctx, ` SELECT tenant_id, billing_provider, billing_customer_id, billing_subscription_id, status, plan_code, COALESCE(currency, 'czk'), price_id, cancel_at_period_end, current_period_start, current_period_end, payment_method_brand, payment_method_last4, last_synced_at FROM billing_snapshots WHERE tenant_id = $1 `, tenantID).Scan( &record.TenantID, &record.BillingProvider, &record.BillingCustomerID, &record.BillingSubscriptionID, &record.Status, &record.PlanCode, &record.Currency, &record.PriceID, &record.CancelAtPeriodEnd, &record.CurrentPeriodStart, &record.CurrentPeriodEnd, &record.PaymentMethodBrand, &record.PaymentMethodLast4, &record.LastSyncedAt, ) return record, err } func (r *PGRepository) UpsertSubscriptionSnapshot(ctx context.Context, params BillingSnapshotRecord) error { _, err := r.pool.Exec(ctx, ` INSERT INTO billing_snapshots ( tenant_id, billing_provider, billing_customer_id, billing_subscription_id, status, plan_code, currency, price_id, cancel_at_period_end, current_period_start, current_period_end, payment_method_brand, payment_method_last4, last_synced_at ) VALUES ($1,$2,$3,$4,$5,$6,$7,$8,$9,$10,$11,$12,$13,$14) ON CONFLICT (tenant_id) DO UPDATE SET billing_provider = EXCLUDED.billing_provider, billing_customer_id = EXCLUDED.billing_customer_id, billing_subscription_id = EXCLUDED.billing_subscription_id, status = EXCLUDED.status, plan_code = EXCLUDED.plan_code, currency = EXCLUDED.currency, price_id = EXCLUDED.price_id, cancel_at_period_end = EXCLUDED.cancel_at_period_end, current_period_start = EXCLUDED.current_period_start, current_period_end = EXCLUDED.current_period_end, payment_method_brand = EXCLUDED.payment_method_brand, payment_method_last4 = EXCLUDED.payment_method_last4, last_synced_at = EXCLUDED.last_synced_at, updated_at = now() `, params.TenantID, firstNonEmpty(params.BillingProvider, "paddle"), params.BillingCustomerID, params.BillingSubscriptionID, params.Status, params.PlanCode, firstNonEmpty(params.Currency, "czk"), params.PriceID, params.CancelAtPeriodEnd, params.CurrentPeriodStart, params.CurrentPeriodEnd, params.PaymentMethodBrand, params.PaymentMethodLast4, params.LastSyncedAt) return err } func (r *PGRepository) RecordBillingEvent(ctx context.Context, tenantID string, provider string, eventID string, eventType string, payload []byte) (bool, error) { result, err := r.pool.Exec(ctx, ` INSERT INTO subscription_events (tenant_id, billing_provider, billing_provider_event_id, event_type, payload, processed_at) VALUES ($1, $2, $3, $4, $5::jsonb, now()) ON CONFLICT (billing_provider, billing_provider_event_id) DO NOTHING `, tenantID, firstNonEmpty(provider, "paddle"), eventID, eventType, payload) if err != nil { return false, err } return result.RowsAffected() == 1, nil }