{"record":{"id":"aa4fcfaddad1fe8e","repo":"nextauthjs/next-auth","slug":"account-not-created","errorCode":null,"errorMessage":"Account not created","messagePattern":"Account not created","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"packages/adapter-surrealdb/src/index.ts","lineNumber":309,"sourceCode":"      } catch {}\n\n      // delete user\n      await surreal.delete(new RecordId(\"user\", userId))\n\n      // TODO: put all 3 deletes inside a Promise all\n    },\n    async linkAccount(account: AdapterAccount) {\n      try {\n        const surreal = await client\n        const accountDoc = await surreal.create<\n          AccountDoc,\n          Omit<AccountDoc, \"id\">\n        >(\"account\", accountToDoc(account))\n        if (accountDoc.length) {\n          return docToAccount(accountDoc[0])\n        }\n      } catch {}\n      throw new Error(\"Account not created\")\n    },\n    async unlinkAccount({\n      providerAccountId,\n      provider,\n    }: Pick<AdapterAccount, \"provider\" | \"providerAccountId\">) {\n      const surreal = await client\n      try {\n        const [accounts] = await surreal.query<[AccountDoc[]]>(\n          `SELECT * FROM account WHERE providerAccountId = $providerAccountId AND provider = $provider LIMIT 1`,\n          { providerAccountId, provider }\n        )\n        const account = accounts.at(0)\n        if (account) {\n          await surreal.delete(account.id)\n        }\n      } catch {}\n    },\n    async createSession({","sourceCodeStart":291,"sourceCodeEnd":327,"githubUrl":"https://github.com/nextauthjs/next-auth/blob/a1a16a5a7780488c7449feece410033f445d0b31/packages/adapter-surrealdb/src/index.ts#L291-L327","documentation":"linkAccount() creates an account document linking an OAuth provider identity to a user. If the SurrealDB create throws, or the returned array is empty, the adapter discards the underlying error and throws 'Account not created'.","triggerScenarios":" surreal.create('account', ...) fails (connection, permissions, schema) or returns zero rows; duplicate account for the same provider/providerAccountId; invalid account fields from the provider profile.","commonSituations":"First OAuth sign-in where the account table has restrictive SurrealDB permissions; SurrealDB down or credentials wrong; account already linked causing an insert conflict that the empty catch hides.","solutions":["Check SurrealDB connectivity and that the `account` table exists and is writable by the adapter user","Inspect SurrealDB permissions/DEFINE TABLE PERMISSIONS so the adapter role can CREATE on account","Look for an existing account row with the same provider + providerAccountId (duplicate link attempt)","Add temporary logging inside the try to expose the swallowed error"],"exampleFix":"// before\nawait adapter.linkAccount(account) // throws 'Account not created'\n// after\nconst existing = await adapter.getAccount(account.providerAccountId, account.provider)\nif (existing) return existing\nawait adapter.linkAccount(account)","handlingStrategy":"try-catch","validationCode":"const existing = await adapter.getAccount(account.providerAccountId, account.provider)\nif (existing) return existing\nawait adapter.linkAccount(account)","typeGuard":null,"tryCatchPattern":"try {\n  return await adapter.linkAccount(account)\n} catch (e) {\n  if (e.message === 'Account not created') {\n    const existing = await adapter.getAccount(account.providerAccountId, account.provider)\n    if (existing) return existing // idempotent retry\n  }\n  throw e\n}","preventionTips":["Make linkAccount calls idempotent by checking getAccount first","Grant CREATE permission on the account table for the adapter DB user","Monitor SurrealDB connection errors; the adapter swallows root causes"],"tags":["adapter","oauth","surrealdb"],"backgroundTag":"adapter-write-failed","analyzedSha":"a1a16a5a7780488c7449feece410033f445d0b31","analyzedAt":"2026-08-28T21:52:38.200Z","schemaVersion":2},"datasetVersion":"2026-08-29T02:17:18.158Z"}