38
38
# Initialize category levels with default level
39
39
_category_levels : dict [str , int ] = dict .fromkeys (CATEGORIES , DEFAULT_LOG_LEVEL )
40
40
41
+ # Telemetry category - only added when explicitly enabled
42
+ _telemetry_enabled = False
43
+ _telemetry_level = None
44
+
41
45
42
46
def config_to_category_levels (category : str , level : str ):
43
47
"""
@@ -99,6 +103,8 @@ def parse_environment_config(env_config: str) -> dict[str, int]:
99
103
Returns:
100
104
Dict[str, int]: A dictionary mapping categories to their log levels.
101
105
"""
106
+ global _telemetry_enabled , _telemetry_level , CATEGORIES
107
+
102
108
category_levels = {}
103
109
delimiter = ","
104
110
for pair in env_config .split (delimiter ):
@@ -109,7 +115,19 @@ def parse_environment_config(env_config: str) -> dict[str, int]:
109
115
category , level = pair .split ("=" , 1 )
110
116
category = category .strip ().lower ()
111
117
level = level .strip ().upper () # Convert to uppercase for logging._nameToLevel
112
- category_levels .update (config_to_category_levels (category = category , level = level ))
118
+
119
+ if category == "telemetry" :
120
+ # Add telemetry to CATEGORIES and enable it
121
+ level_value = logging ._nameToLevel .get (level )
122
+ if level_value is not None :
123
+ _telemetry_enabled = True
124
+ _telemetry_level = level_value
125
+ logging .info (f"Telemetry logging enabled at level '{ level } '." )
126
+ else :
127
+ logging .warning (f"Unknown telemetry log level '{ level } '. Telemetry logging will remain disabled." )
128
+ else :
129
+ # Handle regular categories
130
+ category_levels .update (config_to_category_levels (category = category , level = level ))
113
131
114
132
except ValueError :
115
133
logging .warning (f"Invalid logging configuration: '{ pair } '. Expected format: 'category=level'." )
@@ -171,6 +189,23 @@ def filter(self, record):
171
189
record .category = "uncategorized" # Default to 'uncategorized' if no category found
172
190
return True
173
191
192
+ class TelemetryBlockFilter (logging .Filter ):
193
+ """Block all telemetry logs when telemetry is not enabled."""
194
+
195
+ def __init__ (self , telemetry_enabled = False ):
196
+ super ().__init__ ()
197
+ self .telemetry_enabled = telemetry_enabled
198
+
199
+ def filter (self , record ):
200
+ # If telemetry is not enabled, block all telemetry logs
201
+ if not self .telemetry_enabled :
202
+ # Check if this is a telemetry log by logger name or category
203
+ if (hasattr (record , "name" ) and record .name .startswith ("telemetry" )) or (
204
+ hasattr (record , "category" ) and record .category == "telemetry"
205
+ ):
206
+ return False # Block this log
207
+ return True # Allow all other logs
208
+
174
209
# Determine the root logger's level (default to WARNING if not specified)
175
210
root_level = category_levels .get ("root" , logging .WARNING )
176
211
@@ -182,7 +217,7 @@ def filter(self, record):
182
217
"show_time" : False ,
183
218
"show_path" : False ,
184
219
"markup" : True ,
185
- "filters" : ["category_filter" ],
220
+ "filters" : ["category_filter" , "telemetry_block_filter" ],
186
221
}
187
222
}
188
223
@@ -193,8 +228,27 @@ def filter(self, record):
193
228
"filename" : log_file ,
194
229
"mode" : "a" ,
195
230
"encoding" : "utf-8" ,
231
+ "filters" : ["category_filter" , "telemetry_block_filter" ],
196
232
}
197
233
234
+ # Build loggers configuration step by step
235
+ loggers_config = {}
236
+ for category in CATEGORIES :
237
+ if category == "telemetry" and not _telemetry_enabled :
238
+ # When telemetry is disabled, configure it to be silent
239
+ loggers_config [category ] = {
240
+ "level" : logging .CRITICAL ,
241
+ "propagate" : False ,
242
+ "handlers" : [], # No handlers = no output
243
+ }
244
+ else :
245
+ # Regular categories get standard handlers
246
+ loggers_config [category ] = {
247
+ "handlers" : list (handlers .keys ()), # Apply all handlers
248
+ "level" : category_levels .get (category , DEFAULT_LOG_LEVEL ),
249
+ "propagate" : False , # Disable propagation to root logger
250
+ }
251
+
198
252
logging_config = {
199
253
"version" : 1 ,
200
254
"disable_existing_loggers" : False ,
@@ -208,35 +262,43 @@ def filter(self, record):
208
262
"filters" : {
209
263
"category_filter" : {
210
264
"()" : CategoryFilter ,
211
- }
212
- },
213
- "loggers" : {
214
- category : {
215
- "handlers" : list (handlers .keys ()), # Apply all handlers
216
- "level" : category_levels .get (category , DEFAULT_LOG_LEVEL ),
217
- "propagate" : False , # Disable propagation to root logger
218
- }
219
- for category in CATEGORIES
265
+ },
266
+ "telemetry_block_filter" : {
267
+ "()" : TelemetryBlockFilter ,
268
+ "telemetry_enabled" : _telemetry_enabled ,
269
+ },
220
270
},
271
+ "loggers" : loggers_config ,
221
272
"root" : {
222
273
"handlers" : list (handlers .keys ()),
223
274
"level" : root_level , # Set root logger's level dynamically
224
275
},
225
276
}
277
+
226
278
dictConfig (logging_config )
227
279
228
280
# Ensure third-party libraries follow the root log level
229
281
for _ , logger in logging .root .manager .loggerDict .items ():
230
282
if isinstance (logger , logging .Logger ):
231
283
logger .setLevel (root_level )
232
284
285
+ # Explicitly silence telemetry loggers when telemetry is not enabled
286
+ if not _telemetry_enabled :
287
+ telemetry_logger = logging .getLogger ("telemetry" )
288
+ telemetry_logger .setLevel (logging .CRITICAL ) # Silence all telemetry logs
289
+ # Also silence any child telemetry loggers
290
+ for name , logger in logging .root .manager .loggerDict .items ():
291
+ if isinstance (logger , logging .Logger ) and name .startswith ("telemetry" ):
292
+ logger .setLevel (logging .CRITICAL )
293
+
233
294
234
295
def get_logger (
235
296
name : str , category : str = "uncategorized" , config : LoggingConfig | None | None = None
236
297
) -> logging .LoggerAdapter :
237
298
"""
238
299
Returns a logger with the specified name and category.
239
300
If no category is provided, defaults to 'uncategorized'.
301
+ Note: telemetry category is only available when explicitly enabled via LLAMA_STACK_LOGGING=telemetry=LEVEL
240
302
241
303
Parameters:
242
304
name (str): The name of the logger (e.g., module or filename).
0 commit comments