# rust-query **Repository Path**: Racist/rust-query ## Basic Information - **Project Name**: rust-query - **Description**: 这个项目是从github引用过来,因为浏览速度比较高,原项目地址: https://github.com/LHolten/rust-query - **Primary Language**: Rust - **License**: MIT - **Default Branch**: add-bool-support-in-schema - **Homepage**: https://github.com/LHolten/rust-query - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2025-06-23 - **Last Updated**: 2025-06-23 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README # Type safe queries using the Rust type system The goal of this library is to allow writing relational database queries using familiar Rust syntax. The library should guarantee that a query can not fail if it compiles. This already includes preventing use after free for row ids passed between queries and even database migrations! Writing queries using this library involves: - Interact with row/column references as Rust values. - Lifetimes to check the scopes of row/column references. - Imperative mutation of row sets with methods like `filter` and `join`. Notably it does not involve any new syntax or macro, while still being completely type safe. ## Roadmap This project is under development and there are many things missing. Query types: - [x] SELECT - [x] INSERT - [ ] DELETE - [ ] UPDATE Basic operations: - [x] Eq, Add, Not, And, Lt, UnwrapOr, IsNotNull, AsFloat - [ ] Everything else Advanced operations: - [x] Aggregate - [ ] Limit Backend support: - [x] sqlite - [ ] postgres - [ ] duckdb Despite these limitations, I am dogfooding this query builder and using it in my own project: [advent-of-wasm](https://github.com/LHolten/advent-of-wasm). ## What it looks like Define a schema using `enum` syntax: ```rust use rust_query::migration::schema; #[schema] enum MySchema { User { name: String, }, Image { description: String, uploaded_by: User, // Corresponds to `User` table that was defined just now! }, } ``` Get proof that we are running on a unique thread: ```rust let mut token = ThreadToken::try_new().unwrap(); ``` Initialize a database: ```rust let database = Prepare::open("my_database.sqlite") .create_db_empty() .expect("database version is before supported versions") // migrations go here .finish(&mut token) .expect("database version is after supported versions"); ``` Perform a transaction! ```rust let mut transaction = database.write_lock(&mut token); do_stuff_with_database(&mut transaction); // After we are done we commit the changes! transaction.commit(); ``` Insert in the database: ```rust // Lets make a new user 'mike', let mike = UserDummy { name: "mike" }; let mike_id = db.try_insert(mike).unwrap(); // and also insert a dog picture for 'mike'. let dog_picture = ImageDummy { description: "dog", uploaded_by: mike_id, }; db.try_insert(dog_picture).unwrap(); ``` Query from the database: ```rust // Now we want to get all pictures for 'mike'. let mike_pictures = db.query(|rows| { // Initially there is one empty row. // Lets join the pictures table. let picture = Image::join(rows); // Now lets filter for pictures from mike, rows.filter(picture.uploaded_by().eq(mike_id)); // and finally turn the rows into a vec. rows.into_vec(picture.description()) }); println!("{mike_pictures:?}"); // This should print `["dog"]`. ``` The full example code can be found in [insert_and_select.rs](examples/insert_and_select.rs) Some features not shown in this example are: - Migrations and unique constraints - Lookups by unique constraint - Aggregations ## Examples For more example queries you can look at [the chinook example](/tests/chinook.rs). First download the `Chinook_Sqlite.sqlite` from here https://github.com/lerocha/chinook-database/releases and put it in the root of this repository (the working dir). Then you can run with `cargo test`.