source_monitor 0.3.0 → 0.3.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.claude/skills/sm-architecture/SKILL.md +233 -0
- data/.claude/skills/sm-architecture/reference/extraction-patterns.md +192 -0
- data/.claude/skills/sm-architecture/reference/module-map.md +194 -0
- data/.claude/skills/sm-configuration-setting/SKILL.md +264 -0
- data/.claude/skills/sm-configuration-setting/reference/settings-catalog.md +248 -0
- data/.claude/skills/sm-configuration-setting/reference/settings-pattern.md +297 -0
- data/.claude/skills/sm-configure/SKILL.md +153 -0
- data/.claude/skills/sm-configure/reference/configuration-reference.md +321 -0
- data/.claude/skills/sm-dashboard-widget/SKILL.md +344 -0
- data/.claude/skills/sm-dashboard-widget/reference/dashboard-patterns.md +304 -0
- data/.claude/skills/sm-domain-model/SKILL.md +188 -0
- data/.claude/skills/sm-domain-model/reference/model-graph.md +114 -0
- data/.claude/skills/sm-domain-model/reference/table-structure.md +348 -0
- data/.claude/skills/sm-engine-migration/SKILL.md +395 -0
- data/.claude/skills/sm-engine-migration/reference/migration-conventions.md +255 -0
- data/.claude/skills/sm-engine-test/SKILL.md +302 -0
- data/.claude/skills/sm-engine-test/reference/test-helpers.md +259 -0
- data/.claude/skills/sm-engine-test/reference/test-patterns.md +411 -0
- data/.claude/skills/sm-event-handler/SKILL.md +265 -0
- data/.claude/skills/sm-event-handler/reference/events-api.md +229 -0
- data/.claude/skills/sm-health-rule/SKILL.md +327 -0
- data/.claude/skills/sm-health-rule/reference/health-system.md +269 -0
- data/.claude/skills/sm-host-setup/SKILL.md +223 -0
- data/.claude/skills/sm-host-setup/reference/initializer-template.md +195 -0
- data/.claude/skills/sm-host-setup/reference/setup-checklist.md +134 -0
- data/.claude/skills/sm-job/SKILL.md +263 -0
- data/.claude/skills/sm-job/reference/job-conventions.md +245 -0
- data/.claude/skills/sm-model-extension/SKILL.md +287 -0
- data/.claude/skills/sm-model-extension/reference/extension-api.md +317 -0
- data/.claude/skills/sm-pipeline-stage/SKILL.md +254 -0
- data/.claude/skills/sm-pipeline-stage/reference/completion-handlers.md +152 -0
- data/.claude/skills/sm-pipeline-stage/reference/entry-processing.md +191 -0
- data/.claude/skills/sm-pipeline-stage/reference/feed-fetcher-architecture.md +198 -0
- data/.claude/skills/sm-scraper-adapter/SKILL.md +284 -0
- data/.claude/skills/sm-scraper-adapter/reference/adapter-contract.md +167 -0
- data/.claude/skills/sm-scraper-adapter/reference/example-adapter.md +274 -0
- data/.vbw-planning/.notification-log.jsonl +102 -0
- data/.vbw-planning/.session-log.jsonl +505 -0
- data/AGENTS.md +20 -57
- data/CHANGELOG.md +19 -0
- data/CLAUDE.md +44 -1
- data/CONTRIBUTING.md +5 -5
- data/Gemfile.lock +20 -21
- data/README.md +18 -5
- data/VERSION +1 -0
- data/docs/deployment.md +1 -1
- data/docs/setup.md +4 -4
- data/lib/source_monitor/setup/skills_installer.rb +94 -0
- data/lib/source_monitor/setup/workflow.rb +17 -2
- data/lib/source_monitor/version.rb +1 -1
- data/lib/tasks/source_monitor_setup.rake +58 -0
- data/source_monitor.gemspec +1 -0
- metadata +39 -1
|
@@ -0,0 +1,297 @@
|
|
|
1
|
+
# Step-by-Step: Adding a Configuration Setting
|
|
2
|
+
|
|
3
|
+
## Scenario A: Add to Existing Section
|
|
4
|
+
|
|
5
|
+
### Example: Add `stale_threshold_hours` to FetchingSettings
|
|
6
|
+
|
|
7
|
+
**Step 1: Edit the settings file**
|
|
8
|
+
|
|
9
|
+
```ruby
|
|
10
|
+
# lib/source_monitor/configuration/fetching_settings.rb
|
|
11
|
+
class FetchingSettings
|
|
12
|
+
attr_accessor :min_interval_minutes,
|
|
13
|
+
:max_interval_minutes,
|
|
14
|
+
:increase_factor,
|
|
15
|
+
:decrease_factor,
|
|
16
|
+
:failure_increase_factor,
|
|
17
|
+
:jitter_percent,
|
|
18
|
+
:stale_threshold_hours # ADD: new accessor
|
|
19
|
+
|
|
20
|
+
def reset!
|
|
21
|
+
@min_interval_minutes = 5
|
|
22
|
+
@max_interval_minutes = 24 * 60
|
|
23
|
+
@increase_factor = 1.25
|
|
24
|
+
@decrease_factor = 0.75
|
|
25
|
+
@failure_increase_factor = 1.5
|
|
26
|
+
@jitter_percent = 0.1
|
|
27
|
+
@stale_threshold_hours = 48 # ADD: default value
|
|
28
|
+
end
|
|
29
|
+
end
|
|
30
|
+
```
|
|
31
|
+
|
|
32
|
+
**Step 2: Write tests**
|
|
33
|
+
|
|
34
|
+
```ruby
|
|
35
|
+
# test/lib/source_monitor/configuration_test.rb
|
|
36
|
+
|
|
37
|
+
test "stale_threshold_hours has correct default" do
|
|
38
|
+
assert_equal 48, SourceMonitor.config.fetching.stale_threshold_hours
|
|
39
|
+
end
|
|
40
|
+
|
|
41
|
+
test "stale_threshold_hours can be overridden" do
|
|
42
|
+
SourceMonitor.configure do |config|
|
|
43
|
+
config.fetching.stale_threshold_hours = 72
|
|
44
|
+
end
|
|
45
|
+
assert_equal 72, SourceMonitor.config.fetching.stale_threshold_hours
|
|
46
|
+
end
|
|
47
|
+
|
|
48
|
+
test "stale_threshold_hours resets with configuration" do
|
|
49
|
+
SourceMonitor.configure do |config|
|
|
50
|
+
config.fetching.stale_threshold_hours = 72
|
|
51
|
+
end
|
|
52
|
+
SourceMonitor.reset_configuration!
|
|
53
|
+
assert_equal 48, SourceMonitor.config.fetching.stale_threshold_hours
|
|
54
|
+
end
|
|
55
|
+
```
|
|
56
|
+
|
|
57
|
+
**Step 3: Run tests**
|
|
58
|
+
|
|
59
|
+
```bash
|
|
60
|
+
PARALLEL_WORKERS=1 bin/rails test test/lib/source_monitor/configuration_test.rb
|
|
61
|
+
```
|
|
62
|
+
|
|
63
|
+
---
|
|
64
|
+
|
|
65
|
+
## Scenario B: Add Setting with Validation
|
|
66
|
+
|
|
67
|
+
### Example: Add validated `strategy` to a section
|
|
68
|
+
|
|
69
|
+
**Step 1: Edit the settings file with custom setter**
|
|
70
|
+
|
|
71
|
+
```ruby
|
|
72
|
+
class MySettings
|
|
73
|
+
VALID_MODES = %i[fast balanced thorough].freeze
|
|
74
|
+
|
|
75
|
+
attr_reader :mode
|
|
76
|
+
|
|
77
|
+
def initialize
|
|
78
|
+
reset!
|
|
79
|
+
end
|
|
80
|
+
|
|
81
|
+
def mode=(value)
|
|
82
|
+
normalized = value&.to_sym
|
|
83
|
+
unless VALID_MODES.include?(normalized)
|
|
84
|
+
raise ArgumentError, "Invalid mode #{value.inspect}. Must be one of: #{VALID_MODES.join(', ')}"
|
|
85
|
+
end
|
|
86
|
+
@mode = normalized
|
|
87
|
+
end
|
|
88
|
+
|
|
89
|
+
def reset!
|
|
90
|
+
@mode = :balanced
|
|
91
|
+
end
|
|
92
|
+
end
|
|
93
|
+
```
|
|
94
|
+
|
|
95
|
+
**Step 2: Write tests for all paths**
|
|
96
|
+
|
|
97
|
+
```ruby
|
|
98
|
+
test "mode defaults to balanced" do
|
|
99
|
+
assert_equal :balanced, SourceMonitor.config.my_section.mode
|
|
100
|
+
end
|
|
101
|
+
|
|
102
|
+
test "mode accepts valid values" do
|
|
103
|
+
%i[fast balanced thorough].each do |mode|
|
|
104
|
+
SourceMonitor.configure do |config|
|
|
105
|
+
config.my_section.mode = mode
|
|
106
|
+
end
|
|
107
|
+
assert_equal mode, SourceMonitor.config.my_section.mode
|
|
108
|
+
end
|
|
109
|
+
end
|
|
110
|
+
|
|
111
|
+
test "mode accepts string values" do
|
|
112
|
+
SourceMonitor.configure do |config|
|
|
113
|
+
config.my_section.mode = "fast"
|
|
114
|
+
end
|
|
115
|
+
assert_equal :fast, SourceMonitor.config.my_section.mode
|
|
116
|
+
end
|
|
117
|
+
|
|
118
|
+
test "mode rejects invalid values" do
|
|
119
|
+
assert_raises(ArgumentError, /Invalid mode/) do
|
|
120
|
+
SourceMonitor.configure do |config|
|
|
121
|
+
config.my_section.mode = :invalid
|
|
122
|
+
end
|
|
123
|
+
end
|
|
124
|
+
end
|
|
125
|
+
```
|
|
126
|
+
|
|
127
|
+
---
|
|
128
|
+
|
|
129
|
+
## Scenario C: Add Setting with Normalization
|
|
130
|
+
|
|
131
|
+
### Example: Numeric setting that normalizes edge cases
|
|
132
|
+
|
|
133
|
+
Follow the `ScrapingSettings` pattern:
|
|
134
|
+
|
|
135
|
+
```ruby
|
|
136
|
+
class MySettings
|
|
137
|
+
DEFAULT_LIMIT = 50
|
|
138
|
+
|
|
139
|
+
attr_reader :limit
|
|
140
|
+
|
|
141
|
+
def initialize
|
|
142
|
+
reset!
|
|
143
|
+
end
|
|
144
|
+
|
|
145
|
+
def limit=(value)
|
|
146
|
+
@limit = normalize_numeric(value)
|
|
147
|
+
end
|
|
148
|
+
|
|
149
|
+
def reset!
|
|
150
|
+
@limit = DEFAULT_LIMIT
|
|
151
|
+
end
|
|
152
|
+
|
|
153
|
+
private
|
|
154
|
+
|
|
155
|
+
def normalize_numeric(value)
|
|
156
|
+
return nil if value.nil?
|
|
157
|
+
return nil if value == ""
|
|
158
|
+
integer = value.respond_to?(:to_i) ? value.to_i : value
|
|
159
|
+
integer.positive? ? integer : nil
|
|
160
|
+
end
|
|
161
|
+
end
|
|
162
|
+
```
|
|
163
|
+
|
|
164
|
+
**Test normalization edge cases:**
|
|
165
|
+
|
|
166
|
+
```ruby
|
|
167
|
+
test "limit normalizes string to integer" do
|
|
168
|
+
SourceMonitor.configure { |c| c.my_section.limit = "10" }
|
|
169
|
+
assert_equal 10, SourceMonitor.config.my_section.limit
|
|
170
|
+
end
|
|
171
|
+
|
|
172
|
+
test "limit normalizes nil to nil" do
|
|
173
|
+
SourceMonitor.configure { |c| c.my_section.limit = nil }
|
|
174
|
+
assert_nil SourceMonitor.config.my_section.limit
|
|
175
|
+
end
|
|
176
|
+
|
|
177
|
+
test "limit normalizes empty string to nil" do
|
|
178
|
+
SourceMonitor.configure { |c| c.my_section.limit = "" }
|
|
179
|
+
assert_nil SourceMonitor.config.my_section.limit
|
|
180
|
+
end
|
|
181
|
+
|
|
182
|
+
test "limit normalizes zero to nil" do
|
|
183
|
+
SourceMonitor.configure { |c| c.my_section.limit = 0 }
|
|
184
|
+
assert_nil SourceMonitor.config.my_section.limit
|
|
185
|
+
end
|
|
186
|
+
|
|
187
|
+
test "limit normalizes negative to nil" do
|
|
188
|
+
SourceMonitor.configure { |c| c.my_section.limit = -5 }
|
|
189
|
+
assert_nil SourceMonitor.config.my_section.limit
|
|
190
|
+
end
|
|
191
|
+
```
|
|
192
|
+
|
|
193
|
+
---
|
|
194
|
+
|
|
195
|
+
## Scenario D: Create a New Settings Section
|
|
196
|
+
|
|
197
|
+
### Step 1: Create the settings file
|
|
198
|
+
|
|
199
|
+
```ruby
|
|
200
|
+
# lib/source_monitor/configuration/notifications_settings.rb
|
|
201
|
+
# frozen_string_literal: true
|
|
202
|
+
|
|
203
|
+
module SourceMonitor
|
|
204
|
+
class Configuration
|
|
205
|
+
class NotificationsSettings
|
|
206
|
+
attr_accessor :enabled, :channels, :throttle_seconds
|
|
207
|
+
|
|
208
|
+
def initialize
|
|
209
|
+
reset!
|
|
210
|
+
end
|
|
211
|
+
|
|
212
|
+
def reset!
|
|
213
|
+
@enabled = true
|
|
214
|
+
@channels = []
|
|
215
|
+
@throttle_seconds = 60
|
|
216
|
+
end
|
|
217
|
+
end
|
|
218
|
+
end
|
|
219
|
+
end
|
|
220
|
+
```
|
|
221
|
+
|
|
222
|
+
### Step 2: Add require and reader to Configuration
|
|
223
|
+
|
|
224
|
+
```ruby
|
|
225
|
+
# lib/source_monitor/configuration.rb
|
|
226
|
+
|
|
227
|
+
# At the top, add require:
|
|
228
|
+
require "source_monitor/configuration/notifications_settings"
|
|
229
|
+
|
|
230
|
+
# In the class:
|
|
231
|
+
attr_reader :http, :scrapers, :retention, :events, :models,
|
|
232
|
+
:realtime, :fetching, :health, :authentication, :scraping,
|
|
233
|
+
:notifications
|
|
234
|
+
|
|
235
|
+
# In initialize:
|
|
236
|
+
def initialize
|
|
237
|
+
# ... existing ...
|
|
238
|
+
@notifications = NotificationsSettings.new
|
|
239
|
+
end
|
|
240
|
+
```
|
|
241
|
+
|
|
242
|
+
### Step 3: Write tests
|
|
243
|
+
|
|
244
|
+
```ruby
|
|
245
|
+
# test/lib/source_monitor/configuration_test.rb
|
|
246
|
+
|
|
247
|
+
test "notifications settings have correct defaults" do
|
|
248
|
+
settings = SourceMonitor.config.notifications
|
|
249
|
+
assert_equal true, settings.enabled
|
|
250
|
+
assert_equal [], settings.channels
|
|
251
|
+
assert_equal 60, settings.throttle_seconds
|
|
252
|
+
end
|
|
253
|
+
|
|
254
|
+
test "notifications settings can be configured" do
|
|
255
|
+
SourceMonitor.configure do |config|
|
|
256
|
+
config.notifications.enabled = false
|
|
257
|
+
config.notifications.channels = [:email]
|
|
258
|
+
config.notifications.throttle_seconds = 30
|
|
259
|
+
end
|
|
260
|
+
|
|
261
|
+
settings = SourceMonitor.config.notifications
|
|
262
|
+
assert_equal false, settings.enabled
|
|
263
|
+
assert_equal [:email], settings.channels
|
|
264
|
+
assert_equal 30, settings.throttle_seconds
|
|
265
|
+
end
|
|
266
|
+
|
|
267
|
+
test "notifications reset restores defaults" do
|
|
268
|
+
SourceMonitor.configure do |config|
|
|
269
|
+
config.notifications.enabled = false
|
|
270
|
+
end
|
|
271
|
+
SourceMonitor.reset_configuration!
|
|
272
|
+
assert_equal true, SourceMonitor.config.notifications.enabled
|
|
273
|
+
end
|
|
274
|
+
```
|
|
275
|
+
|
|
276
|
+
### Step 4: Run tests
|
|
277
|
+
|
|
278
|
+
```bash
|
|
279
|
+
PARALLEL_WORKERS=1 bin/rails test test/lib/source_monitor/configuration_test.rb
|
|
280
|
+
```
|
|
281
|
+
|
|
282
|
+
---
|
|
283
|
+
|
|
284
|
+
## Checklist for Any New Setting
|
|
285
|
+
|
|
286
|
+
- [ ] Attribute added to settings class (attr_accessor or custom setter)
|
|
287
|
+
- [ ] Default value set in `reset!` (or `initialize` for classes without `reset!`)
|
|
288
|
+
- [ ] require statement added (if new file)
|
|
289
|
+
- [ ] Reader method exposed on Configuration (if new section)
|
|
290
|
+
- [ ] Initialization in Configuration#initialize (if new section)
|
|
291
|
+
- [ ] Tests: default value is correct
|
|
292
|
+
- [ ] Tests: value can be overridden
|
|
293
|
+
- [ ] Tests: reset restores default
|
|
294
|
+
- [ ] Tests: validation raises ArgumentError (if applicable)
|
|
295
|
+
- [ ] Tests: edge cases for normalization (if applicable)
|
|
296
|
+
- [ ] All tests pass: `PARALLEL_WORKERS=1 bin/rails test test/lib/source_monitor/configuration_test.rb`
|
|
297
|
+
- [ ] RuboCop clean: `bin/rubocop lib/source_monitor/configuration/`
|
|
@@ -0,0 +1,153 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: sm-configure
|
|
3
|
+
description: Use when configuring SourceMonitor engine settings via the DSL, including queue settings, HTTP client, fetching, health, scrapers, retention, scraping controls, events, model extensions, realtime, and authentication.
|
|
4
|
+
allowed-tools: Read, Write, Edit, Bash, Glob, Grep
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
# sm-configure: Engine Configuration DSL
|
|
8
|
+
|
|
9
|
+
Comprehensive reference for configuring SourceMonitor via `SourceMonitor.configure`.
|
|
10
|
+
|
|
11
|
+
## When to Use
|
|
12
|
+
|
|
13
|
+
- Adding or modifying settings in `config/initializers/source_monitor.rb`
|
|
14
|
+
- Understanding what configuration options are available
|
|
15
|
+
- Debugging configuration-related issues
|
|
16
|
+
- Setting up environment-specific overrides
|
|
17
|
+
|
|
18
|
+
## Configuration Entry Point
|
|
19
|
+
|
|
20
|
+
All configuration lives inside the `configure` block in the host app's initializer:
|
|
21
|
+
|
|
22
|
+
```ruby
|
|
23
|
+
SourceMonitor.configure do |config|
|
|
24
|
+
# settings here
|
|
25
|
+
end
|
|
26
|
+
```
|
|
27
|
+
|
|
28
|
+
After the block executes, `ModelExtensions.reload!` runs automatically to apply any model changes. Restart web and worker processes after changes.
|
|
29
|
+
|
|
30
|
+
## Configuration Sections
|
|
31
|
+
|
|
32
|
+
The `config` object (`SourceMonitor::Configuration`) has 10 sub-sections plus top-level queue/job settings:
|
|
33
|
+
|
|
34
|
+
| Section | Accessor | Class |
|
|
35
|
+
|---|---|---|
|
|
36
|
+
| Top-level | `config.*` | `Configuration` |
|
|
37
|
+
| HTTP | `config.http` | `HTTPSettings` |
|
|
38
|
+
| Fetching | `config.fetching` | `FetchingSettings` |
|
|
39
|
+
| Health | `config.health` | `HealthSettings` |
|
|
40
|
+
| Scrapers | `config.scrapers` | `ScraperRegistry` |
|
|
41
|
+
| Retention | `config.retention` | `RetentionSettings` |
|
|
42
|
+
| Scraping | `config.scraping` | `ScrapingSettings` |
|
|
43
|
+
| Events | `config.events` | `Events` |
|
|
44
|
+
| Models | `config.models` | `Models` |
|
|
45
|
+
| Realtime | `config.realtime` | `RealtimeSettings` |
|
|
46
|
+
| Authentication | `config.authentication` | `AuthenticationSettings` |
|
|
47
|
+
|
|
48
|
+
See `reference/configuration-reference.md` for every setting with types, defaults, and examples.
|
|
49
|
+
|
|
50
|
+
## Quick Examples
|
|
51
|
+
|
|
52
|
+
### Queue Configuration
|
|
53
|
+
```ruby
|
|
54
|
+
config.queue_namespace = "source_monitor"
|
|
55
|
+
config.fetch_queue_name = "source_monitor_fetch"
|
|
56
|
+
config.fetch_queue_concurrency = 4
|
|
57
|
+
```
|
|
58
|
+
|
|
59
|
+
### HTTP Client
|
|
60
|
+
```ruby
|
|
61
|
+
config.http.timeout = 30
|
|
62
|
+
config.http.proxy = ENV["HTTP_PROXY"]
|
|
63
|
+
config.http.retry_max = 3
|
|
64
|
+
```
|
|
65
|
+
|
|
66
|
+
### Authentication (Devise)
|
|
67
|
+
```ruby
|
|
68
|
+
config.authentication.authenticate_with :authenticate_user!
|
|
69
|
+
config.authentication.authorize_with ->(c) { c.current_user&.admin? }
|
|
70
|
+
```
|
|
71
|
+
|
|
72
|
+
### Events
|
|
73
|
+
```ruby
|
|
74
|
+
config.events.after_item_created { |e| Notifier.new_item(e.item) }
|
|
75
|
+
config.events.register_item_processor ->(ctx) { Indexer.index(ctx.item) }
|
|
76
|
+
```
|
|
77
|
+
|
|
78
|
+
### Model Extensions
|
|
79
|
+
```ruby
|
|
80
|
+
config.models.table_name_prefix = "sm_"
|
|
81
|
+
config.models.source.include_concern "MyApp::SourceExtension"
|
|
82
|
+
config.models.item.validate :custom_check
|
|
83
|
+
```
|
|
84
|
+
|
|
85
|
+
### Realtime
|
|
86
|
+
```ruby
|
|
87
|
+
config.realtime.adapter = :redis
|
|
88
|
+
config.realtime.redis_url = ENV["REDIS_URL"]
|
|
89
|
+
```
|
|
90
|
+
|
|
91
|
+
## Helper APIs
|
|
92
|
+
|
|
93
|
+
```ruby
|
|
94
|
+
SourceMonitor.config # Current configuration
|
|
95
|
+
SourceMonitor.configure { |c| ... } # Set configuration
|
|
96
|
+
SourceMonitor.reset_configuration! # Revert to defaults (for tests)
|
|
97
|
+
SourceMonitor.events # Shortcut to config.events
|
|
98
|
+
SourceMonitor.queue_name(:fetch) # Resolved queue name
|
|
99
|
+
SourceMonitor.queue_concurrency(:scrape) # Resolved concurrency
|
|
100
|
+
SourceMonitor.mission_control_dashboard_path # Resolved MC path or nil
|
|
101
|
+
```
|
|
102
|
+
|
|
103
|
+
## Key Source Files
|
|
104
|
+
|
|
105
|
+
| File | Purpose |
|
|
106
|
+
|---|---|
|
|
107
|
+
| `lib/source_monitor/configuration.rb` | Main Configuration class |
|
|
108
|
+
| `lib/source_monitor/configuration/http_settings.rb` | HTTP client settings |
|
|
109
|
+
| `lib/source_monitor/configuration/fetching_settings.rb` | Adaptive scheduling |
|
|
110
|
+
| `lib/source_monitor/configuration/health_settings.rb` | Health monitoring |
|
|
111
|
+
| `lib/source_monitor/configuration/scraper_registry.rb` | Scraper adapter registry |
|
|
112
|
+
| `lib/source_monitor/configuration/retention_settings.rb` | Item retention |
|
|
113
|
+
| `lib/source_monitor/configuration/scraping_settings.rb` | Scraping controls |
|
|
114
|
+
| `lib/source_monitor/configuration/events.rb` | Event callbacks |
|
|
115
|
+
| `lib/source_monitor/configuration/models.rb` | Model extensions config |
|
|
116
|
+
| `lib/source_monitor/configuration/model_definition.rb` | Per-model definition |
|
|
117
|
+
| `lib/source_monitor/configuration/realtime_settings.rb` | Action Cable settings |
|
|
118
|
+
| `lib/source_monitor/configuration/authentication_settings.rb` | Auth settings |
|
|
119
|
+
| `lib/source_monitor/configuration/validation_definition.rb` | Validation wrapper |
|
|
120
|
+
|
|
121
|
+
## References
|
|
122
|
+
|
|
123
|
+
- `reference/configuration-reference.md` -- Complete settings reference
|
|
124
|
+
- `docs/configuration.md` -- Official configuration documentation
|
|
125
|
+
- `lib/generators/source_monitor/install/templates/source_monitor.rb.tt` -- Initializer template
|
|
126
|
+
|
|
127
|
+
## Testing
|
|
128
|
+
|
|
129
|
+
Reset configuration between tests:
|
|
130
|
+
```ruby
|
|
131
|
+
setup do
|
|
132
|
+
SourceMonitor.reset_configuration!
|
|
133
|
+
end
|
|
134
|
+
```
|
|
135
|
+
|
|
136
|
+
Test custom configuration:
|
|
137
|
+
```ruby
|
|
138
|
+
test "custom queue name" do
|
|
139
|
+
SourceMonitor.configure do |config|
|
|
140
|
+
config.fetch_queue_name = "custom_fetch"
|
|
141
|
+
end
|
|
142
|
+
assert_equal "custom_fetch", SourceMonitor.queue_name(:fetch)
|
|
143
|
+
end
|
|
144
|
+
```
|
|
145
|
+
|
|
146
|
+
## Checklist
|
|
147
|
+
|
|
148
|
+
- [ ] Initializer exists at `config/initializers/source_monitor.rb`
|
|
149
|
+
- [ ] Queue names match `config/solid_queue.yml` entries
|
|
150
|
+
- [ ] Authentication hooks configured for host auth system
|
|
151
|
+
- [ ] HTTP timeouts appropriate for target feeds
|
|
152
|
+
- [ ] Retention policy set for production
|
|
153
|
+
- [ ] Workers restarted after configuration changes
|