{"record":{"id":"08e81f3190e72ced","repo":"tursodatabase/turso","slug":"transactionasync-is-not-supported-with-remotewrite-08e81f","errorCode":null,"errorMessage":"transactionAsync is not supported with remoteWritesExperimental yet; use the deprecated transaction() for now","messagePattern":"transactionAsync is not supported with remoteWritesExperimental yet; use the deprecated transaction\\(\\) for now","errorType":"validation","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"bindings/javascript/sync/packages/wasm/promise-bundle.ts","lineNumber":333,"sourceCode":"        Object.defineProperties(properties.immediate.value, properties);\n        Object.defineProperties(properties.exclusive.value, properties);\n        return properties.default.value as TransactionFunction<F>;\n    }\n\n    /**\n     * Returns a function that executes the given function in a transaction\n     * on a connection owned for the whole BEGIN..COMMIT window; the callback\n     * receives a {@link Transaction} handle as its first argument.\n     *\n     * Not supported together with {@link DatabaseOpts.remoteWritesExperimental}\n     * yet: remote-writes transactions run on the remote server and have no\n     * local connection to hand out.\n     */\n    override transactionAsync<F extends (txn: Transaction, ...args: any[]) => Promise<any>>(\n        fn: F,\n    ): AsyncTransactionFunction<F> {\n        if (this.#remoteWriter) {\n            throw new Error(\n                \"transactionAsync is not supported with remoteWritesExperimental yet; use the deprecated transaction() for now\",\n            );\n        }\n        return super.transactionAsync(fn);\n    }\n\n    /**\n     * close the database and relevant files\n     */\n    async close() {\n        if (this.#remoteWriter) {\n            await this.#remoteWriter.close();\n        }\n        if (this.#engine != null) {\n            if (this.name != null && this.#worker != null) {\n                await Promise.all([\n                    unregisterFileAtWorker(this.#worker, this.name),\n                    unregisterFileAtWorker(this.#worker, `${this.name}-wal`),","sourceCodeStart":315,"sourceCodeEnd":351,"githubUrl":"https://github.com/tursodatabase/turso/blob/bad083fafbefdeae9a42ec19bdaaad8918dcf411/bindings/javascript/sync/packages/wasm/promise-bundle.ts#L315-L351","documentation":"transactionAsync() runs its callback on a connection owned for the whole BEGIN..COMMIT window and hands it a Transaction handle. When the Database was constructed with remoteWritesExperimental, transactions execute on the remote server and there is no local connection to hand out, so the override throws immediately instead of silently running the transaction locally. The deprecated transaction() is the supported path under remote writes: its wrapper routes BEGIN, the statements and COMMIT to the remote as one transaction.","triggerScenarios":"Constructing with { url, remoteWritesExperimental: true } — which sets this.#remoteWriter — and then calling db.transactionAsync(fn). The guard is the first statement of the override, so it throws before fn is ever touched.","commonSituations":"Enabling remote writes in an existing codebase that already used transactionAsync; upgrading @tursodatabase/sync-wasm where the restriction is new; mixing sync-local and remote-write modes behind a runtime flag where only one branch was migrated to transaction().","solutions":["Replace transactionAsync(fn) with transaction(fn): with remoteWritesExperimental enabled its wrapper sends BEGIN, the statements and COMMIT to the remote server as a single transaction.","If you need the interactive Transaction-handle semantics (held local connection), disable remoteWritesExperimental and keep writes local, syncing via push().","Alternatively express the unit of work as awaited exec/run calls — with remote writes enabled, write statements are forwarded to the remote."],"exampleFix":"// before — throws: no local connection exists to hand out under remote writes\nconst transfer = db.transactionAsync(async (txn, from, to, amount) => {\n    await txn.exec({ sql: \"UPDATE accounts SET bal = bal - ? WHERE id = ?\", args: [amount, from] });\n    await txn.exec({ sql: \"UPDATE accounts SET bal = bal + ? WHERE id = ?\", args: [amount, to] });\n});\nawait transfer(1, 2, 50);\n\n// after — deprecated transaction() is the supported API with remoteWritesExperimental\nconst transfer = db.transaction(async (from: number, to: number, amount: number) => {\n    await db.exec({ sql: \"UPDATE accounts SET bal = bal - ? WHERE id = ?\", args: [amount, from] });\n    await db.exec({ sql: \"UPDATE accounts SET bal = bal + ? WHERE id = ?\", args: [amount, to] });\n});\nawait transfer(1, 2, 50); // whole BEGIN..COMMIT goes to the remote server","handlingStrategy":"fallback","validationCode":"const remoteWrites = process.env.TURSO_REMOTE_WRITES === \"1\";\nconst db = new Database({ path, url, remoteWritesExperimental: remoteWrites });\n\n// Choose the transaction API to match the mode BEFORE calling either method:\nconst makeTx = remoteWrites\n    ? <F extends (...a: any[]) => Promise<any>>(fn: F) => db.transaction(fn)\n    : <F extends (txn: Transaction, ...a: any[]) => Promise<any>>(fn: F) => db.transactionAsync(fn);","typeGuard":"function supportsTransactionAsync(remoteWritesEnabled: boolean): boolean {\n    // transactionAsync is only valid without remoteWritesExperimental\n    return !remoteWritesEnabled;\n}","tryCatchPattern":"let runTx: (...args: unknown[]) => Promise<unknown>;\ntry {\n    runTx = db.transactionAsync(fn);\n} catch (e) {\n    if (e instanceof Error && e.message.includes(\"remoteWritesExperimental\")) {\n        runTx = db.transaction(fn); // documented fallback for remote-write mode\n    } else {\n        throw e;\n    }\n}","preventionTips":["Treat remoteWritesExperimental and transactionAsync as mutually exclusive; pick one per Database instance.","Wrap transaction creation in a single factory function so the remote/local mode choice lives in one place.","Watch release notes of @tursodatabase/sync-wasm — the restriction is explicitly documented as temporary ('yet')."],"tags":["sync","remote-writes","transaction","unsupported-operation","wasm"],"backgroundTag":"unsupported-feature-combination","analyzedSha":"bad083fafbefdeae9a42ec19bdaaad8918dcf411","analyzedAt":"2026-08-16T23:12:11.798Z","schemaVersion":2},"datasetVersion":"2026-08-17T04:17:16.089Z"}