miniextendr_api/optionals.rs
1//! Optional feature integrations with third-party crates.
2//!
3//! This module contains all feature-gated integrations with external crates.
4//! Each submodule is only compiled when its corresponding feature is enabled.
5//!
6//! # Available Features
7//!
8//! | Feature | Module | Description |
9//! |---------|--------|-------------|
10//! | `rayon` | `rayon_bridge` | Parallel computation with R interop |
11//! | `rand` | `rand_impl` | R's RNG wrapped for `rand` crate |
12//! | `rand_distr` | - | Re-exports `rand_distr` distributions |
13//! | `either` | `either_impl` | `Either<L, R>` conversions |
14//! | `ndarray` | `ndarray_impl` | N-dimensional array conversions |
15//! | `nalgebra` | `nalgebra_impl` | Linear algebra type conversions |
16//! | `num-bigint` | `num_bigint_impl` | Big integer support |
17//! | `rust_decimal` | `rust_decimal_impl` | Decimal number support |
18//! | `ordered-float` | `ordered_float_impl` | Ordered floats for sorting |
19//! | `uuid` | `uuid_impl` | UUID conversions |
20//! | `regex` | `regex_impl` | Compiled regex from R strings |
21//! | `indexmap` | `indexmap_impl` | Order-preserving maps |
22//! | `time` | `time_impl` | Date/time conversions |
23//! | `jiff` | `jiff_impl` | Date/time conversions with IANA tz (parallel to `time`) |
24//! | `serde` | `serde_impl` | JSON serialization |
25//! | `num-traits` | `num_traits_impl` | Generic numeric operations |
26//! | `bytes` | `bytes_impl` | Byte buffer operations |
27//! | `num-complex` | `num_complex_impl` | Complex number support |
28//! | `url` | `url_impl` | URL parsing and validation |
29//! | `sha2` | `sha2_impl` | Cryptographic hashing |
30//! | `blake3` | `blake3_impl` | BLAKE3 hashing |
31//! | `md5` | `md5_impl` | MD5 hashing (interop only — broken crypto) |
32//! | `globset` | `globset_impl` | Shell-style glob matching |
33//! | `zstd` | `zstd_impl` | zstd compression |
34//! | `bitflags` | `bitflags_impl` | Bitflag conversions |
35//! | `bitvec` | `bitvec_impl` | Bit vector conversions |
36//! | `aho-corasick` | `aho_corasick_impl` | Multi-pattern string search |
37//! | `toml` | `toml_impl` | TOML parsing |
38//! | `tabled` | `tabled_impl` | Table formatting |
39//! | `tinyvec` | `tinyvec_impl` | Small-vector optimized types |
40//! | `borsh` | `borsh_impl` | Binary serialization |
41//!
42//! # Module template
43//!
44//! Every integration module follows the same regional layout. Use this as
45//! a template when adding a new optional integration:
46//!
47//! ```text
48//! // region: Scalar conversions (TryFromSexp + IntoR for T)
49//! // region: Option conversions (NA support — Option<T>)
50//! // region: Vector conversions (Vec<T>, Box<[T]>, slice views)
51//! // region: Vec<Option<T>> conversions (NA-aware vectors)
52//! // region: R<X>Ops adapter trait (e.g., RUuidOps, RUrlOps —
53//! // convenience methods callable
54//! // from #[miniextendr] code)
55//! // region: Helper functions
56//! // region: Unit tests
57//! ```
58//!
59//! Exceptions: `rayon_bridge.rs` exposes a parallel-iteration API, not a
60//! type-conversion adapter, and does not follow this shape. `serde_impl.rs`
61//! is the JSON adapter (the *native* serde path lives in `crate::serde`).
62//! Array-heavy upstreams (`ndarray_impl`, `arrow_impl`, `nalgebra_impl`,
63//! `jiff_impl`) are larger because their type matrices are larger; the
64//! per-region shape still applies.
65
66// region: Rayon - Parallel computation
67
68/// Rayon integration for parallel computation with R interop.
69///
70/// Provides:
71/// - [`with_r_vec`][rayon_bridge::with_r_vec] - Chunk-based parallel fill into R vectors
72/// - [`with_r_vec_map`][rayon_bridge::with_r_vec_map] - Element-wise parallel fill
73/// - [`par_map`][rayon_bridge::par_map] - Transform input slice → R vector
74/// - [`par_map2`][rayon_bridge::par_map2] - Two-input parallel map → R vector
75/// - [`par_map3`][rayon_bridge::par_map3] - Three-input parallel map → R vector
76/// - [`with_r_matrix`][rayon_bridge::with_r_matrix] - Column-wise parallel matrix fill
77/// - [`with_r_array`][rayon_bridge::with_r_array] - Slab-wise parallel array fill
78/// - [`reduce`][rayon_bridge::reduce] - Parallel reductions returning R scalars
79/// - [`RParallelIterator`][rayon_bridge::RParallelIterator] - Adapter trait for R
80///
81/// Enable with `features = ["rayon"]`.
82#[cfg(feature = "rayon")]
83pub mod rayon_bridge;
84#[cfg(feature = "rayon")]
85pub use rayon_bridge::{RParallelExtend, RParallelIterator};
86// endregion
87
88// region: Parallel - thread pool control
89
90/// Thread pool sizing, CRAN compliance (`_R_CHECK_LIMIT_CORES_`), and
91/// cgroup-aware defaults for the rayon bridge. See `docs/RAYON.md`
92/// ("Controlling parallelism from R").
93///
94/// Enable with `features = ["rayon"]`.
95#[cfg(feature = "rayon")]
96pub mod parallel;
97// endregion
98
99// region: Rand - Random number generation
100
101/// Integration with the `rand` crate for R's RNG.
102///
103/// Provides:
104/// - [`RRng`][rand_impl::RRng] - Wraps R's RNG, implements `rand::Rng`
105/// - [`RDistributions`][rand_impl::RDistributions] - Direct access to R's native distributions
106/// - [`RRngOps`][rand_impl::RRngOps] - Adapter trait for exposing custom RNGs to R
107///
108/// Enable with `features = ["rand"]`.
109#[cfg(feature = "rand")]
110pub mod rand_impl;
111#[cfg(feature = "rand")]
112pub use rand_impl::{RDistributionOps, RDistributions, RRng, RRngOps};
113
114/// Re-export of `rand` so downstream crates can name its traits
115/// (`RngExt`, `SeedableRng`, …) at the exact version [`RRng`] implements —
116/// a mismatched direct `rand` dependency would fail trait coherence.
117/// Enable with `features = ["rand"]`.
118#[cfg(feature = "rand")]
119pub use rand;
120
121/// Re-export of `rand_distr` for probability distributions.
122///
123/// Provides distributions like `Normal`, `Exp`, `Uniform`, etc. that work
124/// with [`RRng`]. Enable with `features = ["rand_distr"]`.
125#[cfg(feature = "rand_distr")]
126pub use rand_distr;
127// endregion
128
129// region: Either - Sum type
130
131/// Integration with the `either` crate.
132///
133/// Provides [`TryFromSexp`](crate::TryFromSexp) and [`IntoR`](crate::IntoR) for [`Either<L, R>`][either::Either].
134///
135/// Enable with `features = ["either"]`.
136#[cfg(feature = "either")]
137pub mod either_impl;
138#[cfg(feature = "either")]
139pub use either_impl::{Either, Left, Right};
140// endregion
141
142// region: Ndarray - N-dimensional arrays
143
144/// Integration with the `ndarray` crate.
145///
146/// Provides conversions between R vectors/matrices and ndarray types
147/// (`Array1`, `Array2`, `ArrayView1`, `ArrayView2`).
148///
149/// Enable with `features = ["ndarray"]`.
150#[cfg(feature = "ndarray")]
151pub mod ndarray_impl;
152#[cfg(feature = "ndarray")]
153pub use ndarray_impl::{
154 // Shared ownership
155 ArcArray1,
156 ArcArray2,
157 // Owned arrays
158 Array0,
159 Array1,
160 Array2,
161 Array3,
162 Array4,
163 Array5,
164 Array6,
165 ArrayD,
166 // Read-only views
167 ArrayView0,
168 ArrayView1,
169 ArrayView2,
170 ArrayView3,
171 ArrayView4,
172 ArrayView5,
173 ArrayView6,
174 ArrayViewD,
175 // Mutable views
176 ArrayViewMut0,
177 ArrayViewMut1,
178 ArrayViewMut2,
179 ArrayViewMut3,
180 ArrayViewMut4,
181 ArrayViewMut5,
182 ArrayViewMut6,
183 ArrayViewMutD,
184 // Index types
185 Ix0,
186 Ix1,
187 Ix2,
188 Ix3,
189 Ix4,
190 Ix5,
191 Ix6,
192 IxDyn,
193 // Adapter traits
194 RNdArrayOps,
195 RNdIndex,
196 RNdSlice,
197 RNdSlice2D,
198 // Shape builder
199 ShapeBuilder,
200};
201#[cfg(feature = "ndarray")]
202pub use ndarray_impl::{RndMat, RndVec};
203// endregion
204
205// region: Nalgebra - Linear algebra
206
207/// Integration with the `nalgebra` crate.
208///
209/// Provides conversions between R vectors/matrices and nalgebra types
210/// (`DVector`, `DMatrix`, `SVector`, `SMatrix`).
211///
212/// Enable with `features = ["nalgebra"]`.
213#[cfg(feature = "nalgebra")]
214pub mod nalgebra_impl;
215#[cfg(feature = "nalgebra")]
216pub use nalgebra_impl::{
217 DMatrix, DVector, RDMatrix, RDVector, RMatrixOps, RVecStorage, RVectorOps, SMatrix, SVector,
218};
219// endregion
220
221// region: Numeric types
222
223/// Integration with the `num-bigint` crate.
224///
225/// Provides conversions for `BigInt` and `BigUint` via R character vectors.
226///
227/// Enable with `features = ["num-bigint"]`.
228#[cfg(feature = "num-bigint")]
229pub mod num_bigint_impl;
230#[cfg(feature = "num-bigint")]
231pub use num_bigint_impl::{
232 BigInt, BigUint, RBigIntBitOps, RBigIntOps, RBigUintBitOps, RBigUintOps,
233};
234
235/// Integration with the `rust_decimal` crate.
236///
237/// Provides conversions for `Decimal` via R character vectors.
238///
239/// Enable with `features = ["rust_decimal"]`.
240#[cfg(feature = "rust_decimal")]
241pub mod rust_decimal_impl;
242#[cfg(feature = "rust_decimal")]
243pub use rust_decimal_impl::{Decimal, RDecimalOps};
244
245/// Integration with the `ordered-float` crate.
246///
247/// Provides conversions for `OrderedFloat<f64>` and `OrderedFloat<f32>`.
248///
249/// Enable with `features = ["ordered-float"]`.
250#[cfg(feature = "ordered-float")]
251pub mod ordered_float_impl;
252#[cfg(feature = "ordered-float")]
253pub use ordered_float_impl::{OrderedFloat, ROrderedFloatOps};
254
255/// Integration with the `num-complex` crate for complex number operations.
256///
257/// Provides conversions between R complex vectors (`CPLXSXP`) and `Complex<f64>`.
258///
259/// Enable with `features = ["num-complex"]`.
260#[cfg(feature = "num-complex")]
261pub mod num_complex_impl;
262#[cfg(feature = "num-complex")]
263pub use num_complex_impl::{Complex, RComplexOps};
264
265/// Integration with the `num-traits` crate for generic numeric operations.
266///
267/// Provides adapter traits for generic numeric types:
268/// - [`RNum`][num_traits_impl::RNum] - Basic numeric operations
269/// - [`RSigned`][num_traits_impl::RSigned] - Signed number operations
270/// - [`RFloat`][num_traits_impl::RFloat] - Floating-point operations
271///
272/// Enable with `features = ["num-traits"]`.
273#[cfg(feature = "num-traits")]
274pub mod num_traits_impl;
275#[cfg(feature = "num-traits")]
276pub use num_traits_impl::{RFloat, RNum, RSigned};
277// endregion
278
279// region: String/Text types
280
281/// UUID support via the `uuid` crate.
282///
283/// Provides conversions between R character vectors and `Uuid` types.
284///
285/// Enable with `features = ["uuid"]`.
286#[cfg(feature = "uuid")]
287pub mod uuid_impl;
288#[cfg(feature = "uuid")]
289pub use uuid_impl::{RUuidOps, Uuid, uuid_helpers};
290
291/// Regex support via the `regex` crate.
292///
293/// Provides compiled regular expressions from R character patterns.
294///
295/// Enable with `features = ["regex"]`.
296#[cfg(feature = "regex")]
297pub mod regex_impl;
298#[cfg(feature = "regex")]
299pub use regex_impl::{CaptureGroups, RCaptureGroups, RRegexOps, Regex};
300
301/// Integration with the `url` crate for URL parsing and validation.
302///
303/// Provides conversions between R character vectors and `Url` types.
304///
305/// Enable with `features = ["url"]`.
306#[cfg(feature = "url")]
307pub mod url_impl;
308#[cfg(feature = "url")]
309pub use url_impl::{RUrlOps, Url, url_helpers};
310
311/// Integration with the `aho-corasick` crate for multi-pattern string search.
312///
313/// Provides fast multi-pattern search using the Aho-Corasick algorithm.
314///
315/// Enable with `features = ["aho-corasick"]`.
316#[cfg(feature = "aho-corasick")]
317pub mod aho_corasick_impl;
318#[cfg(feature = "aho-corasick")]
319pub use aho_corasick_impl::{
320 AhoCorasick, RAhoCorasickOps, aho_compile, aho_count_matches, aho_find_all, aho_find_all_flat,
321 aho_find_first, aho_is_match, aho_replace_all,
322};
323
324/// Integration with the `globset` crate for shell-style glob matching.
325///
326/// Provides multi-pattern glob matching with path-aware defaults.
327///
328/// Enable with `features = ["globset"]`.
329#[cfg(feature = "globset")]
330pub mod globset_impl;
331#[cfg(feature = "globset")]
332pub use globset_impl::{
333 Glob, GlobBuilder, GlobOptions, GlobSet, GlobSetBuilder, build_globset, globset_is_match,
334 globset_matches,
335};
336// endregion
337
338// region: Collections
339
340/// IndexMap support via the `indexmap` crate.
341///
342/// Provides conversions between R named lists and `IndexMap<String, T>`.
343///
344/// Enable with `features = ["indexmap"]`.
345#[cfg(feature = "indexmap")]
346pub mod indexmap_impl;
347#[cfg(feature = "indexmap")]
348pub use indexmap_impl::{IndexMap, RIndexMapOps};
349// endregion
350
351// region: Date/Time
352
353// Shared macro for the REALSXP-backed datetime conversion matrix (8 impls per type).
354// Used by time_impl and jiff_impl; not a public export.
355#[cfg(any(feature = "time", feature = "jiff"))]
356mod datetime_realsxp;
357
358/// Time and date support via the `time` crate.
359///
360/// Provides conversions between R date/time types and `time` crate types.
361///
362/// Enable with `features = ["time"]`.
363#[cfg(feature = "time")]
364pub mod time_impl;
365#[cfg(feature = "time")]
366pub use time_impl::{Date, Duration, OffsetDateTime, RDateTimeFormat, RDuration};
367
368/// Date and time conversions via the `jiff` crate — first-class IANA timezone support.
369///
370/// Coexists with the `time` feature. Enable with `features = ["jiff"]`.
371#[cfg(feature = "jiff")]
372pub mod jiff_impl;
373#[cfg(feature = "jiff")]
374pub use jiff_impl::{
375 Date as JiffDate, DateTime as JiffDateTime, JiffTimestampVec, JiffZonedVec, RDate, RDateTime,
376 RSignedDuration, RSpan, RTime, RTimestamp, RZoned, SignedDuration, Span, Time as JiffTime,
377 Timestamp, Zoned,
378};
379// endregion
380
381// region: Serialization
382
383/// Integration with `serde_json` for JSON string serialization.
384///
385/// Provides adapter traits for serializing/deserializing Rust types to/from JSON strings.
386///
387/// Enable with `features = ["serde_json"]`.
388#[cfg(feature = "serde_json")]
389pub mod serde_impl;
390#[cfg(feature = "serde_json")]
391pub use serde_impl::{
392 FactorHandling, JsonOptions, JsonValue, NaHandling, RDeserialize, RJsonBridge, RJsonValueOps,
393 RSerialize, SpecialFloatHandling, json_from_sexp, json_from_sexp_permissive,
394 json_from_sexp_strict, json_from_sexp_with, json_into_sexp,
395};
396
397/// Integration with the `borsh` crate for binary serialization.
398///
399/// Provides [`Borsh<T>`][borsh_impl::Borsh] wrapper for borsh to/from raw vector conversions.
400///
401/// Enable with `features = ["borsh"]`.
402#[cfg(feature = "borsh")]
403pub mod borsh_impl;
404#[cfg(feature = "borsh")]
405pub use borsh_impl::{Borsh, RBorshOps, borsh_from_raw, borsh_to_raw};
406
407/// Integration with the `toml` crate for TOML value conversions.
408///
409/// Provides conversions between TOML values and R types.
410///
411/// Enable with `features = ["toml"]`.
412#[cfg(feature = "toml")]
413pub mod toml_impl;
414#[cfg(feature = "toml")]
415pub use toml_impl::{RTomlOps, TomlValue, toml_from_str, toml_to_string, toml_to_string_pretty};
416// endregion
417
418// region: Byte/Binary handling
419
420/// Integration with the `bytes` crate for byte buffer operations.
421///
422/// Provides adapter traits for byte buffer types.
423///
424/// Enable with `features = ["bytes"]`.
425#[cfg(feature = "bytes")]
426pub mod bytes_impl;
427#[cfg(feature = "bytes")]
428pub use bytes_impl::{Buf, BufMut, Bytes, BytesMut, RBuf, RBufMut};
429
430/// Integration with the `sha2` crate for cryptographic hashing.
431///
432/// Provides SHA-256 and SHA-512 hashing helpers.
433///
434/// Enable with `features = ["sha2"]`.
435#[cfg(feature = "sha2")]
436pub mod sha2_impl;
437#[cfg(feature = "sha2")]
438pub use sha2_impl::{sha256_bytes, sha256_str, sha512_bytes, sha512_str};
439
440/// Integration with the `blake3` crate for fast cryptographic hashing.
441///
442/// Provides BLAKE3 hashing helpers (hex + raw 32-byte digest).
443///
444/// Enable with `features = ["blake3"]`.
445#[cfg(feature = "blake3")]
446pub mod blake3_impl;
447#[cfg(feature = "blake3")]
448pub use blake3_impl::{blake3_bytes, blake3_hex, blake3_str};
449
450/// Integration with the `md5` crate for legacy hashing.
451///
452/// MD5 is cryptographically broken — exposed for interop/checksums only.
453///
454/// Enable with `features = ["md5"]`.
455#[cfg(feature = "md5")]
456pub mod md5_impl;
457#[cfg(feature = "md5")]
458pub use md5_impl::{md5_bytes, md5_hex, md5_str};
459
460/// Integration with the `zstd` crate for whole-buffer compression.
461///
462/// Provides `zstd_compress` / `zstd_decompress` (R raw in / raw out).
463///
464/// Enable with `features = ["zstd"]`.
465#[cfg(feature = "zstd")]
466pub mod zstd_impl;
467#[cfg(feature = "zstd")]
468pub use zstd_impl::{zstd_compress, zstd_decompress};
469// endregion
470
471// region: Bit manipulation
472
473/// Integration with the `bitflags` crate.
474///
475/// Provides [`RFlags<T>`][bitflags_impl::RFlags] wrapper for bitflags ↔ integer conversions.
476///
477/// Enable with `features = ["bitflags"]`.
478#[cfg(feature = "bitflags")]
479pub mod bitflags_impl;
480#[cfg(feature = "bitflags")]
481pub use bitflags_impl::{Flags, RFlags};
482
483/// Integration with the `bitvec` crate.
484///
485/// Provides conversions between R logical vectors and `BitVec` types.
486///
487/// Enable with `features = ["bitvec"]`.
488#[cfg(feature = "bitvec")]
489pub mod bitvec_impl;
490#[cfg(feature = "bitvec")]
491pub use bitvec_impl::{BitVec, Lsb0, Msb0, RBitVec};
492// endregion
493
494// region: Formatting
495
496/// Integration with the `tabled` crate for table formatting.
497///
498/// Provides helpers for formatting data as ASCII/Unicode tables.
499///
500/// Enable with `features = ["tabled"]`.
501#[cfg(feature = "tabled")]
502pub mod tabled_impl;
503#[cfg(feature = "tabled")]
504pub use tabled_impl::{
505 Builder, Table, Tabled, builder_to_string, table_from_vecs, table_to_string,
506 table_to_string_opts, table_to_string_styled,
507};
508// endregion
509
510// region: TinyVec - Small vector optimization
511
512/// Integration with the `tinyvec` crate for small-vector optimization.
513///
514/// Provides conversions for `TinyVec<[T; N]>` and `ArrayVec<[T; N]>`:
515/// - `TinyVec`: Growable, stores inline up to N elements, then spills to heap
516/// - `ArrayVec`: Fixed capacity N, never allocates, errors if exceeded
517///
518/// Enable with `features = ["tinyvec"]`.
519#[cfg(feature = "tinyvec")]
520pub mod tinyvec_impl;
521#[cfg(feature = "tinyvec")]
522pub use tinyvec_impl::{Array, ArrayVec, TinyVec};
523// endregion
524
525// region: Arrow - Apache Arrow columnar format
526
527/// Integration with the Apache Arrow columnar format.
528///
529/// Provides zero-copy (where possible) conversions between R vectors/data.frames
530/// and Arrow arrays/RecordBatch.
531///
532/// Enable with `features = ["arrow"]`.
533#[cfg(feature = "arrow")]
534pub mod arrow_impl;
535#[cfg(feature = "arrow")]
536pub use arrow_impl::{
537 Array as ArrowArray, ArrayRef, BooleanArray, DataType, Date32Array, DictionaryArray, Field,
538 Float64Array, Int32Array, RecordBatch, Schema, StringArray, StringDictionaryArray,
539 TimestampSecondArray, UInt8Array,
540};
541// endregion
542
543// region: DataFusion - SQL query engine
544
545/// Integration with Apache DataFusion query engine.
546///
547/// Provides `RSessionContext` for running SQL queries on R data frames.
548/// Uses Tokio internally (block_on) so `#[miniextendr]` functions stay sync.
549///
550/// Enable with `features = ["datafusion"]` (implies `arrow`).
551#[cfg(feature = "datafusion")]
552pub mod datafusion_impl;
553#[cfg(feature = "datafusion")]
554pub use datafusion_impl::{RDataFrame, RSessionContext};
555// endregion
556
557// region: Log - Rust logging to R console
558
559/// Integration with the `log` crate for routing Rust diagnostics to R's console.
560///
561/// Enable with `features = ["log"]`.
562#[cfg(feature = "log")]
563pub mod log_impl;
564// endregion