Skip to content
Closed
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
136 changes: 98 additions & 38 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,20 @@

A utility to generate database structs and querying code from diesel schema files. Primarily built for [create-rust-app](https://github.com/Wulf/create-rust-app).

**Why?**

Currently, it's more advantageous to generate code over deriving code with macros because intellisense and autocompletion isn't quite there when it comes to macro expansion.

**Migrating from v0 to v1? See migration notes below.**
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
**Migrating from v0 to v1? See migration notes below.**
**Migrating from v0 to v1? See [migration notes below](#migrating-from-v0-to-v1).**

Note that i have not checked the slug, but it should likely be this


## Features

- Supports `diesel-async` (enable `async` feature flag)
- Generates structs based on your `schema.rs` file (see the `test/simple_table` folder for sample output)
- Optionally generates CRUD functions and helper methods
- Use as a binary or library (read more below)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
- Use as a binary or library (read more below)
- Usable as a binary or library (read more below)

i think this reads better with better understanding

- Many options (see `GenerationConfig` in `lib.rs`) -- you have the ability to customize generated code for specific tables; or entirely ignore a specific table!

## Demo

Given the following schema:
Expand All @@ -30,20 +42,46 @@ cargo dsync -i schema.rs -o models
Now we have everything we need!

```rust
use models::todos;
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

why remove that line? i think this would make sense to get to know where some things come from


async fn demo(db: Connection) {
/*
CRUD examples
*/
let created_todo = todos::create(&mut db, todos::CreateTodo {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
let created_todo = todos::create(&mut db, todos::CreateTodo {
let created_todo = Todo::create(&mut db, todos::CreateTodo {

unless i missed something, this should likely be the actual case (error from before this PR)

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
let created_todo = todos::create(&mut db, todos::CreateTodo {
let created_todo = todos::create(&mut db, CreateTodo {

also to be consistent with later calls

text: "Create a demo",
completed: false,
}).await?;

let todos_list = todos::paginate(&mut db, 1, 10).await?;

let updated_todo = todos::update(&mut db, created_todo.id, UpdateTodo {
})?;

let todos_list = Todo::paginate(db, 1, 10)?;
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

if this PR requires #103, then shouldnt this take one more parameter?


let read_todo = Todo::read(db, created_todo.id)?;

let updated_todo = Todo::update(db, created_todo.id, UpdateTodo {
text: created_todo.text,
completed: true,
}).await?;
})?;

let deleted_todo = Todo::delete(db, created_todo.id)?;

/*
Use the "Filter" helper
--> Works well with intellisense! <--
--> Easily create reusable/portable queries! <--
(Support for date/time and other types coming soon)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

what support is missing?

*/

// example: fetch incomplete todos
let query = Todo::filter(TodoFilter {
completed: Some(false),
..Default::default()
});
let items: Vec<Todo> = query.load(db)?;

// example: delete completed todos
let query = Todo::filter(TodoFilter {
completed: Some(true),
..Default::default()
})
diesel::delete(query).execute(db)?;
}
```

Expand All @@ -59,56 +97,64 @@ For a complete example, see [`test/simple_table/schema.rs`](test/simple_table/sc

2. Create a new binary in your project which uses the crate (for example, `bin/dsync.rs`)

```rust
use std::{collections::HashMap, path::PathBuf};
use dsync::{GenerationConfig, TableOptions};

pub fn main() {
let dir = env!("CARGO_MANIFEST_DIR");

dsync::generate_files(
PathBuf::from_iter([dir, "src/schema.rs"]),
PathBuf::from_iter([dir, "src/models"]),
GenerationConfig { /* ... your generation options ... */ }
);
}
```
```rust
use std::{collections::HashMap, path::PathBuf};
use dsync::{GenerationConfig, TableOptions};

pub fn main() {
let dir = env!("CARGO_MANIFEST_DIR");

dsync::generate_files(
PathBuf::from_iter([dir, "src/schema.rs"]),
PathBuf::from_iter([dir, "src/models"]),
GenerationConfig {
/* ... your generation options ... */
..Default::default()
}
);
}
```

3. Create a `Cargo.toml` binary entry:

```toml
[[bin]]
name = "dsync"
path = "bin/dsync.rs"
```
```toml
[[bin]]
name = "dsync"
path = "bin/dsync.rs"
```

4. Execute!

```sh
cargo run --bin dsync
```
```sh
cargo run --bin dsync
```

**Protip**: to use `cargo dsync`, create an alias in `.cargo/config`:

**Protip**: to use `cargo dsync`, create an alias in `.cargo/config`:

```toml
[alias]
dsync="run --bin dsync"
```
```toml
[alias]
dsync="run --bin dsync"
```

### Pre-built binary

Setting up a custom binary allows you to completely customize the generation; however, if complete customization isn't necessary, you can install the CLI directly
(you'll have to make sure you keep it up-to-date by running this periodically):

```sh
cargo install dsync
cargo install dsync
```

**CLI Usage**

* `-i`: input argument: path to schema file
* `-o`: output argument: path to directory where generated code should be written
* `-c`: connection type (for example: `diesel::r2d2::PooledConnection<diesel::r2d2::ConnectionManager<diesel::PgConnection>>`)
* `-c`: connection type that implements `diesel::connection::Connection`. For example:
* `diesel::r2d2::PooledConnection<diesel::r2d2::ConnectionManager<diesel::PgConnection>>`,
* `diesel::pg::PgConnection`
* `diesel::sqlite::SqliteConnection`
* `diesel::mysql::MysqlConnection`
* or, your custom diesel connection type!
* `-g`: (optional) list of columns that are automatically generated by create/update triggers (for example, `created_at`, `updated_at`)
* `--tsync`: (optional) adds `#[tsync]` attribute to generated structs (see <https://github.com/Wulf/tsync>)
* `--model-path`: (optional) set a custom model import path, default `crate::models::`
Expand All @@ -118,6 +164,11 @@ cargo install dsync
* `--create-str`: (optional) Set which string type to use for `Create*` structs (possible are `string`, `str`, `cow`)
* `--update-str`: (optional) Set which string type to use for `Update*` structs (possible are `string`, `str`, `cow`)
* `--single-model-file`: (optional) Generate only a single model file, instead of a directory with `mod.rs` and `generated.rs`
* `--diesel-backend`: (optional) Specifies the diesel backend type (something which implements `diesel::backend::Backend`). For example:
* `diesel::pg::Pg`,
* `diesel::sqlite::Sqlite`,
* `diesel::mysql::Mysql`,
* or your own type!
* note: the CLI has fail-safes to prevent accidental file overwriting

```sh
Expand All @@ -130,6 +181,15 @@ See `dsync --help` for more information.

Feel free to open tickets for support or feature requests.

## Migrating from v0 to v1
* For those that use plural table names: English-based pluralization is no longer handled. If you had a table named `todos`, dsync will not generate a struct named `Todo` anymore, but instead, `struct Todos` will be generated. It might be easier to rename your tables entirely to singular case.
Comment on lines +184 to +185
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
## Migrating from v0 to v1
* For those that use plural table names: English-based pluralization is no longer handled. If you had a table named `todos`, dsync will not generate a struct named `Todo` anymore, but instead, `struct Todos` will be generated. It might be easier to rename your tables entirely to singular case.
## Migrating from v0 to v1
* For those that use plural table names: English-based pluralization is no longer handled. If you had a table named `todos`, dsync will not generate a struct named `Todo` anymore, but instead, `struct Todos` will be generated. It might be easier to rename your tables entirely to singular case.

* Replace all instances of `/* This file is generated and managed by dsync */` with `/* @generated and managed by dsync */` in your generated model files.
* If using `dsync` as a library, add `..Default::default()` at the end of your args for the `GenerationConfig` struct. It sets the following new params to their default values:
* `once_common_structs: true`,
* `once_connection_type: true`,
* `diesel_backend: "diesel::pg::Pg"`,
* #[tsync] attributes are no longer included by default. To enable them, change the default table config options or supply `--tsync` if using the CLI.

## Development/Testing

Use `./test/test_all.sh` to run tests.
Expand Down