package main import ( "crypto/rand" "crypto/sha256" "encoding/base64" "encoding/json" "fmt" "io" "net/http" "github.com/gofiber/fiber/v2" ) const EDGEDB_AUTH_BASE_URL = "http://127.0.0.1:10700/db/main/ext/auth" func generatePKCE() (string, string) { verifier := make([]byte, 32) _, err := rand.Read(verifier) if err != nil { panic(err) } challenge := sha256.Sum256(verifier) return base64.RawURLEncoding.EncodeToString(verifier), base64.RawURLEncoding.EncodeToString(challenge[:]) } func handleUiSignIn(c *fiber.Ctx) error { verifier, challenge := generatePKCE() fmt.Println("handleUiSignIn verifier: " + verifier) fmt.Println("handleUiSignIn challenge: " + challenge) redirectURL := fmt.Sprintf("%s/ui/signin?challenge=%s", EDGEDB_AUTH_BASE_URL, challenge) c.Cookie(&fiber.Cookie{ Name: "jade-edgedb-pkce-verifier", Value: verifier, HTTPOnly: true, Path: "/", Secure: true, SameSite: "Strict", }) return c.Redirect(redirectURL, fiber.StatusMovedPermanently) } func handleUiSignUp(c *fiber.Ctx) error { verifier, challenge := generatePKCE() fmt.Println("handleUiSignUp verifier: " + verifier) fmt.Println("handleUiSignUp challenge: " + challenge) redirectURL := fmt.Sprintf("%s/ui/signup?challenge=%s", EDGEDB_AUTH_BASE_URL, challenge) c.Cookie(&fiber.Cookie{ Name: "jade-edgedb-pkce-verifier", Value: verifier, HTTPOnly: true, Path: "/", Secure: true, SameSite: "Strict", }) return c.Redirect(redirectURL, fiber.StatusMovedPermanently) } func handleCallbackSignup(c *fiber.Ctx) error { code := c.Query("code") fmt.Println("Callback signup code: " + code) verifier := c.Cookies("jade-edgedb-pkce-verifier") if verifier == "" { return c.Status(fiber.StatusBadRequest).SendString("Could not find 'verifier' in the cookie store. Is this the same user agent/browser that started the authorization flow?") } return c.SendString("OK") } func handleCallback(c *fiber.Ctx) error { code := c.Query("code") if code == "" { error := c.Query("error") return c.Status(fiber.StatusBadRequest).SendString(fmt.Sprintf("OAuth callback is missing 'code'. OAuth provider responded with error: %s", error)) } verifier := c.Cookies("jade-edgedb-pkce-verifier") if verifier == "" { return c.Status(fiber.StatusBadRequest).SendString("Could not find 'verifier' in the cookie store. Is this the same user agent/browser that started the authorization flow?") } fmt.Println("handleCallback code: " + code) fmt.Println("handleCallback verifier: " + verifier) codeExchangeURL := fmt.Sprintf("%s/token?code=%s&verifier=%s", EDGEDB_AUTH_BASE_URL, code, verifier) resp, err := http.Get(codeExchangeURL) if err != nil { return c.Status(fiber.StatusBadRequest).SendString(fmt.Sprintf("Error from the auth server: %s", err.Error())) } defer resp.Body.Close() if resp.StatusCode != fiber.StatusOK { body, _ := io.ReadAll(resp.Body) return c.Status(fiber.StatusBadRequest).SendString(fmt.Sprintf("Error from the auth server: %s", string(body))) } var tokenResponse struct { AuthToken string `json:"auth_token"` } err = json.NewDecoder(resp.Body).Decode(&tokenResponse) if err != nil { return c.Status(fiber.StatusBadRequest).SendString(fmt.Sprintf("Error decoding auth server response: %s", err.Error())) } c.Cookie(&fiber.Cookie{ Name: "edgedb-auth-token", Value: tokenResponse.AuthToken, HTTPOnly: true, Path: "/", Secure: true, SameSite: "Strict", }) fmt.Println("Login successful") fmt.Println("edgedb-auth-token: " + tokenResponse.AuthToken) return c.SendStatus(fiber.StatusNoContent) }