From b2915fe8566c09677568c43aace0aff3e7a2be23 Mon Sep 17 00:00:00 2001 From: Carlo Piovesan Date: Mon, 16 Jun 2025 17:01:44 +0200 Subject: [PATCH] Fixup access flags for checking files (without actually creating them) --- packages/duckdb-wasm/src/bindings/runtime.ts | 5 +++++ .../duckdb-wasm/src/bindings/runtime_browser.ts | 5 +++++ .../duckdb-wasm/src/bindings/runtime_node.ts | 5 +++++ patches/duckdb/fix_load_database.patch | 17 ++++++++++------- 4 files changed, 25 insertions(+), 7 deletions(-) diff --git a/packages/duckdb-wasm/src/bindings/runtime.ts b/packages/duckdb-wasm/src/bindings/runtime.ts index 86b27d992..d8e3f1357 100644 --- a/packages/duckdb-wasm/src/bindings/runtime.ts +++ b/packages/duckdb-wasm/src/bindings/runtime.ts @@ -58,6 +58,11 @@ export enum FileFlags { FILE_FLAGS_FILE_CREATE_NEW = 1 << 4, //! Open file in append mode FILE_FLAGS_APPEND = 1 << 5, + FILE_FLAGS_PRIVATE = 1 << 6, + FILE_FLAGS_NULL_IF_NOT_EXISTS = 1 << 7, + FILE_FLAGS_PARALLEL_ACCESS = 1 << 8, + FILE_FLAGS_EXCLUSIVE_CREATE = 1 << 9, + FILE_FLAGS_NULL_IF_EXISTS = 1 << 10 } /** Configuration for the AWS S3 Filesystem */ diff --git a/packages/duckdb-wasm/src/bindings/runtime_browser.ts b/packages/duckdb-wasm/src/bindings/runtime_browser.ts index 5aebb03ef..b549716b6 100644 --- a/packages/duckdb-wasm/src/bindings/runtime_browser.ts +++ b/packages/duckdb-wasm/src/bindings/runtime_browser.ts @@ -381,6 +381,11 @@ export const BROWSER_RUNTIME: DuckDBRuntime & { return result; } + // Depending on file flags, return nullptr + if (flags & FileFlags.FILE_FLAGS_NULL_IF_NOT_EXISTS) { + return 0; + } + // Fall back to empty buffered file in the browser console.warn(`Buffering missing file: ${file.fileName}`); const result = mod._malloc(2 * 8); diff --git a/packages/duckdb-wasm/src/bindings/runtime_node.ts b/packages/duckdb-wasm/src/bindings/runtime_node.ts index 7f331d079..193d84af0 100644 --- a/packages/duckdb-wasm/src/bindings/runtime_node.ts +++ b/packages/duckdb-wasm/src/bindings/runtime_node.ts @@ -76,6 +76,11 @@ export const NODE_RUNTIME: DuckDBRuntime & { case DuckDBDataProtocol.NODE_FS: { let fd = NODE_RUNTIME._files?.get(file.dataUrl!); if (fd === null || fd === undefined) { + // Depending on file flags, return nullptr + if (flags & FileFlags.FILE_FLAGS_NULL_IF_NOT_EXISTS) { + return 0; + } + fd = fs.openSync( file.dataUrl!, fs.constants.O_CREAT | fs.constants.O_RDWR, diff --git a/patches/duckdb/fix_load_database.patch b/patches/duckdb/fix_load_database.patch index 5399bfc4d..1790e5027 100644 --- a/patches/duckdb/fix_load_database.patch +++ b/patches/duckdb/fix_load_database.patch @@ -1,20 +1,23 @@ diff --git a/src/storage/storage_manager.cpp b/src/storage/storage_manager.cpp -index cb6c654e5f..a6b2af3b85 100644 +index 45d42174f1..10b3ce47b1 100644 --- a/src/storage/storage_manager.cpp +++ b/src/storage/storage_manager.cpp -@@ -160,9 +160,12 @@ void SingleFileStorageManager::LoadDatabase(StorageOptions storage_options) { +@@ -162,9 +162,15 @@ void SingleFileStorageManager::LoadDatabase(StorageOptions storage_options) { row_group_size, STANDARD_VECTOR_SIZE); } } - // Check if the database file already exists. - // Note: a file can also exist if there was a ROLLBACK on a previous transaction creating that file. - if (!read_only && !fs.FileExists(path)) { -+ auto db_file_handle = fs.OpenFile(path, FileFlags::FILE_FLAGS_READ | FileFlags::FILE_FLAGS_NULL_IF_NOT_EXISTS); -+ bool is_empty_file = db_file_handle->GetFileSize() == 0; -+ db_file_handle.reset(); ++ bool is_empty_file = true; ++ auto db_file_handle = fs.OpenFile(path, FileFlags::FILE_FLAGS_READ | FileFlags::FILE_FLAGS_NULL_IF_NOT_EXISTS); ++ if (db_file_handle && db_file_handle->GetFileSize() != 0) { ++ is_empty_file = false; ++ db_file_handle.reset(); ++ } + -+ // first check if the database exists -+ if (!read_only && ( !fs.FileExists(path) || ( options.use_direct_io && is_empty_file )) ) { ++ // first check if the database exists ++ if (!read_only && (!fs.FileExists(path) || (options.use_direct_io && is_empty_file))) { // file does not exist and we are in read-write mode // create a new file