Skip to content

Commit

Permalink
Add currency auto transform (#83)
Browse files Browse the repository at this point in the history
Co-authored-by: AceDataCloud <office@acedata.cloud>
  • Loading branch information
Germey and AceDataCloud authored Jul 14, 2024
1 parent 3f16b60 commit c83b4fc
Show file tree
Hide file tree
Showing 21 changed files with 245 additions and 22 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
{
"type": "minor",
"comment": "add auto concurrency transform",
"packageName": "@acedatacloud/nexior",
"email": "office@acedata.cloud",
"dependentChangeType": "patch"
}
8 changes: 7 additions & 1 deletion src/components/common/Price.vue
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
<template>
<div class="price-text">
<span v-if="price > 0" class="unfree"
>${{ price }} {{ unit ? ` / ${unit}` : '' }}{{ start ? $t('common.message.startPrice') : '' }}
>{{ getPriceString({ value: price }) }} {{ unit ? ` / ${unit}` : ''
}}{{ start ? $t('common.message.startPrice') : '' }}
</span>
<span v-else class="free">
{{ $t('common.message.free') }}
Expand All @@ -11,6 +12,8 @@

<script>
import { defineComponent } from 'vue';
import { getPriceString } from '@/utils';
export default defineComponent({
name: 'ApiPrice',
props: {
Expand All @@ -29,6 +32,9 @@ export default defineComponent({
required: false,
default: false
}
},
methods: {
getPriceString
}
});
</script>
Expand Down
1 change: 1 addition & 0 deletions src/constants/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,3 +5,4 @@ export * from './chat';
export * from './chatdoc';
export * from './midjourney';
export * from './qrart';
export * from './mapping';
56 changes: 56 additions & 0 deletions src/constants/mapping.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
/*
{ value: 'en', label: 'English' },
{ value: 'de', label: 'Deutsch' },
{ value: 'pt', label: 'Português' },
{ value: 'es', label: 'Español' },
{ value: 'fr', label: 'Français' },
{ value: 'zh-CN', label: '简体中文' },
{ value: 'zh-TW', label: '繁體中文' },
{ value: 'it', label: 'Italiano' },
{ value: 'ko', label: '한국어' },
{ value: 'ja', label: '日本語' },
{ value: 'ru', label: 'Русский' },
{ value: 'pl', label: 'Polski' },
{ value: 'fi', label: 'Suomi' },
{ value: 'sv', label: 'Svenska' },
{ value: 'el', label: 'Ελληνικά' },
{ value: 'uk', label: 'Українська' },
{ value: 'ar', label: 'العربية' },
{ value: 'sr', label: 'Српски' }
*/

export const LOCALE_CURRENCY_MAPPING: any = {
'zh-CN': 'cny',
'zh-TW': 'cny',
en: 'usd',
de: 'eur',
pt: 'eur',
es: 'eur',
fr: 'eur',
it: 'eur',
ko: 'krw',
ja: 'jpy',
ru: 'rub',
pl: 'pln',
fi: 'eur',
sv: 'sek',
el: 'eur',
uk: 'uah',
ar: 'sar',
sr: 'rsd'
};

export const CURRENCY_LABEL_MAPPING: any = {
cny: '¥',
usd: '$',
eur: '€',
jpy: '¥',
krw: '₩',
gbp: '£',
rub: '₽',
pln: 'zł',
sek: 'kr',
uah: '₴',
sar: '﷼',
rsd: 'din'
};
17 changes: 12 additions & 5 deletions src/main.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,18 +17,25 @@ import {
initializeUser,
initializeKeywords,
initializeSite,
initializeTitle
initializeTitle,
initializeCurrency,
initializeExchangeRate
} from './utils/initializer';

const main = async () => {
// async and need to await
await initializeCookies();
await initializeToken();
await initializeUser();
await initializeSite();
await initializeTitle();
await initializeDescription();
await initializeKeywords();
await initializeFavicon();

// non-async and no need to await
initializeCurrency();
initializeExchangeRate();
initializeTitle();
initializeDescription();
initializeKeywords();
initializeFavicon();

const app = createApp(App);

Expand Down
10 changes: 10 additions & 0 deletions src/models/exchange.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
export interface IExchangeRateRequest {
source: string;
target: string;
}

export interface IExchangeRateResponse {
source: string;
target: string;
rate: number;
}
1 change: 1 addition & 0 deletions src/models/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,3 +13,4 @@ export * from './service';
export * from './credential';
export * from './qrart';
export * from './site';
export * from './exchange';
11 changes: 11 additions & 0 deletions src/operators/exchange.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
import { AxiosResponse } from 'axios';
import { httpClient } from './common';
import { IExchangeRateRequest, IExchangeRateResponse } from '@/models';

class ExchangeOperator {
async rate(payload: IExchangeRateRequest): Promise<AxiosResponse<IExchangeRateResponse>> {
return httpClient.post('/exchange-rate', payload);
}
}

export const exchangeOperator = new ExchangeOperator();
1 change: 1 addition & 0 deletions src/operators/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,3 +13,4 @@ export * from './service';
export * from './credential';
export * from './qrart';
export * from './site';
export * from './exchange';
8 changes: 4 additions & 4 deletions src/pages/console/application/Buy.vue
Original file line number Diff line number Diff line change
Expand Up @@ -32,9 +32,7 @@
<price :price="package?.price" />
<span v-if="package" class="ml-2"
>({{
$t('service.message.around') +
' $' +
(package?.price / package?.amount).toFixed(4) +
getPriceString({ value: package?.price / package?.amount }) +
' / ' +
$t(`service.unit.${application?.service?.unit}`)
}})
Expand All @@ -46,7 +44,7 @@
v-if="package"
:class="{ price: true, unfree: package?.price > 0, free: package?.price === 0 }"
>
${{ package?.price?.toFixed(2) }}
{{ getPriceString({ value: package?.price }) }}
</span>
<span v-else :class="{ price: true, free: true }"> $ 0 </span>
</el-form-item>
Expand Down Expand Up @@ -91,6 +89,7 @@ import {
import { ROUTE_CONSOLE_ORDER_DETAIL } from '@/router';
import Price from '@/components/common/Price.vue';
import { applicationOperator, orderOperator } from '@/operators';
import { getPriceString } from '@/utils';
interface IData {
application: IApplication | undefined;
Expand Down Expand Up @@ -152,6 +151,7 @@ export default defineComponent({
this.onFetchApplication();
},
methods: {
getPriceString,
onFetchApplication() {
this.loading = true;
applicationOperator
Expand Down
4 changes: 3 additions & 1 deletion src/pages/console/order/Detail.vue
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@
</el-descriptions-item>
<el-descriptions-item :label="$t('order.field.price')">
<span v-if="order?.price && order?.price > 0" class="price unfree">
${{ order?.price?.toFixed(2) }}
{{ getPriceString({ value: order?.price }) }}
</span>
<span v-else class="price free"> {{ $t('order.message.free') }} </span>
</el-descriptions-item>
Expand Down Expand Up @@ -142,6 +142,7 @@ import {
import WechatPayOrder from '@/components/order/WechatPay.vue';
import StripePayOrder from '@/components/order/StripePay.vue';
import { IApplicationType, IOrder, IOrderDetailResponse, OrderState } from '@/models';
import { getPriceString } from '@/utils';
enum PayWay {
WechatPay = 'WechatPay',
Expand Down Expand Up @@ -216,6 +217,7 @@ export default defineComponent({
this.onFetchData();
},
methods: {
getPriceString,
onFetchData() {
this.loading = true;
orderOperator
Expand Down
4 changes: 3 additions & 1 deletion src/pages/console/order/List.vue
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@
</el-table-column>
<el-table-column :label="$t('order.field.price')" width="100px">
<template #default="scope">
<span class="price">${{ scope.row?.price?.toFixed(2) }}</span>
<span class="price">{{ getPriceString({ value: scope.row?.price }) }}</span>
</template>
</el-table-column>
<el-table-column prop="state" :label="$t('order.field.state')" class-name="text-center" width="150px">
Expand Down Expand Up @@ -108,6 +108,7 @@ import Pagination from '@/components/common/Pagination.vue';
import CopyToClipboard from '@/components/common/CopyToClipboard.vue';
import { ElRow, ElCol, ElTable, ElTableColumn, ElButton, ElTag, ElCard } from 'element-plus';
import { IOrder, IOrderListResponse, OrderState } from '@/models';
import { getPriceString } from '@/utils';

interface IData {
orders: IOrder[];
Expand Down Expand Up @@ -159,6 +160,7 @@ export default defineComponent({
this.onFetchData();
},
methods: {
getPriceString,
onPageChange(page: number) {
this.$router.push({
name: this.$route.name?.toString(),
Expand Down
2 changes: 1 addition & 1 deletion src/store/chat/actions.ts
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ export const setCredential = async ({ commit }: any, payload: ICredential): Prom

export const setConversation = async ({ commit, state }: any, payload: IChatConversation): Promise<void> => {
log(setConversation, 'set conversation', payload);
const conversations = state.conversations;
const conversations = state.conversations || [];
const index = conversations?.findIndex((conversation: IChatConversation) => conversation.id === payload.id);
if (index > -1) {
conversations[index] = payload;
Expand Down
36 changes: 34 additions & 2 deletions src/store/common/actions.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { ActionContext } from 'vuex';
import { IRootState } from '../common/models';
import { userOperator, oauthOperator, siteOperator } from '@/operators';
import { userOperator, oauthOperator, siteOperator, exchangeOperator } from '@/operators';
import { log } from '@/utils/log';
import { IToken, IUser } from '@/models';
import { getSiteOrigin } from '@/utils/site';
Expand Down Expand Up @@ -31,6 +31,14 @@ export const setUser = ({ commit }: ActionContext<IRootState, IRootState>, paylo
commit('setUser', payload);
};

export const setCurrency = ({ commit }: ActionContext<IRootState, IRootState>, payload: string) => {
commit('setCurrency', payload);
};

export const setExchange = ({ commit }: ActionContext<IRootState, IRootState>, payload: any) => {
commit('setExchange', payload);
};

export const getUser = async ({ commit }: ActionContext<IRootState, IRootState>): Promise<IUser> => {
log(getUser, 'start to get user');
try {
Expand Down Expand Up @@ -62,6 +70,27 @@ export const getToken = async ({ commit }: ActionContext<IRootState, IRootState>
}
};

export const getExchangeRate = async (
{ state, commit }: ActionContext<IRootState, IRootState>,
payload: { source: string; target: string }
) => {
if (payload.source === payload.target) {
return;
}
const key = `${payload.source}-${payload.target}`;
if (!state.exchange || !state.exchange[key]) {
try {
const { data } = await exchangeOperator.rate(payload);
commit('setExchange', {
[key]: data.rate
});
return state.exchange![key];
} catch (e) {
log(getExchangeRate, 'get exchange rate failed');
}
}
};

export const initializeSite = async ({ state, commit, dispatch }: ActionContext<IRootState, IRootState>) => {
log(initializeSite, 'start to initialize site');
const origin = getSiteOrigin(state?.site);
Expand Down Expand Up @@ -113,9 +142,12 @@ export default {
resetUser,
resetSite,
setToken,
setCurrency,
setUser,
getExchangeRate,
getToken,
getUser,
initializeSite,
getSite
getSite,
setExchange
};
10 changes: 7 additions & 3 deletions src/store/common/models.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,15 +4,19 @@ import { IChatState } from '../chat/models';
import { IChatdocState } from '../chatdoc/models';
import { IQrartState } from '../qrart/models';

export interface ISetting {
navigationCollapsed?: boolean;
}
export interface ISetting {}

export interface ICommonState {
token: IToken;
user?: IUser;
setting?: ISetting;
site?: ISite;
currency: string;
exchange:
| {
[key: string]: number;
}
| undefined;
}

export interface IRootState extends ICommonState {
Expand Down
13 changes: 13 additions & 0 deletions src/store/common/mutations.ts
Original file line number Diff line number Diff line change
Expand Up @@ -34,9 +34,22 @@ export const setSite = (state: IRootState, payload: any): void => {
};
};

export const setExchange = (state: IRootState, payload: any): void => {
state.exchange = {
...state.exchange,
...payload
};
};

export const setCurrency = (state: IRootState, payload: string): void => {
state.currency = payload;
};

export default {
setUser,
setSite,
setCurrency,
setExchange,
resetUser,
setToken,
resetToken,
Expand Down
2 changes: 1 addition & 1 deletion src/store/common/persist.ts
Original file line number Diff line number Diff line change
@@ -1 +1 @@
export default ['user', 'token', 'setting', 'locale', 'dark', 'site'];
export default ['user', 'token', 'setting', 'locale', 'dark', 'site', 'currency', 'exchange'];
6 changes: 3 additions & 3 deletions src/store/common/state.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,15 +6,15 @@ import qrartState from '../qrart/state';

export default (): IRootState => {
return {
currency: 'usd',
exchange: undefined,
user: {},
token: {
access: undefined,
refresh: undefined,
expiration: undefined
},
setting: {
navigationCollapsed: true
},
setting: {},
site: {},
chatdoc: chatdocState(),
chat: chatState(),
Expand Down
1 change: 1 addition & 0 deletions src/utils/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,3 +6,4 @@ export * from './highlight';
export * from './is';
export * from './login';
export * from './site';
export * from './price';
Loading

0 comments on commit c83b4fc

Please sign in to comment.