mirror of
https://github.com/henry4682/fin_buddy_fe.git
synced 2026-07-16 01:30:00 +00:00
fix: chage api string
All checks were successful
Deploy Frontend to 1Panel / build-and-deploy (push) Successful in 17s
All checks were successful
Deploy Frontend to 1Panel / build-and-deploy (push) Successful in 17s
This commit is contained in:
@@ -45,7 +45,7 @@ const accountTrendData = ref([]);
|
|||||||
|
|
||||||
const fetchAccountTrend = async () => {
|
const fetchAccountTrend = async () => {
|
||||||
try {
|
try {
|
||||||
const res = await api.get(`/api/accounts/${accountId}/holdings-trend`);
|
const res = await api.get(`/v1/accounts/${accountId}/holdings-trend`);
|
||||||
accountTrendData.value = res.data;
|
accountTrendData.value = res.data;
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
console.error("無法撈取帳戶多線趨勢圖", e);
|
console.error("無法撈取帳戶多線趨勢圖", e);
|
||||||
@@ -53,12 +53,12 @@ const fetchAccountTrend = async () => {
|
|||||||
};
|
};
|
||||||
|
|
||||||
const fetchAccount = async () => {
|
const fetchAccount = async () => {
|
||||||
const res = await api.get(`/api/accounts/${accountId}`);
|
const res = await api.get(`/v1/accounts/${accountId}`);
|
||||||
account.value = res.data;
|
account.value = res.data;
|
||||||
};
|
};
|
||||||
|
|
||||||
const fetchHoldings = async () => {
|
const fetchHoldings = async () => {
|
||||||
const res = await api.get(`/api/accounts/${accountId}/holdings`);
|
const res = await api.get(`/v1/accounts/${accountId}/holdings`);
|
||||||
holdings.value = res.data;
|
holdings.value = res.data;
|
||||||
|
|
||||||
// 🟢 修正:直接從大列表的內建數據裡,把最新價格和現值綁定給前端變數
|
// 🟢 修正:直接從大列表的內建數據裡,把最新價格和現值綁定給前端變數
|
||||||
@@ -68,7 +68,7 @@ const fetchHoldings = async () => {
|
|||||||
};
|
};
|
||||||
|
|
||||||
const loadTransactions = async (holding) => {
|
const loadTransactions = async (holding) => {
|
||||||
const res = await api.get(`/api/holdings/${holding.id}/transactions`);
|
const res = await api.get(`/v1/holdings/${holding.id}/transactions`);
|
||||||
transactions.value[holding.id] = res.data;
|
transactions.value[holding.id] = res.data;
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -86,7 +86,7 @@ const toggleHolding = async (holding) => {
|
|||||||
|
|
||||||
const loadHistory = async (holding) => {
|
const loadHistory = async (holding) => {
|
||||||
try {
|
try {
|
||||||
const res = await api.get(`/api/holdings/${holding.id}/history`);
|
const res = await api.get(`/v1/holdings/${holding.id}/history`);
|
||||||
investmentHistory.value[holding.id] = res.data;
|
investmentHistory.value[holding.id] = res.data;
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
console.error("取得歷史資料失敗", e);
|
console.error("取得歷史資料失敗", e);
|
||||||
@@ -94,7 +94,7 @@ const loadHistory = async (holding) => {
|
|||||||
};
|
};
|
||||||
|
|
||||||
const submitHolding = async () => {
|
const submitHolding = async () => {
|
||||||
await api.post(`/api/accounts/${accountId}/holdings`, holdingForm.value);
|
await api.post(`/v1/accounts/${accountId}/holdings`, holdingForm.value);
|
||||||
showHoldingModal.value = false;
|
showHoldingModal.value = false;
|
||||||
holdingForm.value = { type: "stock", symbol: "", name: "" };
|
holdingForm.value = { type: "stock", symbol: "", name: "" };
|
||||||
await fetchHoldings();
|
await fetchHoldings();
|
||||||
@@ -102,13 +102,13 @@ const submitHolding = async () => {
|
|||||||
|
|
||||||
const deleteHolding = async (id) => {
|
const deleteHolding = async (id) => {
|
||||||
if (!confirm("確定要刪除這筆持倉嗎?")) return;
|
if (!confirm("確定要刪除這筆持倉嗎?")) return;
|
||||||
await api.delete(`/api/holdings/delete/${accountId}/${id}`);
|
await api.delete(`/v1/holdings/delete/${accountId}/${id}`);
|
||||||
fetchHoldings();
|
fetchHoldings();
|
||||||
};
|
};
|
||||||
|
|
||||||
const submitTransaction = async (holding) => {
|
const submitTransaction = async (holding) => {
|
||||||
await api.post(
|
await api.post(
|
||||||
`/api/holdings/${holding.id}/transactions`,
|
`/v1/holdings/${holding.id}/transactions`,
|
||||||
transactionForm.value,
|
transactionForm.value,
|
||||||
);
|
);
|
||||||
transactionForm.value = {
|
transactionForm.value = {
|
||||||
@@ -129,7 +129,7 @@ const submitTransaction = async (holding) => {
|
|||||||
|
|
||||||
const deleteTransaction = async (holding, txId) => {
|
const deleteTransaction = async (holding, txId) => {
|
||||||
if (!confirm("確定要刪除這筆交易嗎?")) return;
|
if (!confirm("確定要刪除這筆交易嗎?")) return;
|
||||||
await api.delete(`/api/holdings/${holding.id}/transactions/${txId}`);
|
await api.delete(`/v1/holdings/${holding.id}/transactions/${txId}`);
|
||||||
await fetchHoldings();
|
await fetchHoldings();
|
||||||
await loadTransactions(holding);
|
await loadTransactions(holding);
|
||||||
};
|
};
|
||||||
@@ -152,7 +152,7 @@ const calcAmount = (tx, holding) => {
|
|||||||
|
|
||||||
const fetchPrice = async (holding) => {
|
const fetchPrice = async (holding) => {
|
||||||
try {
|
try {
|
||||||
const res = await api.get(`/api/holdings/${holding.id}/realtime`);
|
const res = await api.get(`/v1/holdings/${holding.id}/realtime`);
|
||||||
currentPrices.value[holding.id] = res.data.price;
|
currentPrices.value[holding.id] = res.data.price;
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
currentPrices.value[holding.id] = null;
|
currentPrices.value[holding.id] = null;
|
||||||
@@ -186,7 +186,7 @@ const searchSecurities = async (keyword) => {
|
|||||||
securityOptions.value = [];
|
securityOptions.value = [];
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const { data } = await api.get("/api/securities/search", {
|
const { data } = await api.get("/v1/securities/search", {
|
||||||
params: { type: holdingForm.value.type, keyword },
|
params: { type: holdingForm.value.type, keyword },
|
||||||
});
|
});
|
||||||
securityOptions.value = data;
|
securityOptions.value = data;
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
<script setup>
|
<script setup>
|
||||||
import { ref, onMounted, computed } from "vue"; // 💡 補上 ref, onMounted
|
import { ref, onMounted, computed } from "vue"; // 💡 補上 ref, onMounted
|
||||||
import axios from "axios"; // 💡 引入你的 axios 或全域 API 工具
|
import api from "@/axios";
|
||||||
import AuthenticatedLayout from '@/Layouts/AuthenticatedLayout.vue'
|
import AuthenticatedLayout from '@/Layouts/AuthenticatedLayout.vue'
|
||||||
import { Pie, Bar } from 'vue-chartjs'
|
import { Pie, Bar } from 'vue-chartjs'
|
||||||
import {
|
import {
|
||||||
@@ -68,7 +68,7 @@ const barOptions = {
|
|||||||
onMounted(async () => {
|
onMounted(async () => {
|
||||||
try {
|
try {
|
||||||
// 🟢 修正:精準指定後端 Laragon 的完整 API 網址
|
// 🟢 修正:精準指定後端 Laragon 的完整 API 網址
|
||||||
const response = await axios.get('http://127.0.0.1:8000/api/dashboard/stats', {
|
const response = await api.get("/v1/dashboard/stats", {
|
||||||
// 如果你是用 localStorage 存 token 的話,要在這邊帶上 Bearer Token:
|
// 如果你是用 localStorage 存 token 的話,要在這邊帶上 Bearer Token:
|
||||||
headers: {
|
headers: {
|
||||||
Authorization: `Bearer ${localStorage.getItem('auth_token')}` // 💡 依據你儲存 Token 的 key 調整
|
Authorization: `Bearer ${localStorage.getItem('auth_token')}` // 💡 依據你儲存 Token 的 key 調整
|
||||||
|
|||||||
@@ -23,7 +23,7 @@ const submit = async () => {
|
|||||||
formData.append('file', form.file);
|
formData.append('file', form.file);
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const response = await api.post("/api/expenses/import", formData, {
|
const response = await api.post("/v1/expenses/import", formData, {
|
||||||
headers: {
|
headers: {
|
||||||
"Content-Type": "multipart/form-data",
|
"Content-Type": "multipart/form-data",
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -14,9 +14,9 @@ const fetchAllData = async () => {
|
|||||||
loading.value = true;
|
loading.value = true;
|
||||||
try {
|
try {
|
||||||
const [expRes, catRes, ruleRes] = await Promise.all([
|
const [expRes, catRes, ruleRes] = await Promise.all([
|
||||||
api.get("/api/expenses"),
|
api.get("/v1/expenses"),
|
||||||
api.get("/api/categories"),
|
api.get("/v1/categories"),
|
||||||
api.get("/api/category-rules"),
|
api.get("/v1/category-rules"),
|
||||||
]);
|
]);
|
||||||
expenses.value = expRes.data;
|
expenses.value = expRes.data;
|
||||||
categories.value = catRes.data;
|
categories.value = catRes.data;
|
||||||
@@ -64,7 +64,7 @@ watch(
|
|||||||
|
|
||||||
const submit = async () => {
|
const submit = async () => {
|
||||||
try {
|
try {
|
||||||
const response = await api.post("/api/expenses", form);
|
const response = await api.post("/v1/expenses", form);
|
||||||
expenses.value.unshift(response.data);
|
expenses.value.unshift(response.data);
|
||||||
|
|
||||||
// 🟢 重置表單:一併歸零分攤欄位
|
// 🟢 重置表單:一併歸零分攤欄位
|
||||||
@@ -130,7 +130,7 @@ const startEdit = (expense) => {
|
|||||||
|
|
||||||
const submitEdit = async (id) => {
|
const submitEdit = async (id) => {
|
||||||
try {
|
try {
|
||||||
const response = await api.put(`/api/expenses/${id}`, editForm);
|
const response = await api.put(`/v1/expenses/${id}`, editForm);
|
||||||
const index = expenses.value.findIndex((ex) => ex.id === id);
|
const index = expenses.value.findIndex((ex) => ex.id === id);
|
||||||
expenses.value[index] = response.data;
|
expenses.value[index] = response.data;
|
||||||
editing.value = null;
|
editing.value = null;
|
||||||
@@ -142,7 +142,7 @@ const submitEdit = async (id) => {
|
|||||||
const destroy = async (id) => {
|
const destroy = async (id) => {
|
||||||
if (!confirm("確定刪除?")) return;
|
if (!confirm("確定刪除?")) return;
|
||||||
try {
|
try {
|
||||||
await api.delete(`/api/expenses/${id}`);
|
await api.delete(`/v1/expenses/${id}`);
|
||||||
expenses.value = expenses.value.filter((ex) => ex.id !== id);
|
expenses.value = expenses.value.filter((ex) => ex.id !== id);
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
alert("刪除失敗");
|
alert("刪除失敗");
|
||||||
@@ -157,7 +157,7 @@ const editCategoryForm = reactive({ name: "", color: "" });
|
|||||||
|
|
||||||
const submitCategory = async () => {
|
const submitCategory = async () => {
|
||||||
try {
|
try {
|
||||||
const response = await api.post("/api/categories", categoryForm);
|
const response = await api.post("/v1/categories", categoryForm);
|
||||||
categories.value.push(response.data);
|
categories.value.push(response.data);
|
||||||
Object.assign(categoryForm, { name: "", color: "#3B82F6" });
|
Object.assign(categoryForm, { name: "", color: "#3B82F6" });
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
@@ -172,7 +172,7 @@ const startEditCategory = (cat) => {
|
|||||||
|
|
||||||
const submitEditCategory = async (id) => {
|
const submitEditCategory = async (id) => {
|
||||||
try {
|
try {
|
||||||
const response = await api.put(`/api/categories/${id}`, editCategoryForm);
|
const response = await api.put(`/v1/categories/${id}`, editCategoryForm);
|
||||||
const index = categories.value.findIndex((cat) => cat.id === id);
|
const index = categories.value.findIndex((cat) => cat.id === id);
|
||||||
categories.value[index] = response.data;
|
categories.value[index] = response.data;
|
||||||
editingCategory.value = null;
|
editingCategory.value = null;
|
||||||
@@ -184,7 +184,7 @@ const submitEditCategory = async (id) => {
|
|||||||
const destroyCategory = async (id) => {
|
const destroyCategory = async (id) => {
|
||||||
if (!confirm("刪除分類不會刪除明細,但明細會變未分類。確定刪除?")) return;
|
if (!confirm("刪除分類不會刪除明細,但明細會變未分類。確定刪除?")) return;
|
||||||
try {
|
try {
|
||||||
await api.delete(`/api/categories/${id}`);
|
await api.delete(`/v1/categories/${id}`);
|
||||||
categories.value = categories.value.filter((cat) => cat.id !== id);
|
categories.value = categories.value.filter((cat) => cat.id !== id);
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
alert("分類刪除失敗");
|
alert("分類刪除失敗");
|
||||||
@@ -197,7 +197,7 @@ const ruleForm = reactive({ keyword: "", category_id: "" });
|
|||||||
|
|
||||||
const submitRule = async () => {
|
const submitRule = async () => {
|
||||||
try {
|
try {
|
||||||
const response = await api.post("/api/category-rules", ruleForm);
|
const response = await api.post("/v1/category-rules", ruleForm);
|
||||||
rules.value.push(response.data);
|
rules.value.push(response.data);
|
||||||
Object.assign(ruleForm, { keyword: "", category_id: "" });
|
Object.assign(ruleForm, { keyword: "", category_id: "" });
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
@@ -215,7 +215,7 @@ const deleteSelected = async () => {
|
|||||||
if (selected.value.length === 0) return;
|
if (selected.value.length === 0) return;
|
||||||
if (!confirm(`確定刪除 ${selected.value.length} 筆?`)) return;
|
if (!confirm(`確定刪除 ${selected.value.length} 筆?`)) return;
|
||||||
try {
|
try {
|
||||||
await api.post("/api/expenses/destroy-batch", { ids: selected.value });
|
await api.post("/v1/expenses/destroy-batch", { ids: selected.value });
|
||||||
expenses.value = expenses.value.filter(
|
expenses.value = expenses.value.filter(
|
||||||
(ex) => !selected.value.includes(ex.id),
|
(ex) => !selected.value.includes(ex.id),
|
||||||
);
|
);
|
||||||
|
|||||||
Reference in New Issue
Block a user