xberg 1.3.0 → 1.3.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,5 +1,5 @@
1
1
  // This file is auto-generated by alef. DO NOT EDIT.
2
- // alef:hash:7b7e0e3e79a8cf968d66bcaa7adae77d99bdb0dc86ad64a75c1e785c57a13371
2
+ // alef:hash:e004b1d953b206d06d83d0462afc0689784b447478a1e0085a43e79980b1fd22
3
3
  // Re-generate with: alef generate
4
4
  #![allow(dead_code, unused_imports, unused_variables)]
5
5
  #![allow(
@@ -18,6 +18,7 @@
18
18
  clippy::useless_conversion,
19
19
  clippy::clone_on_copy
20
20
  )]
21
+ #![allow(deprecated)]
21
22
 
22
23
  use async_trait::async_trait;
23
24
  use magnus::{Error, IntoValueFromNative, Ruby, function, method, prelude::*, try_convert::TryConvertOwned};
@@ -1515,6 +1516,7 @@ pub struct CaptioningConfig {
1515
1516
  llm: LlmConfig,
1516
1517
  prompt: Option<String>,
1517
1518
  min_image_area: u32,
1519
+ alt_text: CaptionAltTextMode,
1518
1520
  }
1519
1521
 
1520
1522
  unsafe impl IntoValueFromNative for CaptioningConfig {}
@@ -1559,6 +1561,7 @@ impl Default for CaptioningConfig {
1559
1561
  llm: LlmConfig::default(),
1560
1562
  prompt: None,
1561
1563
  min_image_area: 1000,
1564
+ alt_text: CaptionAltTextMode::Preserve,
1562
1565
  }
1563
1566
  }
1564
1567
  }
@@ -1602,6 +1605,15 @@ impl CaptioningConfig {
1602
1605
  })?,
1603
1606
  None => 1000,
1604
1607
  },
1608
+ alt_text: match kwargs.get(ruby.to_symbol("alt_text")) {
1609
+ Some(v) => CaptionAltTextMode::try_convert(v).map_err(|e| {
1610
+ magnus::Error::new(
1611
+ unsafe { magnus::Ruby::get_unchecked() }.exception_type_error(),
1612
+ format!("invalid value for `alt_text`: {}", e),
1613
+ )
1614
+ })?,
1615
+ None => CaptionAltTextMode::Preserve,
1616
+ },
1605
1617
  })
1606
1618
  }
1607
1619
 
@@ -1616,6 +1628,10 @@ impl CaptioningConfig {
1616
1628
  fn min_image_area(&self) -> u32 {
1617
1629
  self.min_image_area
1618
1630
  }
1631
+
1632
+ fn alt_text(&self) -> CaptionAltTextMode {
1633
+ self.alt_text.clone()
1634
+ }
1619
1635
  }
1620
1636
 
1621
1637
  #[derive(Clone, Debug, serde::Serialize, serde::Deserialize)]
@@ -1724,9 +1740,9 @@ pub struct Chunk {
1724
1740
  content: String,
1725
1741
  chunk_type: ChunkType,
1726
1742
  embedding: Option<Vec<f32>>,
1727
- #[cfg(feature = "sparse-embedding-presets")]
1743
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
1728
1744
  sparse_embedding: Option<SparseEmbedding>,
1729
- #[cfg(feature = "late-interaction-presets")]
1745
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
1730
1746
  late_interaction: Option<MultiVectorEmbedding>,
1731
1747
  metadata: ChunkMetadata,
1732
1748
  }
@@ -1782,12 +1798,7 @@ impl Chunk {
1782
1798
  format!("invalid value for `chunk_type`: {}", e),
1783
1799
  )
1784
1800
  })?,
1785
- None => {
1786
- return Err(magnus::Error::new(
1787
- unsafe { magnus::Ruby::get_unchecked() }.exception_arg_error(),
1788
- "missing required field: chunk_type",
1789
- ));
1790
- }
1801
+ None => ChunkType::Unknown,
1791
1802
  },
1792
1803
  embedding: match kwargs.get(ruby.to_symbol("embedding")).filter(|v| !v.is_nil()) {
1793
1804
  Some(v) => Some(<Vec<f32>>::try_convert(v).map_err(|e| {
@@ -1798,7 +1809,7 @@ impl Chunk {
1798
1809
  })?),
1799
1810
  None => None,
1800
1811
  },
1801
- #[cfg(feature = "sparse-embedding-presets")]
1812
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
1802
1813
  sparse_embedding: match kwargs.get(ruby.to_symbol("sparse_embedding")).filter(|v| !v.is_nil()) {
1803
1814
  Some(v) => Some(SparseEmbedding::try_convert(v).map_err(|e| {
1804
1815
  magnus::Error::new(
@@ -1808,7 +1819,7 @@ impl Chunk {
1808
1819
  })?),
1809
1820
  None => None,
1810
1821
  },
1811
- #[cfg(feature = "late-interaction-presets")]
1822
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
1812
1823
  late_interaction: match kwargs.get(ruby.to_symbol("late_interaction")).filter(|v| !v.is_nil()) {
1813
1824
  Some(v) => Some(MultiVectorEmbedding::try_convert(v).map_err(|e| {
1814
1825
  magnus::Error::new(
@@ -1847,12 +1858,12 @@ impl Chunk {
1847
1858
  self.embedding.clone()
1848
1859
  }
1849
1860
 
1850
- #[cfg(feature = "sparse-embedding-presets")]
1861
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
1851
1862
  fn sparse_embedding(&self) -> Option<SparseEmbedding> {
1852
1863
  self.sparse_embedding.clone()
1853
1864
  }
1854
1865
 
1855
- #[cfg(feature = "late-interaction-presets")]
1866
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
1856
1867
  fn late_interaction(&self) -> Option<MultiVectorEmbedding> {
1857
1868
  self.late_interaction.clone()
1858
1869
  }
@@ -7804,12 +7815,7 @@ impl DocumentNode {
7804
7815
  format!("invalid value for `content_layer`: {}", e),
7805
7816
  )
7806
7817
  })?,
7807
- None => {
7808
- return Err(magnus::Error::new(
7809
- unsafe { magnus::Ruby::get_unchecked() }.exception_arg_error(),
7810
- "missing required field: content_layer",
7811
- ));
7812
- }
7818
+ None => ContentLayer::Body,
7813
7819
  },
7814
7820
  page: match kwargs.get(ruby.to_symbol("page")).filter(|v| !v.is_nil()) {
7815
7821
  Some(v) => Some(u32::try_convert(v).map_err(|e| {
@@ -10682,6 +10688,135 @@ impl ExcelWorkbook {
10682
10688
  }
10683
10689
  }
10684
10690
 
10691
+ #[derive(Clone, Debug, serde::Serialize)]
10692
+ #[serde(default)]
10693
+ #[magnus::wrap(class = "Xberg::ExternalRedactionFinding")]
10694
+ pub struct ExternalRedactionFinding {
10695
+ label: String,
10696
+ text: Option<String>,
10697
+ start: Option<u32>,
10698
+ end: Option<u32>,
10699
+ score: Option<f32>,
10700
+ }
10701
+
10702
+ unsafe impl IntoValueFromNative for ExternalRedactionFinding {}
10703
+
10704
+ impl magnus::TryConvert for ExternalRedactionFinding {
10705
+ fn try_convert(val: magnus::Value) -> Result<Self, magnus::Error> {
10706
+ if let Ok(r) = <&ExternalRedactionFinding as magnus::TryConvert>::try_convert(val) {
10707
+ return Ok(r.clone());
10708
+ }
10709
+ let json_str: String = if let Ok(s) = <String as magnus::TryConvert>::try_convert(val) {
10710
+ s
10711
+ } else {
10712
+ val.funcall::<_, _, String>("to_json", ()).map_err(|e| {
10713
+ magnus::Error::new(
10714
+ unsafe { magnus::Ruby::get_unchecked() }.exception_type_error(),
10715
+ format!("no implicit conversion into ExternalRedactionFinding: {}", e),
10716
+ )
10717
+ })?
10718
+ };
10719
+ serde_json::from_str::<ExternalRedactionFinding>(&json_str).map_err(|e| {
10720
+ magnus::Error::new(
10721
+ unsafe { magnus::Ruby::get_unchecked() }.exception_type_error(),
10722
+ format!("failed to deserialize ExternalRedactionFinding: {}", e),
10723
+ )
10724
+ })
10725
+ }
10726
+ }
10727
+
10728
+ unsafe impl TryConvertOwned for ExternalRedactionFinding {}
10729
+ impl<'de> serde::Deserialize<'de> for ExternalRedactionFinding {
10730
+ fn deserialize<D>(deserializer: D) -> ::core::result::Result<Self, D::Error>
10731
+ where
10732
+ D: serde::Deserializer<'de>,
10733
+ {
10734
+ <xberg::ExternalRedactionFinding as serde::Deserialize>::deserialize(deserializer).map(Into::into)
10735
+ }
10736
+ }
10737
+
10738
+ impl Default for ExternalRedactionFinding {
10739
+ fn default() -> Self {
10740
+ xberg::ExternalRedactionFinding::default().into()
10741
+ }
10742
+ }
10743
+
10744
+ impl ExternalRedactionFinding {
10745
+ fn new(args: &[magnus::Value]) -> Result<Self, magnus::Error> {
10746
+ let ruby = unsafe { magnus::Ruby::get_unchecked() };
10747
+ let args = magnus::scan_args::scan_args::<(), (Option<magnus::RHash>,), (), (), (), ()>(args)?;
10748
+ let (kwargs_opt,) = args.optional;
10749
+ let kwargs = kwargs_opt.unwrap_or_else(|| ruby.hash_new());
10750
+ Ok(Self {
10751
+ label: match kwargs.get(ruby.to_symbol("label")) {
10752
+ Some(v) => String::try_convert(v).map_err(|e| {
10753
+ magnus::Error::new(
10754
+ unsafe { magnus::Ruby::get_unchecked() }.exception_type_error(),
10755
+ format!("invalid value for `label`: {}", e),
10756
+ )
10757
+ })?,
10758
+ None => Default::default(),
10759
+ },
10760
+ text: match kwargs.get(ruby.to_symbol("text")).filter(|v| !v.is_nil()) {
10761
+ Some(v) => Some(String::try_convert(v).map_err(|e| {
10762
+ magnus::Error::new(
10763
+ unsafe { magnus::Ruby::get_unchecked() }.exception_type_error(),
10764
+ format!("invalid value for `text`: {}", e),
10765
+ )
10766
+ })?),
10767
+ None => None,
10768
+ },
10769
+ start: match kwargs.get(ruby.to_symbol("start")).filter(|v| !v.is_nil()) {
10770
+ Some(v) => Some(u32::try_convert(v).map_err(|e| {
10771
+ magnus::Error::new(
10772
+ unsafe { magnus::Ruby::get_unchecked() }.exception_type_error(),
10773
+ format!("invalid value for `start`: {}", e),
10774
+ )
10775
+ })?),
10776
+ None => None,
10777
+ },
10778
+ end: match kwargs.get(ruby.to_symbol("end")).filter(|v| !v.is_nil()) {
10779
+ Some(v) => Some(u32::try_convert(v).map_err(|e| {
10780
+ magnus::Error::new(
10781
+ unsafe { magnus::Ruby::get_unchecked() }.exception_type_error(),
10782
+ format!("invalid value for `end`: {}", e),
10783
+ )
10784
+ })?),
10785
+ None => None,
10786
+ },
10787
+ score: match kwargs.get(ruby.to_symbol("score")).filter(|v| !v.is_nil()) {
10788
+ Some(v) => Some(f32::try_convert(v).map_err(|e| {
10789
+ magnus::Error::new(
10790
+ unsafe { magnus::Ruby::get_unchecked() }.exception_type_error(),
10791
+ format!("invalid value for `score`: {}", e),
10792
+ )
10793
+ })?),
10794
+ None => None,
10795
+ },
10796
+ })
10797
+ }
10798
+
10799
+ fn label(&self) -> String {
10800
+ self.label.clone()
10801
+ }
10802
+
10803
+ fn text(&self) -> Option<String> {
10804
+ self.text.clone()
10805
+ }
10806
+
10807
+ fn start(&self) -> Option<u32> {
10808
+ self.start
10809
+ }
10810
+
10811
+ fn end(&self) -> Option<u32> {
10812
+ self.end
10813
+ }
10814
+
10815
+ fn score(&self) -> Option<f32> {
10816
+ self.score
10817
+ }
10818
+ }
10819
+
10685
10820
  #[derive(Clone, Debug, serde::Serialize)]
10686
10821
  #[serde(default)]
10687
10822
  #[magnus::wrap(class = "Xberg::ExtractInput")]
@@ -18774,7 +18909,7 @@ impl LateInteractionConfig {
18774
18909
  }
18775
18910
  }
18776
18911
 
18777
- #[cfg(feature = "late-interaction-presets")]
18912
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
18778
18913
  #[derive(Clone, Debug, serde::Serialize, serde::Deserialize)]
18779
18914
  #[magnus::wrap(class = "Xberg::LateInteractionMatch")]
18780
18915
  pub struct LateInteractionMatch {
@@ -18782,10 +18917,10 @@ pub struct LateInteractionMatch {
18782
18917
  score: f32,
18783
18918
  }
18784
18919
 
18785
- #[cfg(feature = "late-interaction-presets")]
18920
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
18786
18921
  unsafe impl IntoValueFromNative for LateInteractionMatch {}
18787
18922
 
18788
- #[cfg(feature = "late-interaction-presets")]
18923
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
18789
18924
  impl magnus::TryConvert for LateInteractionMatch {
18790
18925
  fn try_convert(val: magnus::Value) -> Result<Self, magnus::Error> {
18791
18926
  if let Ok(r) = <&LateInteractionMatch as magnus::TryConvert>::try_convert(val) {
@@ -18810,10 +18945,10 @@ impl magnus::TryConvert for LateInteractionMatch {
18810
18945
  }
18811
18946
  }
18812
18947
 
18813
- #[cfg(feature = "late-interaction-presets")]
18948
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
18814
18949
  unsafe impl TryConvertOwned for LateInteractionMatch {}
18815
18950
 
18816
- #[cfg(feature = "late-interaction-presets")]
18951
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
18817
18952
  impl LateInteractionMatch {
18818
18953
  fn new(args: &[magnus::Value]) -> Result<Self, magnus::Error> {
18819
18954
  let ruby = unsafe { magnus::Ruby::get_unchecked() };
@@ -18851,7 +18986,7 @@ impl LateInteractionMatch {
18851
18986
  }
18852
18987
  }
18853
18988
 
18854
- #[cfg(feature = "late-interaction-presets")]
18989
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
18855
18990
  #[derive(Clone, Debug, serde::Serialize, serde::Deserialize)]
18856
18991
  #[magnus::wrap(class = "Xberg::LateInteractionPreset")]
18857
18992
  pub struct LateInteractionPreset {
@@ -18865,10 +19000,10 @@ pub struct LateInteractionPreset {
18865
19000
  description: String,
18866
19001
  }
18867
19002
 
18868
- #[cfg(feature = "late-interaction-presets")]
19003
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
18869
19004
  unsafe impl IntoValueFromNative for LateInteractionPreset {}
18870
19005
 
18871
- #[cfg(feature = "late-interaction-presets")]
19006
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
18872
19007
  impl magnus::TryConvert for LateInteractionPreset {
18873
19008
  fn try_convert(val: magnus::Value) -> Result<Self, magnus::Error> {
18874
19009
  if let Ok(r) = <&LateInteractionPreset as magnus::TryConvert>::try_convert(val) {
@@ -18893,10 +19028,10 @@ impl magnus::TryConvert for LateInteractionPreset {
18893
19028
  }
18894
19029
  }
18895
19030
 
18896
- #[cfg(feature = "late-interaction-presets")]
19031
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
18897
19032
  unsafe impl TryConvertOwned for LateInteractionPreset {}
18898
19033
 
18899
- #[cfg(feature = "late-interaction-presets")]
19034
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
18900
19035
  impl LateInteractionPreset {
18901
19036
  fn new(args: &[magnus::Value]) -> Result<Self, magnus::Error> {
18902
19037
  let ruby = unsafe { magnus::Ruby::get_unchecked() };
@@ -21338,7 +21473,6 @@ impl Metadata {
21338
21473
  }
21339
21474
  }
21340
21475
 
21341
- #[cfg(feature = "paddle-ocr-types")]
21342
21476
  #[derive(Clone, Debug, serde::Serialize, serde::Deserialize)]
21343
21477
  #[magnus::wrap(class = "Xberg::ModelPaths")]
21344
21478
  pub struct ModelPaths {
@@ -21348,10 +21482,8 @@ pub struct ModelPaths {
21348
21482
  dict_file: String,
21349
21483
  }
21350
21484
 
21351
- #[cfg(feature = "paddle-ocr-types")]
21352
21485
  unsafe impl IntoValueFromNative for ModelPaths {}
21353
21486
 
21354
- #[cfg(feature = "paddle-ocr-types")]
21355
21487
  impl magnus::TryConvert for ModelPaths {
21356
21488
  fn try_convert(val: magnus::Value) -> Result<Self, magnus::Error> {
21357
21489
  if let Ok(r) = <&ModelPaths as magnus::TryConvert>::try_convert(val) {
@@ -21376,10 +21508,8 @@ impl magnus::TryConvert for ModelPaths {
21376
21508
  }
21377
21509
  }
21378
21510
 
21379
- #[cfg(feature = "paddle-ocr-types")]
21380
21511
  unsafe impl TryConvertOwned for ModelPaths {}
21381
21512
 
21382
- #[cfg(feature = "paddle-ocr-types")]
21383
21513
  impl ModelPaths {
21384
21514
  fn new(args: &[magnus::Value]) -> Result<Self, magnus::Error> {
21385
21515
  let ruby = unsafe { magnus::Ruby::get_unchecked() };
@@ -21443,7 +21573,7 @@ impl ModelPaths {
21443
21573
  }
21444
21574
  }
21445
21575
 
21446
- #[cfg(feature = "late-interaction-presets")]
21576
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
21447
21577
  #[derive(Clone, Debug, serde::Serialize, serde::Deserialize)]
21448
21578
  #[magnus::wrap(class = "Xberg::MultiVectorEmbedding")]
21449
21579
  pub struct MultiVectorEmbedding {
@@ -21452,10 +21582,10 @@ pub struct MultiVectorEmbedding {
21452
21582
  data: Vec<f32>,
21453
21583
  }
21454
21584
 
21455
- #[cfg(feature = "late-interaction-presets")]
21585
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
21456
21586
  unsafe impl IntoValueFromNative for MultiVectorEmbedding {}
21457
21587
 
21458
- #[cfg(feature = "late-interaction-presets")]
21588
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
21459
21589
  impl magnus::TryConvert for MultiVectorEmbedding {
21460
21590
  fn try_convert(val: magnus::Value) -> Result<Self, magnus::Error> {
21461
21591
  if let Ok(r) = <&MultiVectorEmbedding as magnus::TryConvert>::try_convert(val) {
@@ -21480,10 +21610,10 @@ impl magnus::TryConvert for MultiVectorEmbedding {
21480
21610
  }
21481
21611
  }
21482
21612
 
21483
- #[cfg(feature = "late-interaction-presets")]
21613
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
21484
21614
  unsafe impl TryConvertOwned for MultiVectorEmbedding {}
21485
21615
 
21486
- #[cfg(feature = "late-interaction-presets")]
21616
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
21487
21617
  impl MultiVectorEmbedding {
21488
21618
  fn new(args: &[magnus::Value]) -> Result<Self, magnus::Error> {
21489
21619
  let ruby = unsafe { magnus::Ruby::get_unchecked() };
@@ -22093,6 +22223,7 @@ pub struct OcrConfig {
22093
22223
  tesseract_config: Option<TesseractConfig>,
22094
22224
  output_format: Option<OutputFormat>,
22095
22225
  paddle_ocr_config: Option<String>,
22226
+ paddle_ocr_settings: Option<PaddleOcrConfig>,
22096
22227
  backend_options: Option<String>,
22097
22228
  element_config: Option<OcrElementConfig>,
22098
22229
  quality_thresholds: Option<OcrQualityThresholds>,
@@ -22211,6 +22342,18 @@ impl OcrConfig {
22211
22342
  })?),
22212
22343
  None => None,
22213
22344
  },
22345
+ paddle_ocr_settings: match kwargs
22346
+ .get(ruby.to_symbol("paddle_ocr_settings"))
22347
+ .filter(|v| !v.is_nil())
22348
+ {
22349
+ Some(v) => Some(PaddleOcrConfig::try_convert(v).map_err(|e| {
22350
+ magnus::Error::new(
22351
+ unsafe { magnus::Ruby::get_unchecked() }.exception_type_error(),
22352
+ format!("invalid value for `paddle_ocr_settings`: {}", e),
22353
+ )
22354
+ })?),
22355
+ None => None,
22356
+ },
22214
22357
  backend_options: match kwargs.get(ruby.to_symbol("backend_options")).filter(|v| !v.is_nil()) {
22215
22358
  Some(v) => Some(String::try_convert(v).map_err(|e| {
22216
22359
  magnus::Error::new(
@@ -22355,6 +22498,10 @@ impl OcrConfig {
22355
22498
  self.paddle_ocr_config.clone()
22356
22499
  }
22357
22500
 
22501
+ fn paddle_ocr_settings(&self) -> Option<PaddleOcrConfig> {
22502
+ self.paddle_ocr_settings.clone()
22503
+ }
22504
+
22358
22505
  fn backend_options(&self) -> Option<String> {
22359
22506
  self.backend_options.clone()
22360
22507
  }
@@ -23065,6 +23212,7 @@ pub struct OcrPipelineStage {
23065
23212
  language: Option<Vec<String>>,
23066
23213
  tesseract_config: Option<TesseractConfig>,
23067
23214
  paddle_ocr_config: Option<String>,
23215
+ paddle_ocr_settings: Option<PaddleOcrConfig>,
23068
23216
  vlm_config: Option<LlmConfig>,
23069
23217
  backend_options: Option<String>,
23070
23218
  }
@@ -23113,6 +23261,7 @@ impl Default for OcrPipelineStage {
23113
23261
  language: None,
23114
23262
  tesseract_config: None,
23115
23263
  paddle_ocr_config: None,
23264
+ paddle_ocr_settings: None,
23116
23265
  vlm_config: None,
23117
23266
  backend_options: None,
23118
23267
  }
@@ -23171,6 +23320,18 @@ impl OcrPipelineStage {
23171
23320
  })?),
23172
23321
  None => None,
23173
23322
  },
23323
+ paddle_ocr_settings: match kwargs
23324
+ .get(ruby.to_symbol("paddle_ocr_settings"))
23325
+ .filter(|v| !v.is_nil())
23326
+ {
23327
+ Some(v) => Some(PaddleOcrConfig::try_convert(v).map_err(|e| {
23328
+ magnus::Error::new(
23329
+ unsafe { magnus::Ruby::get_unchecked() }.exception_type_error(),
23330
+ format!("invalid value for `paddle_ocr_settings`: {}", e),
23331
+ )
23332
+ })?),
23333
+ None => None,
23334
+ },
23174
23335
  vlm_config: match kwargs.get(ruby.to_symbol("vlm_config")).filter(|v| !v.is_nil()) {
23175
23336
  Some(v) => Some(LlmConfig::try_convert(v).map_err(|e| {
23176
23337
  magnus::Error::new(
@@ -23212,6 +23373,10 @@ impl OcrPipelineStage {
23212
23373
  self.paddle_ocr_config.clone()
23213
23374
  }
23214
23375
 
23376
+ fn paddle_ocr_settings(&self) -> Option<PaddleOcrConfig> {
23377
+ self.paddle_ocr_settings.clone()
23378
+ }
23379
+
23215
23380
  fn vlm_config(&self) -> Option<LlmConfig> {
23216
23381
  self.vlm_config.clone()
23217
23382
  }
@@ -24095,7 +24260,6 @@ impl OrientationResult {
24095
24260
  }
24096
24261
  }
24097
24262
 
24098
- #[cfg(feature = "paddle-ocr-types")]
24099
24263
  #[derive(Clone, Debug, serde::Serialize)]
24100
24264
  #[serde(default)]
24101
24265
  #[magnus::wrap(class = "Xberg::PaddleOcrConfig")]
@@ -24116,10 +24280,8 @@ pub struct PaddleOcrConfig {
24116
24280
  inference_backend: Option<PaddleInferenceBackend>,
24117
24281
  }
24118
24282
 
24119
- #[cfg(feature = "paddle-ocr-types")]
24120
24283
  unsafe impl IntoValueFromNative for PaddleOcrConfig {}
24121
24284
 
24122
- #[cfg(feature = "paddle-ocr-types")]
24123
24285
  impl magnus::TryConvert for PaddleOcrConfig {
24124
24286
  fn try_convert(val: magnus::Value) -> Result<Self, magnus::Error> {
24125
24287
  if let Ok(r) = <&PaddleOcrConfig as magnus::TryConvert>::try_convert(val) {
@@ -24144,9 +24306,7 @@ impl magnus::TryConvert for PaddleOcrConfig {
24144
24306
  }
24145
24307
  }
24146
24308
 
24147
- #[cfg(feature = "paddle-ocr-types")]
24148
24309
  unsafe impl TryConvertOwned for PaddleOcrConfig {}
24149
- #[cfg(feature = "paddle-ocr-types")]
24150
24310
  impl<'de> serde::Deserialize<'de> for PaddleOcrConfig {
24151
24311
  fn deserialize<D>(deserializer: D) -> ::core::result::Result<Self, D::Error>
24152
24312
  where
@@ -24156,14 +24316,12 @@ impl<'de> serde::Deserialize<'de> for PaddleOcrConfig {
24156
24316
  }
24157
24317
  }
24158
24318
 
24159
- #[cfg(feature = "paddle-ocr-types")]
24160
24319
  impl Default for PaddleOcrConfig {
24161
24320
  fn default() -> Self {
24162
24321
  xberg::PaddleOcrConfig::default().into()
24163
24322
  }
24164
24323
  }
24165
24324
 
24166
- #[cfg(feature = "paddle-ocr-types")]
24167
24325
  impl PaddleOcrConfig {
24168
24326
  fn new(args: &[magnus::Value]) -> Result<Self, magnus::Error> {
24169
24327
  let ruby = unsafe { magnus::Ruby::get_unchecked() };
@@ -29681,6 +29839,10 @@ pub struct RedactionConfig {
29681
29839
  preserve_offsets: bool,
29682
29840
  custom_terms: Vec<RedactionTerm>,
29683
29841
  custom_patterns: Vec<RedactionPattern>,
29842
+ findings: Vec<ExternalRedactionFinding>,
29843
+ min_score: Option<f32>,
29844
+ findings_path: Option<String>,
29845
+ findings_offset_encoding: RedactionOffsetEncoding,
29684
29846
  }
29685
29847
 
29686
29848
  unsafe impl IntoValueFromNative for RedactionConfig {}
@@ -29786,6 +29948,42 @@ impl RedactionConfig {
29786
29948
  })?,
29787
29949
  None => Default::default(),
29788
29950
  },
29951
+ findings: match kwargs.get(ruby.to_symbol("findings")) {
29952
+ Some(v) => <Vec<ExternalRedactionFinding>>::try_convert(v).map_err(|e| {
29953
+ magnus::Error::new(
29954
+ unsafe { magnus::Ruby::get_unchecked() }.exception_type_error(),
29955
+ format!("invalid value for `findings`: {}", e),
29956
+ )
29957
+ })?,
29958
+ None => Default::default(),
29959
+ },
29960
+ min_score: match kwargs.get(ruby.to_symbol("min_score")).filter(|v| !v.is_nil()) {
29961
+ Some(v) => Some(f32::try_convert(v).map_err(|e| {
29962
+ magnus::Error::new(
29963
+ unsafe { magnus::Ruby::get_unchecked() }.exception_type_error(),
29964
+ format!("invalid value for `min_score`: {}", e),
29965
+ )
29966
+ })?),
29967
+ None => None,
29968
+ },
29969
+ findings_path: match kwargs.get(ruby.to_symbol("findings_path")).filter(|v| !v.is_nil()) {
29970
+ Some(v) => Some(String::try_convert(v).map_err(|e| {
29971
+ magnus::Error::new(
29972
+ unsafe { magnus::Ruby::get_unchecked() }.exception_type_error(),
29973
+ format!("invalid value for `findings_path`: {}", e),
29974
+ )
29975
+ })?),
29976
+ None => None,
29977
+ },
29978
+ findings_offset_encoding: match kwargs.get(ruby.to_symbol("findings_offset_encoding")) {
29979
+ Some(v) => RedactionOffsetEncoding::try_convert(v).map_err(|e| {
29980
+ magnus::Error::new(
29981
+ unsafe { magnus::Ruby::get_unchecked() }.exception_type_error(),
29982
+ format!("invalid value for `findings_offset_encoding`: {}", e),
29983
+ )
29984
+ })?,
29985
+ None => RedactionOffsetEncoding::UnicodeCodePoints,
29986
+ },
29789
29987
  })
29790
29988
  }
29791
29989
 
@@ -29813,6 +30011,22 @@ impl RedactionConfig {
29813
30011
  self.custom_patterns.clone()
29814
30012
  }
29815
30013
 
30014
+ fn findings(&self) -> Vec<ExternalRedactionFinding> {
30015
+ self.findings.clone()
30016
+ }
30017
+
30018
+ fn min_score(&self) -> Option<f32> {
30019
+ self.min_score
30020
+ }
30021
+
30022
+ fn findings_path(&self) -> Option<String> {
30023
+ self.findings_path.clone()
30024
+ }
30025
+
30026
+ fn findings_offset_encoding(&self) -> RedactionOffsetEncoding {
30027
+ self.findings_offset_encoding.clone()
30028
+ }
30029
+
29816
30030
  fn validate(&self) -> Result<(), Error> {
29817
30031
  #[allow(clippy::needless_update)]
29818
30032
  let core_self = xberg::RedactionConfig {
@@ -29828,6 +30042,14 @@ impl RedactionConfig {
29828
30042
 
29829
30043
  custom_patterns: self.custom_patterns.clone().into_iter().map(Into::into).collect(),
29830
30044
 
30045
+ findings: self.findings.clone().into_iter().map(Into::into).collect(),
30046
+
30047
+ min_score: self.min_score,
30048
+
30049
+ findings_path: self.findings_path.clone().map(Into::into),
30050
+
30051
+ findings_offset_encoding: self.findings_offset_encoding.clone().into(),
30052
+
29831
30053
  ..Default::default()
29832
30054
  };
29833
30055
  let result = core_self.validate().map_err(|e| {
@@ -30313,7 +30535,10 @@ impl Registry {
30313
30535
  }
30314
30536
  }
30315
30537
 
30316
- #[cfg(any(feature = "reranker-presets", feature = "reranker"))]
30538
+ #[cfg(any(
30539
+ any(feature = "reranker-presets", feature = "reranker"),
30540
+ not(feature = "reranker-presets")
30541
+ ))]
30317
30542
  #[derive(Clone, Debug, serde::Serialize, serde::Deserialize)]
30318
30543
  #[magnus::wrap(class = "Xberg::RerankedDocument")]
30319
30544
  pub struct RerankedDocument {
@@ -30322,10 +30547,16 @@ pub struct RerankedDocument {
30322
30547
  document: String,
30323
30548
  }
30324
30549
 
30325
- #[cfg(any(feature = "reranker-presets", feature = "reranker"))]
30550
+ #[cfg(any(
30551
+ any(feature = "reranker-presets", feature = "reranker"),
30552
+ not(feature = "reranker-presets")
30553
+ ))]
30326
30554
  unsafe impl IntoValueFromNative for RerankedDocument {}
30327
30555
 
30328
- #[cfg(any(feature = "reranker-presets", feature = "reranker"))]
30556
+ #[cfg(any(
30557
+ any(feature = "reranker-presets", feature = "reranker"),
30558
+ not(feature = "reranker-presets")
30559
+ ))]
30329
30560
  impl magnus::TryConvert for RerankedDocument {
30330
30561
  fn try_convert(val: magnus::Value) -> Result<Self, magnus::Error> {
30331
30562
  if let Ok(r) = <&RerankedDocument as magnus::TryConvert>::try_convert(val) {
@@ -30350,10 +30581,16 @@ impl magnus::TryConvert for RerankedDocument {
30350
30581
  }
30351
30582
  }
30352
30583
 
30353
- #[cfg(any(feature = "reranker-presets", feature = "reranker"))]
30584
+ #[cfg(any(
30585
+ any(feature = "reranker-presets", feature = "reranker"),
30586
+ not(feature = "reranker-presets")
30587
+ ))]
30354
30588
  unsafe impl TryConvertOwned for RerankedDocument {}
30355
30589
 
30356
- #[cfg(any(feature = "reranker-presets", feature = "reranker"))]
30590
+ #[cfg(any(
30591
+ any(feature = "reranker-presets", feature = "reranker"),
30592
+ not(feature = "reranker-presets")
30593
+ ))]
30357
30594
  impl RerankedDocument {
30358
30595
  fn new(args: &[magnus::Value]) -> Result<Self, magnus::Error> {
30359
30596
  let ruby = unsafe { magnus::Ruby::get_unchecked() };
@@ -31411,7 +31648,7 @@ impl SitemapUrl {
31411
31648
  }
31412
31649
  }
31413
31650
 
31414
- #[cfg(feature = "sparse-embedding-presets")]
31651
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
31415
31652
  #[derive(Clone, Debug, serde::Serialize, serde::Deserialize)]
31416
31653
  #[magnus::wrap(class = "Xberg::SparseEmbedding")]
31417
31654
  pub struct SparseEmbedding {
@@ -31419,10 +31656,10 @@ pub struct SparseEmbedding {
31419
31656
  values: Vec<f32>,
31420
31657
  }
31421
31658
 
31422
- #[cfg(feature = "sparse-embedding-presets")]
31659
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
31423
31660
  unsafe impl IntoValueFromNative for SparseEmbedding {}
31424
31661
 
31425
- #[cfg(feature = "sparse-embedding-presets")]
31662
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
31426
31663
  impl magnus::TryConvert for SparseEmbedding {
31427
31664
  fn try_convert(val: magnus::Value) -> Result<Self, magnus::Error> {
31428
31665
  if let Ok(r) = <&SparseEmbedding as magnus::TryConvert>::try_convert(val) {
@@ -31447,10 +31684,10 @@ impl magnus::TryConvert for SparseEmbedding {
31447
31684
  }
31448
31685
  }
31449
31686
 
31450
- #[cfg(feature = "sparse-embedding-presets")]
31687
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
31451
31688
  unsafe impl TryConvertOwned for SparseEmbedding {}
31452
31689
 
31453
- #[cfg(feature = "sparse-embedding-presets")]
31690
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
31454
31691
  impl SparseEmbedding {
31455
31692
  fn new(args: &[magnus::Value]) -> Result<Self, magnus::Error> {
31456
31693
  let ruby = unsafe { magnus::Ruby::get_unchecked() };
@@ -31648,7 +31885,7 @@ impl SparseEmbeddingConfig {
31648
31885
  }
31649
31886
  }
31650
31887
 
31651
- #[cfg(feature = "sparse-embedding-presets")]
31888
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
31652
31889
  #[derive(Clone, Debug, serde::Serialize, serde::Deserialize)]
31653
31890
  #[magnus::wrap(class = "Xberg::SparseEmbeddingPreset")]
31654
31891
  pub struct SparseEmbeddingPreset {
@@ -31660,10 +31897,10 @@ pub struct SparseEmbeddingPreset {
31660
31897
  description: String,
31661
31898
  }
31662
31899
 
31663
- #[cfg(feature = "sparse-embedding-presets")]
31900
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
31664
31901
  unsafe impl IntoValueFromNative for SparseEmbeddingPreset {}
31665
31902
 
31666
- #[cfg(feature = "sparse-embedding-presets")]
31903
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
31667
31904
  impl magnus::TryConvert for SparseEmbeddingPreset {
31668
31905
  fn try_convert(val: magnus::Value) -> Result<Self, magnus::Error> {
31669
31906
  if let Ok(r) = <&SparseEmbeddingPreset as magnus::TryConvert>::try_convert(val) {
@@ -31688,10 +31925,10 @@ impl magnus::TryConvert for SparseEmbeddingPreset {
31688
31925
  }
31689
31926
  }
31690
31927
 
31691
- #[cfg(feature = "sparse-embedding-presets")]
31928
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
31692
31929
  unsafe impl TryConvertOwned for SparseEmbeddingPreset {}
31693
31930
 
31694
- #[cfg(feature = "sparse-embedding-presets")]
31931
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
31695
31932
  impl SparseEmbeddingPreset {
31696
31933
  fn new(args: &[magnus::Value]) -> Result<Self, magnus::Error> {
31697
31934
  let ruby = unsafe { magnus::Ruby::get_unchecked() };
@@ -36613,6 +36850,59 @@ impl magnus::TryConvert for CandleTrocrVariant {
36613
36850
  unsafe impl IntoValueFromNative for CandleTrocrVariant {}
36614
36851
  unsafe impl TryConvertOwned for CandleTrocrVariant {}
36615
36852
 
36853
+ #[derive(Clone, Copy, PartialEq, Eq, Hash, Debug, serde::Serialize, serde::Deserialize)]
36854
+ #[serde(rename_all = "snake_case")]
36855
+ pub enum CaptionAltTextMode {
36856
+ Preserve,
36857
+ Combine,
36858
+ Replace,
36859
+ }
36860
+
36861
+ impl Default for CaptionAltTextMode {
36862
+ fn default() -> Self {
36863
+ Self::Preserve
36864
+ }
36865
+ }
36866
+
36867
+ impl magnus::IntoValue for CaptionAltTextMode {
36868
+ fn into_value_with(self, handle: &Ruby) -> magnus::Value {
36869
+ let sym = match self {
36870
+ CaptionAltTextMode::Preserve => "preserve",
36871
+ CaptionAltTextMode::Combine => "combine",
36872
+ CaptionAltTextMode::Replace => "replace",
36873
+ };
36874
+ handle.to_symbol(sym).into_value_with(handle)
36875
+ }
36876
+ }
36877
+
36878
+ impl magnus::TryConvert for CaptionAltTextMode {
36879
+ fn try_convert(val: magnus::Value) -> Result<Self, magnus::Error> {
36880
+ // IntoValue emits Symbols, including when this enum is a Hash key.
36881
+ // Accept that exact representation as well as String inputs; do not
36882
+ // coerce arbitrary objects through to_s.
36883
+ let s: String = if let Some(symbol) = magnus::Symbol::from_value(val) {
36884
+ symbol.name()?.into_owned()
36885
+ } else {
36886
+ magnus::TryConvert::try_convert(val)?
36887
+ };
36888
+ // Accept the real serde wire value, the legacy always-snake_case symbol Magnus used to
36889
+ // emit unconditionally, and the verbatim PascalCase Rust variant name, so fixtures and
36890
+ // existing consumer code written in any of those styles keep working.
36891
+ match s.as_str() {
36892
+ "preserve" | "Preserve" => Ok(CaptionAltTextMode::Preserve),
36893
+ "combine" | "Combine" => Ok(CaptionAltTextMode::Combine),
36894
+ "replace" | "Replace" => Ok(CaptionAltTextMode::Replace),
36895
+ other => Err(magnus::Error::new(
36896
+ unsafe { Ruby::get_unchecked() }.exception_arg_error(),
36897
+ format!("invalid CaptionAltTextMode value: {other}"),
36898
+ )),
36899
+ }
36900
+ }
36901
+ }
36902
+
36903
+ unsafe impl IntoValueFromNative for CaptionAltTextMode {}
36904
+ unsafe impl TryConvertOwned for CaptionAltTextMode {}
36905
+
36616
36906
  #[derive(Clone, Debug, serde::Serialize, serde::Deserialize)]
36617
36907
  #[serde(tag = "type")]
36618
36908
  #[serde(rename_all = "snake_case")]
@@ -41104,6 +41394,59 @@ impl magnus::TryConvert for ProcessingStage {
41104
41394
  unsafe impl IntoValueFromNative for ProcessingStage {}
41105
41395
  unsafe impl TryConvertOwned for ProcessingStage {}
41106
41396
 
41397
+ #[derive(Clone, Copy, PartialEq, Eq, Hash, Debug, serde::Serialize, serde::Deserialize)]
41398
+ #[serde(rename_all = "snake_case")]
41399
+ pub enum RedactionOffsetEncoding {
41400
+ Utf8Bytes,
41401
+ UnicodeCodePoints,
41402
+ Utf16CodeUnits,
41403
+ }
41404
+
41405
+ impl Default for RedactionOffsetEncoding {
41406
+ fn default() -> Self {
41407
+ Self::UnicodeCodePoints
41408
+ }
41409
+ }
41410
+
41411
+ impl magnus::IntoValue for RedactionOffsetEncoding {
41412
+ fn into_value_with(self, handle: &Ruby) -> magnus::Value {
41413
+ let sym = match self {
41414
+ RedactionOffsetEncoding::Utf8Bytes => "utf8_bytes",
41415
+ RedactionOffsetEncoding::UnicodeCodePoints => "unicode_code_points",
41416
+ RedactionOffsetEncoding::Utf16CodeUnits => "utf16_code_units",
41417
+ };
41418
+ handle.to_symbol(sym).into_value_with(handle)
41419
+ }
41420
+ }
41421
+
41422
+ impl magnus::TryConvert for RedactionOffsetEncoding {
41423
+ fn try_convert(val: magnus::Value) -> Result<Self, magnus::Error> {
41424
+ // IntoValue emits Symbols, including when this enum is a Hash key.
41425
+ // Accept that exact representation as well as String inputs; do not
41426
+ // coerce arbitrary objects through to_s.
41427
+ let s: String = if let Some(symbol) = magnus::Symbol::from_value(val) {
41428
+ symbol.name()?.into_owned()
41429
+ } else {
41430
+ magnus::TryConvert::try_convert(val)?
41431
+ };
41432
+ // Accept the real serde wire value, the legacy always-snake_case symbol Magnus used to
41433
+ // emit unconditionally, and the verbatim PascalCase Rust variant name, so fixtures and
41434
+ // existing consumer code written in any of those styles keep working.
41435
+ match s.as_str() {
41436
+ "utf8_bytes" | "Utf8Bytes" => Ok(RedactionOffsetEncoding::Utf8Bytes),
41437
+ "unicode_code_points" | "UnicodeCodePoints" => Ok(RedactionOffsetEncoding::UnicodeCodePoints),
41438
+ "utf16_code_units" | "Utf16CodeUnits" => Ok(RedactionOffsetEncoding::Utf16CodeUnits),
41439
+ other => Err(magnus::Error::new(
41440
+ unsafe { Ruby::get_unchecked() }.exception_arg_error(),
41441
+ format!("invalid RedactionOffsetEncoding value: {other}"),
41442
+ )),
41443
+ }
41444
+ }
41445
+ }
41446
+
41447
+ unsafe impl IntoValueFromNative for RedactionOffsetEncoding {}
41448
+ unsafe impl TryConvertOwned for RedactionOffsetEncoding {}
41449
+
41107
41450
  #[derive(Clone, Copy, PartialEq, Eq, Hash, Debug, serde::Serialize, serde::Deserialize)]
41108
41451
  #[serde(rename_all = "snake_case")]
41109
41452
  pub enum RedactionStrategy {
@@ -42701,6 +43044,130 @@ fn extract_batch_async(args: &[magnus::Value]) -> Result<ExtractionResult, Error
42701
43044
  Ok(result.into())
42702
43045
  }
42703
43046
 
43047
+ #[cfg(feature = "redaction")]
43048
+ fn extract_with_external_redaction(args: &[magnus::Value]) -> Result<ExtractionResult, Error> {
43049
+ let args = magnus::scan_args::scan_args::<
43050
+ (magnus::Value, magnus::Value, String),
43051
+ (Option<magnus::Value>, Option<u32>),
43052
+ (),
43053
+ (),
43054
+ (),
43055
+ (),
43056
+ >(args)?;
43057
+ let (input, config, findings_json) = args.required;
43058
+
43059
+ let (offset_encoding, max_findings) = args.optional;
43060
+
43061
+ let offset_encoding: Option<String> = offset_encoding.and_then(|v| {
43062
+ if v.is_nil() {
43063
+ None
43064
+ } else {
43065
+ Some(String::try_convert(v).unwrap_or_default())
43066
+ }
43067
+ });
43068
+
43069
+ let input_core: xberg::ExtractInput = {
43070
+ let binding_val: ExtractInput = ExtractInput::try_convert(input).map_err(|e| {
43071
+ magnus::Error::new(
43072
+ unsafe { Ruby::get_unchecked() }.exception_runtime_error(),
43073
+ e.to_string(),
43074
+ )
43075
+ })?;
43076
+ binding_val.into()
43077
+ };
43078
+ let config_core: xberg::ExtractionConfig = {
43079
+ let binding_val: ExtractionConfig = ExtractionConfig::try_convert(config).map_err(|e| {
43080
+ magnus::Error::new(
43081
+ unsafe { Ruby::get_unchecked() }.exception_runtime_error(),
43082
+ e.to_string(),
43083
+ )
43084
+ })?;
43085
+ binding_val.into()
43086
+ };
43087
+ let async_result = alef_magnus_run_without_gvl(move || -> Result<_, String> {
43088
+ let rt = tokio::runtime::Builder::new_current_thread()
43089
+ .enable_all()
43090
+ .build()
43091
+ .map_err(|e| e.to_string())?;
43092
+ rt.block_on(async {
43093
+ xberg::extract_with_external_redaction(
43094
+ input_core,
43095
+ &config_core,
43096
+ &findings_json,
43097
+ offset_encoding.as_deref(),
43098
+ max_findings,
43099
+ )
43100
+ .await
43101
+ })
43102
+ .map_err(|e| e.to_string())
43103
+ });
43104
+ let result = async_result
43105
+ .map_err(|message| magnus::Error::new(unsafe { Ruby::get_unchecked() }.exception_runtime_error(), message))?;
43106
+ Ok(result.into())
43107
+ }
43108
+
43109
+ #[cfg(feature = "redaction")]
43110
+ fn extract_with_external_redaction_async(args: &[magnus::Value]) -> Result<ExtractionResult, Error> {
43111
+ let args = magnus::scan_args::scan_args::<
43112
+ (magnus::Value, magnus::Value, String),
43113
+ (Option<magnus::Value>, Option<u32>),
43114
+ (),
43115
+ (),
43116
+ (),
43117
+ (),
43118
+ >(args)?;
43119
+ let (input, config, findings_json) = args.required;
43120
+
43121
+ let (offset_encoding, max_findings) = args.optional;
43122
+
43123
+ let offset_encoding: Option<String> = offset_encoding.and_then(|v| {
43124
+ if v.is_nil() {
43125
+ None
43126
+ } else {
43127
+ Some(String::try_convert(v).unwrap_or_default())
43128
+ }
43129
+ });
43130
+
43131
+ let input_core: xberg::ExtractInput = {
43132
+ let binding_val: ExtractInput = ExtractInput::try_convert(input).map_err(|e| {
43133
+ magnus::Error::new(
43134
+ unsafe { Ruby::get_unchecked() }.exception_runtime_error(),
43135
+ e.to_string(),
43136
+ )
43137
+ })?;
43138
+ binding_val.into()
43139
+ };
43140
+ let config_core: xberg::ExtractionConfig = {
43141
+ let binding_val: ExtractionConfig = ExtractionConfig::try_convert(config).map_err(|e| {
43142
+ magnus::Error::new(
43143
+ unsafe { Ruby::get_unchecked() }.exception_runtime_error(),
43144
+ e.to_string(),
43145
+ )
43146
+ })?;
43147
+ binding_val.into()
43148
+ };
43149
+ let async_result = alef_magnus_run_without_gvl(move || -> Result<_, String> {
43150
+ let rt = tokio::runtime::Builder::new_current_thread()
43151
+ .enable_all()
43152
+ .build()
43153
+ .map_err(|e| e.to_string())?;
43154
+ rt.block_on(async {
43155
+ xberg::extract_with_external_redaction(
43156
+ input_core,
43157
+ &config_core,
43158
+ &findings_json,
43159
+ offset_encoding.as_deref(),
43160
+ max_findings,
43161
+ )
43162
+ .await
43163
+ })
43164
+ .map_err(|e| e.to_string())
43165
+ });
43166
+ let result = async_result
43167
+ .map_err(|message| magnus::Error::new(unsafe { Ruby::get_unchecked() }.exception_runtime_error(), message))?;
43168
+ Ok(result.into())
43169
+ }
43170
+
42704
43171
  #[cfg(feature = "markdown-footnotes")]
42705
43172
  fn find_unmarked_claims(markdown: String) -> Vec<String> {
42706
43173
  xberg::find_unmarked_claims(&markdown)
@@ -42997,6 +43464,114 @@ fn pdf_page_count(args: &[magnus::Value]) -> Result<usize, Error> {
42997
43464
  Ok(result)
42998
43465
  }
42999
43466
 
43467
+ #[cfg(feature = "redaction")]
43468
+ fn redact_external(args: &[magnus::Value]) -> Result<ExtractedDocument, Error> {
43469
+ let args = magnus::scan_args::scan_args::<
43470
+ (magnus::Value, magnus::Value, String),
43471
+ (Option<magnus::Value>, Option<u32>),
43472
+ (),
43473
+ (),
43474
+ (),
43475
+ (),
43476
+ >(args)?;
43477
+ let (document, config, findings_json) = args.required;
43478
+
43479
+ let (offset_encoding, max_findings) = args.optional;
43480
+
43481
+ let offset_encoding: Option<String> = offset_encoding.and_then(|v| {
43482
+ if v.is_nil() {
43483
+ None
43484
+ } else {
43485
+ Some(String::try_convert(v).unwrap_or_default())
43486
+ }
43487
+ });
43488
+
43489
+ let document: xberg::ExtractedDocument = {
43490
+ let binding_val: ExtractedDocument = ExtractedDocument::try_convert(document)
43491
+ .map_err(|e| magnus::Error::new(unsafe { Ruby::get_unchecked() }.exception_type_error(), e.to_string()))?;
43492
+ binding_val.into()
43493
+ };
43494
+ let config: xberg::RedactionConfig = {
43495
+ let binding_val: RedactionConfig = RedactionConfig::try_convert(config)
43496
+ .map_err(|e| magnus::Error::new(unsafe { Ruby::get_unchecked() }.exception_type_error(), e.to_string()))?;
43497
+ binding_val.into()
43498
+ };
43499
+ let async_result = alef_magnus_run_without_gvl(move || -> Result<_, String> {
43500
+ let rt = tokio::runtime::Builder::new_current_thread()
43501
+ .enable_all()
43502
+ .build()
43503
+ .map_err(|e| e.to_string())?;
43504
+ rt.block_on(async {
43505
+ xberg::redact_external(
43506
+ document.into(),
43507
+ config.into(),
43508
+ &findings_json,
43509
+ offset_encoding.as_deref(),
43510
+ max_findings,
43511
+ )
43512
+ .await
43513
+ })
43514
+ .map_err(|e| e.to_string())
43515
+ });
43516
+ let result = async_result
43517
+ .map_err(|message| magnus::Error::new(unsafe { Ruby::get_unchecked() }.exception_runtime_error(), message))?;
43518
+ Ok(result.into())
43519
+ }
43520
+
43521
+ #[cfg(feature = "redaction")]
43522
+ fn redact_external_async(args: &[magnus::Value]) -> Result<ExtractedDocument, Error> {
43523
+ let args = magnus::scan_args::scan_args::<
43524
+ (magnus::Value, magnus::Value, String),
43525
+ (Option<magnus::Value>, Option<u32>),
43526
+ (),
43527
+ (),
43528
+ (),
43529
+ (),
43530
+ >(args)?;
43531
+ let (document, config, findings_json) = args.required;
43532
+
43533
+ let (offset_encoding, max_findings) = args.optional;
43534
+
43535
+ let offset_encoding: Option<String> = offset_encoding.and_then(|v| {
43536
+ if v.is_nil() {
43537
+ None
43538
+ } else {
43539
+ Some(String::try_convert(v).unwrap_or_default())
43540
+ }
43541
+ });
43542
+
43543
+ let document: xberg::ExtractedDocument = {
43544
+ let binding_val: ExtractedDocument = ExtractedDocument::try_convert(document)
43545
+ .map_err(|e| magnus::Error::new(unsafe { Ruby::get_unchecked() }.exception_type_error(), e.to_string()))?;
43546
+ binding_val.into()
43547
+ };
43548
+ let config: xberg::RedactionConfig = {
43549
+ let binding_val: RedactionConfig = RedactionConfig::try_convert(config)
43550
+ .map_err(|e| magnus::Error::new(unsafe { Ruby::get_unchecked() }.exception_type_error(), e.to_string()))?;
43551
+ binding_val.into()
43552
+ };
43553
+ let async_result = alef_magnus_run_without_gvl(move || -> Result<_, String> {
43554
+ let rt = tokio::runtime::Builder::new_current_thread()
43555
+ .enable_all()
43556
+ .build()
43557
+ .map_err(|e| e.to_string())?;
43558
+ rt.block_on(async {
43559
+ xberg::redact_external(
43560
+ document.into(),
43561
+ config.into(),
43562
+ &findings_json,
43563
+ offset_encoding.as_deref(),
43564
+ max_findings,
43565
+ )
43566
+ .await
43567
+ })
43568
+ .map_err(|e| e.to_string())
43569
+ });
43570
+ let result = async_result
43571
+ .map_err(|message| magnus::Error::new(unsafe { Ruby::get_unchecked() }.exception_runtime_error(), message))?;
43572
+ Ok(result.into())
43573
+ }
43574
+
43000
43575
  #[cfg(feature = "markdown-footnotes")]
43001
43576
  fn verify_excerpt(excerpt: String, source_text: String) -> bool {
43002
43577
  xberg::verify_excerpt(&excerpt, &source_text)
@@ -47731,6 +48306,7 @@ impl From<CaptioningConfig> for xberg::CaptioningConfig {
47731
48306
  llm: val.llm.into(),
47732
48307
  prompt: val.prompt,
47733
48308
  min_image_area: val.min_image_area,
48309
+ alt_text: val.alt_text.into(),
47734
48310
  }
47735
48311
  }
47736
48312
  }
@@ -47742,6 +48318,7 @@ impl From<xberg::CaptioningConfig> for CaptioningConfig {
47742
48318
  llm: val.llm.into(),
47743
48319
  prompt: val.prompt.map(|v| v.to_string()),
47744
48320
  min_image_area: val.min_image_area,
48321
+ alt_text: val.alt_text.into(),
47745
48322
  }
47746
48323
  }
47747
48324
  }
@@ -47775,9 +48352,9 @@ impl From<Chunk> for xberg::Chunk {
47775
48352
  content: val.content,
47776
48353
  chunk_type: val.chunk_type.into(),
47777
48354
  embedding: val.embedding.map(|v| v.into_iter().collect()),
47778
- #[cfg(feature = "sparse-embedding-presets")]
48355
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
47779
48356
  sparse_embedding: val.sparse_embedding.map(Into::into),
47780
- #[cfg(feature = "late-interaction-presets")]
48357
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
47781
48358
  late_interaction: val.late_interaction.map(Into::into),
47782
48359
  metadata: val.metadata.into(),
47783
48360
  }
@@ -47791,9 +48368,9 @@ impl From<xberg::Chunk> for Chunk {
47791
48368
  content: val.content.to_string(),
47792
48369
  chunk_type: val.chunk_type.into(),
47793
48370
  embedding: val.embedding.map(|v| v.into_iter().collect()),
47794
- #[cfg(feature = "sparse-embedding-presets")]
48371
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
47795
48372
  sparse_embedding: val.sparse_embedding.map(Into::into),
47796
- #[cfg(feature = "late-interaction-presets")]
48373
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
47797
48374
  late_interaction: val.late_interaction.map(Into::into),
47798
48375
  metadata: val.metadata.into(),
47799
48376
  }
@@ -49443,6 +50020,33 @@ impl From<xberg::ExcelWorkbook> for ExcelWorkbook {
49443
50020
  }
49444
50021
  }
49445
50022
 
50023
+ #[allow(clippy::needless_update)]
50024
+ impl From<ExternalRedactionFinding> for xberg::ExternalRedactionFinding {
50025
+ fn from(val: ExternalRedactionFinding) -> Self {
50026
+ Self {
50027
+ label: val.label,
50028
+ text: val.text,
50029
+ start: val.start,
50030
+ end: val.end,
50031
+ score: val.score,
50032
+ ..Default::default()
50033
+ }
50034
+ }
50035
+ }
50036
+
50037
+ #[allow(clippy::redundant_closure)]
50038
+ impl From<xberg::ExternalRedactionFinding> for ExternalRedactionFinding {
50039
+ fn from(val: xberg::ExternalRedactionFinding) -> Self {
50040
+ Self {
50041
+ label: val.label.to_string(),
50042
+ text: val.text.map(|v| v.to_string()),
50043
+ start: val.start,
50044
+ end: val.end,
50045
+ score: val.score,
50046
+ }
50047
+ }
50048
+ }
50049
+
49446
50050
  #[allow(clippy::needless_update)]
49447
50051
  #[allow(clippy::redundant_closure, clippy::useless_conversion)]
49448
50052
  impl From<ExtractInput> for xberg::ExtractInput {
@@ -50930,7 +51534,7 @@ impl From<xberg::LateInteractionConfig> for LateInteractionConfig {
50930
51534
  }
50931
51535
  }
50932
51536
 
50933
- #[cfg(feature = "late-interaction-presets")]
51537
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
50934
51538
  impl From<LateInteractionMatch> for xberg::LateInteractionMatch {
50935
51539
  fn from(val: LateInteractionMatch) -> Self {
50936
51540
  Self {
@@ -50940,7 +51544,7 @@ impl From<LateInteractionMatch> for xberg::LateInteractionMatch {
50940
51544
  }
50941
51545
  }
50942
51546
 
50943
- #[cfg(feature = "late-interaction-presets")]
51547
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
50944
51548
  impl From<xberg::LateInteractionMatch> for LateInteractionMatch {
50945
51549
  fn from(val: xberg::LateInteractionMatch) -> Self {
50946
51550
  Self {
@@ -50950,7 +51554,7 @@ impl From<xberg::LateInteractionMatch> for LateInteractionMatch {
50950
51554
  }
50951
51555
  }
50952
51556
 
50953
- #[cfg(feature = "late-interaction-presets")]
51557
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
50954
51558
  impl From<xberg::LateInteractionPreset> for LateInteractionPreset {
50955
51559
  fn from(val: xberg::LateInteractionPreset) -> Self {
50956
51560
  Self {
@@ -51409,7 +52013,6 @@ impl From<xberg::Metadata> for Metadata {
51409
52013
  }
51410
52014
  }
51411
52015
 
51412
- #[cfg(feature = "paddle-ocr-types")]
51413
52016
  impl From<xberg::ModelPaths> for ModelPaths {
51414
52017
  fn from(val: xberg::ModelPaths) -> Self {
51415
52018
  Self {
@@ -51421,7 +52024,7 @@ impl From<xberg::ModelPaths> for ModelPaths {
51421
52024
  }
51422
52025
  }
51423
52026
 
51424
- #[cfg(feature = "late-interaction-presets")]
52027
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
51425
52028
  impl From<MultiVectorEmbedding> for xberg::MultiVectorEmbedding {
51426
52029
  fn from(val: MultiVectorEmbedding) -> Self {
51427
52030
  Self {
@@ -51432,7 +52035,7 @@ impl From<MultiVectorEmbedding> for xberg::MultiVectorEmbedding {
51432
52035
  }
51433
52036
  }
51434
52037
 
51435
- #[cfg(feature = "late-interaction-presets")]
52038
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
51436
52039
  impl From<xberg::MultiVectorEmbedding> for MultiVectorEmbedding {
51437
52040
  fn from(val: xberg::MultiVectorEmbedding) -> Self {
51438
52041
  Self {
@@ -51579,6 +52182,7 @@ impl From<OcrConfig> for xberg::OcrConfig {
51579
52182
  .paddle_ocr_config
51580
52183
  .as_ref()
51581
52184
  .and_then(|s| serde_json::from_str(s).ok()),
52185
+ paddle_ocr_settings: val.paddle_ocr_settings.map(Into::into),
51582
52186
  backend_options: val.backend_options.as_ref().and_then(|s| serde_json::from_str(s).ok()),
51583
52187
  element_config: val.element_config.map(Into::into),
51584
52188
  quality_thresholds: val.quality_thresholds.map(Into::into),
@@ -51609,6 +52213,7 @@ impl From<xberg::OcrConfig> for OcrConfig {
51609
52213
  tesseract_config: val.tesseract_config.map(Into::into),
51610
52214
  output_format: val.output_format.map(Into::into),
51611
52215
  paddle_ocr_config: val.paddle_ocr_config.as_ref().map(ToString::to_string),
52216
+ paddle_ocr_settings: val.paddle_ocr_settings.map(Into::into),
51612
52217
  backend_options: val.backend_options.as_ref().map(ToString::to_string),
51613
52218
  element_config: val.element_config.map(Into::into),
51614
52219
  quality_thresholds: val.quality_thresholds.map(Into::into),
@@ -51773,6 +52378,7 @@ impl From<OcrPipelineStage> for xberg::OcrPipelineStage {
51773
52378
  .paddle_ocr_config
51774
52379
  .as_ref()
51775
52380
  .and_then(|s| serde_json::from_str(s).ok()),
52381
+ paddle_ocr_settings: val.paddle_ocr_settings.map(Into::into),
51776
52382
  vlm_config: val.vlm_config.map(Into::into),
51777
52383
  backend_options: val.backend_options.as_ref().and_then(|s| serde_json::from_str(s).ok()),
51778
52384
  }
@@ -51788,6 +52394,7 @@ impl From<xberg::OcrPipelineStage> for OcrPipelineStage {
51788
52394
  language: val.language.map(|v| v.into_iter().collect()),
51789
52395
  tesseract_config: val.tesseract_config.map(Into::into),
51790
52396
  paddle_ocr_config: val.paddle_ocr_config.as_ref().map(ToString::to_string),
52397
+ paddle_ocr_settings: val.paddle_ocr_settings.map(Into::into),
51791
52398
  vlm_config: val.vlm_config.map(Into::into),
51792
52399
  backend_options: val.backend_options.as_ref().map(ToString::to_string),
51793
52400
  }
@@ -51930,7 +52537,6 @@ impl From<xberg::OrientationResult> for OrientationResult {
51930
52537
  }
51931
52538
  }
51932
52539
 
51933
- #[cfg(feature = "paddle-ocr-types")]
51934
52540
  #[allow(clippy::needless_update)]
51935
52541
  #[allow(clippy::useless_conversion)]
51936
52542
  impl From<PaddleOcrConfig> for xberg::PaddleOcrConfig {
@@ -51955,7 +52561,6 @@ impl From<PaddleOcrConfig> for xberg::PaddleOcrConfig {
51955
52561
  }
51956
52562
  }
51957
52563
 
51958
- #[cfg(feature = "paddle-ocr-types")]
51959
52564
  #[allow(clippy::redundant_closure, clippy::useless_conversion)]
51960
52565
  impl From<xberg::PaddleOcrConfig> for PaddleOcrConfig {
51961
52566
  fn from(val: xberg::PaddleOcrConfig) -> Self {
@@ -52901,12 +53506,16 @@ impl From<RedactionConfig> for xberg::RedactionConfig {
52901
53506
  preserve_offsets: val.preserve_offsets,
52902
53507
  custom_terms: val.custom_terms.into_iter().map(Into::into).collect(),
52903
53508
  custom_patterns: val.custom_patterns.into_iter().map(Into::into).collect(),
53509
+ findings: val.findings.into_iter().map(Into::into).collect(),
53510
+ min_score: val.min_score,
53511
+ findings_path: val.findings_path.map(Into::into),
53512
+ findings_offset_encoding: val.findings_offset_encoding.into(),
52904
53513
  ..Default::default()
52905
53514
  }
52906
53515
  }
52907
53516
  }
52908
53517
 
52909
- #[allow(clippy::useless_conversion)]
53518
+ #[allow(clippy::redundant_closure, clippy::useless_conversion)]
52910
53519
  impl From<xberg::RedactionConfig> for RedactionConfig {
52911
53520
  fn from(val: xberg::RedactionConfig) -> Self {
52912
53521
  Self {
@@ -52916,6 +53525,10 @@ impl From<xberg::RedactionConfig> for RedactionConfig {
52916
53525
  preserve_offsets: val.preserve_offsets,
52917
53526
  custom_terms: val.custom_terms.into_iter().map(Into::into).collect(),
52918
53527
  custom_patterns: val.custom_patterns.into_iter().map(Into::into).collect(),
53528
+ findings: val.findings.into_iter().map(Into::into).collect(),
53529
+ min_score: val.min_score,
53530
+ findings_path: val.findings_path.map(|p| p.to_string_lossy().to_string()),
53531
+ findings_offset_encoding: val.findings_offset_encoding.into(),
52919
53532
  }
52920
53533
  }
52921
53534
  }
@@ -53006,7 +53619,10 @@ impl From<xberg::RedactionTerm> for RedactionTerm {
53006
53619
  }
53007
53620
  }
53008
53621
 
53009
- #[cfg(any(feature = "reranker-presets", feature = "reranker"))]
53622
+ #[cfg(any(
53623
+ any(feature = "reranker-presets", feature = "reranker"),
53624
+ not(feature = "reranker-presets")
53625
+ ))]
53010
53626
  impl From<xberg::RerankedDocument> for RerankedDocument {
53011
53627
  fn from(val: xberg::RerankedDocument) -> Self {
53012
53628
  Self {
@@ -53182,7 +53798,7 @@ impl From<crawlberg::SitemapUrl> for SitemapUrl {
53182
53798
  }
53183
53799
  }
53184
53800
 
53185
- #[cfg(feature = "sparse-embedding-presets")]
53801
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
53186
53802
  impl From<SparseEmbedding> for xberg::SparseEmbedding {
53187
53803
  fn from(val: SparseEmbedding) -> Self {
53188
53804
  Self {
@@ -53192,7 +53808,7 @@ impl From<SparseEmbedding> for xberg::SparseEmbedding {
53192
53808
  }
53193
53809
  }
53194
53810
 
53195
- #[cfg(feature = "sparse-embedding-presets")]
53811
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
53196
53812
  impl From<xberg::SparseEmbedding> for SparseEmbedding {
53197
53813
  fn from(val: xberg::SparseEmbedding) -> Self {
53198
53814
  Self {
@@ -53234,7 +53850,7 @@ impl From<xberg::SparseEmbeddingConfig> for SparseEmbeddingConfig {
53234
53850
  }
53235
53851
  }
53236
53852
 
53237
- #[cfg(feature = "sparse-embedding-presets")]
53853
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
53238
53854
  impl From<xberg::SparseEmbeddingPreset> for SparseEmbeddingPreset {
53239
53855
  fn from(val: xberg::SparseEmbeddingPreset) -> Self {
53240
53856
  Self {
@@ -54289,6 +54905,26 @@ impl From<xberg::candle_ocr::CandleTrocrVariant> for CandleTrocrVariant {
54289
54905
  }
54290
54906
  }
54291
54907
 
54908
+ impl From<CaptionAltTextMode> for xberg::CaptionAltTextMode {
54909
+ fn from(val: CaptionAltTextMode) -> Self {
54910
+ match val {
54911
+ CaptionAltTextMode::Preserve => Self::Preserve,
54912
+ CaptionAltTextMode::Combine => Self::Combine,
54913
+ CaptionAltTextMode::Replace => Self::Replace,
54914
+ }
54915
+ }
54916
+ }
54917
+
54918
+ impl From<xberg::CaptionAltTextMode> for CaptionAltTextMode {
54919
+ fn from(val: xberg::CaptionAltTextMode) -> Self {
54920
+ match val {
54921
+ xberg::CaptionAltTextMode::Preserve => Self::Preserve,
54922
+ xberg::CaptionAltTextMode::Combine => Self::Combine,
54923
+ xberg::CaptionAltTextMode::Replace => Self::Replace,
54924
+ }
54925
+ }
54926
+ }
54927
+
54292
54928
  impl From<ChunkSizing> for xberg::ChunkSizing {
54293
54929
  fn from(val: ChunkSizing) -> Self {
54294
54930
  match val {
@@ -55802,7 +56438,6 @@ impl From<xberg::PSMMode> for PSMMode {
55802
56438
  }
55803
56439
  }
55804
56440
 
55805
- #[cfg(feature = "paddle-ocr-types")]
55806
56441
  impl From<PaddleInferenceBackend> for xberg::PaddleInferenceBackend {
55807
56442
  fn from(val: PaddleInferenceBackend) -> Self {
55808
56443
  match val {
@@ -55812,7 +56447,6 @@ impl From<PaddleInferenceBackend> for xberg::PaddleInferenceBackend {
55812
56447
  }
55813
56448
  }
55814
56449
 
55815
- #[cfg(feature = "paddle-ocr-types")]
55816
56450
  impl From<xberg::PaddleInferenceBackend> for PaddleInferenceBackend {
55817
56451
  fn from(val: xberg::PaddleInferenceBackend) -> Self {
55818
56452
  match val {
@@ -55822,7 +56456,6 @@ impl From<xberg::PaddleInferenceBackend> for PaddleInferenceBackend {
55822
56456
  }
55823
56457
  }
55824
56458
 
55825
- #[cfg(feature = "paddle-ocr-types")]
55826
56459
  impl From<xberg::PaddleLanguage> for PaddleLanguage {
55827
56460
  fn from(val: xberg::PaddleLanguage) -> Self {
55828
56461
  match val {
@@ -56100,6 +56733,26 @@ impl From<xberg::ProcessingStage> for ProcessingStage {
56100
56733
  }
56101
56734
  }
56102
56735
 
56736
+ impl From<RedactionOffsetEncoding> for xberg::RedactionOffsetEncoding {
56737
+ fn from(val: RedactionOffsetEncoding) -> Self {
56738
+ match val {
56739
+ RedactionOffsetEncoding::Utf8Bytes => Self::Utf8Bytes,
56740
+ RedactionOffsetEncoding::UnicodeCodePoints => Self::UnicodeCodePoints,
56741
+ RedactionOffsetEncoding::Utf16CodeUnits => Self::Utf16CodeUnits,
56742
+ }
56743
+ }
56744
+ }
56745
+
56746
+ impl From<xberg::RedactionOffsetEncoding> for RedactionOffsetEncoding {
56747
+ fn from(val: xberg::RedactionOffsetEncoding) -> Self {
56748
+ match val {
56749
+ xberg::RedactionOffsetEncoding::Utf8Bytes => Self::Utf8Bytes,
56750
+ xberg::RedactionOffsetEncoding::UnicodeCodePoints => Self::UnicodeCodePoints,
56751
+ xberg::RedactionOffsetEncoding::Utf16CodeUnits => Self::Utf16CodeUnits,
56752
+ }
56753
+ }
56754
+ }
56755
+
56103
56756
  impl From<RedactionStrategy> for xberg::RedactionStrategy {
56104
56757
  fn from(val: RedactionStrategy) -> Self {
56105
56758
  match val {
@@ -56874,6 +57527,8 @@ fn ruby_init(ruby: &Ruby) -> Result<(), Error> {
56874
57527
 
56875
57528
  class.define_method("min_image_area", method!(CaptioningConfig::min_image_area, 0))?;
56876
57529
 
57530
+ class.define_method("alt_text", method!(CaptioningConfig::alt_text, 0))?;
57531
+
56877
57532
  let class = module.define_class("CellChange", ruby.class_object())?;
56878
57533
 
56879
57534
  class.define_singleton_method("new", function!(CellChange::new, -1))?;
@@ -56896,10 +57551,10 @@ fn ruby_init(ruby: &Ruby) -> Result<(), Error> {
56896
57551
 
56897
57552
  class.define_method("embedding", method!(Chunk::embedding, 0))?;
56898
57553
 
56899
- #[cfg(feature = "sparse-embedding-presets")]
57554
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
56900
57555
  class.define_method("sparse_embedding", method!(Chunk::sparse_embedding, 0))?;
56901
57556
 
56902
- #[cfg(feature = "late-interaction-presets")]
57557
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
56903
57558
  class.define_method("late_interaction", method!(Chunk::late_interaction, 0))?;
56904
57559
 
56905
57560
  class.define_method("metadata", method!(Chunk::metadata, 0))?;
@@ -58096,6 +58751,20 @@ fn ruby_init(ruby: &Ruby) -> Result<(), Error> {
58096
58751
 
58097
58752
  class.define_method("revisions", method!(ExcelWorkbook::revisions, 0))?;
58098
58753
 
58754
+ let class = module.define_class("ExternalRedactionFinding", ruby.class_object())?;
58755
+
58756
+ class.define_singleton_method("new", function!(ExternalRedactionFinding::new, -1))?;
58757
+
58758
+ class.define_method("label", method!(ExternalRedactionFinding::label, 0))?;
58759
+
58760
+ class.define_method("text", method!(ExternalRedactionFinding::text, 0))?;
58761
+
58762
+ class.define_method("start", method!(ExternalRedactionFinding::start, 0))?;
58763
+
58764
+ class.define_method("end", method!(ExternalRedactionFinding::end, 0))?;
58765
+
58766
+ class.define_method("score", method!(ExternalRedactionFinding::score, 0))?;
58767
+
58099
58768
  let class = module.define_class("ExtractInput", ruby.class_object())?;
58100
58769
 
58101
58770
  class.define_singleton_method("new", function!(ExtractInput::new, -1))?;
@@ -59252,42 +59921,42 @@ fn ruby_init(ruby: &Ruby) -> Result<(), Error> {
59252
59921
 
59253
59922
  let class = module.define_class("LateInteractionMatch", ruby.class_object())?;
59254
59923
 
59255
- #[cfg(feature = "late-interaction-presets")]
59924
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
59256
59925
  class.define_singleton_method("new", function!(LateInteractionMatch::new, -1))?;
59257
59926
 
59258
- #[cfg(feature = "late-interaction-presets")]
59927
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
59259
59928
  class.define_method("index", method!(LateInteractionMatch::index, 0))?;
59260
59929
 
59261
- #[cfg(feature = "late-interaction-presets")]
59930
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
59262
59931
  class.define_method("score", method!(LateInteractionMatch::score, 0))?;
59263
59932
 
59264
59933
  let class = module.define_class("LateInteractionPreset", ruby.class_object())?;
59265
59934
 
59266
- #[cfg(feature = "late-interaction-presets")]
59935
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
59267
59936
  class.define_singleton_method("new", function!(LateInteractionPreset::new, -1))?;
59268
59937
 
59269
- #[cfg(feature = "late-interaction-presets")]
59938
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
59270
59939
  class.define_method("name", method!(LateInteractionPreset::name, 0))?;
59271
59940
 
59272
- #[cfg(feature = "late-interaction-presets")]
59941
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
59273
59942
  class.define_method("model_repo", method!(LateInteractionPreset::model_repo, 0))?;
59274
59943
 
59275
- #[cfg(feature = "late-interaction-presets")]
59944
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
59276
59945
  class.define_method("model_file", method!(LateInteractionPreset::model_file, 0))?;
59277
59946
 
59278
- #[cfg(feature = "late-interaction-presets")]
59947
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
59279
59948
  class.define_method("additional_files", method!(LateInteractionPreset::additional_files, 0))?;
59280
59949
 
59281
- #[cfg(feature = "late-interaction-presets")]
59950
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
59282
59951
  class.define_method("max_length", method!(LateInteractionPreset::max_length, 0))?;
59283
59952
 
59284
- #[cfg(feature = "late-interaction-presets")]
59953
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
59285
59954
  class.define_method("query_max_length", method!(LateInteractionPreset::query_max_length, 0))?;
59286
59955
 
59287
- #[cfg(feature = "late-interaction-presets")]
59956
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
59288
59957
  class.define_method("dim", method!(LateInteractionPreset::dim, 0))?;
59289
59958
 
59290
- #[cfg(feature = "late-interaction-presets")]
59959
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
59291
59960
  class.define_method("description", method!(LateInteractionPreset::description, 0))?;
59292
59961
 
59293
59962
  let class = module.define_class("LayoutDetection", ruby.class_object())?;
@@ -59573,36 +60242,31 @@ fn ruby_init(ruby: &Ruby) -> Result<(), Error> {
59573
60242
 
59574
60243
  let class = module.define_class("ModelPaths", ruby.class_object())?;
59575
60244
 
59576
- #[cfg(feature = "paddle-ocr-types")]
59577
60245
  class.define_singleton_method("new", function!(ModelPaths::new, -1))?;
59578
60246
 
59579
- #[cfg(feature = "paddle-ocr-types")]
59580
60247
  class.define_method("det_model", method!(ModelPaths::det_model, 0))?;
59581
60248
 
59582
- #[cfg(feature = "paddle-ocr-types")]
59583
60249
  class.define_method("cls_model", method!(ModelPaths::cls_model, 0))?;
59584
60250
 
59585
- #[cfg(feature = "paddle-ocr-types")]
59586
60251
  class.define_method("rec_model", method!(ModelPaths::rec_model, 0))?;
59587
60252
 
59588
- #[cfg(feature = "paddle-ocr-types")]
59589
60253
  class.define_method("dict_file", method!(ModelPaths::dict_file, 0))?;
59590
60254
 
59591
60255
  let class = module.define_class("MultiVectorEmbedding", ruby.class_object())?;
59592
60256
 
59593
- #[cfg(feature = "late-interaction-presets")]
60257
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
59594
60258
  class.define_singleton_method("new", function!(MultiVectorEmbedding::new, -1))?;
59595
60259
 
59596
- #[cfg(feature = "late-interaction-presets")]
60260
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
59597
60261
  class.define_method("num_tokens", method!(MultiVectorEmbedding::num_tokens, 0))?;
59598
60262
 
59599
- #[cfg(feature = "late-interaction-presets")]
60263
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
59600
60264
  class.define_method("dim", method!(MultiVectorEmbedding::dim, 0))?;
59601
60265
 
59602
- #[cfg(feature = "late-interaction-presets")]
60266
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
59603
60267
  class.define_method("data", method!(MultiVectorEmbedding::data, 0))?;
59604
60268
 
59605
- #[cfg(feature = "late-interaction-presets")]
60269
+ #[cfg(any(feature = "late-interaction-presets", not(feature = "late-interaction-presets")))]
59606
60270
  class.define_method("is_well_formed", method!(MultiVectorEmbedding::is_well_formed, 0))?;
59607
60271
 
59608
60272
  let class = module.define_class("MultidocInput", ruby.class_object())?;
@@ -59690,6 +60354,8 @@ fn ruby_init(ruby: &Ruby) -> Result<(), Error> {
59690
60354
 
59691
60355
  class.define_method("paddle_ocr_config", method!(OcrConfig::paddle_ocr_config, 0))?;
59692
60356
 
60357
+ class.define_method("paddle_ocr_settings", method!(OcrConfig::paddle_ocr_settings, 0))?;
60358
+
59693
60359
  class.define_method("backend_options", method!(OcrConfig::backend_options, 0))?;
59694
60360
 
59695
60361
  class.define_method("element_config", method!(OcrConfig::element_config, 0))?;
@@ -59802,6 +60468,8 @@ fn ruby_init(ruby: &Ruby) -> Result<(), Error> {
59802
60468
 
59803
60469
  class.define_method("paddle_ocr_config", method!(OcrPipelineStage::paddle_ocr_config, 0))?;
59804
60470
 
60471
+ class.define_method("paddle_ocr_settings", method!(OcrPipelineStage::paddle_ocr_settings, 0))?;
60472
+
59805
60473
  class.define_method("vlm_config", method!(OcrPipelineStage::vlm_config, 0))?;
59806
60474
 
59807
60475
  class.define_method("backend_options", method!(OcrPipelineStage::backend_options, 0))?;
@@ -59987,100 +60655,73 @@ fn ruby_init(ruby: &Ruby) -> Result<(), Error> {
59987
60655
 
59988
60656
  let class = module.define_class("PaddleOcrConfig", ruby.class_object())?;
59989
60657
 
59990
- #[cfg(feature = "paddle-ocr-types")]
59991
60658
  class.define_singleton_method("new", function!(PaddleOcrConfig::new, -1))?;
59992
60659
 
59993
- #[cfg(feature = "paddle-ocr-types")]
59994
60660
  class.define_method("language", method!(PaddleOcrConfig::language, 0))?;
59995
60661
 
59996
- #[cfg(feature = "paddle-ocr-types")]
59997
60662
  class.define_method("cache_dir", method!(PaddleOcrConfig::cache_dir, 0))?;
59998
60663
 
59999
- #[cfg(feature = "paddle-ocr-types")]
60000
60664
  class.define_method("use_angle_cls", method!(PaddleOcrConfig::use_angle_cls, 0))?;
60001
60665
 
60002
- #[cfg(feature = "paddle-ocr-types")]
60003
60666
  class.define_method(
60004
60667
  "enable_table_detection",
60005
60668
  method!(PaddleOcrConfig::enable_table_detection, 0),
60006
60669
  )?;
60007
60670
 
60008
- #[cfg(feature = "paddle-ocr-types")]
60009
60671
  class.define_method("det_db_thresh", method!(PaddleOcrConfig::det_db_thresh, 0))?;
60010
60672
 
60011
- #[cfg(feature = "paddle-ocr-types")]
60012
60673
  class.define_method("det_db_box_thresh", method!(PaddleOcrConfig::det_db_box_thresh, 0))?;
60013
60674
 
60014
- #[cfg(feature = "paddle-ocr-types")]
60015
60675
  class.define_method("det_db_unclip_ratio", method!(PaddleOcrConfig::det_db_unclip_ratio, 0))?;
60016
60676
 
60017
- #[cfg(feature = "paddle-ocr-types")]
60018
60677
  class.define_method("det_limit_side_len", method!(PaddleOcrConfig::det_limit_side_len, 0))?;
60019
60678
 
60020
- #[cfg(feature = "paddle-ocr-types")]
60021
60679
  class.define_method("rec_batch_num", method!(PaddleOcrConfig::rec_batch_num, 0))?;
60022
60680
 
60023
- #[cfg(feature = "paddle-ocr-types")]
60024
60681
  class.define_method("padding", method!(PaddleOcrConfig::padding, 0))?;
60025
60682
 
60026
- #[cfg(feature = "paddle-ocr-types")]
60027
60683
  class.define_method("drop_score", method!(PaddleOcrConfig::drop_score, 0))?;
60028
60684
 
60029
- #[cfg(feature = "paddle-ocr-types")]
60030
60685
  class.define_method("model_tier", method!(PaddleOcrConfig::model_tier, 0))?;
60031
60686
 
60032
- #[cfg(feature = "paddle-ocr-types")]
60033
60687
  class.define_method("model_version", method!(PaddleOcrConfig::model_version, 0))?;
60034
60688
 
60035
- #[cfg(feature = "paddle-ocr-types")]
60036
60689
  class.define_method("inference_backend", method!(PaddleOcrConfig::inference_backend, 0))?;
60037
60690
 
60038
- #[cfg(feature = "paddle-ocr-types")]
60039
60691
  class.define_method("with_cache_dir", method!(PaddleOcrConfig::with_cache_dir, 1))?;
60040
60692
 
60041
- #[cfg(feature = "paddle-ocr-types")]
60042
60693
  class.define_method(
60043
60694
  "with_table_detection",
60044
60695
  method!(PaddleOcrConfig::with_table_detection, 1),
60045
60696
  )?;
60046
60697
 
60047
- #[cfg(feature = "paddle-ocr-types")]
60048
60698
  class.define_method("with_angle_cls", method!(PaddleOcrConfig::with_angle_cls, 1))?;
60049
60699
 
60050
- #[cfg(feature = "paddle-ocr-types")]
60051
60700
  class.define_method("with_det_db_thresh", method!(PaddleOcrConfig::with_det_db_thresh, 1))?;
60052
60701
 
60053
- #[cfg(feature = "paddle-ocr-types")]
60054
60702
  class.define_method(
60055
60703
  "with_det_db_box_thresh",
60056
60704
  method!(PaddleOcrConfig::with_det_db_box_thresh, 1),
60057
60705
  )?;
60058
60706
 
60059
- #[cfg(feature = "paddle-ocr-types")]
60060
60707
  class.define_method(
60061
60708
  "with_det_db_unclip_ratio",
60062
60709
  method!(PaddleOcrConfig::with_det_db_unclip_ratio, 1),
60063
60710
  )?;
60064
60711
 
60065
- #[cfg(feature = "paddle-ocr-types")]
60066
60712
  class.define_method(
60067
60713
  "with_det_limit_side_len",
60068
60714
  method!(PaddleOcrConfig::with_det_limit_side_len, 1),
60069
60715
  )?;
60070
60716
 
60071
- #[cfg(feature = "paddle-ocr-types")]
60072
60717
  class.define_method("with_rec_batch_num", method!(PaddleOcrConfig::with_rec_batch_num, 1))?;
60073
60718
 
60074
- #[cfg(feature = "paddle-ocr-types")]
60075
60719
  class.define_method("with_drop_score", method!(PaddleOcrConfig::with_drop_score, 1))?;
60076
60720
 
60077
- #[cfg(feature = "paddle-ocr-types")]
60078
60721
  class.define_method("with_padding", method!(PaddleOcrConfig::with_padding, 1))?;
60079
60722
 
60080
- #[cfg(feature = "paddle-ocr-types")]
60081
60723
  class.define_method("with_model_tier", method!(PaddleOcrConfig::with_model_tier, 1))?;
60082
60724
 
60083
- #[cfg(feature = "paddle-ocr-types")]
60084
60725
  class.define_method("with_model_version", method!(PaddleOcrConfig::with_model_version, 1))?;
60085
60726
 
60086
60727
  let class = module.define_class("PaddleOcrVlBackendOptions", ruby.class_object())?;
@@ -60755,6 +61396,17 @@ fn ruby_init(ruby: &Ruby) -> Result<(), Error> {
60755
61396
 
60756
61397
  class.define_method("custom_patterns", method!(RedactionConfig::custom_patterns, 0))?;
60757
61398
 
61399
+ class.define_method("findings", method!(RedactionConfig::findings, 0))?;
61400
+
61401
+ class.define_method("min_score", method!(RedactionConfig::min_score, 0))?;
61402
+
61403
+ class.define_method("findings_path", method!(RedactionConfig::findings_path, 0))?;
61404
+
61405
+ class.define_method(
61406
+ "findings_offset_encoding",
61407
+ method!(RedactionConfig::findings_offset_encoding, 0),
61408
+ )?;
61409
+
60758
61410
  class.define_method("validate", method!(RedactionConfig::validate, 0))?;
60759
61411
 
60760
61412
  let class = module.define_class("RedactionFinding", ruby.class_object())?;
@@ -60821,16 +61473,28 @@ fn ruby_init(ruby: &Ruby) -> Result<(), Error> {
60821
61473
 
60822
61474
  let class = module.define_class("RerankedDocument", ruby.class_object())?;
60823
61475
 
60824
- #[cfg(any(feature = "reranker-presets", feature = "reranker"))]
61476
+ #[cfg(any(
61477
+ any(feature = "reranker-presets", feature = "reranker"),
61478
+ not(feature = "reranker-presets")
61479
+ ))]
60825
61480
  class.define_singleton_method("new", function!(RerankedDocument::new, -1))?;
60826
61481
 
60827
- #[cfg(any(feature = "reranker-presets", feature = "reranker"))]
61482
+ #[cfg(any(
61483
+ any(feature = "reranker-presets", feature = "reranker"),
61484
+ not(feature = "reranker-presets")
61485
+ ))]
60828
61486
  class.define_method("index", method!(RerankedDocument::index, 0))?;
60829
61487
 
60830
- #[cfg(any(feature = "reranker-presets", feature = "reranker"))]
61488
+ #[cfg(any(
61489
+ any(feature = "reranker-presets", feature = "reranker"),
61490
+ not(feature = "reranker-presets")
61491
+ ))]
60831
61492
  class.define_method("score", method!(RerankedDocument::score, 0))?;
60832
61493
 
60833
- #[cfg(any(feature = "reranker-presets", feature = "reranker"))]
61494
+ #[cfg(any(
61495
+ any(feature = "reranker-presets", feature = "reranker"),
61496
+ not(feature = "reranker-presets")
61497
+ ))]
60834
61498
  class.define_method("document", method!(RerankedDocument::document, 0))?;
60835
61499
 
60836
61500
  let class = module.define_class("RerankerConfig", ruby.class_object())?;
@@ -60987,13 +61651,13 @@ fn ruby_init(ruby: &Ruby) -> Result<(), Error> {
60987
61651
 
60988
61652
  let class = module.define_class("SparseEmbedding", ruby.class_object())?;
60989
61653
 
60990
- #[cfg(feature = "sparse-embedding-presets")]
61654
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
60991
61655
  class.define_singleton_method("new", function!(SparseEmbedding::new, -1))?;
60992
61656
 
60993
- #[cfg(feature = "sparse-embedding-presets")]
61657
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
60994
61658
  class.define_method("indices", method!(SparseEmbedding::indices, 0))?;
60995
61659
 
60996
- #[cfg(feature = "sparse-embedding-presets")]
61660
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
60997
61661
  class.define_method("values", method!(SparseEmbedding::values, 0))?;
60998
61662
 
60999
61663
  let class = module.define_class("SparseEmbeddingConfig", ruby.class_object())?;
@@ -61022,25 +61686,25 @@ fn ruby_init(ruby: &Ruby) -> Result<(), Error> {
61022
61686
 
61023
61687
  let class = module.define_class("SparseEmbeddingPreset", ruby.class_object())?;
61024
61688
 
61025
- #[cfg(feature = "sparse-embedding-presets")]
61689
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
61026
61690
  class.define_singleton_method("new", function!(SparseEmbeddingPreset::new, -1))?;
61027
61691
 
61028
- #[cfg(feature = "sparse-embedding-presets")]
61692
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
61029
61693
  class.define_method("name", method!(SparseEmbeddingPreset::name, 0))?;
61030
61694
 
61031
- #[cfg(feature = "sparse-embedding-presets")]
61695
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
61032
61696
  class.define_method("model_repo", method!(SparseEmbeddingPreset::model_repo, 0))?;
61033
61697
 
61034
- #[cfg(feature = "sparse-embedding-presets")]
61698
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
61035
61699
  class.define_method("model_file", method!(SparseEmbeddingPreset::model_file, 0))?;
61036
61700
 
61037
- #[cfg(feature = "sparse-embedding-presets")]
61701
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
61038
61702
  class.define_method("additional_files", method!(SparseEmbeddingPreset::additional_files, 0))?;
61039
61703
 
61040
- #[cfg(feature = "sparse-embedding-presets")]
61704
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
61041
61705
  class.define_method("max_length", method!(SparseEmbeddingPreset::max_length, 0))?;
61042
61706
 
61043
- #[cfg(feature = "sparse-embedding-presets")]
61707
+ #[cfg(any(feature = "sparse-embedding-presets", not(feature = "sparse-embedding-presets")))]
61044
61708
  class.define_method("description", method!(SparseEmbeddingPreset::description, 0))?;
61045
61709
 
61046
61710
  let class = module.define_class("SsrfPolicy", ruby.class_object())?;
@@ -61643,6 +62307,12 @@ fn ruby_init(ruby: &Ruby) -> Result<(), Error> {
61643
62307
 
61644
62308
  module.define_module_function("extract_batch", function!(extract_batch_async, -1))?;
61645
62309
 
62310
+ #[cfg(feature = "redaction")]
62311
+ module.define_module_function(
62312
+ "extract_with_external_redaction",
62313
+ function!(extract_with_external_redaction_async, -1),
62314
+ )?;
62315
+
61646
62316
  #[cfg(feature = "markdown-footnotes")]
61647
62317
  module.define_module_function("find_unmarked_claims", function!(find_unmarked_claims, 1))?;
61648
62318
 
@@ -61702,6 +62372,9 @@ fn ruby_init(ruby: &Ruby) -> Result<(), Error> {
61702
62372
  #[cfg(feature = "pdf")]
61703
62373
  module.define_module_function("pdf_page_count", function!(pdf_page_count, -1))?;
61704
62374
 
62375
+ #[cfg(feature = "redaction")]
62376
+ module.define_module_function("redact_external", function!(redact_external_async, -1))?;
62377
+
61705
62378
  #[cfg(feature = "markdown-footnotes")]
61706
62379
  module.define_module_function("verify_excerpt", function!(verify_excerpt, 2))?;
61707
62380