Skip to content

feat(db): support jiff types as database fields - #699

Open
m4tx wants to merge 1 commit into
chrono-storage-testsfrom
jiff-2
Open

m4tx wants to merge 1 commit into
chrono-storage-testsfrom
jiff-2

Conversation

@m4tx

@m4tx m4tx commented Oct 12, 2026

Copy link
Copy Markdown
Member

Related issue or discussion

#631

Description

Add DatabaseField implementations for jiff::Timestamp and jiff::civil::{Date, Time, DateTime}, and a new public cot::common_types::WeekdaySet built on jiff::civil::Weekday.

SQLx doesn't support jiff natively yet (and sea-query-sqlx panics when binding jiff values for PostgreSQL and MySQL), so the values are represented as DbValue::Jiff* in Cot and converted right before binding: to time types for PostgreSQL and MySQL, and to text for SQLite. The SQLite text format is the same as the one used for chrono values, so the existing data stays comparable with the new values.

chrono::WeekdaySet is now stored through the new WeekdaySet type; the on-disk representation is unchanged.

Type of change

  • Bug fix
  • New feature
  • Documentation
  • Refactor / cleanup
  • Performance improvement
  • Other (describe above)

Add `DatabaseField` implementations for `jiff::Timestamp` and
`jiff::civil::{Date, Time, DateTime}`, and a new public
`cot::common_types::WeekdaySet` built on `jiff::civil::Weekday`.

SQLx doesn't support jiff natively yet (and sea-query-sqlx panics when
binding jiff values for PostgreSQL and MySQL), so the values are
represented as `DbValue::Jiff*` in Cot and converted right before
binding: to `time` types for PostgreSQL and MySQL, and to text for
SQLite. The SQLite text format is the same as the one used for chrono
values, so the existing data stays comparable with the new values.

`chrono::WeekdaySet` is now stored through the new `WeekdaySet` type;
the on-disk representation is unchanged.
@m4tx
m4tx added this pull request to stack #700 October 12, 2026 16:50
Copilot AI balanced review requested due to automatic review settings October 12, 2026 16:50
@github-actions github-actions Bot added A-deps Area: Dependencies C-lib Crate: cot (main library crate) labels Oct 12, 2026

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

🟡 Changes recommended

Several new compatibility tests use dates inconsistent with their fixtures, and two assertions rely on unspecified database row ordering.

4 open findings
What changed in this PR

Adds database support for jiff date/time types while preserving compatibility with existing chrono storage.

Changes:

  • Adds DatabaseField implementations and backend conversions for jiff.
  • Introduces the public WeekdaySet type.
  • Adds cross-backend storage and compatibility tests.
File Description
cot/​tests/​db_testing/​fields.rs Tests new field types.
cot/​tests/​db_testing/​datetime_storage.rs Tests chrono/jiff compatibility.
cot/​src/​utils/​jiff.rs Converts between jiff and time.
cot/​src/​utils.rs Registers conversion utilities.
cot/​src/​db/​impl_sqlite.rs Prepares SQLite values.
cot/​src/​db/​impl_postgres.rs Prepares PostgreSQL values.
cot/​src/​db/​impl_mysql.rs Prepares MySQL values.
cot/​src/​db/​fields/​jiff_fields.rs Implements jiff database fields.
cot/​src/​db/​fields/​chrono_wrapper.rs Bridges chrono::WeekdaySet.
cot/​src/​db/​fields.rs Registers field implementations.
cot/​src/​common_types.rs Adds public WeekdaySet.
cot/​Cargo.toml Enables required crate features.
Cargo.toml Adds the workspace dependency.
Cargo.lock Locks new dependencies.

🧠 Review effort: Balanced


💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.

Comment on lines +261 to +263
expected[1].datetime_fixed = "2023-01-02T11:34:56.789+00:00".to_owned();
expected[2].datetime_fixed = "2023-01-02T15:04:56.123456+00:00".to_owned();
expected[3].datetime_fixed = "2023-01-02T06:49:56.123456789+00:00".to_owned();
expected[2].datetime_fixed = "2023-01-02T15:04:56.123456+00:00".to_owned();
expected[3].datetime_fixed = "2023-01-02T06:49:56.123456789+00:00".to_owned();

let text_models = TextModel::objects().all(&**db).await.unwrap();
let mut third = models[2].clone();
third.save(&**db).await.unwrap();

let threshold: jiff::Timestamp = "2023-01-02T12:34:56.5Z".parse().unwrap();
Comment on lines +390 to +405
let datetime_threshold = jiff::civil::date(2023, 1, 2).at(12, 34, 56, 500_000_000);
let earlier = query!(JiffModel, $datetime < datetime_threshold)
.order_by([<JiffModel as Model>::Fields::datetime.asc()])
.all(&**db)
.await
.unwrap();
assert_eq!(
earlier
.iter()
.map(|model| model.datetime)
.collect::<Vec<_>>(),
[
jiff::civil::date(2023, 1, 2).at(12, 34, 56, 0),
jiff::civil::date(2023, 1, 2).at(12, 34, 56, 123_456_000),
]
);
@github-actions

Copy link
Copy Markdown

🐰 Bencher Report

Projectcot
Branchjiff-2
Testbedgithub-ubuntu-latest
Click to view all benchmark results
BenchmarkLatencyBenchmark Result
milliseconds (ms)
(Result Δ%)
Upper Boundary
milliseconds (ms)
(Limit %)
empty_router/empty_router📈 view plot
🚷 view threshold
13.15 ms
(+13.48%)Baseline: 11.59 ms
18.61 ms
(70.67%)
json_api/json_api📈 view plot
🚷 view threshold
1.11 ms
(+9.99%)Baseline: 1.01 ms
1.35 ms
(82.66%)
nested_routers/nested_routers📈 view plot
🚷 view threshold
1.07 ms
(+12.58%)Baseline: 0.95 ms
1.25 ms
(85.69%)
single_root_route/single_root_route📈 view plot
🚷 view threshold
1.00 ms
(+9.35%)Baseline: 0.92 ms
1.21 ms
(82.73%)
single_root_route_burst/single_root_route_burst📈 view plot
🚷 view threshold
16.96 ms
(+0.88%)Baseline: 16.81 ms
22.15 ms
(76.57%)
🐰 View full continuous benchmarking report in Bencher

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

A-deps Area: Dependencies C-lib Crate: cot (main library crate)

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants