diff --git a/server/cmd/server/buy.html b/server/cmd/server/buy.html new file mode 100644 index 0000000..21a8e46 --- /dev/null +++ b/server/cmd/server/buy.html @@ -0,0 +1,410 @@ + + + + + +่ดญไนฐ Pangolin + + + +
+
+ +

่ดญไนฐ Pangolin

+
+ + +
+

็™ปๅฝ•่ดฆๅท

+
+
+ + + + + +
+
+ + + + + + +
+ + + + diff --git a/server/cmd/server/buy_page.go b/server/cmd/server/buy_page.go new file mode 100644 index 0000000..41819ff --- /dev/null +++ b/server/cmd/server/buy_page.go @@ -0,0 +1,22 @@ +package main + +import ( + _ "embed" + "net/http" +) + +// buyPageHTML is the self-contained, same-origin "/buy" purchase page: login +// -> pick a plan + payment method (USDT/nezha) -> create order -> poll until +// activated. It talks to /v1/auth/login, /v1/pay/catalog, /v1/pay/orders and +// /v1/pay/orders/{orderNo} via relative fetch() calls, so it's always same +// origin as the API (no CORS needed) as long as it's served from this binary. +// +//go:embed buy.html +var buyPageHTML []byte + +// serveBuyPage handles GET /buy. Public (no JWT) โ€” the page itself drives the +// login flow client-side. +func serveBuyPage(w http.ResponseWriter, _ *http.Request) { + w.Header().Set("Content-Type", "text/html; charset=utf-8") + _, _ = w.Write(buyPageHTML) +} diff --git a/server/cmd/server/main.go b/server/cmd/server/main.go index c1bfdd4..9b683d0 100644 --- a/server/cmd/server/main.go +++ b/server/cmd/server/main.go @@ -131,6 +131,10 @@ func main() { _ = json.NewEncoder(w).Encode(map[string]string{"status": "ok"}) }) + // Public (no JWT): self-contained purchase page, same-origin as /v1/pay/* + // so it can call the API with plain relative fetch()s (no CORS). + r.Get("/buy", serveBuyPage) + // Optional probe ingest route. sharedProbeStore is reused by the scheduler // (below) when both are enabled, so they share one Redis-backed store. var sharedProbeStore *probe.Store