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
//! # xtax-blob-storage
//!
//! > **Experimental** blob storage abstraction for Rust with filesystem and S3
//! > backends, streaming uploads, optional encryption, and composable layers.
//!
//! A compact, builder-driven blob storage abstraction. See the
//! [crate-level README](https://github.com/cz-jcode/xtax/blob/main/crates/xtax-blob-storage/README.md)
//! for the full rationale and comparisons.
//!
//! ## Status
//!
//! **Experimental / learning project.** Not production-ready.
//!
//! ## Architecture
//!
//! ```text
//! BlobStore trait ← everyone implements this
//! ↑
//! ┌────┴──────────────┐
//! │ FsBlobStore │ filesystem backend (feature = "fs")
//! │ S3BlobStore │ S3/Garage backend (feature = "s3")
//! └────┬──────────────┘
//! │
//! ┌────┴───────────────────────────────┐
//! │ PrefixBlobStore │ key prefix manipulation
//! │ EncryptedBlobStore │ encryption
//! │ BlobCleanup │ cleanup by predicate
//! └────┬───────────────────────────────┘
//! │
//! BlobStore trait ← still the same trait, fully composable
//! ```
//!
//! ## Quick start
//!
//! ```rust,no_run
//! use xtax_blob_storage::{BlobStoreBuilder, BlobInput};
//!
//! # #[cfg(feature = "fs")]
//! # #[tokio::main]
//! # async fn main() -> Result<(), Box<dyn std::error::Error>> {
//! # #[cfg(feature = "fs")]
//! # {
//! let store = BlobStoreBuilder::new()
//! .with_fs("/tmp/data")
//! .with_prefix("my-app/")
//! .build()
//! .await?;
//!
//! use tokio::io::AsyncReadExt;
//!
//! store.put(vec![BlobInput::new("hello.txt", b"data".as_slice())]).await?;
//!
//! let mut reader = store.get("hello.txt").await?;
//! let mut buf = String::new();
//! reader.read_to_string(&mut buf).await?;
//! assert_eq!(buf, "data");
//! # Ok(())
//! # }
//! # }
//! # #[cfg(not(feature = "fs"))]
//! # fn main() {}
//! ```
//!
//! ## AI contribution note
//!
//! This library was developed with LLM assistance under continuous human supervision.
//!
// ---------------------------------------------------------------------------
// Internal modules (private) — types are re-exported below
// ---------------------------------------------------------------------------
// ---------------------------------------------------------------------------
// Backend modules — public so users can construct them directly if needed
// ---------------------------------------------------------------------------
/// Filesystem-backed blob store.
///
/// Blobs are stored as individual files under a root directory. Keys
/// containing `/` are mapped to nested directories — identical behaviour
/// to S3.
///
/// For full documentation see the
/// [Backends guide](https://github.com/cz-jcode/xtax/blob/main/crates/xtax-blob-storage/docs/backends.md).
///
/// *Requires the `fs` feature (enabled by default).*
/// S3-compatible blob store.
///
/// Works with AWS S3, Garage, MinIO, and any S3-compatible service.
/// Supports multipart uploads with configurable threshold.
///
/// For full documentation see the
/// [Backends guide](https://github.com/cz-jcode/xtax/blob/main/crates/xtax-blob-storage/docs/backends.md).
///
/// *Requires the `s3` feature (opt-in).*
// ---------------------------------------------------------------------------
// Re-exports — the public API surface
// ---------------------------------------------------------------------------
pub use BlobStore;
pub use ;
pub use ;
pub use ;
pub use ;
pub use ;
pub use ;
pub use validate_blob_key;
pub use BlobVisitor;