Skip to content
This repository was archived by the owner on Jul 22, 2025. It is now read-only.

Commit 3009292

Browse files
committed
DEV: updates...
1 parent c3cd5d6 commit 3009292

File tree

7 files changed

+532
-591
lines changed

7 files changed

+532
-591
lines changed

app/controllers/discourse_ai/admin/ai_embeddings_controller.rb

Lines changed: 48 additions & 82 deletions
Original file line numberDiff line numberDiff line change
@@ -56,9 +56,8 @@ def update
5656
)
5757
end
5858

59-
# Capture initial state for logging
6059
initial_attributes = embedding_def.attributes.dup
61-
60+
6261
if embedding_def.update(ai_embeddings_params.except(:dimensions))
6362
log_ai_embedding_update(embedding_def, initial_attributes)
6463
render json: AiEmbeddingDefinitionSerializer.new(embedding_def)
@@ -80,15 +79,14 @@ def destroy
8079
return render_json_error(I18n.t("discourse_ai.embeddings.delete_failed"), status: 409)
8180
end
8281

83-
# Capture embedding details for logging before destruction
8482
embedding_details = {
8583
embedding_id: embedding_def.id,
8684
display_name: embedding_def.display_name,
8785
provider: embedding_def.provider,
8886
dimensions: embedding_def.dimensions,
89-
subject: embedding_def.display_name # Use display_name as the subject for EmbeddingDefinition
87+
subject: embedding_def.display_name,
9088
}
91-
89+
9290
if embedding_def.destroy
9391
log_ai_embedding_deletion(embedding_details)
9492
head :no_content
@@ -143,88 +141,56 @@ def ai_embeddings_params
143141

144142
permitted
145143
end
146-
147-
def log_ai_embedding_creation(embedding_def)
148-
# Create log details
149-
log_details = {
150-
embedding_id: embedding_def.id,
151-
display_name: embedding_def.display_name,
152-
provider: embedding_def.provider,
153-
dimensions: embedding_def.dimensions,
154-
subject: embedding_def.display_name # Use display_name as the subject for EmbeddingDefinition
144+
145+
def ai_embeddings_logger_fields
146+
{
147+
display_name: {
148+
},
149+
provider: {
150+
},
151+
url: {
152+
},
153+
tokenizer_class: {
154+
},
155+
max_sequence_length: {
156+
},
157+
embed_prompt: {
158+
type: :large_text,
159+
},
160+
search_prompt: {
161+
type: :large_text,
162+
},
163+
matryoshka_dimensions: {
164+
},
165+
api_key: {
166+
type: :sensitive,
167+
},
168+
# JSON fields should be tracked as simple changes
169+
json_fields: [:provider_params],
155170
}
156-
157-
# Only include tokenizer if present
158-
if embedding_def.tokenizer_class.present?
159-
log_details[:tokenizer] = embedding_def.tokenizer_class
160-
end
161-
162-
# For sensitive fields, don't include the actual content
163-
if embedding_def.api_key.present?
164-
log_details[:api_key_set] = true
165-
end
166-
167-
# Get subject for the log
168-
subject = log_details[:subject]
169-
170-
# Log the action
171-
StaffActionLogger.new(current_user).log_custom("create_ai_embedding", log_details)
172171
end
173-
172+
173+
def log_ai_embedding_creation(embedding_def)
174+
logger = DiscourseAi::Utils::AiStaffActionLogger.new(current_user)
175+
entity_details = { embedding_id: embedding_def.id, subject: embedding_def.display_name }
176+
logger.log_creation("embedding", embedding_def, ai_embeddings_logger_fields, entity_details)
177+
end
178+
174179
def log_ai_embedding_update(embedding_def, initial_attributes)
175-
# Create log details
176-
log_details = {
177-
embedding_id: embedding_def.id,
178-
display_name: embedding_def.display_name,
179-
subject: embedding_def.display_name # Use display_name as the subject for EmbeddingDefinition
180-
}
181-
182-
# Track changes in fields
183-
changed_fields = []
184-
185-
# Fields to check for changes
186-
%w[display_name provider url tokenizer_class max_sequence_length embed_prompt search_prompt matryoshka_dimensions].each do |field|
187-
if initial_attributes[field] != embedding_def.attributes[field]
188-
changed_fields << field
189-
log_details["#{field}_changed"] = true
190-
end
191-
end
192-
193-
# Special handling for API key (sensitive)
194-
if initial_attributes['api_key'].present? != embedding_def.api_key.present?
195-
changed_fields << 'api_key'
196-
197-
if embedding_def.api_key.present?
198-
log_details[:api_key_set] = true
199-
else
200-
log_details[:api_key_removed] = true
201-
end
202-
end
203-
204-
# Special handling for provider_params (JSON)
205-
if initial_attributes['provider_params'].to_s != embedding_def.provider_params.to_s
206-
changed_fields << 'provider_params'
207-
log_details[:provider_params_changed] = true
208-
end
209-
210-
# Only log if there are actual changes
211-
if changed_fields.any?
212-
log_details[:changed_fields] = changed_fields
213-
214-
# Get subject for the log
215-
subject = log_details[:subject]
216-
217-
# Log the action
218-
StaffActionLogger.new(current_user).log_custom("update_ai_embedding", log_details)
219-
end
180+
logger = DiscourseAi::Utils::AiStaffActionLogger.new(current_user)
181+
entity_details = { embedding_id: embedding_def.id, subject: embedding_def.display_name }
182+
logger.log_update(
183+
"embedding",
184+
embedding_def,
185+
initial_attributes,
186+
ai_embeddings_logger_fields,
187+
entity_details,
188+
)
220189
end
221-
190+
222191
def log_ai_embedding_deletion(embedding_details)
223-
# Get subject for the log (but keep it in the details hash)
224-
subject = embedding_details[:subject]
225-
226-
# Log the action
227-
StaffActionLogger.new(current_user).log_custom("delete_ai_embedding", embedding_details)
192+
logger = DiscourseAi::Utils::AiStaffActionLogger.new(current_user)
193+
logger.log_deletion("embedding", embedding_details)
228194
end
229195
end
230196
end

app/controllers/discourse_ai/admin/ai_llms_controller.rb

Lines changed: 67 additions & 77 deletions
Original file line numberDiff line numberDiff line change
@@ -120,7 +120,7 @@ def destroy
120120
model_id: llm_model.id,
121121
display_name: llm_model.display_name,
122122
name: llm_model.name,
123-
provider: llm_model.provider
123+
provider: llm_model.provider,
124124
}
125125

126126
# Clean up companion users
@@ -206,97 +206,87 @@ def ai_llm_params(updating: nil)
206206
permitted
207207
end
208208

209-
def log_llm_model_creation(llm_model)
210-
# Create basic entity details with important attributes
211-
log_details = {
212-
model_id: llm_model.id,
213-
model_name: llm_model.name,
214-
display_name: llm_model.display_name,
215-
provider: llm_model.provider,
216-
tokenizer: llm_model.tokenizer
209+
def ai_llm_logger_fields
210+
{
211+
display_name: {
212+
},
213+
name: {
214+
},
215+
provider: {
216+
},
217+
tokenizer: {
218+
},
219+
url: {
220+
},
221+
max_prompt_tokens: {
222+
},
223+
max_output_tokens: {
224+
},
225+
enabled_chat_bot: {
226+
},
227+
vision_enabled: {
228+
},
229+
api_key: {
230+
type: :sensitive,
231+
},
232+
input_cost: {
233+
},
234+
output_cost: {
235+
},
236+
# JSON fields should be tracked as simple changes
237+
json_fields: [:provider_params],
217238
}
218-
219-
# Add API key indication if present (without showing the key)
220-
if llm_model.api_key.present?
221-
log_details[:api_key_set] = true
222-
end
239+
end
240+
241+
def log_llm_model_creation(llm_model)
242+
logger = DiscourseAi::Utils::AiStaffActionLogger.new(current_user)
243+
entity_details = { model_id: llm_model.id, subject: llm_model.display_name }
223244

224-
# Add token limits if set
225-
if llm_model.max_prompt_tokens.present?
226-
log_details[:max_prompt_tokens] = llm_model.max_prompt_tokens
227-
end
228-
229-
if llm_model.max_output_tokens.present?
230-
log_details[:max_output_tokens] = llm_model.max_output_tokens
231-
end
232-
233245
# Add quota information as a special case
234246
if llm_model.llm_quotas.any?
235-
log_details[:quotas] = llm_model.llm_quotas.map do |quota|
236-
"Group #{quota.group_id}: #{quota.max_tokens} tokens, #{quota.max_usages} usages, #{quota.duration_seconds}s"
237-
end.join("; ")
247+
entity_details[:quotas] = llm_model
248+
.llm_quotas
249+
.map do |quota|
250+
"Group #{quota.group_id}: #{quota.max_tokens} tokens, #{quota.max_usages} usages, #{quota.duration_seconds}s"
251+
end
252+
.join("; ")
238253
end
239-
240-
# Use StaffActionLogger directly with the proper subject
241-
StaffActionLogger.new(current_user).log_custom("create_ai_llm_model", log_details.merge(subject: llm_model.display_name))
254+
255+
logger.log_creation("llm_model", llm_model, ai_llm_logger_fields, entity_details)
242256
end
243257

244258
def log_llm_model_update(llm_model, initial_attributes, initial_quotas)
245-
# Create basic entity details
246-
log_details = {
247-
model_id: llm_model.id,
248-
model_name: llm_model.name,
249-
display_name: llm_model.display_name
250-
}
251-
252-
# Track simple changes
253-
%w[display_name name provider tokenizer url max_prompt_tokens max_output_tokens enabled_chat_bot vision_enabled].each do |field|
254-
if initial_attributes[field] != llm_model.attributes[field]
255-
log_details["#{field}_changed"] = true
256-
257-
# For simple fields, show the before/after values
258-
unless field == "api_key" # Skip sensitive fields
259-
initial_value = initial_attributes[field]
260-
current_value = llm_model.attributes[field]
261-
log_details[field] = "#{initial_value}#{current_value}"
262-
end
263-
end
264-
end
265-
266-
# Handle API key changes specially
267-
if initial_attributes["api_key"].present? != llm_model.api_key.present?
268-
log_details[:api_key_changed] = true
269-
if llm_model.api_key.present?
270-
log_details[:api_key_status] = "set"
271-
else
272-
log_details[:api_key_status] = "removed"
273-
end
274-
end
275-
259+
logger = DiscourseAi::Utils::AiStaffActionLogger.new(current_user)
260+
entity_details = { model_id: llm_model.id, subject: llm_model.display_name }
261+
276262
# Track quota changes separately as they're a special case
277263
current_quotas = llm_model.llm_quotas.reload.map(&:attributes)
278264
if initial_quotas != current_quotas
279-
initial_quota_summary = initial_quotas.map { |q| "Group #{q['group_id']}: #{q['max_tokens']} tokens" }.join("; ")
280-
current_quota_summary = current_quotas.map { |q| "Group #{q['group_id']}: #{q['max_tokens']} tokens" }.join("; ")
281-
log_details[:quotas_changed] = true
282-
log_details[:quotas] = "#{initial_quota_summary}#{current_quota_summary}"
283-
end
284-
285-
# Check JSON fields like provider_params
286-
if initial_attributes["provider_params"].to_s != llm_model.attributes["provider_params"].to_s
287-
log_details[:provider_params_changed] = true
288-
end
289-
290-
# Only log if there are actual changes
291-
if log_details.keys.any? { |k| k.to_s.end_with?("_changed") }
292-
# Use StaffActionLogger directly with the proper subject
293-
StaffActionLogger.new(current_user).log_custom("update_ai_llm_model", log_details.merge(subject: llm_model.display_name))
265+
initial_quota_summary =
266+
initial_quotas
267+
.map { |q| "Group #{q["group_id"]}: #{q["max_tokens"]} tokens" }
268+
.join("; ")
269+
current_quota_summary =
270+
current_quotas
271+
.map { |q| "Group #{q["group_id"]}: #{q["max_tokens"]} tokens" }
272+
.join("; ")
273+
entity_details[:quotas_changed] = true
274+
entity_details[:quotas] = "#{initial_quota_summary}#{current_quota_summary}"
294275
end
276+
277+
logger.log_update(
278+
"llm_model",
279+
llm_model,
280+
initial_attributes,
281+
ai_llm_logger_fields,
282+
entity_details,
283+
)
295284
end
296285

297286
def log_llm_model_deletion(model_details)
298-
# Use StaffActionLogger directly with the proper subject
299-
StaffActionLogger.new(current_user).log_custom("delete_ai_llm_model", model_details.merge(subject: model_details[:display_name]))
287+
logger = DiscourseAi::Utils::AiStaffActionLogger.new(current_user)
288+
model_details[:subject] = model_details[:display_name]
289+
logger.log_deletion("llm_model", model_details)
300290
end
301291
end
302292
end

0 commit comments

Comments
 (0)