You've already forked AstralRinth
Billing / plus frontend (#2130)
* [wip] initial * [wip] subscriptions/plus frontend * [wip] finish payment flow * Charges page * finish most subscriptions work * Finish * update eslint * Fix issues * fix intl extract * fix omorphia locale extract * fix responsiveness * fix lint
This commit is contained in:
88
apps/frontend/src/pages/settings/billing/charges.vue
Normal file
88
apps/frontend/src/pages/settings/billing/charges.vue
Normal file
@@ -0,0 +1,88 @@
|
||||
<template>
|
||||
<div>
|
||||
<section class="card">
|
||||
<Breadcrumbs
|
||||
current-title="Past charges"
|
||||
:link-stack="[{ href: '/settings/billing', label: 'Billing and subscriptions' }]"
|
||||
/>
|
||||
<h2>Past charges</h2>
|
||||
<p>All of your past charges to your Modrinth account will be listed here:</p>
|
||||
<div
|
||||
v-for="charge in charges"
|
||||
:key="charge.id"
|
||||
class="universal-card recessed flex items-center justify-between gap-4"
|
||||
>
|
||||
<div class="flex flex-col gap-1">
|
||||
<div class="flex items-center gap-1">
|
||||
<span class="font-bold text-primary">
|
||||
<template v-if="charge.product.metadata.type === 'midas'"> Modrinth Plus </template>
|
||||
<template v-else> Unknown product </template>
|
||||
<template v-if="charge.metadata.modrinth_subscription_interval">
|
||||
{{ charge.metadata.modrinth_subscription_interval }}
|
||||
</template>
|
||||
</span>
|
||||
⋅
|
||||
<span>{{ formatPrice(charge.amount, charge.currency) }}</span>
|
||||
</div>
|
||||
<div class="flex items-center gap-1">
|
||||
<Badge :color="charge.status === 'succeeded' ? 'green' : 'red'" :type="charge.status" />
|
||||
⋅
|
||||
{{ $dayjs.unix(charge.created).format("YYYY-MM-DD") }}
|
||||
</div>
|
||||
</div>
|
||||
<a
|
||||
v-if="charge.receipt_url"
|
||||
class="iconified-button raised-button"
|
||||
:href="charge.receipt_url"
|
||||
>
|
||||
<ReceiptTextIcon />
|
||||
View receipt
|
||||
</a>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</template>
|
||||
<script setup>
|
||||
import { ReceiptTextIcon } from "@modrinth/assets";
|
||||
import { Breadcrumbs, Badge } from "@modrinth/ui";
|
||||
import { products } from "~/generated/state.json";
|
||||
|
||||
definePageMeta({
|
||||
middleware: "auth",
|
||||
});
|
||||
|
||||
const vintl = useVIntl();
|
||||
|
||||
const { data: charges } = await useAsyncData(
|
||||
"billing/payments",
|
||||
() => useBaseFetch("billing/payments", { internal: true }),
|
||||
{
|
||||
transform: (charges) => {
|
||||
return charges.map((charge) => {
|
||||
const product = products.find((product) =>
|
||||
product.prices.some((price) => price.id === charge.metadata.modrinth_price_id),
|
||||
);
|
||||
|
||||
charge.product = product;
|
||||
|
||||
return charge;
|
||||
});
|
||||
},
|
||||
},
|
||||
);
|
||||
|
||||
// TODO move to omorphia utils , duplicated from index
|
||||
function formatPrice(price, currency) {
|
||||
const formatter = new Intl.NumberFormat(vintl.locale, {
|
||||
style: "currency",
|
||||
currency,
|
||||
});
|
||||
|
||||
const maxDigits = formatter.resolvedOptions().maximumFractionDigits;
|
||||
|
||||
const convertedPrice = price / Math.pow(10, maxDigits);
|
||||
|
||||
return formatter.format(convertedPrice);
|
||||
}
|
||||
console.log(charges);
|
||||
</script>
|
||||
Reference in New Issue
Block a user