use std::sync::{LazyLock, RwLock, RwLockReadGuard, RwLockWriteGuard};
use zarrs_registry::{
ExtensionAliasesCodecV2, ExtensionAliasesCodecV3, ExtensionAliasesDataTypeV2,
ExtensionAliasesDataTypeV3,
};
#[cfg(doc)]
use crate::array::{codec::CodecOptions, ArrayMetadataOptions};
#[derive(Debug)]
#[allow(clippy::struct_excessive_bools)]
pub struct Config {
validate_checksums: bool,
store_empty_chunks: bool,
codec_concurrent_target: usize,
chunk_concurrent_minimum: usize,
codec_store_metadata_if_encode_only: bool,
metadata_convert_version: MetadataConvertVersion,
metadata_erase_version: MetadataEraseVersion,
include_zarrs_metadata: bool,
codec_aliases_v3: ExtensionAliasesCodecV3,
codec_aliases_v2: ExtensionAliasesCodecV2,
data_type_aliases_v3: ExtensionAliasesDataTypeV3,
data_type_aliases_v2: ExtensionAliasesDataTypeV2,
experimental_partial_encoding: bool,
convert_aliased_extension_names: bool,
}
#[allow(clippy::derivable_impls)]
impl Default for Config {
fn default() -> Self {
Self {
validate_checksums: true,
store_empty_chunks: false,
codec_concurrent_target: rayon::current_num_threads(),
chunk_concurrent_minimum: 4,
codec_store_metadata_if_encode_only: true,
metadata_convert_version: MetadataConvertVersion::Default,
metadata_erase_version: MetadataEraseVersion::Default,
include_zarrs_metadata: true,
codec_aliases_v3: ExtensionAliasesCodecV3::default(),
codec_aliases_v2: ExtensionAliasesCodecV2::default(),
data_type_aliases_v3: ExtensionAliasesDataTypeV3::default(),
data_type_aliases_v2: ExtensionAliasesDataTypeV2::default(),
experimental_partial_encoding: false,
convert_aliased_extension_names: false,
}
}
}
impl Config {
#[must_use]
pub fn validate_checksums(&self) -> bool {
self.validate_checksums
}
pub fn set_validate_checksums(&mut self, validate_checksums: bool) -> &mut Self {
self.validate_checksums = validate_checksums;
self
}
#[must_use]
pub fn store_empty_chunks(&self) -> bool {
self.store_empty_chunks
}
pub fn set_store_empty_chunks(&mut self, store_empty_chunks: bool) -> &mut Self {
self.store_empty_chunks = store_empty_chunks;
self
}
#[must_use]
pub fn codec_concurrent_target(&self) -> usize {
self.codec_concurrent_target
}
pub fn set_codec_concurrent_target(&mut self, concurrent_target: usize) -> &mut Self {
self.codec_concurrent_target = concurrent_target;
self
}
#[must_use]
pub fn chunk_concurrent_minimum(&self) -> usize {
self.chunk_concurrent_minimum
}
pub fn set_chunk_concurrent_minimum(&mut self, concurrent_minimum: usize) -> &mut Self {
self.chunk_concurrent_minimum = concurrent_minimum;
self
}
#[must_use]
pub fn codec_store_metadata_if_encode_only(&self) -> bool {
self.codec_store_metadata_if_encode_only
}
pub fn set_codec_store_metadata_if_encode_only(&mut self, enabled: bool) -> &mut Self {
self.codec_store_metadata_if_encode_only = enabled;
self
}
#[must_use]
pub fn metadata_convert_version(&self) -> MetadataConvertVersion {
self.metadata_convert_version
}
pub fn set_metadata_convert_version(&mut self, version: MetadataConvertVersion) -> &mut Self {
self.metadata_convert_version = version;
self
}
#[must_use]
pub fn metadata_erase_version(&self) -> MetadataEraseVersion {
self.metadata_erase_version
}
pub fn set_metadata_erase_version(&mut self, version: MetadataEraseVersion) -> &mut Self {
self.metadata_erase_version = version;
self
}
#[must_use]
pub fn include_zarrs_metadata(&self) -> bool {
self.include_zarrs_metadata
}
pub fn set_include_zarrs_metadata(&mut self, include_zarrs_metadata: bool) -> &mut Self {
self.include_zarrs_metadata = include_zarrs_metadata;
self
}
#[must_use]
pub fn codec_aliases_v3(&self) -> &ExtensionAliasesCodecV3 {
&self.codec_aliases_v3
}
pub fn codec_aliases_v3_mut(&mut self) -> &mut ExtensionAliasesCodecV3 {
&mut self.codec_aliases_v3
}
#[must_use]
pub fn data_type_aliases_v3(&self) -> &ExtensionAliasesDataTypeV3 {
&self.data_type_aliases_v3
}
pub fn data_type_aliases_v3_mut(&mut self) -> &mut ExtensionAliasesDataTypeV3 {
&mut self.data_type_aliases_v3
}
#[must_use]
pub fn codec_aliases_v2(&self) -> &ExtensionAliasesCodecV2 {
&self.codec_aliases_v2
}
pub fn codec_aliases_v2_mut(&mut self) -> &mut ExtensionAliasesCodecV2 {
&mut self.codec_aliases_v2
}
#[must_use]
pub fn data_type_aliases_v2(&self) -> &ExtensionAliasesDataTypeV2 {
&self.data_type_aliases_v2
}
pub fn data_type_aliases_v2_mut(&mut self) -> &mut ExtensionAliasesDataTypeV2 {
&mut self.data_type_aliases_v2
}
#[must_use]
pub fn experimental_partial_encoding(&self) -> bool {
self.experimental_partial_encoding
}
pub fn set_experimental_partial_encoding(
&mut self,
experimental_partial_encoding: bool,
) -> &mut Self {
self.experimental_partial_encoding = experimental_partial_encoding;
self
}
#[must_use]
pub fn convert_aliased_extension_names(&self) -> bool {
self.convert_aliased_extension_names
}
pub fn set_convert_aliased_extension_names(
&mut self,
convert_aliased_extension_names: bool,
) -> &mut Self {
self.convert_aliased_extension_names = convert_aliased_extension_names;
self
}
}
static CONFIG: LazyLock<RwLock<Config>> = LazyLock::new(|| RwLock::new(Config::default()));
pub fn global_config() -> RwLockReadGuard<'static, Config> {
CONFIG.read().unwrap()
}
pub fn global_config_mut() -> RwLockWriteGuard<'static, Config> {
CONFIG.write().unwrap()
}
pub enum MetadataRetrieveVersion {
Default,
V3,
V2,
}
#[derive(Debug, Clone, Copy)]
pub enum MetadataConvertVersion {
Default,
V3,
}
#[derive(Debug, Clone, Copy)]
pub enum MetadataEraseVersion {
Default,
All,
V3,
V2,
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn config_validate_checksums() {
assert!(global_config().validate_checksums());
global_config_mut().set_validate_checksums(false);
assert!(!global_config().validate_checksums());
global_config_mut().set_validate_checksums(true);
}
}