Move metered billing settings to the subscription tab

This commit is contained in:
2026-10-06 01:00:53 +02:00
parent a50ac7310f
commit e3e8a1db1a
6 changed files with 114 additions and 108 deletions

View File

@@ -0,0 +1,101 @@
<script lang="ts">
import { formatDataVolume, formatEuros } from "util/Formatting";
import ProgressBar from "util/ProgressBar.svelte";
import { loading_run } from "lib/Loading";
import { period_price, put_user } from "lib/NovaAPI";
import SuccessMessage from "util/SuccessMessage.svelte";
import { user } from "lib/UserStore";
import ToggleButton from "layout/ToggleButton.svelte";
let success_message: SuccessMessage = $state()
// The toggle button has already flipped the value in the user store when this
// runs. put_user reloads the store from the server, so only a failed request
// has to flip it back
const set_usage_based_billing = () => {
loading_run(async () => {
try {
await put_user({usage_based_billing: $user.usage_based_billing})
success_message.set(true, "Usage based billing updated")
} catch (err) {
$user.usage_based_billing = !$user.usage_based_billing
success_message.set(false, "Failed to update user: "+(err?.message ?? err))
}
})
}
let transfer_cap = $state($user === null ? 0 : $user.monthly_transfer_cap / 1e12)
let transfer_used = $derived($user === null ? 0 : $user.monthly_transfer_used)
const set_transfer_cap = (e: SubmitEvent) => {
e.preventDefault()
loading_run(async () => {
try {
await put_user({transfer_cap: transfer_cap*1e12})
success_message.set(true, "Bill shock limit updated")
} catch (err) {
success_message.set(false, "Failed to update user: "+(err?.message ?? err))
}
})
}
</script>
<section>
<SuccessMessage bind:this={success_message}/>
{#if $user !== null && $user.subscription.type === "subscription"}
<h2>Usage based billing</h2>
<p>
When your storage or data transfer goes over the limits of your
plan, uploads and downloads are blocked. With usage based billing
they keep working and the usage above the limits is billed at
{formatEuros($user.subscription.price_per_tb_storage, 2)} per TB per
month for storage and
{formatEuros($user.subscription.price_per_tb_bandwidth, 2)} per TB
for data transfer.
</p>
<p>
This usage is charged from your account credit afterwards. When
your balance is more than {formatEuros(period_price($user), 2)} below zero
(the price of your subscription period) the limits of your plan
apply again, until you top up your credit.
</p>
<ToggleButton bind:on={$user.usage_based_billing} action={set_usage_based_billing}>
Usage based billing
</ToggleButton>
{/if}
<h2>Bill shock limit</h2>
<p>
Billshock limit in terabytes per month (1 TB = 1000 GB). Set to 0 to
disable.
</p>
<form onsubmit={set_transfer_cap} class="billshock_container">
<input type="number" bind:value={transfer_cap} step="0.1" min="0" style="width: 5em;"/>
<div style="margin: 0.5em;">TB</div>
<button type="submit">
<i class="icon">save</i> Save
</button>
</form>
<p>
Bandwidth used in the last 30 days: {formatDataVolume(transfer_used, 3)},
new limit: {formatDataVolume(transfer_cap*1e12, 3)}
</p>
<ProgressBar used={transfer_used} total={transfer_cap*1e12} warn></ProgressBar>
<p>
The billshock limit limits how much bandwidth your account can use in a
30 day window. When this limit is reached your files can't be downloaded
until your usage drops below it, and you will no longer be charged for
bandwidth usage. This is mostly useful with usage based billing, but it
works without it too. Set to 0 to disable the limit.
</p>
</section>
<style>
.billshock_container {
display: flex;
flex-direction: row;
align-items: center;
}
</style>