helm_schema/
load_budget.rs1use std::io::Read;
2
3use crate::error::{CliError, EngineResult};
4
5#[derive(Debug, Clone, Copy, PartialEq, Eq)]
11#[expect(
12 clippy::struct_field_names,
13 reason = "the shared max prefix makes each public budget field's bound explicit"
14)]
15pub struct LoadBudget {
16 pub max_chart_archive_bytes: usize,
18 pub max_schema_document_bytes: usize,
20 pub max_chart_archive_entries: usize,
22 pub max_chart_archive_unpacked_bytes: usize,
24}
25
26impl LoadBudget {
27 #[must_use]
29 pub const fn new(max_chart_archive_bytes: usize, max_schema_document_bytes: usize) -> Self {
30 Self {
31 max_chart_archive_bytes,
32 max_schema_document_bytes,
33 max_chart_archive_entries: 4096,
34 max_chart_archive_unpacked_bytes: 256 * 1024 * 1024,
35 }
36 }
37}
38
39impl Default for LoadBudget {
40 fn default() -> Self {
41 Self::new(64 * 1024 * 1024, 16 * 1024 * 1024)
42 }
43}
44
45pub(crate) fn read_to_end_capped(
46 reader: &mut impl Read,
47 limit_bytes: usize,
48 subject: impl Into<String>,
49) -> EngineResult<Vec<u8>> {
50 let subject = subject.into();
51 let limit_plus_one = u64::try_from(limit_bytes)
52 .unwrap_or(u64::MAX)
53 .saturating_add(1);
54 let mut limited = reader.take(limit_plus_one);
55 let mut bytes = Vec::new();
56 limited.read_to_end(&mut bytes)?;
57 if bytes.len() > limit_bytes {
58 return Err(CliError::LoadBudgetExceeded {
59 subject,
60 limit_bytes,
61 });
62 }
63 Ok(bytes)
64}