Coverage for openhcs/constants/constants.py: 100.0%

119 statements  

« prev     ^ index     » next       coverage.py v7.10.7, created at 2025-10-01 18:33 +0000

1""" 

2Consolidated constants for OpenHCS. 

3 

4This module defines all constants related to backends, defaults, I/O, memory, and pipeline. 

5These constants are governed by various doctrinal clauses. 

6""" 

7 

8from enum import Enum 

9from functools import lru_cache 

10from typing import Any, Callable, Dict, List, Optional, Set, Type, TypeVar 

11 

12 

13class Microscope(Enum): 

14 AUTO = "auto" 

15 OPENHCS = "openhcs" # Added for the OpenHCS pre-processed format 

16 IMAGEXPRESS = "ImageXpress" 

17 OPERAPHENIX = "OperaPhenix" 

18 

19 

20def get_openhcs_config(): 

21 """Get the OpenHCS configuration, initializing it if needed.""" 

22 from openhcs.core.components.framework import ComponentConfigurationFactory 

23 return ComponentConfigurationFactory.create_openhcs_default_configuration() 

24 

25 

26# Simple lazy initialization - just defer the config call 

27@lru_cache(maxsize=1) 

28def _create_enums(): 

29 """Create enums when first needed.""" 

30 config = get_openhcs_config() 

31 remaining = config.get_remaining_components() 

32 

33 # AllComponents: ALL possible dimensions (including multiprocessing axis) 

34 all_components = Enum('AllComponents', {c.name: c.value for c in config.all_components}) 

35 

36 # VariableComponents: Components available for variable selection (excludes multiprocessing axis) 

37 vc = Enum('VariableComponents', {c.name: c.value for c in remaining}) 

38 

39 # GroupBy: Same as VariableComponents + NONE option (they're the same concept) 

40 gb_dict = {c.name: c.value for c in remaining} 

41 gb_dict['NONE'] = None 

42 GroupBy = Enum('GroupBy', gb_dict) 

43 

44 # Add original interface methods 

45 GroupBy.component = property(lambda self: self.value) 

46 GroupBy.__eq__ = lambda self, other: self.value == getattr(other, 'value', other) 

47 GroupBy.__hash__ = lambda self: hash("GroupBy.NONE") if self.value is None else hash(self.value) 

48 GroupBy.__str__ = lambda self: f"GroupBy.{self.name}" 

49 GroupBy.__repr__ = lambda self: f"GroupBy.{self.name}" 

50 

51 return all_components, vc, GroupBy 

52 

53 

54def __getattr__(name): 

55 """Lazy enum creation.""" 

56 if name in ('AllComponents', 'VariableComponents', 'GroupBy'): 

57 all_components, vc, gb = _create_enums() 

58 globals()['AllComponents'] = all_components 

59 globals()['VariableComponents'] = vc 

60 globals()['GroupBy'] = gb 

61 return globals()[name] 

62 raise AttributeError(f"module '{__name__}' has no attribute '{name}'") 

63 

64 

65 

66 

67 

68#Documentation URL 

69DOCUMENTATION_URL = "https://openhcs.readthedocs.io/en/latest/" 

70 

71 

72class OrchestratorState(Enum): 

73 """Simple orchestrator state tracking - no complex state machine.""" 

74 CREATED = "created" # Object exists, not initialized 

75 READY = "ready" # Initialized, ready for compilation 

76 COMPILED = "compiled" # Compilation complete, ready for execution 

77 EXECUTING = "executing" # Execution in progress 

78 COMPLETED = "completed" # Execution completed successfully 

79 INIT_FAILED = "init_failed" # Initialization failed 

80 COMPILE_FAILED = "compile_failed" # Compilation failed (implies initialized) 

81 EXEC_FAILED = "exec_failed" # Execution failed (implies compiled) 

82 

83# I/O-related constants 

84DEFAULT_IMAGE_EXTENSION = ".tif" 

85DEFAULT_IMAGE_EXTENSIONS: Set[str] = {".tif", ".tiff", ".TIF", ".TIFF"} 

86DEFAULT_SITE_PADDING = 3 

87DEFAULT_RECURSIVE_PATTERN_SEARCH = False 

88# Lazy default resolution using lru_cache 

89@lru_cache(maxsize=1) 

90def get_default_variable_components(): 

91 """Get default variable components from ComponentConfiguration.""" 

92 _, vc, _ = _create_enums() # Get the enum directly 

93 return [getattr(vc, c.name) for c in get_openhcs_config().default_variable] 

94 

95 

96@lru_cache(maxsize=1) 

97def get_default_group_by(): 

98 """Get default group_by from ComponentConfiguration.""" 

99 _, _, gb = _create_enums() # Get the enum directly 

100 config = get_openhcs_config() 

101 return getattr(gb, config.default_group_by.name) if config.default_group_by else None 

102 

103@lru_cache(maxsize=1) 

104def get_multiprocessing_axis(): 

105 """Get multiprocessing axis from ComponentConfiguration.""" 

106 config = get_openhcs_config() 

107 return config.multiprocessing_axis 

108 

109DEFAULT_MICROSCOPE: Microscope = Microscope.AUTO 

110 

111 

112 

113 

114 

115# Backend-related constants 

116class Backend(Enum): 

117 AUTO = "auto" 

118 DISK = "disk" 

119 MEMORY = "memory" 

120 ZARR = "zarr" 

121 NAPARI_STREAM = "napari_stream" 

122 FIJI_STREAM = "fiji_stream" 

123 

124class FileFormat(Enum): 

125 TIFF = list(DEFAULT_IMAGE_EXTENSIONS) 

126 NUMPY = [".npy"] 

127 TORCH = [".pt", ".torch", ".pth"] 

128 JAX = [".jax"] 

129 CUPY = [".cupy",".craw"] 

130 TENSORFLOW = [".tf"] 

131 TEXT = [".txt",".csv",".json",".py",".md"] 

132 

133DEFAULT_BACKEND = Backend.MEMORY 

134REQUIRES_DISK_READ = "requires_disk_read" 

135REQUIRES_DISK_WRITE = "requires_disk_write" 

136FORCE_DISK_WRITE = "force_disk_write" 

137READ_BACKEND = "read_backend" 

138WRITE_BACKEND = "write_backend" 

139 

140# Default values 

141DEFAULT_TILE_OVERLAP = 10.0 

142DEFAULT_MAX_SHIFT = 50 

143DEFAULT_MARGIN_RATIO = 0.1 

144DEFAULT_PIXEL_SIZE = 1.0 

145DEFAULT_ASSEMBLER_LOG_LEVEL = "INFO" 

146DEFAULT_INTERPOLATION_MODE = "nearest" 

147DEFAULT_INTERPOLATION_ORDER = 1 

148DEFAULT_CPU_THREAD_COUNT = 4 

149DEFAULT_PATCH_SIZE = 128 

150DEFAULT_SEARCH_RADIUS = 20 

151# Consolidated definition for CPU thread count 

152 

153# Napari streaming constants 

154DEFAULT_NAPARI_STREAM_PORT = 5555 

155 

156 

157# Memory-related constants 

158T = TypeVar('T') 

159ConversionFunc = Callable[[Any], Any] 

160 

161class MemoryType(Enum): 

162 NUMPY = "numpy" 

163 CUPY = "cupy" 

164 TORCH = "torch" 

165 TENSORFLOW = "tensorflow" 

166 JAX = "jax" 

167 PYCLESPERANTO = "pyclesperanto" 

168 

169CPU_MEMORY_TYPES: Set[MemoryType] = {MemoryType.NUMPY} 

170GPU_MEMORY_TYPES: Set[MemoryType] = { 

171 MemoryType.CUPY, 

172 MemoryType.TORCH, 

173 MemoryType.TENSORFLOW, 

174 MemoryType.JAX, 

175 MemoryType.PYCLESPERANTO 

176} 

177SUPPORTED_MEMORY_TYPES: Set[MemoryType] = CPU_MEMORY_TYPES | GPU_MEMORY_TYPES 

178 

179VALID_MEMORY_TYPES = {mt.value for mt in MemoryType} 

180VALID_GPU_MEMORY_TYPES = {mt.value for mt in GPU_MEMORY_TYPES} 

181 

182# Memory type constants for direct access 

183MEMORY_TYPE_NUMPY = MemoryType.NUMPY.value 

184MEMORY_TYPE_CUPY = MemoryType.CUPY.value 

185MEMORY_TYPE_TORCH = MemoryType.TORCH.value 

186MEMORY_TYPE_TENSORFLOW = MemoryType.TENSORFLOW.value 

187MEMORY_TYPE_JAX = MemoryType.JAX.value 

188MEMORY_TYPE_PYCLESPERANTO = MemoryType.PYCLESPERANTO.value 

189 

190DEFAULT_NUM_WORKERS = 1 

191# Consolidated definition for number of workers 

192DEFAULT_OUT_DIR_SUFFIX = "_out" 

193DEFAULT_POSITIONS_DIR_SUFFIX = "_positions" 

194DEFAULT_STITCHED_DIR_SUFFIX = "_stitched" 

195DEFAULT_WORKSPACE_DIR_SUFFIX = "_workspace"