mirror of
https://github.com/aljazceru/opencode.git
synced 2025-12-21 17:54:23 +01:00
zen: check balance on enable billing
This commit is contained in:
@@ -4,6 +4,8 @@ import { Billing } from "@opencode/console-core/billing.js"
|
|||||||
import { withActor } from "~/context/auth.withActor"
|
import { withActor } from "~/context/auth.withActor"
|
||||||
import { IconCreditCard } from "~/component/icon"
|
import { IconCreditCard } from "~/component/icon"
|
||||||
import styles from "./billing-section.module.css"
|
import styles from "./billing-section.module.css"
|
||||||
|
import { Database, eq } from "@opencode/console-core/drizzle/index.js"
|
||||||
|
import { BillingTable } from "@opencode/console-core/schema/billing.sql.js"
|
||||||
|
|
||||||
const createCheckoutUrl = action(async (workspaceID: string, successUrl: string, cancelUrl: string) => {
|
const createCheckoutUrl = action(async (workspaceID: string, successUrl: string, cancelUrl: string) => {
|
||||||
"use server"
|
"use server"
|
||||||
@@ -17,12 +19,23 @@ const reload = action(async (form: FormData) => {
|
|||||||
return json(await withActor(() => Billing.reload(), workspaceID), { revalidate: getBillingInfo.key })
|
return json(await withActor(() => Billing.reload(), workspaceID), { revalidate: getBillingInfo.key })
|
||||||
}, "billing.reload")
|
}, "billing.reload")
|
||||||
|
|
||||||
const disableReload = action(async (form: FormData) => {
|
const setReload = action(async (form: FormData) => {
|
||||||
"use server"
|
"use server"
|
||||||
const workspaceID = form.get("workspaceID")?.toString()
|
const workspaceID = form.get("workspaceID")?.toString()
|
||||||
if (!workspaceID) return { error: "Workspace ID is required" }
|
if (!workspaceID) return { error: "Workspace ID is required" }
|
||||||
return json(await withActor(() => Billing.disableReload(), workspaceID), { revalidate: getBillingInfo.key })
|
const reload = form.get("reload")?.toString() === "true"
|
||||||
}, "billing.disableReload")
|
return json(
|
||||||
|
await Database.use((tx) =>
|
||||||
|
tx
|
||||||
|
.update(BillingTable)
|
||||||
|
.set({
|
||||||
|
reload,
|
||||||
|
})
|
||||||
|
.where(eq(BillingTable.workspaceID, workspaceID)),
|
||||||
|
),
|
||||||
|
{ revalidate: getBillingInfo.key },
|
||||||
|
)
|
||||||
|
}, "billing.setReload")
|
||||||
|
|
||||||
const createSessionUrl = action(async (workspaceID: string, returnUrl: string) => {
|
const createSessionUrl = action(async (workspaceID: string, returnUrl: string) => {
|
||||||
"use server"
|
"use server"
|
||||||
@@ -44,7 +57,7 @@ export function BillingSection() {
|
|||||||
const createCheckoutUrlSubmission = useSubmission(createCheckoutUrl)
|
const createCheckoutUrlSubmission = useSubmission(createCheckoutUrl)
|
||||||
const createSessionUrlAction = useAction(createSessionUrl)
|
const createSessionUrlAction = useAction(createSessionUrl)
|
||||||
const createSessionUrlSubmission = useSubmission(createSessionUrl)
|
const createSessionUrlSubmission = useSubmission(createSessionUrl)
|
||||||
const disableReloadSubmission = useSubmission(disableReload)
|
const setReloadSubmission = useSubmission(setReload)
|
||||||
const reloadSubmission = useSubmission(reload)
|
const reloadSubmission = useSubmission(reload)
|
||||||
|
|
||||||
// DUMMY DATA FOR TESTING - UNCOMMENT ONE OF THE SCENARIOS BELOW
|
// DUMMY DATA FOR TESTING - UNCOMMENT ONE OF THE SCENARIOS BELOW
|
||||||
@@ -89,6 +102,10 @@ export function BillingSection() {
|
|||||||
return ((balanceInfo()?.balance ?? 0) / 100000000).toFixed(2)
|
return ((balanceInfo()?.balance ?? 0) / 100000000).toFixed(2)
|
||||||
})
|
})
|
||||||
|
|
||||||
|
const hasBalance = createMemo(() => {
|
||||||
|
return (balanceInfo()?.balance ?? 0) > 0 && balanceAmount() !== "0.00"
|
||||||
|
})
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<section class={styles.root}>
|
<section class={styles.root}>
|
||||||
<div data-slot="section-title">
|
<div data-slot="section-title">
|
||||||
@@ -135,6 +152,9 @@ export function BillingSection() {
|
|||||||
<div data-slot="button-row">
|
<div data-slot="button-row">
|
||||||
<Show
|
<Show
|
||||||
when={balanceInfo()?.reload}
|
when={balanceInfo()?.reload}
|
||||||
|
fallback={
|
||||||
|
<Show
|
||||||
|
when={hasBalance()}
|
||||||
fallback={
|
fallback={
|
||||||
<button
|
<button
|
||||||
data-color="primary"
|
data-color="primary"
|
||||||
@@ -150,6 +170,16 @@ export function BillingSection() {
|
|||||||
{createCheckoutUrlSubmission.pending ? "Loading..." : "Enable Billing"}
|
{createCheckoutUrlSubmission.pending ? "Loading..." : "Enable Billing"}
|
||||||
</button>
|
</button>
|
||||||
}
|
}
|
||||||
|
>
|
||||||
|
<form action={setReload} method="post" data-slot="create-form">
|
||||||
|
<input type="hidden" name="workspaceID" value={params.id} />
|
||||||
|
<input type="hidden" name="reload" value="true" />
|
||||||
|
<button data-color="primary" type="submit" disabled={setReloadSubmission.pending}>
|
||||||
|
{setReloadSubmission.pending ? "Enabling..." : "Enable Billing"}
|
||||||
|
</button>
|
||||||
|
</form>
|
||||||
|
</Show>
|
||||||
|
}
|
||||||
>
|
>
|
||||||
<button
|
<button
|
||||||
data-color="primary"
|
data-color="primary"
|
||||||
@@ -164,10 +194,11 @@ export function BillingSection() {
|
|||||||
>
|
>
|
||||||
{createSessionUrlSubmission.pending ? "Loading..." : "Manage Payment Methods"}
|
{createSessionUrlSubmission.pending ? "Loading..." : "Manage Payment Methods"}
|
||||||
</button>
|
</button>
|
||||||
<form action={disableReload} method="post" data-slot="create-form">
|
<form action={setReload} method="post" data-slot="create-form">
|
||||||
<input type="hidden" name="workspaceID" value={params.id} />
|
<input type="hidden" name="workspaceID" value={params.id} />
|
||||||
<button data-color="ghost" type="submit" disabled={disableReloadSubmission.pending}>
|
<input type="hidden" name="reload" value="false" />
|
||||||
{disableReloadSubmission.pending ? "Disabling..." : "Disable"}
|
<button data-color="ghost" type="submit" disabled={setReloadSubmission.pending}>
|
||||||
|
{setReloadSubmission.pending ? "Disabling..." : "Disable"}
|
||||||
</button>
|
</button>
|
||||||
</form>
|
</form>
|
||||||
</Show>
|
</Show>
|
||||||
@@ -176,7 +207,7 @@ export function BillingSection() {
|
|||||||
<div data-slot="usage">
|
<div data-slot="usage">
|
||||||
<Show when={!balanceInfo()?.reload}>
|
<Show when={!balanceInfo()?.reload}>
|
||||||
<Show
|
<Show
|
||||||
when={!(balanceAmount() === "0.00" || balanceAmount() === "-0.00")}
|
when={hasBalance()}
|
||||||
fallback={
|
fallback={
|
||||||
<p>
|
<p>
|
||||||
We'll load <b>$20</b> (+$1.23 processing fee) and reload it when it reaches <b>$5</b>.
|
We'll load <b>$20</b> (+$1.23 processing fee) and reload it when it reaches <b>$5</b>.
|
||||||
|
|||||||
Reference in New Issue
Block a user