1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
// Copyright (C) 2024-2025 Greg Burd. Licensed under either of the
// Apache License, Version 2.0 or the MIT license, at your option.
// See LICENSE-APACHE and LICENSE-MIT at the root of this repository.
// SPDX-License-Identifier: Apache-2.0 OR MIT
//! > **Internal component of the [`noxu`](https://crates.io/crates/noxu) database.**
//! >
//! > This crate is published only so the `noxu` umbrella crate can depend on it.
//! > Use `noxu` (`noxu = "3"`) in applications; depend on this crate directly only
//! > if you are extending the engine internals. Its API may change without a major
//! > version bump.
//!
//! > **Note on derive macros**: `#[derive(Entity)]`, `#[derive(PrimaryKey)]`, and
//! > `#[derive(SecondaryKey)]` emit `::noxu::persist::` paths in generated code by
//! > default, so the `noxu` umbrella crate must be present. Users who depend on
//! > `noxu-persist` directly (without the umbrella) can add
//! > `#[entity(crate = "noxu_persist")]` to each struct to redirect generated
//! > code to `::noxu_persist::…` instead — see the
//! > [crate-path escape hatch](#crate-path-escape-hatch) section below.
//!
//! Derive-macro-based entity persistence for Noxu DB.
//!
//! Direct Persistence Layer — provides trait-based entity-to-database
//! mapping with a proc-macro derive shortcut.
//!
//! ## Umbrella usage (recommended)
//!
//! Most users depend on the `noxu` umbrella crate and use `noxu::persist`
//! as their import path. The derive macros default to emitting
//! `::noxu::persist::…` paths, which works automatically:
//!
//! ```no_run
//! use noxu::persist::{Entity, SecondaryKey};
//!
//! #[derive(Clone, Debug, Entity, SecondaryKey)]
//! struct User {
//! #[primary_key]
//! id: u64,
//! #[secondary_key(name = "by_email", relate = OneToOne)]
//! email: String,
//! }
//! ```
//!
//! ## Crate-path escape hatch
//!
//! Users who add `noxu-persist` as a **direct** dependency (without the
//! `noxu` umbrella) can add `#[entity(crate = "noxu_persist")]` to each
//! annotated struct. Generated code then uses `::noxu_persist::…` paths
//! instead, and the umbrella crate is not required.
//!
//! ```ignore
//! // Cargo.toml: noxu-persist = "3" (no noxu umbrella)
//! use noxu_persist::{Entity, SecondaryKey};
//!
//! #[derive(Clone, Debug, Entity, SecondaryKey)]
//! #[entity(crate = "noxu_persist")]
//! struct Widget {
//! #[primary_key]
//! id: u64,
//! #[secondary_key(name = "by_kind", relate = ManyToOne)]
//! kind: String,
//! }
//! ```
//!
//! The same `#[entity(crate = "…")]` attribute is recognised by all three
//! derives: `Entity`, `PrimaryKey`, and `SecondaryKey`. Any valid Rust
//! module path is accepted; a malformed path produces a descriptive
//! compile error.
//!
//! # Overview
//!
//! The persistence layer provides typed access to database records through:
//!
//! - **`Entity`** - Trait marking a type as storable
//! - **`PrimaryKey`** - Trait for primary key types
//! - **`EntitySerializer`** - Trait for custom serialization strategies
//! - **`PrimaryIndex`** - Typed CRUD operations on entities by primary key
//! - **`EntityStore`** - Manages databases for entity types
//! - **`StoreConfig`** - Configuration for entity stores
//!
//! # Example
//!
//! ```ignore
//! use noxu_persist::*;
//! use noxu_db::{Environment, EnvironmentConfig};
//!
//! // Define an entity
//! struct User { id: u64, name: String }
//!
//! impl Entity for User {
//! type PrimaryKey = u64;
//! fn primary_key(&self) -> &u64 { &self.id }
//! fn entity_name() -> &'static str { "User" }
//! }
//!
//! // Define a serializer
//! struct UserSerializer;
//! impl EntitySerializer<User> for UserSerializer {
//! fn serialize(&self, user: &User) -> error::Result<Vec<u8>> { /* ... */ }
//! fn deserialize(&self, bytes: &[u8]) -> error::Result<User> { /* ... */ }
//! }
//!
//! // Use the store
//! let config = StoreConfig::new("my_store").with_allow_create(true);
//! // let mut store = EntityStore::open(&env, config)?;
//! // let index: PrimaryIndex<u64, User> = store.get_primary_index()?;
//! // index.put(&UserSerializer, &User { id: 1, name: "Alice".into() })?;
//! ```
// Re-export commonly used types
pub use ;
pub use EntitySerializer;
pub use EntityStore;
pub use ;
pub use ;
pub use SecondaryIndex;
pub use ;
// Derive-macro re-exports — see `noxu-persist-derive`.
// The user only needs `noxu_persist` in their `Cargo.toml`; the derive
// crate is pulled in transitively. This mirrors the `serde` /
// `serde_derive` re-export pattern.
pub use ;
pub use ;
pub use ;
pub use StoreConfig;
// Schema evolution re-exports
pub use ;