Kaynağa Gözat

Merge branch 'front-dev' of http://git.choozmo.com:3000/ai-anchor/video-maker

tomoya 1 yıl önce
ebeveyn
işleme
e279461cb4

+ 19 - 4
frontend/src/api.ts

@@ -1,6 +1,7 @@
 import axios from "axios";
 import { apiUrl } from "@/env";
-import type { IUserProfile, IUserProfileUpdate, IUserProfileCreate, Video, VideoCreate, ArticleCreate, ImageDownload, VideoUploaded, YTViewsUserData } from "@/interfaces";
+import type { IUserProfile, IUserProfileUpdate, IUserProfileCreate, Video, VideoCreate, ArticleCreate, ImageDownload, VideoUploaded, YTViewsUserData, PaymentData} from "@/interfaces";
+import type { StringOptionsWithImporter } from "sass";
 
 function authHeaders(token: string) {
   return {
@@ -147,12 +148,26 @@ export const api = {
         lang: lang
       }
     };
-    return axios.post<string>(`${apiUrl}/api/v1/payment/ytviews-ecpay-payment`, user_data, config);
+    return axios.post<string>(`${apiUrl}/api/v1/payment/ytviews-ecpay-payment?lang=${lang}`, user_data);
   },
-  async YTViewsTestPayment(user_data: YTViewsUserData) {
-    return axios.post<string>(`${apiUrl}/api/v1/payment/ytviews-ecpay-test-payment`, user_data);
+  async YTViewsTestPayment(user_data: YTViewsUserData, lang:string) {
+    return axios.post<string>(`${apiUrl}/api/v1/payment/ytviews-ecpay-test-payment?lang=${lang}`, user_data);
   },
   async getYTViewsList() {
     return axios.get(`${apiUrl}/api/v1/payment/ytviews-list-all`);
   },
+  async Payment(payment_data: PaymentData, token:string, lang: string) {
+    const config = {
+      params: {
+        lang: lang
+      }
+    };
+    return axios.post<string>(`${apiUrl}/api/v1/payment/ecpay-payment?lang=${lang}`, payment_data, authHeaders(token));
+  },
+  async TestPayment(payment_data:PaymentData, token:string, lang:string) {
+    return axios.post<string>(`${apiUrl}/api/v1/payment/ecpay-test-payment?lang=${lang}`, payment_data, authHeaders(token));
+  },
+  async getPaymentList() {
+    return axios.get(`${apiUrl}/api/v1/payment/list-all`);
+  },
 };

+ 90 - 0
frontend/src/components/Payment.vue

@@ -0,0 +1,90 @@
+<script setup lang="ts">
+import { ref } from "vue";
+import type { PaymentData } from "@/interfaces";
+import { useMainStore } from "@/stores/main";
+
+const mainStore = useMainStore();
+let isLoading = ref(false);
+const credit = ref(1);
+
+function increment() {
+  credit.value++;
+}
+function decrement() {
+  if (credit.value > 1) {
+    credit.value--;
+  }
+}
+
+const epayment = ref("ecpay");
+
+async function ecpay() {
+  isLoading.value = true;
+  const data: PaymentData = {
+    item: `Credit 60 X${credit.value}`,
+    amount: 500 * credit.value,
+  };
+  if (data.amount <= 0) {
+    return;
+  }
+
+  const originalHTML = await mainStore.Payment(data, "zh");
+
+  let formHTML = originalHTML?.replace(
+    '<script type="text/javascript">document.getElementById("data_set").submit();</scr',
+    ""
+  );
+  formHTML = formHTML?.replace("ipt>", "");
+  const payFormElement = document.getElementById("pay-form");
+  payFormElement!.innerHTML = formHTML!;
+  const ecpayForm: HTMLFormElement = <HTMLFormElement>(
+    document.getElementById("data_set")
+  );
+  ecpayForm.submit();
+
+  setTimeout(() => {
+    isLoading.value = false;
+  }, 3000);
+}
+</script>
+
+<template>
+  <div class="payment-item me-6">
+    <span>分鐘數:</span>
+    <v-btn
+      density="compact"
+      icon="remove"
+      color="grey"
+      class="mx-2"
+      @click="decrement"
+    ></v-btn>
+    <span class="px-2">{{ credit }}</span>
+    <v-btn
+      density="compact"
+      icon="add"
+      color="grey"
+      class="mx-2"
+      @click="increment"
+    ></v-btn>
+    <span class="ms-2">NT${{ 500 * credit }}</span>
+  </div>
+
+  <v-btn
+    @click="ecpay"
+    variant="flat"
+    color="primary"
+    class="px-4"
+    prepend-icon="add"
+    :loading="isLoading"
+    >我要加值</v-btn
+  >
+  <div id="pay-form"></div>
+</template>
+
+<style lang="scss" scoped>
+.payment-item {
+  .v-btn {
+    border: 1px solid #a6a6a6;
+  }
+}
+</style>

+ 5 - 0
frontend/src/interfaces/index.ts

@@ -95,4 +95,9 @@ export interface YTViewsUserData {
   target: string;
   theme: string;
   taxID: string | null;
+}
+
+export interface PaymentData {
+  item: string,
+  amount: number
 }

+ 1 - 1
frontend/src/language/zh.json

@@ -64,7 +64,7 @@
     "sendingEmail": "傳送電子郵件中",
     "passwordMailSent": "重置密碼電子郵件已傳送",
     "acceptZipMessage": "影片處理需要約 5-10 分鐘,敬請耐心等候",
-    "ytViews": "網紅加速器",
+    "ytViews": "影音流量推手",
     "contactUs": "聯絡我們",
     "orderDetails": "訂單明細",
     "required": "此為必填欄位",

+ 6 - 0
frontend/src/router/index.ts

@@ -160,6 +160,12 @@ const router = createRouter({
                   component: () => import(
                     /* webpackChunkName: "main-admin-users-create" */ '@/views/main/admin/TestECPay.vue'),
                 },
+                {
+                  path: 'test-payment',
+                  name: 'test-payment',
+                  component: () => import(
+                    /* webpackChunkName: "main-admin-users-create" */ '@/views/main/admin/TestPayment.vue'),
+                },
               ],
             },
           ],

+ 46 - 3
frontend/src/stores/main.ts

@@ -4,7 +4,7 @@ import { api } from "@/api"
 import router from "@/router"
 import { getLocalToken, removeLocalToken, saveLocalToken } from "@/utils";
 import type { AppNotification } from '@/interfaces';
-import type { IUserProfile, IUserProfileCreate, IUserProfileUpdate, MainState, Video, VideoCreate, ArticleCreate, Image, ImageDownload, VideoUploaded, YTViewsUserData } from '@/interfaces';
+import type { IUserProfile, IUserProfileCreate, IUserProfileUpdate, MainState, Video, VideoCreate, ArticleCreate, Image, ImageDownload, VideoUploaded, YTViewsUserData, PaymentData } from '@/interfaces';
 import i18n from '@/plugins/i18n'
 import { wsUrl } from "@/env";
 
@@ -465,12 +465,12 @@ export const useMainStore = defineStore("MainStoreId", {
         await mainStore.checkApiError(error);
       }
     },
-    async YTViewsTestPayment(user_data: YTViewsUserData) {
+    async YTViewsTestPayment(user_data: YTViewsUserData, lang:string) {
       const mainStore = useMainStore();
       try {
         const response = (
           await Promise.all([
-            api.YTViewsTestPayment(user_data),
+            api.YTViewsTestPayment(user_data, lang),
             await new Promise<void>((resolve, _) => setTimeout(() => resolve(), 0)),
           ])
         );
@@ -508,5 +508,48 @@ export const useMainStore = defineStore("MainStoreId", {
         await mainStore.checkApiError(error);
       }
     },
+    async TestPayment(payment_data: PaymentData, lang:string) {
+      const mainStore = useMainStore();
+      try {
+        const response = (
+          await Promise.all([
+            api.TestPayment(payment_data, mainStore.token, lang),
+            await new Promise<void>((resolve, _) => setTimeout(() => resolve(), 0)),
+          ])
+        );
+        if (response[0]) {
+          return response[0].data;
+        }
+      } catch (error) {
+        await mainStore.checkApiError(error);
+      }
+    },
+    async Payment(payment_data: PaymentData, lang: string) {
+      const mainStore = useMainStore();
+      try {
+        const response = (
+          await Promise.all([
+            api.Payment(payment_data, mainStore.token, lang),
+            await new Promise<void>((resolve, _) => setTimeout(() => resolve(), 0)),
+          ])
+        );
+        if (response[0]) {
+          return response[0].data;
+        }
+      } catch (error) {
+        await mainStore.checkApiError(error);
+      }
+    },
+    async getPaymentList() {
+      const mainStore = useMainStore();
+      try {
+        const response = await api.getYTViewsList();
+        if (response) {
+          return response.data;
+        }
+      } catch (error) {
+        await mainStore.checkApiError(error);
+      }
+    },
   }
 });

+ 1 - 1
frontend/src/views/TestYTViews.vue

@@ -152,7 +152,7 @@ async function ECPaySubmit() {
     theme: userData.theme,
     taxID: userData.taxID,
   };
-  const originalHTML = await mainStore.YTViewsTestPayment(data);
+  const originalHTML = await mainStore.YTViewsTestPayment(data, 'zh');
   let formHTML = originalHTML?.replace(
     '<script type="text/javascript">document.getElementById("data_set").submit();</scr',
     ""

+ 5 - 3
frontend/src/views/main/Dashboard.vue

@@ -3,6 +3,7 @@ import { computed } from "vue";
 import { useMainStore } from "@/stores/main";
 import { storeToRefs } from "pinia";
 import { useI18n } from "vue-i18n";
+import Payment from "@/components/Payment.vue";
 
 const { t } = useI18n();
 const mainStore = useMainStore();
@@ -98,14 +99,15 @@ const greetedUser = computed(() => {
             ><small>秒</small>
           </v-card-text>
           <v-divider></v-divider>
-          <v-card-actions>
-            <v-btn
+          <v-card-actions class="d-flex align-center mt-3">
+            <Payment />
+            <!-- <v-btn
               variant="flat"
               color="primary"
               class="mt-3"
               prepend-icon="add"
               >我要加值</v-btn
-            >
+            > -->
           </v-card-actions>
         </v-card>
       </v-col>

+ 6 - 0
frontend/src/views/main/Main.vue

@@ -164,6 +164,12 @@ const routeGuardAdmin = async (
             >
               <v-list-item-title>Test Style Preview</v-list-item-title>
             </v-list-item>
+            <v-list-item
+              to="/main/admin/test-payment"
+              prepend-icon="payments"
+            >
+              <v-list-item-title>Test Payment</v-list-item-title>
+            </v-list-item>
           </v-list>
         </v-sheet>
         <!-- <v-spacer></v-spacer> -->

+ 62 - 0
frontend/src/views/main/admin/TestPayment.vue

@@ -0,0 +1,62 @@
+<script setup lang="ts">
+import { ref, reactive, computed } from "vue";
+import type { PaymentData } from "@/interfaces";
+import { useMainStore } from "@/stores/main";
+
+const mainStore = useMainStore();
+const credit = ref(0);
+function increment() {
+  credit.value++;
+}
+function decrement() {
+  if (credit.value > 0) {
+    credit.value--;
+  }
+}
+const epayment = ref("ecpay");
+
+async function ecpay() {
+  const data: PaymentData = {
+    item: `Credit 60 X${credit.value}`,
+    amount: 500 * credit.value,
+  };
+  if (data.amount <= 0) {
+    return;
+  }
+
+  const originalHTML = await mainStore.TestPayment(data, "zh");
+  console.log(originalHTML);
+  let formHTML = originalHTML?.replace(
+    '<script type="text/javascript">document.getElementById("data_set").submit();</scr',
+    ""
+  );
+  formHTML = formHTML?.replace("ipt>", "");
+  const payFormElement = document.getElementById("pay-form");
+  payFormElement!.innerHTML = formHTML!;
+  const ecpayForm: HTMLFormElement = <HTMLFormElement>(
+    document.getElementById("data_set")
+  );
+  ecpayForm.submit();
+}
+</script>
+
+<template>
+  <v-col>
+    <span>Credit 60</span>
+    <span>$500</span>
+    <v-btn icon="remove" @click="decrement"></v-btn>
+    {{ credit }}
+    <v-btn icon="add" @click="increment"></v-btn>
+    <span>{{ 500 * credit }}</span>
+  </v-col>
+  <div>
+    <span>付款方式</span>
+    <v-row>
+      <span>ecpay</span>
+    </v-row>
+  </div>
+  <v-btn @click="ecpay">往前</v-btn>
+  <div id="pay-form"></div>
+</template>
+
+<style lang="scss"></style>