diff --git a/src/App.test.tsx b/src/App.test.tsx
index 5c022f0..57ad49c 100644
--- a/src/App.test.tsx
+++ b/src/App.test.tsx
@@ -22,14 +22,24 @@ describe("pricing explorer", () => {
render();
expect((await screen.findAllByText("S$32.00")).length).toBeGreaterThan(0);
- expect(screen.getByRole("button", { name: "$ USD" })).toHaveAttribute("aria-pressed", "false");
- await user.click(screen.getByRole("button", { name: "$ USD" }));
expect(screen.getByRole("button", { name: "$ USD" })).toHaveAttribute("aria-pressed", "true");
expect((await screen.findAllByText("$23.80")).length).toBeGreaterThan(0);
+ await user.click(screen.getByRole("button", { name: "¥ CNY" }));
+ expect(screen.getByRole("button", { name: "¥ CNY" })).toHaveAttribute("aria-pressed", "true");
+ expect((await screen.findAllByText("¥161.93")).length).toBeGreaterThan(0);
expect((screen.getAllByText("S$32.00")).length).toBeGreaterThan(0);
expect(fetch).toHaveBeenCalledTimes(2);
});
+ it("links to the project repository and honors a saved CNY preference", () => {
+ window.localStorage.setItem("business-price-radar:currency", "CNY");
+ render();
+
+ expect(screen.getByRole("button", { name: "¥ CNY" })).toHaveAttribute("aria-pressed", "true");
+ expect(screen.getByRole("link", { name: "在 GitHub 查看 zhangkaihua88/chatgpt-business-price-radar" }))
+ .toHaveAttribute("href", "https://github.com/zhangkaihua88/chatgpt-business-price-radar");
+ });
+
it("filters by country and tax treatment", async () => {
const user = userEvent.setup();
render();
diff --git a/src/App.tsx b/src/App.tsx
index 2d4dca0..e96d9b5 100644
--- a/src/App.tsx
+++ b/src/App.tsx
@@ -5,6 +5,7 @@ import {
CheckCircle2,
CircleDollarSign,
Database,
+ Github,
Info,
Search,
ShieldCheck,
@@ -46,7 +47,7 @@ async function loadSnapshot(): Promise {
function initialCurrency(): DisplayCurrency {
const stored = window.localStorage.getItem(currencyStorageKey);
- return stored === "USD" ? "USD" : "CNY";
+ return stored === "CNY" ? "CNY" : "USD";
}
export default function App() {
@@ -118,6 +119,17 @@ export default function App() {
OpenAI 公开配置
+
+
+ GitHub
+
diff --git a/src/styles.css b/src/styles.css
index 00af988..38a30e4 100644
--- a/src/styles.css
+++ b/src/styles.css
@@ -34,6 +34,9 @@ button:focus-visible, input:focus-visible, select:focus-visible, a:focus-visible
.topbar-actions { display: flex; align-items: center; gap: 18px; }
.source-pill { display: inline-flex; align-items: center; gap: 7px; color: var(--muted); font-size: 12px; font-weight: 600; }
.live-dot { width: 7px; height: 7px; border-radius: 50%; background: #2ca675; box-shadow: 0 0 0 4px rgba(44,166,117,.12); }
+.github-badge { display: inline-flex; align-items: center; justify-content: center; gap: 7px; height: 38px; padding: 0 12px; border: 1px solid var(--line); border-radius: 12px; background: rgba(255,255,255,.75); color: var(--ink); font-size: 11px; font-weight: 750; text-decoration: none; transition: color .18s ease, background .18s ease, border-color .18s ease, transform .18s ease; }
+.github-badge:hover { color: white; background: var(--ink); border-color: var(--ink); transform: translateY(-1px); }
+.github-badge:focus-visible { outline: 3px solid rgba(23,107,77,.24); outline-offset: 2px; }
.currency-toggle { display: inline-flex; padding: 4px; border: 1px solid var(--line); border-radius: 12px; background: rgba(255,255,255,.75); }
.currency-toggle button { border: 0; background: transparent; color: var(--muted); padding: 8px 11px; border-radius: 8px; font-size: 12px; font-weight: 750; cursor: pointer; }
.currency-toggle button.active { background: var(--ink); color: white; box-shadow: 0 3px 10px rgba(20,30,27,.14); }
@@ -149,8 +152,11 @@ footer > span:last-child { text-align: right; }
@media (max-width: 760px) {
.topbar, main, footer { width: min(100% - 32px, 680px); }
.topbar { height: 74px; }
+ .topbar-actions { gap: 8px; }
.source-pill { display: none; }
.brand small { display: none; }
+ .github-badge { width: 36px; height: 36px; padding: 0; }
+ .github-badge span { display: none; }
.currency-toggle button { padding: 7px 9px; font-size: 10px; }
.hero { min-height: auto; grid-template-columns: 1fr; gap: 34px; padding: 64px 0 46px; }
.hero::before { width: 360px; height: 360px; right: -250px; }