@@ -1743,3 +1743,145 @@ func (q *Queries) UpsertInvoice(ctx context.Context, db DBTX, arg UpsertInvoiceP |
| 1743 | 1743 | ) |
| 1744 | 1744 | return i, err |
| 1745 | 1745 | } |
| 1746 | + |
| 1747 | +const upsertInvoiceForSubject = `-- name: UpsertInvoiceForSubject :one |
| 1748 | +INSERT INTO billing_invoices ( |
| 1749 | + subject_kind, |
| 1750 | + subject_id, |
| 1751 | + provider, |
| 1752 | + stripe_invoice_id, |
| 1753 | + stripe_customer_id, |
| 1754 | + stripe_subscription_id, |
| 1755 | + status, |
| 1756 | + number, |
| 1757 | + currency, |
| 1758 | + amount_due_cents, |
| 1759 | + amount_paid_cents, |
| 1760 | + amount_remaining_cents, |
| 1761 | + hosted_invoice_url, |
| 1762 | + invoice_pdf_url, |
| 1763 | + period_start, |
| 1764 | + period_end, |
| 1765 | + due_at, |
| 1766 | + paid_at, |
| 1767 | + voided_at |
| 1768 | +) |
| 1769 | +VALUES ( |
| 1770 | + $1::billing_subject_kind, |
| 1771 | + $2::bigint, |
| 1772 | + 'stripe', |
| 1773 | + $3::text, |
| 1774 | + $4::text, |
| 1775 | + $5::text, |
| 1776 | + $6::billing_invoice_status, |
| 1777 | + $7::text, |
| 1778 | + $8::text, |
| 1779 | + $9::bigint, |
| 1780 | + $10::bigint, |
| 1781 | + $11::bigint, |
| 1782 | + $12::text, |
| 1783 | + $13::text, |
| 1784 | + $14::timestamptz, |
| 1785 | + $15::timestamptz, |
| 1786 | + $16::timestamptz, |
| 1787 | + $17::timestamptz, |
| 1788 | + $18::timestamptz |
| 1789 | +) |
| 1790 | +ON CONFLICT (provider, stripe_invoice_id) DO UPDATE |
| 1791 | + SET subject_kind = EXCLUDED.subject_kind, |
| 1792 | + subject_id = EXCLUDED.subject_id, |
| 1793 | + stripe_customer_id = EXCLUDED.stripe_customer_id, |
| 1794 | + stripe_subscription_id = EXCLUDED.stripe_subscription_id, |
| 1795 | + status = EXCLUDED.status, |
| 1796 | + number = EXCLUDED.number, |
| 1797 | + currency = EXCLUDED.currency, |
| 1798 | + amount_due_cents = EXCLUDED.amount_due_cents, |
| 1799 | + amount_paid_cents = EXCLUDED.amount_paid_cents, |
| 1800 | + amount_remaining_cents = EXCLUDED.amount_remaining_cents, |
| 1801 | + hosted_invoice_url = EXCLUDED.hosted_invoice_url, |
| 1802 | + invoice_pdf_url = EXCLUDED.invoice_pdf_url, |
| 1803 | + period_start = EXCLUDED.period_start, |
| 1804 | + period_end = EXCLUDED.period_end, |
| 1805 | + due_at = EXCLUDED.due_at, |
| 1806 | + paid_at = EXCLUDED.paid_at, |
| 1807 | + voided_at = EXCLUDED.voided_at, |
| 1808 | + updated_at = now() |
| 1809 | +RETURNING id, org_id, provider, stripe_invoice_id, stripe_customer_id, stripe_subscription_id, status, number, currency, amount_due_cents, amount_paid_cents, amount_remaining_cents, hosted_invoice_url, invoice_pdf_url, period_start, period_end, due_at, paid_at, voided_at, created_at, updated_at, subject_kind, subject_id |
| 1810 | +` |
| 1811 | + |
| 1812 | +type UpsertInvoiceForSubjectParams struct { |
| 1813 | + SubjectKind BillingSubjectKind |
| 1814 | + SubjectID int64 |
| 1815 | + StripeInvoiceID string |
| 1816 | + StripeCustomerID string |
| 1817 | + StripeSubscriptionID pgtype.Text |
| 1818 | + Status BillingInvoiceStatus |
| 1819 | + Number string |
| 1820 | + Currency string |
| 1821 | + AmountDueCents int64 |
| 1822 | + AmountPaidCents int64 |
| 1823 | + AmountRemainingCents int64 |
| 1824 | + HostedInvoiceUrl string |
| 1825 | + InvoicePdfUrl string |
| 1826 | + PeriodStart pgtype.Timestamptz |
| 1827 | + PeriodEnd pgtype.Timestamptz |
| 1828 | + DueAt pgtype.Timestamptz |
| 1829 | + PaidAt pgtype.Timestamptz |
| 1830 | + VoidedAt pgtype.Timestamptz |
| 1831 | +} |
| 1832 | + |
| 1833 | +// PRO04 polymorphic invoice upsert. Writes (subject_kind, |
| 1834 | +// subject_id) directly; org_id stays NULL for user-kind rows (per |
| 1835 | +// the 0074 migration's nullable change). The existing |
| 1836 | +// UpsertInvoice query stays as the org-kind path during the |
| 1837 | +// transitional deploy — both can coexist because the UNIQUE |
| 1838 | +// (provider, stripe_invoice_id) prevents duplicate rows. |
| 1839 | +func (q *Queries) UpsertInvoiceForSubject(ctx context.Context, db DBTX, arg UpsertInvoiceForSubjectParams) (BillingInvoice, error) { |
| 1840 | + row := db.QueryRow(ctx, upsertInvoiceForSubject, |
| 1841 | + arg.SubjectKind, |
| 1842 | + arg.SubjectID, |
| 1843 | + arg.StripeInvoiceID, |
| 1844 | + arg.StripeCustomerID, |
| 1845 | + arg.StripeSubscriptionID, |
| 1846 | + arg.Status, |
| 1847 | + arg.Number, |
| 1848 | + arg.Currency, |
| 1849 | + arg.AmountDueCents, |
| 1850 | + arg.AmountPaidCents, |
| 1851 | + arg.AmountRemainingCents, |
| 1852 | + arg.HostedInvoiceUrl, |
| 1853 | + arg.InvoicePdfUrl, |
| 1854 | + arg.PeriodStart, |
| 1855 | + arg.PeriodEnd, |
| 1856 | + arg.DueAt, |
| 1857 | + arg.PaidAt, |
| 1858 | + arg.VoidedAt, |
| 1859 | + ) |
| 1860 | + var i BillingInvoice |
| 1861 | + err := row.Scan( |
| 1862 | + &i.ID, |
| 1863 | + &i.OrgID, |
| 1864 | + &i.Provider, |
| 1865 | + &i.StripeInvoiceID, |
| 1866 | + &i.StripeCustomerID, |
| 1867 | + &i.StripeSubscriptionID, |
| 1868 | + &i.Status, |
| 1869 | + &i.Number, |
| 1870 | + &i.Currency, |
| 1871 | + &i.AmountDueCents, |
| 1872 | + &i.AmountPaidCents, |
| 1873 | + &i.AmountRemainingCents, |
| 1874 | + &i.HostedInvoiceUrl, |
| 1875 | + &i.InvoicePdfUrl, |
| 1876 | + &i.PeriodStart, |
| 1877 | + &i.PeriodEnd, |
| 1878 | + &i.DueAt, |
| 1879 | + &i.PaidAt, |
| 1880 | + &i.VoidedAt, |
| 1881 | + &i.CreatedAt, |
| 1882 | + &i.UpdatedAt, |
| 1883 | + &i.SubjectKind, |
| 1884 | + &i.SubjectID, |
| 1885 | + ) |
| 1886 | + return i, err |
| 1887 | +} |