billing.sql.ts 4.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152
  1. import {
  2. bigint,
  3. boolean,
  4. index,
  5. int,
  6. json,
  7. mysqlEnum,
  8. mysqlTable,
  9. primaryKey,
  10. uniqueIndex,
  11. varchar,
  12. } from "drizzle-orm/mysql-core"
  13. import { timestamps, ulid, utc, workspaceColumns } from "../drizzle/types"
  14. import { workspaceIndexes } from "./workspace.sql"
  15. export const BlackPlans = ["20", "100", "200"] as const
  16. export const BillingTable = mysqlTable(
  17. "billing",
  18. {
  19. ...workspaceColumns,
  20. ...timestamps,
  21. customerID: varchar("customer_id", { length: 255 }),
  22. paymentMethodID: varchar("payment_method_id", { length: 255 }),
  23. paymentMethodType: varchar("payment_method_type", { length: 32 }),
  24. paymentMethodLast4: varchar("payment_method_last4", { length: 4 }),
  25. balance: bigint("balance", { mode: "number" }).notNull(),
  26. monthlyLimit: int("monthly_limit"),
  27. monthlyUsage: bigint("monthly_usage", { mode: "number" }),
  28. timeMonthlyUsageUpdated: utc("time_monthly_usage_updated"),
  29. reload: boolean("reload"),
  30. reloadTrigger: int("reload_trigger"),
  31. reloadAmount: int("reload_amount"),
  32. reloadError: varchar("reload_error", { length: 255 }),
  33. timeReloadError: utc("time_reload_error"),
  34. timeReloadLockedTill: utc("time_reload_locked_till"),
  35. subscription: json("subscription").$type<{
  36. status: "subscribed"
  37. seats: number
  38. plan: (typeof BlackPlans)[number]
  39. useBalance?: boolean
  40. coupon?: string
  41. }>(),
  42. subscriptionID: varchar("subscription_id", { length: 28 }),
  43. subscriptionPlan: mysqlEnum("subscription_plan", BlackPlans),
  44. timeSubscriptionBooked: utc("time_subscription_booked"),
  45. timeSubscriptionSelected: utc("time_subscription_selected"),
  46. liteSubscriptionID: varchar("lite_subscription_id", { length: 28 }),
  47. lite: json("lite").$type<{
  48. useBalance?: boolean
  49. }>(),
  50. },
  51. (table) => [
  52. ...workspaceIndexes(table),
  53. uniqueIndex("global_customer_id").on(table.customerID),
  54. uniqueIndex("global_subscription_id").on(table.subscriptionID),
  55. ],
  56. )
  57. export const SubscriptionTable = mysqlTable(
  58. "subscription",
  59. {
  60. ...workspaceColumns,
  61. ...timestamps,
  62. userID: ulid("user_id").notNull(),
  63. rollingUsage: bigint("rolling_usage", { mode: "number" }),
  64. fixedUsage: bigint("fixed_usage", { mode: "number" }),
  65. timeRollingUpdated: utc("time_rolling_updated"),
  66. timeFixedUpdated: utc("time_fixed_updated"),
  67. },
  68. (table) => [...workspaceIndexes(table), uniqueIndex("workspace_user_id").on(table.workspaceID, table.userID)],
  69. )
  70. export const LiteTable = mysqlTable(
  71. "lite",
  72. {
  73. ...workspaceColumns,
  74. ...timestamps,
  75. userID: ulid("user_id").notNull(),
  76. rollingUsage: bigint("rolling_usage", { mode: "number" }),
  77. weeklyUsage: bigint("weekly_usage", { mode: "number" }),
  78. monthlyUsage: bigint("monthly_usage", { mode: "number" }),
  79. timeRollingUpdated: utc("time_rolling_updated"),
  80. timeWeeklyUpdated: utc("time_weekly_updated"),
  81. timeMonthlyUpdated: utc("time_monthly_updated"),
  82. },
  83. (table) => [...workspaceIndexes(table), uniqueIndex("workspace_user_id").on(table.workspaceID, table.userID)],
  84. )
  85. export const PaymentTable = mysqlTable(
  86. "payment",
  87. {
  88. ...workspaceColumns,
  89. ...timestamps,
  90. customerID: varchar("customer_id", { length: 255 }),
  91. invoiceID: varchar("invoice_id", { length: 255 }),
  92. paymentID: varchar("payment_id", { length: 255 }),
  93. amount: bigint("amount", { mode: "number" }).notNull(),
  94. timeRefunded: utc("time_refunded"),
  95. enrichment: json("enrichment").$type<
  96. | {
  97. type: "subscription" | "lite"
  98. currency?: "inr"
  99. couponID?: string
  100. }
  101. | {
  102. type: "credit"
  103. }
  104. >(),
  105. },
  106. (table) => [...workspaceIndexes(table)],
  107. )
  108. export const UsageTable = mysqlTable(
  109. "usage",
  110. {
  111. ...workspaceColumns,
  112. ...timestamps,
  113. model: varchar("model", { length: 255 }).notNull(),
  114. provider: varchar("provider", { length: 255 }).notNull(),
  115. inputTokens: int("input_tokens").notNull(),
  116. outputTokens: int("output_tokens").notNull(),
  117. reasoningTokens: int("reasoning_tokens"),
  118. cacheReadTokens: int("cache_read_tokens"),
  119. cacheWrite5mTokens: int("cache_write_5m_tokens"),
  120. cacheWrite1hTokens: int("cache_write_1h_tokens"),
  121. cost: bigint("cost", { mode: "number" }).notNull(),
  122. keyID: ulid("key_id"),
  123. sessionID: varchar("session_id", { length: 30 }),
  124. enrichment: json("enrichment").$type<{
  125. plan: "sub" | "byok" | "lite"
  126. }>(),
  127. },
  128. (table) => [...workspaceIndexes(table), index("usage_time_created").on(table.workspaceID, table.timeCreated)],
  129. )
  130. export const CouponType = [
  131. "BUILDATHON",
  132. "GO1MONTH50",
  133. "GOFREEMONTH",
  134. "GO3MONTHS100",
  135. "GO6MONTHS100",
  136. "GO12MONTHS100",
  137. ] as const
  138. export const CouponTable = mysqlTable(
  139. "coupon",
  140. {
  141. email: varchar("email", { length: 255 }),
  142. type: mysqlEnum("type", CouponType).notNull(),
  143. timeRedeemed: utc("time_redeemed"),
  144. },
  145. (table) => [primaryKey({ columns: [table.email, table.type] })],
  146. )