diff --git a/node/package-lock.json b/node/package-lock.json index e0179ab0..70203950 100644 --- a/node/package-lock.json +++ b/node/package-lock.json @@ -23,7 +23,7 @@ "chai": "^4.3.7", "eslint": "^8.39.0", "eslint-config-standard-with-typescript": "^34.0.1", - "eslint-plugin-import": "^2.27.5", + "eslint-plugin-import": "^2.26.0", "eslint-plugin-n": "^15.7.0", "eslint-plugin-promise": "^6.1.1", "mocha": "^10.2.0", @@ -787,24 +787,6 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/array.prototype.flatmap": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/array.prototype.flatmap/-/array.prototype.flatmap-1.3.1.tgz", - "integrity": "sha512-8UGn9O1FDVvMNB0UlLv4voxRMze7+FpHyF5mSMRjWHUMlpoDViniy05870VlxhfgTnLbpuwTzvD76MTtWxB/mQ==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.4", - "es-abstract": "^1.20.4", - "es-shim-unscopables": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/assertion-error": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/assertion-error/-/assertion-error-1.1.0.tgz", @@ -1633,25 +1615,23 @@ } }, "node_modules/eslint-plugin-import": { - "version": "2.27.5", - "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.27.5.tgz", - "integrity": "sha512-LmEt3GVofgiGuiE+ORpnvP+kAm3h6MLZJ4Q5HCyHADofsb4VzXFsRiWj3c0OFiV+3DWFh0qg3v9gcPlfc3zRow==", + "version": "2.26.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.26.0.tgz", + "integrity": "sha512-hYfi3FXaM8WPLf4S1cikh/r4IxnO6zrhZbEGz2b660EJRbuxgpDS5gkCuYgGWg2xxh2rBuIr4Pvhve/7c31koA==", "dev": true, "dependencies": { - "array-includes": "^3.1.6", - "array.prototype.flat": "^1.3.1", - "array.prototype.flatmap": "^1.3.1", - "debug": "^3.2.7", + "array-includes": "^3.1.4", + "array.prototype.flat": "^1.2.5", + "debug": "^2.6.9", "doctrine": "^2.1.0", - "eslint-import-resolver-node": "^0.3.7", - "eslint-module-utils": "^2.7.4", + "eslint-import-resolver-node": "^0.3.6", + "eslint-module-utils": "^2.7.3", "has": "^1.0.3", - "is-core-module": "^2.11.0", + "is-core-module": "^2.8.1", "is-glob": "^4.0.3", "minimatch": "^3.1.2", - "object.values": "^1.1.6", - "resolve": "^1.22.1", - "semver": "^6.3.0", + "object.values": "^1.1.5", + "resolve": "^1.22.0", "tsconfig-paths": "^3.14.1" }, "engines": { @@ -1662,12 +1642,12 @@ } }, "node_modules/eslint-plugin-import/node_modules/debug": { - "version": "3.2.7", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", - "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", "dev": true, "dependencies": { - "ms": "^2.1.1" + "ms": "2.0.0" } }, "node_modules/eslint-plugin-import/node_modules/doctrine": { @@ -1682,14 +1662,11 @@ "node": ">=0.10.0" } }, - "node_modules/eslint-plugin-import/node_modules/semver": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", - "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", - "dev": true, - "bin": { - "semver": "bin/semver.js" - } + "node_modules/eslint-plugin-import/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "dev": true }, "node_modules/eslint-plugin-n": { "version": "15.7.0", @@ -3619,9 +3596,9 @@ } }, "node_modules/semver": { - "version": "7.5.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.5.0.tgz", - "integrity": "sha512-+XC0AD/R7Q2mPSRuy2Id0+CGTZ98+8f+KvwirxOKIEyid+XSx6HbC63p+O4IndTHuX5Z+JxQ0TghCkO5Cg/2HA==", + "version": "7.5.3", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.5.3.tgz", + "integrity": "sha512-QBlUtyVk/5EeHbi7X0fw6liDZc7BBmEaSYn01fMU1OUYbf6GPsbTtd8WmnqbI20SeycoHSeiybkE/q1Q+qlThQ==", "dev": true, "dependencies": { "lru-cache": "^6.0.0" @@ -5038,18 +5015,6 @@ "es-shim-unscopables": "^1.0.0" } }, - "array.prototype.flatmap": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/array.prototype.flatmap/-/array.prototype.flatmap-1.3.1.tgz", - "integrity": "sha512-8UGn9O1FDVvMNB0UlLv4voxRMze7+FpHyF5mSMRjWHUMlpoDViniy05870VlxhfgTnLbpuwTzvD76MTtWxB/mQ==", - "dev": true, - "requires": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.4", - "es-abstract": "^1.20.4", - "es-shim-unscopables": "^1.0.0" - } - }, "assertion-error": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/assertion-error/-/assertion-error-1.1.0.tgz", @@ -5707,35 +5672,33 @@ } }, "eslint-plugin-import": { - "version": "2.27.5", - "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.27.5.tgz", - "integrity": "sha512-LmEt3GVofgiGuiE+ORpnvP+kAm3h6MLZJ4Q5HCyHADofsb4VzXFsRiWj3c0OFiV+3DWFh0qg3v9gcPlfc3zRow==", + "version": "2.26.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.26.0.tgz", + "integrity": "sha512-hYfi3FXaM8WPLf4S1cikh/r4IxnO6zrhZbEGz2b660EJRbuxgpDS5gkCuYgGWg2xxh2rBuIr4Pvhve/7c31koA==", "dev": true, "requires": { - "array-includes": "^3.1.6", - "array.prototype.flat": "^1.3.1", - "array.prototype.flatmap": "^1.3.1", - "debug": "^3.2.7", + "array-includes": "^3.1.4", + "array.prototype.flat": "^1.2.5", + "debug": "^2.6.9", "doctrine": "^2.1.0", - "eslint-import-resolver-node": "^0.3.7", - "eslint-module-utils": "^2.7.4", + "eslint-import-resolver-node": "^0.3.6", + "eslint-module-utils": "^2.7.3", "has": "^1.0.3", - "is-core-module": "^2.11.0", + "is-core-module": "^2.8.1", "is-glob": "^4.0.3", "minimatch": "^3.1.2", - "object.values": "^1.1.6", - "resolve": "^1.22.1", - "semver": "^6.3.0", + "object.values": "^1.1.5", + "resolve": "^1.22.0", "tsconfig-paths": "^3.14.1" }, "dependencies": { "debug": { - "version": "3.2.7", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", - "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", "dev": true, "requires": { - "ms": "^2.1.1" + "ms": "2.0.0" } }, "doctrine": { @@ -5747,10 +5710,10 @@ "esutils": "^2.0.2" } }, - "semver": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", - "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", + "ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", "dev": true } } @@ -7078,9 +7041,9 @@ } }, "semver": { - "version": "7.5.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.5.0.tgz", - "integrity": "sha512-+XC0AD/R7Q2mPSRuy2Id0+CGTZ98+8f+KvwirxOKIEyid+XSx6HbC63p+O4IndTHuX5Z+JxQ0TghCkO5Cg/2HA==", + "version": "7.5.3", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.5.3.tgz", + "integrity": "sha512-QBlUtyVk/5EeHbi7X0fw6liDZc7BBmEaSYn01fMU1OUYbf6GPsbTtd8WmnqbI20SeycoHSeiybkE/q1Q+qlThQ==", "dev": true, "requires": { "lru-cache": "^6.0.0" diff --git a/node/package.json b/node/package.json index 39c24e31..ec59e710 100644 --- a/node/package.json +++ b/node/package.json @@ -35,7 +35,7 @@ "chai": "^4.3.7", "eslint": "^8.39.0", "eslint-config-standard-with-typescript": "^34.0.1", - "eslint-plugin-import": "^2.27.5", + "eslint-plugin-import": "^2.26.0", "eslint-plugin-n": "^15.7.0", "eslint-plugin-promise": "^6.1.1", "mocha": "^10.2.0", diff --git a/node/src/index.ts b/node/src/index.ts index 547d8503..4294b697 100644 --- a/node/src/index.ts +++ b/node/src/index.ts @@ -22,7 +22,7 @@ import { fromRecordsToBuffer } from './arrow' import type { EmbeddingFunction } from './embedding/embedding_function' // eslint-disable-next-line @typescript-eslint/no-var-requires -const { databaseNew, databaseTableNames, databaseOpenTable, tableCreate, tableSearch, tableAdd, tableCreateVectorIndex, tableCountRows, tableDelete } = require('../native.js') +const { databaseNew, databaseTableNames, databaseOpenTable, databaseDropTable, tableCreate, tableSearch, tableAdd, tableCreateVectorIndex, tableCountRows, tableDelete } = require('../native.js') export type { EmbeddingFunction } export { OpenAIEmbeddingFunction } from './embedding/openai' @@ -111,6 +111,14 @@ export class Connection { await tableCreate.call(this._db, name, Buffer.from(await writer.toUint8Array())) return await this.openTable(name) } + + /** + * Drop an existing table. + * @param name The name of the table to drop. + */ + async dropTable (name: string): Promise { + await databaseDropTable.call(this._db, name) + } } export class Table { diff --git a/node/src/test/test.ts b/node/src/test/test.ts index bd291750..e5169e07 100644 --- a/node/src/test/test.ts +++ b/node/src/test/test.ts @@ -235,3 +235,22 @@ async function createTestDB (numDimensions: number = 2, numRows: number = 2): Pr await con.createTable('vectors', data) return dir } + +describe('Drop table', function () { + it('drop a table', async function () { + const dir = await track().mkdir('lancejs') + const con = await lancedb.connect(dir) + + const data = [ + { price: 10, name: 'foo', vector: [1, 2, 3] }, + { price: 50, name: 'bar', vector: [4, 5, 6] } + ] + await con.createTable('t1', data) + await con.createTable('t2', data) + + assert.deepEqual(await con.tableNames(), ['t1', 't2']) + + await con.dropTable('t1') + assert.deepEqual(await con.tableNames(), ['t2']) + }) +}) diff --git a/rust/ffi/node/src/lib.rs b/rust/ffi/node/src/lib.rs index 20fa0021..a1f68b54 100644 --- a/rust/ffi/node/src/lib.rs +++ b/rust/ffi/node/src/lib.rs @@ -122,6 +122,27 @@ fn database_open_table(mut cx: FunctionContext) -> JsResult { Ok(promise) } +fn database_drop_table(mut cx: FunctionContext) -> JsResult { + let db = cx + .this() + .downcast_or_throw::, _>(&mut cx)?; + let table_name = cx.argument::(0)?.value(&mut cx); + + let rt = runtime(&mut cx)?; + let channel = cx.channel(); + let database = db.database.clone(); + + let (deferred, promise) = cx.promise(); + rt.spawn(async move { + let result = database.drop_table(&table_name).await; + deferred.settle_with(&channel, move |mut cx| { + result.or_else(|err| cx.throw_error(err.to_string()))?; + Ok(cx.null()) + }); + }); + Ok(promise) +} + fn table_search(mut cx: FunctionContext) -> JsResult { let js_table = cx.this().downcast_or_throw::, _>(&mut cx)?; let query_obj = cx.argument::(0)?; @@ -308,6 +329,7 @@ fn main(mut cx: ModuleContext) -> NeonResult<()> { cx.export_function("databaseNew", database_new)?; cx.export_function("databaseTableNames", database_table_names)?; cx.export_function("databaseOpenTable", database_open_table)?; + cx.export_function("databaseDropTable", database_drop_table)?; cx.export_function("tableSearch", table_search)?; cx.export_function("tableCreate", table_create)?; cx.export_function("tableAdd", table_add)?; diff --git a/rust/vectordb/Cargo.toml b/rust/vectordb/Cargo.toml index 54f646b2..71a47d5e 100644 --- a/rust/vectordb/Cargo.toml +++ b/rust/vectordb/Cargo.toml @@ -12,7 +12,7 @@ repository = "https://github.com/lancedb/lancedb" arrow-array = "40.0" arrow-data = "40.0" arrow-schema = "40.0" -object_store = "0.5.6" +object_store = "0.6.1" snafu = "0.7.4" lance = "0.5.0" tokio = { version = "1.23", features = ["rt-multi-thread"] } diff --git a/rust/vectordb/src/database.rs b/rust/vectordb/src/database.rs index 283d41dc..c058e59d 100644 --- a/rust/vectordb/src/database.rs +++ b/rust/vectordb/src/database.rs @@ -1,4 +1,4 @@ -// Copyright 2023 Lance Developers. +// Copyright 2023 LanceDB Developers. // // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. @@ -109,6 +109,16 @@ impl Database { pub async fn open_table(&self, name: &str) -> Result { Table::open(&self.uri, name).await } + + /// Drop a table in the database. + /// + /// # Arguments + /// * `name` - The name of the table. + pub async fn drop_table(&self, name: &str) -> Result<()> { + let dir_name = format!("{}/{}.{}", self.uri, name, LANCE_EXTENSION); + self.object_store.remove_dir_all(dir_name).await?; + Ok(()) + } } #[cfg(test)] @@ -146,4 +156,17 @@ mod tests { async fn test_connect_s3() { // let db = Database::connect("s3://bucket/path/to/database").await.unwrap(); } + + #[tokio::test] + async fn drop_table() { + let tmp_dir = tempdir().unwrap(); + create_dir_all(tmp_dir.path().join("table1.lance")).unwrap(); + + let uri = tmp_dir.path().to_str().unwrap(); + let db = Database::connect(uri).await.unwrap(); + db.drop_table("table1").await.unwrap(); + + let tables = db.table_names().await.unwrap(); + assert_eq!(tables.len(), 0); + } } diff --git a/rust/vectordb/src/lib.rs b/rust/vectordb/src/lib.rs index 3c885575..c191784b 100644 --- a/rust/vectordb/src/lib.rs +++ b/rust/vectordb/src/lib.rs @@ -17,3 +17,5 @@ pub mod error; pub mod index; pub mod query; pub mod table; + +pub use database::Database;