TypeError: Invalid URL string In Social and Magic Link Login #840

Closed
opened 2026-03-13 08:06:38 -05:00 by GiteaMirror · 1 comment
Owner

Originally created by @avera-hills-admin on GitHub (Mar 13, 2025).

Is this suited for github?

  • Yes, this is suited for github

To Reproduce

Create a nextjs x hono server and upload hono to cloudflare ( use jstack )

Current vs. Expected behavior

  "source": {
    "level": "error",
    "message": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.",
    "$workers": {
      "event": {
        "request": {
          "url": "https://avera-hills-server.theaverahills.workers.dev/api/auth/sign-in/magic-link",
          "method": "POST",
          "path": "/api/auth/sign-in/magic-link"
        }
      },
      "outcome": "ok",
      "scriptName": "avera-hills-server",
      "eventType": "fetch",
      "executionModel": "stateless",
      "scriptVersion": {
        "id": "8898a206-4368-4185-bf1a-e67d5e02c818"
      },
      "truncated": false,
      "requestId": "91f9864b4fc0dbd0"
    },
    "$cloudflare": {
      "$metadata": {
        "id": "01JP73JAZDCZCDMGYQB3HQB9RZ",
        "type": "cf-worker",
        "error": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.",
        "errorPattern": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.",
        "messagePattern": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string."
      }
    }
  },
  "dataset": "",
  "timestamp": "2025-03-13T06:37:46.349Z",
  "$workers": {
    "event": {
      "request": {
        "url": "https://avera-hills-server.theaverahills.workers.dev/api/auth/sign-in/magic-link",
        "method": "POST",
        "path": "/api/auth/sign-in/magic-link"
      }
    },
    "outcome": "ok",
    "scriptName": "avera-hills-server",
    "eventType": "fetch",
    "executionModel": "stateless",
    "scriptVersion": {
      "id": "8898a206-4368-4185-bf1a-e67d5e02c818"
    },
    "truncated": false,
    "requestId": "91f9864b4fc0dbd0"
  },
  "$metadata": {
    "now": "2025-03-13T06:37:46.370Z",
    "id": "01JP73JAZDCZCDMGYQB3HQB9RZ",
    "requestId": "91f9864b4fc0dbd0",
    "service": "avera-hills-server",
    "level": "error",
    "statusCode": 500,
    "error": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.",
    "message": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.",
    "url": "https://avera-hills-server.theaverahills.workers.dev/api/auth/sign-in/magic-link",
    "account": "e37e276faa0a3ff1140a323b705ba4b1",
    "provider": "cloudflare",
    "type": "cf-worker",
    "fingerprint": "1c583c304ac6b7a9021c1a7b68fc6bdf",
    "origin": "fetch",
    "messageTemplate": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.",
    "errorTemplate": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string."
  },
  "_source": {
    "level": "error",
    "message": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.",
    "$workers.event.request.url": "https://avera-hills-server.theaverahills.workers.dev/api/auth/sign-in/magic-link",
    "$workers.event.request.method": "POST",
    "$workers.event.request.path": "/api/auth/sign-in/magic-link",
    "$workers.outcome": "ok",
    "$workers.scriptName": "avera-hills-server",
    "$workers.eventType": "fetch",
    "$workers.executionModel": "stateless",
    "$workers.scriptVersion.id": "8898a206-4368-4185-bf1a-e67d5e02c818",
    "$workers.truncated": false,
    "$workers.requestId": "91f9864b4fc0dbd0",
    "$cloudflare.$metadata.id": "01JP73JAZDCZCDMGYQB3HQB9RZ",
    "$cloudflare.$metadata.type": "cf-worker",
    "$cloudflare.$metadata.error": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.",
    "$cloudflare.$metadata.errorPattern": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.",
    "$cloudflare.$metadata.messagePattern": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string."
  },
  "_type": "cf-worker",
  "_baselimeId": "01JP73JAZDCZCDMGYQB3HQB9RZ",
  "_account": "e37e276faa0a3ff1140a323b705ba4b1",
  "_billableState": 0,
  "_now": 1741847866370,
  "_level": "error",
  "_requestId": "91f9864b4fc0dbd0",
  "_message": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.",
  "_namespace": "/api/auth/sign-in/magic-link",
  "_service": "avera-hills-server",
  "_samplingInterval": 1,
  "_timestamp": 1741847866349,
  "_error": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.",
  "_origin": "fetch",
  "_provider": "cloudflare",
  "_url": "https://avera-hills-server.theaverahills.workers.dev/api/auth/sign-in/magic-link",
  "_statusCode": 500,
  "_messageTemplate": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.",
  "_messageTemplateParams": [
    "2025-03-13T06:37:46.349Z"
  ],
  "_errorTemplate": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.",
  "_errorTemplateParams": [
    "2025-03-13T06:37:46.349Z"
  ],
  "_fingerprint": "1c583c304ac6b7a9021c1a7b68fc6bdf",
  "_parsed": {
    "level": "error",
    "message": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.",
    "$workers": {
      "event": {
        "request": {
          "url": "https://avera-hills-server.theaverahills.workers.dev/api/auth/sign-in/magic-link",
          "method": "POST",
          "path": "/api/auth/sign-in/magic-link"
        }
      },
      "outcome": "ok",
      "scriptName": "avera-hills-server",
      "eventType": "fetch",
      "executionModel": "stateless",
      "scriptVersion": {
        "id": "8898a206-4368-4185-bf1a-e67d5e02c818"
      },
      "truncated": false,
      "requestId": "91f9864b4fc0dbd0"
    },
    "$cloudflare": {
      "$metadata": {
        "id": "01JP73JAZDCZCDMGYQB3HQB9RZ",
        "type": "cf-worker",
        "error": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.",
        "errorPattern": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.",
        "messagePattern": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string."
      }
    }
  },
  "_workspaceId": "",
  "_environmentId": "",
  "_dataset": "",
  "links": []
}```
// Cloudflare Dashboard

{
  "response": {},
  "request": {
    "baseURL": "https://avera-hills-server.theaverahills.workers.dev/api/auth",
    "credentials": "include",
    "method": "POST",
    "plugins": [
      {
        "id": "redirect",
        "name": "Redirect",
        "hooks": {}
      },
      {
        "id": "apply-schema",
        "name": "Apply Schema",
        "version": "1.0.0"
      }
    ],
    "body": "{\"email\":\"tenukaomaljith2009@gmail.com\",\"callbackURL\":\"/api/auth-callback/\"}",
    "url": "https://avera-hills-server.theaverahills.workers.dev/api/auth/sign-in/magic-link",
    "headers": {},
    "signal": {}
  },
  "error": {
    "status": 500,
    "statusText": ""
  }
}
// client Error 

HTTP/2 500 
date: Thu, 13 Mar 2025 06:49:00 GMT
content-length: 0
access-control-allow-origin: http://localhost:3000
vary: Origin, Accept-Encoding
access-control-allow-credentials: true
access-control-expose-headers: x-is-superjson,set-auth-jwt,Content-Length
report-to: {"endpoints":[{"url":"https:\/\/a.nel.cloudflare.com\/report\/v4?s=gF5gtWgKd9mr0uUgjjJMnN5%2B4wym5h7KD%2B7o0luygmAzjShzaIVIbFD5g7Gi5002jzJYaimkdVPAymcifqQjOLZXx87qdJoAs%2B08ohO%2B40ob7U7dRzBDj%2BRRG9g5LwhQHcDlSoaCwRZcWnvW0Z7RIIFc%2BXJu8Wm6db8L%2FYgY3w%3D%3D"}],"group":"cf-nel","max_age":604800}
nel: {"success_fraction":0,"report_to":"cf-nel","max_age":604800}
server: cloudflare
cf-ray: 91f996c09c913f0f-FRA
alt-svc: h3=":443"; ma=86400
server-timing: cfL4;desc="?proto=TCP&rtt=741&min_rtt=692&rtt_var=257&sent=6&recv=9&lost=0&retrans=0&sent_bytes=1896&recv_bytes=3071&delivery_rate=2092485&cwnd=251&unsent_bytes=0&cid=d7aae9b104589689&ts=420&x=0"
X-Firefox-Spdy: h2

// network res header

POST /api/auth/sign-in/magic-link HTTP/2
Host: avera-hills-server.theaverahills.workers.dev
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:136.0) Gecko/20100101 Firefox/136.0
Accept: */*
Accept-Language: en-US,en;q=0.5
Accept-Encoding: gzip, deflate, br, zstd
Referer: http://localhost:3000/
content-type: application/json
Content-Length: 76
Origin: http://localhost:3000
DNT: 1
Sec-GPC: 1
Connection: keep-alive
Sec-Fetch-Dest: empty
Sec-Fetch-Mode: cors
Sec-Fetch-Site: cross-site
Priority: u=0
TE: trailers

// network req header

![Image](https://github.com/user-attachments/assets/e7269843-d63a-4ba4-97f9-cf68b81078f5)

// the net response


### What version of Better Auth are you using?

^1.1.21

### Provide environment information

```bash
OS - Win 10
Browser - Zen ( Firefox based )

Which area(s) are affected? (Select all that apply)

Backend

Auth config (if applicable)

import { betterAuth } from "better-auth";
import { drizzleAdapter } from "better-auth/adapters/drizzle";
import { admin, magicLink } from "better-auth/plugins";
import { Effect } from "effect";
import siteOptions from "../../src/lib/constants/site-options";
import * as schema from "./schema";
import { getDB } from "./drizzle";
import { serverClient } from "@/lib/server-client";
import adminEmails from "@/lib/admins/list";

export const auth = ({
  AUTH_SECRET,
  FACEBOOK_CLIENT_ID,
  FACEBOOK_CLIENT_SECRET,
  GOOGLE_CLIENT_ID,
  GOOGLE_CLIENT_SECRET,
  NODE_ENV,
  DATABASE_URL,
  NEXT_PUBLIC_BASE_URL,
  NEXT_PUBLIC_SERVER_URL,
}: {
  DATABASE_URL: string;
  NEXT_PUBLIC_BASE_URL: string;
  NEXT_PUBLIC_SERVER_URL: string;
  FACEBOOK_CLIENT_ID: string;
  FACEBOOK_CLIENT_SECRET: string;
  GOOGLE_CLIENT_ID: string;
  GOOGLE_CLIENT_SECRET: string;
  AUTH_SECRET: string;
  NODE_ENV: string;
}) =>
  betterAuth({
    database: drizzleAdapter(getDB({ DATABASE_URL }), {
      provider: "pg",
      schema,
    }),
    trustedOrigins: [
      "localhost:3000",
      "http://localhost:3000",
      "127.0.0.1:8787",
      "http://127.0.0.1:8787",
      "https://avera-hills-server.theaverahills.workers.dev",
      "avera-hills-server.theaverahills.workers.dev",
    ],
    secret: AUTH_SECRET,
    baseURL: NEXT_PUBLIC_BASE_URL,
    basePath: "/api/auth",
    databaseHooks: {
      user: {
        create: {
          before: async (user) => {
            const isUserAdmin = adminEmails.find((a) => user.email === a);
            const userObj = { ...user, role: isUserAdmin ? "admin" : "user" };

            return await { data: userObj };
          },
        },
      },
    },
    socialProviders: {
      facebook: {
        clientId: FACEBOOK_CLIENT_ID,
        clientSecret: FACEBOOK_CLIENT_SECRET,
      },
      google: {
        clientId: GOOGLE_CLIENT_ID,
        clientSecret: GOOGLE_CLIENT_SECRET,
      },
    },
    emailAndPassword: {
      enabled: false,
    },
    plugins: [
      admin({
        defaultRole: "user",
        adminRole: ["admin", "wroker"],
      }),
      magicLink({
        sendMagicLink: async ({ email, url }) => {
          NODE_ENV === "development" &&
            console.log(`Magic Link Email Send to ${email} : ${url}`);

          Effect.runPromise(
            Effect.promise(async () => {
              const { emailResponse } = await (
                await serverClient(
                  NEXT_PUBLIC_SERVER_URL
                ).email.sendMagicLink.$post({
                  magicLink: url,
                  to: email,
                })
              ).json();

              NODE_ENV === "development" && console.log(emailResponse);
            })
          );
        },
      }),
    ],
    user: {
      additionalFields: {
        role: {
          type: "string",
          defaultValue: "user",
          required: true,
        },
      },
    },
    account: {
      accountLinking: {
        enabled: true,
      },
    },
    advanced: {
      defaultCookieAttributes: {
        sameSite: "none",
        secure: true,
      },
    },
    appName: siteOptions.name,
  });

Additional context

import { AppContext, j } from "./jstack";
import { emailRouter } from "./routers/email-router";
import { createRouteHandler } from "uploadthing/server";
import { adminRouter } from "./routers/admin-router";
import { aiRouter } from "./routers/ai-router";
import { uploadthingRouter } from "./routers/uploadthing-router";
import { propertyRouter } from "./routers/property-router";
import { mapsRouter } from "./routers/map-router";
import { blogRouter } from "./routers/blog-router";
import { roomRouter } from "./routers/room-router";
import { userRouter } from "./routers/auth-router";
import { uploadRouter } from "../src/lib/uploadthing/router";
import { cors } from "hono/cors";
import { auth } from "./db/auth.server";
import { Context } from "hono";

export const corsMiddleware = cors({
  origin: (origin) => origin,
  exposeHeaders: ["x-is-superjson", "set-auth-jwt", "Content-Length"],
  allowHeaders: [
    "Content-Type",
    "Authorization",
    "x-is-superjson",
    "Access-Control-Allow-Headers",
    "set-auth-jwt",
    "X-Requested-With",
  ],
  allowMethods: ["POST", "GET", "OPTIONS"],
  maxAge: 600,
  credentials: true,
});

const api = j
  .router()
  .basePath("/api")
  .use(corsMiddleware)
  .onError(j.defaults.errorHandler);

const appRouter = j.mergeRouters(api, {
  email: emailRouter,
  admin: adminRouter,
  ai: aiRouter,
  property: propertyRouter,
  uploadthing: uploadthingRouter,
  map: mapsRouter,
  blog: blogRouter,
  room: roomRouter,
  user: userRouter,
});

const authHandlers = (BASE_URL: string) =>
  createRouteHandler({
    router: uploadRouter,
    config: {
      callbackUrl: BASE_URL,
    },
  });

appRouter.get("/auth-callback/*", (c: Context<AppContext>) => {
  const fullUrl = c.req.url;

  const basePathEndIndex =
    fullUrl.indexOf("/auth-callback/") + "/auth-callback".length;

  const redirectPath = fullUrl.substring(basePathEndIndex);
  return c.redirect(`${c.env.NEXT_PUBLIC_BASE_URL}${redirectPath}`);
});

appRouter.all("/uploadthing", (context: Context<AppContext>) => {
  return authHandlers(context.env.UPLOADTHING_TOKEN)(context.req.raw);
});

appRouter.use("*", async (c, next) => {
  const session = await auth({ ...c.env }).api.getSession({
    headers: c.req.raw.headers,
  });

  if (!session) {
    c.set("user", null);
    c.set("session", null);
    return await next();
  }

  c.set("", session.user);
  c.set("session", session.session);

  return await next();
});

appRouter.on(["POST", "GET"], "/auth/**", (c) => {
  return auth({ ...c.env }).handler(c.req.raw);
});

export type AppRouter = typeof appRouter;
export default appRouter;

// server.ts

NEXT_PUBLIC_BASE_URL="http://localhost:3000"
NEXT_PUBLIC_SERVER_URL="https://avera-hills-server.theaverahills.workers.dev"

//env

The magic link and the social login works in dev mode of the server.ts but not in the cloudflare way. Thank you

Originally created by @avera-hills-admin on GitHub (Mar 13, 2025). ### Is this suited for github? - [ ] Yes, this is suited for github ### To Reproduce Create a nextjs x hono server and upload hono to cloudflare ( use jstack ) ### Current vs. Expected behavior ```{ "source": { "level": "error", "message": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.", "$workers": { "event": { "request": { "url": "https://avera-hills-server.theaverahills.workers.dev/api/auth/sign-in/magic-link", "method": "POST", "path": "/api/auth/sign-in/magic-link" } }, "outcome": "ok", "scriptName": "avera-hills-server", "eventType": "fetch", "executionModel": "stateless", "scriptVersion": { "id": "8898a206-4368-4185-bf1a-e67d5e02c818" }, "truncated": false, "requestId": "91f9864b4fc0dbd0" }, "$cloudflare": { "$metadata": { "id": "01JP73JAZDCZCDMGYQB3HQB9RZ", "type": "cf-worker", "error": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.", "errorPattern": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.", "messagePattern": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string." } } }, "dataset": "", "timestamp": "2025-03-13T06:37:46.349Z", "$workers": { "event": { "request": { "url": "https://avera-hills-server.theaverahills.workers.dev/api/auth/sign-in/magic-link", "method": "POST", "path": "/api/auth/sign-in/magic-link" } }, "outcome": "ok", "scriptName": "avera-hills-server", "eventType": "fetch", "executionModel": "stateless", "scriptVersion": { "id": "8898a206-4368-4185-bf1a-e67d5e02c818" }, "truncated": false, "requestId": "91f9864b4fc0dbd0" }, "$metadata": { "now": "2025-03-13T06:37:46.370Z", "id": "01JP73JAZDCZCDMGYQB3HQB9RZ", "requestId": "91f9864b4fc0dbd0", "service": "avera-hills-server", "level": "error", "statusCode": 500, "error": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.", "message": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.", "url": "https://avera-hills-server.theaverahills.workers.dev/api/auth/sign-in/magic-link", "account": "e37e276faa0a3ff1140a323b705ba4b1", "provider": "cloudflare", "type": "cf-worker", "fingerprint": "1c583c304ac6b7a9021c1a7b68fc6bdf", "origin": "fetch", "messageTemplate": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.", "errorTemplate": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string." }, "_source": { "level": "error", "message": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.", "$workers.event.request.url": "https://avera-hills-server.theaverahills.workers.dev/api/auth/sign-in/magic-link", "$workers.event.request.method": "POST", "$workers.event.request.path": "/api/auth/sign-in/magic-link", "$workers.outcome": "ok", "$workers.scriptName": "avera-hills-server", "$workers.eventType": "fetch", "$workers.executionModel": "stateless", "$workers.scriptVersion.id": "8898a206-4368-4185-bf1a-e67d5e02c818", "$workers.truncated": false, "$workers.requestId": "91f9864b4fc0dbd0", "$cloudflare.$metadata.id": "01JP73JAZDCZCDMGYQB3HQB9RZ", "$cloudflare.$metadata.type": "cf-worker", "$cloudflare.$metadata.error": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.", "$cloudflare.$metadata.errorPattern": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.", "$cloudflare.$metadata.messagePattern": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string." }, "_type": "cf-worker", "_baselimeId": "01JP73JAZDCZCDMGYQB3HQB9RZ", "_account": "e37e276faa0a3ff1140a323b705ba4b1", "_billableState": 0, "_now": 1741847866370, "_level": "error", "_requestId": "91f9864b4fc0dbd0", "_message": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.", "_namespace": "/api/auth/sign-in/magic-link", "_service": "avera-hills-server", "_samplingInterval": 1, "_timestamp": 1741847866349, "_error": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.", "_origin": "fetch", "_provider": "cloudflare", "_url": "https://avera-hills-server.theaverahills.workers.dev/api/auth/sign-in/magic-link", "_statusCode": 500, "_messageTemplate": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.", "_messageTemplateParams": [ "2025-03-13T06:37:46.349Z" ], "_errorTemplate": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.", "_errorTemplateParams": [ "2025-03-13T06:37:46.349Z" ], "_fingerprint": "1c583c304ac6b7a9021c1a7b68fc6bdf", "_parsed": { "level": "error", "message": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.", "$workers": { "event": { "request": { "url": "https://avera-hills-server.theaverahills.workers.dev/api/auth/sign-in/magic-link", "method": "POST", "path": "/api/auth/sign-in/magic-link" } }, "outcome": "ok", "scriptName": "avera-hills-server", "eventType": "fetch", "executionModel": "stateless", "scriptVersion": { "id": "8898a206-4368-4185-bf1a-e67d5e02c818" }, "truncated": false, "requestId": "91f9864b4fc0dbd0" }, "$cloudflare": { "$metadata": { "id": "01JP73JAZDCZCDMGYQB3HQB9RZ", "type": "cf-worker", "error": "\u001b[2m2025-03-13T06:37:46.349Z\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.", "errorPattern": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string.", "messagePattern": "\u001b[2m<UTC>\u001b[0m \u001b[31mERROR\u001b[0m \u001b[1m[Better Auth]:\u001b[0m TypeError TypeError: Invalid URL string." } } }, "_workspaceId": "", "_environmentId": "", "_dataset": "", "links": [] }``` // Cloudflare Dashboard { "response": {}, "request": { "baseURL": "https://avera-hills-server.theaverahills.workers.dev/api/auth", "credentials": "include", "method": "POST", "plugins": [ { "id": "redirect", "name": "Redirect", "hooks": {} }, { "id": "apply-schema", "name": "Apply Schema", "version": "1.0.0" } ], "body": "{\"email\":\"tenukaomaljith2009@gmail.com\",\"callbackURL\":\"/api/auth-callback/\"}", "url": "https://avera-hills-server.theaverahills.workers.dev/api/auth/sign-in/magic-link", "headers": {}, "signal": {} }, "error": { "status": 500, "statusText": "" } } // client Error HTTP/2 500 date: Thu, 13 Mar 2025 06:49:00 GMT content-length: 0 access-control-allow-origin: http://localhost:3000 vary: Origin, Accept-Encoding access-control-allow-credentials: true access-control-expose-headers: x-is-superjson,set-auth-jwt,Content-Length report-to: {"endpoints":[{"url":"https:\/\/a.nel.cloudflare.com\/report\/v4?s=gF5gtWgKd9mr0uUgjjJMnN5%2B4wym5h7KD%2B7o0luygmAzjShzaIVIbFD5g7Gi5002jzJYaimkdVPAymcifqQjOLZXx87qdJoAs%2B08ohO%2B40ob7U7dRzBDj%2BRRG9g5LwhQHcDlSoaCwRZcWnvW0Z7RIIFc%2BXJu8Wm6db8L%2FYgY3w%3D%3D"}],"group":"cf-nel","max_age":604800} nel: {"success_fraction":0,"report_to":"cf-nel","max_age":604800} server: cloudflare cf-ray: 91f996c09c913f0f-FRA alt-svc: h3=":443"; ma=86400 server-timing: cfL4;desc="?proto=TCP&rtt=741&min_rtt=692&rtt_var=257&sent=6&recv=9&lost=0&retrans=0&sent_bytes=1896&recv_bytes=3071&delivery_rate=2092485&cwnd=251&unsent_bytes=0&cid=d7aae9b104589689&ts=420&x=0" X-Firefox-Spdy: h2 // network res header POST /api/auth/sign-in/magic-link HTTP/2 Host: avera-hills-server.theaverahills.workers.dev User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:136.0) Gecko/20100101 Firefox/136.0 Accept: */* Accept-Language: en-US,en;q=0.5 Accept-Encoding: gzip, deflate, br, zstd Referer: http://localhost:3000/ content-type: application/json Content-Length: 76 Origin: http://localhost:3000 DNT: 1 Sec-GPC: 1 Connection: keep-alive Sec-Fetch-Dest: empty Sec-Fetch-Mode: cors Sec-Fetch-Site: cross-site Priority: u=0 TE: trailers // network req header ![Image](https://github.com/user-attachments/assets/e7269843-d63a-4ba4-97f9-cf68b81078f5) // the net response ### What version of Better Auth are you using? ^1.1.21 ### Provide environment information ```bash OS - Win 10 Browser - Zen ( Firefox based ) ``` ### Which area(s) are affected? (Select all that apply) Backend ### Auth config (if applicable) ```typescript import { betterAuth } from "better-auth"; import { drizzleAdapter } from "better-auth/adapters/drizzle"; import { admin, magicLink } from "better-auth/plugins"; import { Effect } from "effect"; import siteOptions from "../../src/lib/constants/site-options"; import * as schema from "./schema"; import { getDB } from "./drizzle"; import { serverClient } from "@/lib/server-client"; import adminEmails from "@/lib/admins/list"; export const auth = ({ AUTH_SECRET, FACEBOOK_CLIENT_ID, FACEBOOK_CLIENT_SECRET, GOOGLE_CLIENT_ID, GOOGLE_CLIENT_SECRET, NODE_ENV, DATABASE_URL, NEXT_PUBLIC_BASE_URL, NEXT_PUBLIC_SERVER_URL, }: { DATABASE_URL: string; NEXT_PUBLIC_BASE_URL: string; NEXT_PUBLIC_SERVER_URL: string; FACEBOOK_CLIENT_ID: string; FACEBOOK_CLIENT_SECRET: string; GOOGLE_CLIENT_ID: string; GOOGLE_CLIENT_SECRET: string; AUTH_SECRET: string; NODE_ENV: string; }) => betterAuth({ database: drizzleAdapter(getDB({ DATABASE_URL }), { provider: "pg", schema, }), trustedOrigins: [ "localhost:3000", "http://localhost:3000", "127.0.0.1:8787", "http://127.0.0.1:8787", "https://avera-hills-server.theaverahills.workers.dev", "avera-hills-server.theaverahills.workers.dev", ], secret: AUTH_SECRET, baseURL: NEXT_PUBLIC_BASE_URL, basePath: "/api/auth", databaseHooks: { user: { create: { before: async (user) => { const isUserAdmin = adminEmails.find((a) => user.email === a); const userObj = { ...user, role: isUserAdmin ? "admin" : "user" }; return await { data: userObj }; }, }, }, }, socialProviders: { facebook: { clientId: FACEBOOK_CLIENT_ID, clientSecret: FACEBOOK_CLIENT_SECRET, }, google: { clientId: GOOGLE_CLIENT_ID, clientSecret: GOOGLE_CLIENT_SECRET, }, }, emailAndPassword: { enabled: false, }, plugins: [ admin({ defaultRole: "user", adminRole: ["admin", "wroker"], }), magicLink({ sendMagicLink: async ({ email, url }) => { NODE_ENV === "development" && console.log(`Magic Link Email Send to ${email} : ${url}`); Effect.runPromise( Effect.promise(async () => { const { emailResponse } = await ( await serverClient( NEXT_PUBLIC_SERVER_URL ).email.sendMagicLink.$post({ magicLink: url, to: email, }) ).json(); NODE_ENV === "development" && console.log(emailResponse); }) ); }, }), ], user: { additionalFields: { role: { type: "string", defaultValue: "user", required: true, }, }, }, account: { accountLinking: { enabled: true, }, }, advanced: { defaultCookieAttributes: { sameSite: "none", secure: true, }, }, appName: siteOptions.name, }); ``` ### Additional context ``` import { AppContext, j } from "./jstack"; import { emailRouter } from "./routers/email-router"; import { createRouteHandler } from "uploadthing/server"; import { adminRouter } from "./routers/admin-router"; import { aiRouter } from "./routers/ai-router"; import { uploadthingRouter } from "./routers/uploadthing-router"; import { propertyRouter } from "./routers/property-router"; import { mapsRouter } from "./routers/map-router"; import { blogRouter } from "./routers/blog-router"; import { roomRouter } from "./routers/room-router"; import { userRouter } from "./routers/auth-router"; import { uploadRouter } from "../src/lib/uploadthing/router"; import { cors } from "hono/cors"; import { auth } from "./db/auth.server"; import { Context } from "hono"; export const corsMiddleware = cors({ origin: (origin) => origin, exposeHeaders: ["x-is-superjson", "set-auth-jwt", "Content-Length"], allowHeaders: [ "Content-Type", "Authorization", "x-is-superjson", "Access-Control-Allow-Headers", "set-auth-jwt", "X-Requested-With", ], allowMethods: ["POST", "GET", "OPTIONS"], maxAge: 600, credentials: true, }); const api = j .router() .basePath("/api") .use(corsMiddleware) .onError(j.defaults.errorHandler); const appRouter = j.mergeRouters(api, { email: emailRouter, admin: adminRouter, ai: aiRouter, property: propertyRouter, uploadthing: uploadthingRouter, map: mapsRouter, blog: blogRouter, room: roomRouter, user: userRouter, }); const authHandlers = (BASE_URL: string) => createRouteHandler({ router: uploadRouter, config: { callbackUrl: BASE_URL, }, }); appRouter.get("/auth-callback/*", (c: Context<AppContext>) => { const fullUrl = c.req.url; const basePathEndIndex = fullUrl.indexOf("/auth-callback/") + "/auth-callback".length; const redirectPath = fullUrl.substring(basePathEndIndex); return c.redirect(`${c.env.NEXT_PUBLIC_BASE_URL}${redirectPath}`); }); appRouter.all("/uploadthing", (context: Context<AppContext>) => { return authHandlers(context.env.UPLOADTHING_TOKEN)(context.req.raw); }); appRouter.use("*", async (c, next) => { const session = await auth({ ...c.env }).api.getSession({ headers: c.req.raw.headers, }); if (!session) { c.set("user", null); c.set("session", null); return await next(); } c.set("", session.user); c.set("session", session.session); return await next(); }); appRouter.on(["POST", "GET"], "/auth/**", (c) => { return auth({ ...c.env }).handler(c.req.raw); }); export type AppRouter = typeof appRouter; export default appRouter; ``` // server.ts NEXT_PUBLIC_BASE_URL="http://localhost:3000" NEXT_PUBLIC_SERVER_URL="https://avera-hills-server.theaverahills.workers.dev" //env The magic link and the social login works in dev mode of the server.ts but not in the cloudflare way. Thank you
GiteaMirror added the bug label 2026-03-13 08:06:38 -05:00
Author
Owner

@Kinfe123 commented on GitHub (May 29, 2025):

is this still an issue ?

@Kinfe123 commented on GitHub (May 29, 2025): is this still an issue ?
Sign in to join this conversation.
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: github-starred/better-auth#840