dnsmadeeasy 0.4.0 → 1.0.1

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.
Files changed (63) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/ruby.yml +5 -10
  3. data/.gitignore +2 -0
  4. data/.rubocop.yml +5 -4
  5. data/.rubocop_todo.yml +251 -143
  6. data/CLAUDE.md +67 -0
  7. data/Gemfile +9 -1
  8. data/README.md +858 -0
  9. data/Rakefile +4 -4
  10. data/dnsmadeeasy.gemspec +42 -26
  11. data/docs/badges/coverage_badge.svg +21 -0
  12. data/docs/dry-cli-based-tools.webloc +8 -0
  13. data/docs/plan-zone-management.md +756 -0
  14. data/docs/plans/01-plan-ruby4-baseline.md +38 -0
  15. data/docs/plans/02-plan-dry-cli-launcher.md +44 -0
  16. data/docs/plans/03-plan-account-command.md +43 -0
  17. data/docs/plans/04-plan-zone-record-model.md +48 -0
  18. data/docs/plans/05-plan-zone-parser.md +41 -0
  19. data/docs/plans/06-plan-zone-formatter.md +43 -0
  20. data/docs/plans/07-plan-zone-export.md +58 -0
  21. data/docs/plans/08-plan-zone-diff.md +42 -0
  22. data/docs/plans/09-plan-zone-apply.md +69 -0
  23. data/docs/plans/10-plan-docs-cleanup.md +55 -0
  24. data/docs/spec-zone-management.md +242 -0
  25. data/exe/dme +13 -2
  26. data/exe/dmez +6 -0
  27. data/lib/dme.rb +7 -2
  28. data/lib/dnsmadeeasy/api/client.rb +32 -26
  29. data/lib/dnsmadeeasy/cli/box_output.rb +9 -0
  30. data/lib/dnsmadeeasy/cli/commands/account.rb +222 -0
  31. data/lib/dnsmadeeasy/cli/commands/base.rb +119 -0
  32. data/lib/dnsmadeeasy/cli/commands/legacy_operation.rb +30 -0
  33. data/lib/dnsmadeeasy/cli/commands/version.rb +22 -0
  34. data/lib/dnsmadeeasy/cli/commands/zone.rb +326 -0
  35. data/lib/dnsmadeeasy/cli/commands.rb +19 -0
  36. data/lib/dnsmadeeasy/cli/input.rb +14 -0
  37. data/lib/dnsmadeeasy/cli/launcher.rb +53 -0
  38. data/lib/dnsmadeeasy/cli/message_helpers.rb +81 -0
  39. data/lib/dnsmadeeasy/cli/reported_error.rb +10 -0
  40. data/lib/dnsmadeeasy/credentials/api_keys.rb +11 -9
  41. data/lib/dnsmadeeasy/credentials.rb +0 -1
  42. data/lib/dnsmadeeasy/runner.rb +24 -24
  43. data/lib/dnsmadeeasy/types.rb +19 -0
  44. data/lib/dnsmadeeasy/version.rb +2 -1
  45. data/lib/dnsmadeeasy/zone/aname_flattener.rb +63 -0
  46. data/lib/dnsmadeeasy/zone/apply_executor.rb +189 -0
  47. data/lib/dnsmadeeasy/zone/apply_result.rb +22 -0
  48. data/lib/dnsmadeeasy/zone/diff.rb +152 -0
  49. data/lib/dnsmadeeasy/zone/file.rb +26 -0
  50. data/lib/dnsmadeeasy/zone/parser.rb +172 -0
  51. data/lib/dnsmadeeasy/zone/plan.rb +28 -0
  52. data/lib/dnsmadeeasy/zone/plan_action.rb +29 -0
  53. data/lib/dnsmadeeasy/zone/plan_renderer.rb +91 -0
  54. data/lib/dnsmadeeasy/zone/provider_record.rb +18 -0
  55. data/lib/dnsmadeeasy/zone/record.rb +44 -0
  56. data/lib/dnsmadeeasy/zone/record_set.rb +23 -0
  57. data/lib/dnsmadeeasy/zone/remote_adapter.rb +94 -0
  58. data/lib/dnsmadeeasy/zone/remote_records.rb +26 -0
  59. data/lib/dnsmadeeasy/zone/serializer.rb +115 -0
  60. data/lib/dnsmadeeasy.rb +61 -27
  61. metadata +184 -25
  62. data/.dme-help.png +0 -0
  63. data/README.adoc +0 -690
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: d76d863a9aad518d693425c6f30c38ab00cfd265c2bd0f01657e357fa0d296e0
4
- data.tar.gz: 6b0d42f29ae86a30cab7e47447381d2ce3d6b24b69b9073eda3d75dc59d78efa
3
+ metadata.gz: d0f9aeef63a3d355105f72a76fd1a6e95253e9b775add1d12d25577ac9ef46db
4
+ data.tar.gz: e0db6a9ef9998115f6bf024afdb3abd29edebf38e8fa5dee4999665c6deee10d
5
5
  SHA512:
6
- metadata.gz: ce16dfcdd6f2cf2d2215b77be7c00b8eb3021ea8d10f431e2c38f65422967a710bc5885316fd944b95297d1a5484e021c69de878a3bee65c3a6c0a34236576b0
7
- data.tar.gz: 734ad666cb687601a7570938a2513e15a53a002e1cb286683274ae6bef1eece1d57e2ab8ccd1f646bf3a398328fdf36268f911d65158575d38033791a8f4d224
6
+ metadata.gz: 250b4a573fce114618674cc3ec4312f988e55871171fb084b639ea8e2499cecd3dfda1770fdaa2d7248a814e6bf97b3cf99612bdbb4daea79880e32f5651a496
7
+ data.tar.gz: c8d96e17308ae83bd082be46609c06353bb3f5a4d308c6015eaa8978c0657c7715697bc6b1f4b8d3dd5004b1e7da297ae35e4b94537fc76798e383a42bf843fd
@@ -13,17 +13,13 @@ jobs:
13
13
  runs-on: ubuntu-latest
14
14
 
15
15
  steps:
16
- - uses: actions/checkout@v2
16
+ - uses: actions/checkout@v7
17
17
 
18
- - name: Set up Ruby 2.7
19
- uses: actions/setup-ruby@v1
18
+ - name: Set up Ruby 4.0
19
+ uses: ruby/setup-ruby@v1
20
20
  with:
21
- ruby-version: 2.7.x
22
-
23
- - name: Install dependencies
24
- run: |
25
- gem install bundler
26
- bundle install --jobs 4 --retry 3
21
+ ruby-version: '4.0'
22
+ bundler-cache: true
27
23
 
28
24
  - name: Run all specs
29
25
  run: |
@@ -33,4 +29,3 @@ jobs:
33
29
  run: |
34
30
  bundle exec rubocop
35
31
 
36
-
data/.gitignore CHANGED
@@ -12,3 +12,5 @@
12
12
  .ruby-version
13
13
  .rspec_status
14
14
  .rake_tasks~
15
+ /zonefile_*
16
+ /*.zone
data/.rubocop.yml CHANGED
@@ -1,7 +1,8 @@
1
- # vim: ft=yaml
2
1
  inherit_from: .rubocop_todo.yml
3
2
 
4
- Naming/HeredocDelimiterNaming:
5
- Enabled: false
6
-
3
+ AllCops:
4
+ NewCops: enable
5
+ SuggestExtensions: true
7
6
 
7
+ plugins:
8
+ - rubocop-rspec
data/.rubocop_todo.yml CHANGED
@@ -1,139 +1,288 @@
1
1
  # This configuration was generated by
2
- # `rubocop --auto-gen-config`
3
- # on 2020-04-14 21:02:14 -0700 using RuboCop version 0.81.0.
2
+ # `rubocop --auto-gen-config --exclude-limit 999 --no-offense-counts`
3
+ # on 2026-07-16 20:18:02 UTC using RuboCop version 1.88.2.
4
4
  # The point is for the user to remove these configuration records
5
5
  # one by one as the offenses are removed from the code base.
6
6
  # Note that changes in the inspected code, or installation of new
7
7
  # versions of RuboCop, may require this file to be generated again.
8
8
 
9
- # Offense count: 2
10
- # Cop supports --auto-correct.
11
- # Configuration parameters: AllowAdjacentOneLineDefs, NumberOfEmptyLines.
12
- Layout/EmptyLineBetweenDefs:
13
- Exclude:
14
- - 'lib/dme.rb'
15
- - 'lib/dnsmadeeasy/api/client.rb'
16
-
17
- # Offense count: 1
18
- # Cop supports --auto-correct.
19
- # Configuration parameters: EnforcedStyle.
20
- # SupportedStyles: empty_lines, no_empty_lines
21
- Layout/EmptyLinesAroundBlockBody:
22
- Exclude:
23
- - 'spec/lib/dnsmadeeasy/runner_spec.rb'
24
-
25
- # Offense count: 2
26
- # Cop supports --auto-correct.
27
- # Configuration parameters: EnforcedStyle.
28
- # SupportedStyles: squiggly, active_support, powerpack, unindent
29
- Layout/HeredocIndentation:
9
+ # Configuration parameters: EnforcedStyle, AllowedGems.
10
+ # SupportedStyles: Gemfile, gems.rb, gemspec
11
+ Gemspec/DevelopmentDependencies:
30
12
  Exclude:
31
13
  - 'dnsmadeeasy.gemspec'
32
14
 
33
- # Offense count: 1
34
- # Cop supports --auto-correct.
35
- # Configuration parameters: EnforcedStyle, IndentationWidth.
36
- # SupportedStyles: aligned, indented
37
- Layout/MultilineOperationIndentation:
15
+ Lint/BinaryOperatorWithIdenticalOperands:
38
16
  Exclude:
39
17
  - 'lib/dnsmadeeasy/runner.rb'
40
18
 
41
- # Offense count: 3
42
- # Cop supports --auto-correct.
43
- # Configuration parameters: EnforcedStyle.
44
- # SupportedStyles: space, no_space
45
- Layout/SpaceInsideParens:
19
+ # Configuration parameters: AllowedMethods.
20
+ # AllowedMethods: enums
21
+ Lint/ConstantDefinitionInBlock:
46
22
  Exclude:
47
- - 'Rakefile'
48
23
  - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
49
24
 
50
- # Offense count: 3
51
- Lint/AmbiguousRegexpLiteral:
25
+ # Configuration parameters: IgnoreLiteralBranches, IgnoreConstantBranches, IgnoreDuplicateElseBranch.
26
+ Lint/DuplicateBranch:
27
+ Exclude:
28
+ - 'lib/dnsmadeeasy/runner.rb'
29
+
30
+ Lint/DuplicateMethods:
52
31
  Exclude:
53
- - 'spec/lib/dnsmadeeasy/credentials/api_keys_spec.rb'
54
32
  - 'spec/lib/dnsmadeeasy/runner_spec.rb'
55
33
 
56
- # Offense count: 1
57
- # Configuration parameters: MaximumRangeSize.
34
+ # Configuration parameters: MaxRangeSize.
58
35
  Lint/MissingCopEnableDirective:
59
36
  Exclude:
60
37
  - 'dnsmadeeasy.gemspec'
61
38
 
62
- # Offense count: 1
63
- Lint/UselessAssignment:
64
- Exclude:
65
- - 'lib/dnsmadeeasy/runner.rb'
66
-
67
- # Offense count: 8
68
- # Configuration parameters: IgnoredMethods.
39
+ # Configuration parameters: AllowedMethods, AllowedPatterns, CountRepeatedAttributes.
69
40
  Metrics/AbcSize:
70
41
  Max: 38
71
42
 
72
- # Offense count: 10
73
- # Configuration parameters: CountComments, ExcludedMethods.
74
- # ExcludedMethods: refine
75
- Metrics/BlockLength:
76
- Max: 501
77
-
78
- # Offense count: 2
79
- # Configuration parameters: CountComments.
43
+ # Configuration parameters: CountComments, CountAsOne.
80
44
  Metrics/ClassLength:
81
- Max: 250
45
+ Max: 260
82
46
 
83
- # Offense count: 2
84
- # Configuration parameters: IgnoredMethods.
47
+ # Configuration parameters: AllowedMethods, AllowedPatterns.
85
48
  Metrics/CyclomaticComplexity:
86
49
  Max: 8
87
50
 
88
- # Offense count: 12
89
- # Configuration parameters: CountComments, ExcludedMethods.
51
+ # Configuration parameters: CountComments, CountAsOne, AllowedMethods, AllowedPatterns.
90
52
  Metrics/MethodLength:
91
53
  Max: 32
92
54
 
93
- # Offense count: 3
94
55
  # Configuration parameters: CountKeywordArgs.
95
56
  Metrics/ParameterLists:
57
+ MaxOptionalParameters: 5
96
58
  Max: 8
97
59
 
98
- # Offense count: 2
99
- # Configuration parameters: IgnoredMethods.
60
+ # Configuration parameters: AllowedMethods, AllowedPatterns.
100
61
  Metrics/PerceivedComplexity:
101
62
  Max: 9
102
63
 
103
- # Offense count: 2
64
+ # Configuration parameters: ForbiddenDelimiters.
65
+ # ForbiddenDelimiters: (?i-mx:(^|\s)(EO[A-Z]{1}|END)(\s|$))
66
+ Naming/HeredocDelimiterNaming:
67
+ Exclude:
68
+ - 'dnsmadeeasy.gemspec'
69
+ - 'lib/dnsmadeeasy/runner.rb'
70
+
104
71
  # Configuration parameters: MinNameLength, AllowNamesEndingInNumbers, AllowedNames, ForbiddenNames.
105
- # AllowedNames: io, id, to, by, on, in, at, ip, db, os, pp
72
+ # AllowedNames: as, at, by, cc, db, id, if, in, io, ip, of, on, os, pp, to
106
73
  Naming/MethodParameterName:
107
74
  Exclude:
108
75
  - 'lib/dnsmadeeasy/api/client.rb'
109
76
  - 'lib/dnsmadeeasy/runner.rb'
110
77
 
111
- # Offense count: 2
112
- # Configuration parameters: EnforcedStyle.
78
+ # Configuration parameters: EnforcedStyle, AllowedIdentifiers, AllowedPatterns, ForbiddenIdentifiers, ForbiddenPatterns.
113
79
  # SupportedStyles: snake_case, camelCase
114
80
  Naming/VariableName:
115
81
  Exclude:
116
82
  - 'lib/dnsmadeeasy/api/client.rb'
117
83
 
118
- # Offense count: 1
119
- # Configuration parameters: AllowedChars.
120
- Style/AsciiComments:
84
+ # This cop supports unsafe autocorrection (--autocorrect-all).
85
+ RSpec/BeEq:
121
86
  Exclude:
122
- - 'lib/dnsmadeeasy/credentials.rb'
87
+ - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
88
+
89
+ # This cop supports safe autocorrection (--autocorrect).
90
+ # Configuration parameters: EnforcedStyle.
91
+ # SupportedStyles: be_a, be_kind_of
92
+ RSpec/ClassCheck:
93
+ Exclude:
94
+ - 'spec/lib/dnsmadeeasy/credentials_spec.rb'
95
+ - 'spec/lib/dnsmadeeasy_spec.rb'
96
+
97
+ # This cop supports safe autocorrection (--autocorrect).
98
+ RSpec/ContextMethod:
99
+ Exclude:
100
+ - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
101
+ - 'spec/lib/dnsmadeeasy/credentials_spec.rb'
102
+
103
+ # Configuration parameters: Prefixes, AllowedPatterns.
104
+ # Prefixes: when, with, without
105
+ RSpec/ContextWording:
106
+ Exclude:
107
+ - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
108
+ - 'spec/lib/dnsmadeeasy/credentials/api_keys_spec.rb'
109
+ - 'spec/lib/dnsmadeeasy/credentials/yaml_file_spec.rb'
110
+ - 'spec/lib/dnsmadeeasy/credentials_spec.rb'
111
+ - 'spec/lib/dnsmadeeasy_spec.rb'
112
+
113
+ # This cop supports unsafe autocorrection (--autocorrect-all).
114
+ # Configuration parameters: SkipBlocks, EnforcedStyle, OnlyStaticConstants.
115
+ # SupportedStyles: described_class, explicit
116
+ RSpec/DescribedClass:
117
+ Exclude:
118
+ - 'spec/lib/dnsmadeeasy/runner_spec.rb'
119
+ - 'spec/lib/dnsmadeeasy_spec.rb'
120
+
121
+ # This cop supports safe autocorrection (--autocorrect).
122
+ # Configuration parameters: AllowConsecutiveOneLiners.
123
+ RSpec/EmptyLineAfterExample:
124
+ Exclude:
125
+ - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
126
+ - 'spec/lib/dnsmadeeasy/credentials/api_keys_spec.rb'
127
+
128
+ # This cop supports safe autocorrection (--autocorrect).
129
+ RSpec/EmptyLineAfterExampleGroup:
130
+ Exclude:
131
+ - 'spec/lib/dnsmadeeasy/credentials/api_keys_spec.rb'
132
+
133
+ # This cop supports safe autocorrection (--autocorrect).
134
+ RSpec/EmptyLineAfterFinalLet:
135
+ Exclude:
136
+ - 'spec/lib/dnsmadeeasy/credentials/api_keys_spec.rb'
137
+ - 'spec/lib/dnsmadeeasy/credentials/yaml_file_spec.rb'
138
+ - 'spec/lib/dnsmadeeasy/credentials_spec.rb'
139
+ - 'spec/lib/dnsmadeeasy/runner_spec.rb'
140
+ - 'spec/lib/dnsmadeeasy_spec.rb'
141
+
142
+ # This cop supports safe autocorrection (--autocorrect).
143
+ # Configuration parameters: AllowConsecutiveOneLiners.
144
+ RSpec/EmptyLineAfterHook:
145
+ Exclude:
146
+ - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
147
+
148
+ # This cop supports safe autocorrection (--autocorrect).
149
+ RSpec/EmptyLineAfterSubject:
150
+ Exclude:
151
+ - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
152
+
153
+ # Configuration parameters: CountAsOne.
154
+ RSpec/ExampleLength:
155
+ Max: 23
156
+
157
+ # This cop supports safe autocorrection (--autocorrect).
158
+ # Configuration parameters: CustomTransform, IgnoredWords, DisallowedExamples.
159
+ # DisallowedExamples: works
160
+ RSpec/ExampleWording:
161
+ Exclude:
162
+ - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
163
+ - 'spec/lib/dnsmadeeasy/credentials/api_keys_spec.rb'
164
+ - 'spec/lib/dnsmadeeasy/credentials/yaml_file_spec.rb'
165
+ - 'spec/lib/dnsmadeeasy_spec.rb'
166
+
167
+ RSpec/ExpectInHook:
168
+ Exclude:
169
+ - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
170
+
171
+ # This cop supports safe autocorrection (--autocorrect).
172
+ RSpec/HooksBeforeExamples:
173
+ Exclude:
174
+ - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
175
+
176
+ # This cop supports safe autocorrection (--autocorrect).
177
+ # Configuration parameters: EnforcedStyle.
178
+ # SupportedStyles: is_expected, should
179
+ RSpec/ImplicitExpect:
180
+ Exclude:
181
+ - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
182
+ - 'spec/lib/dnsmadeeasy/cli/commands/version_spec.rb'
183
+ - 'spec/lib/dnsmadeeasy/credentials/api_keys_spec.rb'
184
+ - 'spec/lib/dnsmadeeasy/credentials/yaml_file_spec.rb'
185
+ - 'spec/lib/dnsmadeeasy/credentials_spec.rb'
186
+ - 'spec/lib/dnsmadeeasy/runner_spec.rb'
187
+ - 'spec/lib/dnsmadeeasy_spec.rb'
123
188
 
124
- # Offense count: 4
125
- # Cop supports --auto-correct.
126
- # Configuration parameters: EnforcedStyle, ProceduralMethods, FunctionalMethods, IgnoredMethods, AllowBracesOnProceduralOneLiners, BracesRequiredMethods.
127
- # SupportedStyles: line_count_based, semantic, braces_for_chaining, always_braces
128
- # ProceduralMethods: benchmark, bm, bmbm, create, each_with_object, measure, new, realtime, tap, with_object
129
- # FunctionalMethods: let, let!, subject, watch
130
- # IgnoredMethods: lambda, proc, it
131
- Style/BlockDelimiters:
189
+ # This cop supports safe autocorrection (--autocorrect).
190
+ RSpec/LeadingSubject:
132
191
  Exclude:
133
192
  - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
193
+ - 'spec/lib/dnsmadeeasy/runner_spec.rb'
194
+
195
+ RSpec/LeakyConstantDeclaration:
196
+ Exclude:
197
+ - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
198
+
199
+ RSpec/LeakyLocalVariable:
200
+ Exclude:
201
+ - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
202
+
203
+ # This cop supports safe autocorrection (--autocorrect).
204
+ RSpec/LetBeforeExamples:
205
+ Exclude:
206
+ - 'spec/lib/dnsmadeeasy/credentials/yaml_file_spec.rb'
207
+
208
+ # This cop supports safe autocorrection (--autocorrect).
209
+ RSpec/MatchWithSimpleRegex:
210
+ Exclude:
211
+ - 'spec/lib/dnsmadeeasy/runner_spec.rb'
212
+
213
+ # Configuration parameters: .
214
+ # SupportedStyles: have_received, receive
215
+ RSpec/MessageSpies:
216
+ EnforcedStyle: receive
217
+
218
+ RSpec/MultipleExpectations:
219
+ Max: 2
220
+
221
+ # Configuration parameters: AllowSubject.
222
+ RSpec/MultipleMemoizedHelpers:
223
+ Max: 9
224
+
225
+ # Configuration parameters: EnforcedStyle, IgnoreSharedExamples.
226
+ # SupportedStyles: always, named_only
227
+ RSpec/NamedSubject:
228
+ Exclude:
229
+ - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
230
+ - 'spec/lib/dnsmadeeasy/credentials/api_keys_spec.rb'
231
+
232
+ # Configuration parameters: AllowedGroups.
233
+ RSpec/NestedGroups:
234
+ Max: 4
235
+
236
+ # This cop supports safe autocorrection (--autocorrect).
237
+ # Configuration parameters: EnforcedStyle.
238
+ # SupportedStyles: not_to, to_not
239
+ RSpec/NotToNot:
240
+ Exclude:
134
241
  - 'spec/lib/dnsmadeeasy/credentials/yaml_file_spec.rb'
242
+ - 'spec/lib/dnsmadeeasy/credentials_spec.rb'
243
+ - 'spec/lib/dnsmadeeasy/runner_spec.rb'
244
+
245
+ RSpec/RepeatedExampleGroupDescription:
246
+ Exclude:
247
+ - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
248
+
249
+ # This cop supports safe autocorrection (--autocorrect).
250
+ RSpec/ScatteredLet:
251
+ Exclude:
252
+ - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
253
+ - 'spec/lib/dnsmadeeasy/credentials/yaml_file_spec.rb'
254
+ - 'spec/lib/dnsmadeeasy_spec.rb'
255
+
256
+ # This cop supports safe autocorrection (--autocorrect).
257
+ RSpec/ScatteredSetup:
258
+ Exclude:
259
+ - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
260
+
261
+ # Configuration parameters: CustomTransform, IgnoreMethods, IgnoreMetadata, InflectorPath, EnforcedInflector.
262
+ # SupportedInflectors: default, active_support
263
+ RSpec/SpecFilePathFormat:
264
+ Exclude:
265
+ - '**/spec/routing/**/*'
266
+ - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
267
+ - 'spec/lib/dnsmadeeasy/cli/commands/account_spec.rb'
268
+ - 'spec/lib/dnsmadeeasy/cli/commands/version_spec.rb'
269
+ - 'spec/lib/dnsmadeeasy/cli/launcher_spec.rb'
270
+ - 'spec/lib/dnsmadeeasy/runner_spec.rb'
271
+
272
+ RSpec/StubbedMock:
273
+ Exclude:
274
+ - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
135
275
 
136
- # Offense count: 6
276
+ RSpec/SubjectStub:
277
+ Exclude:
278
+ - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
279
+
280
+ # This cop supports unsafe autocorrection (--autocorrect-all).
281
+ Style/ArrayIntersect:
282
+ Exclude:
283
+ - 'lib/dnsmadeeasy/runner.rb'
284
+
285
+ # Configuration parameters: AllowedConstants.
137
286
  Style/Documentation:
138
287
  Exclude:
139
288
  - 'spec/**/*'
@@ -145,87 +294,46 @@ Style/Documentation:
145
294
  - 'lib/dnsmadeeasy/credentials/yaml_file.rb'
146
295
  - 'lib/dnsmadeeasy/runner.rb'
147
296
 
148
- # Offense count: 5
149
- # Configuration parameters: MinBodyLength.
150
- Style/GuardClause:
297
+ # This cop supports unsafe autocorrection (--autocorrect-all).
298
+ Style/FileNull:
151
299
  Exclude:
152
- - 'lib/dnsmadeeasy.rb'
153
- - 'lib/dnsmadeeasy/api/client.rb'
154
300
  - 'lib/dnsmadeeasy/credentials/api_keys.rb'
155
- - 'lib/dnsmadeeasy/runner.rb'
156
-
157
- # Offense count: 2
158
- Style/MethodMissingSuper:
159
- Exclude:
160
- - 'lib/dme.rb'
161
- - 'lib/dnsmadeeasy.rb'
162
-
163
- # Offense count: 2
164
- Style/MissingRespondToMissing:
165
- Exclude:
166
- - 'lib/dme.rb'
167
- - 'lib/dnsmadeeasy.rb'
168
301
 
169
- # Offense count: 3
170
- # Cop supports --auto-correct.
171
- # Configuration parameters: PreferredDelimiters.
172
- Style/PercentLiteralDelimiters:
302
+ Style/FileOpen:
173
303
  Exclude:
174
- - 'Rakefile'
175
- - 'dnsmadeeasy.gemspec'
304
+ - 'lib/dnsmadeeasy/credentials/api_keys.rb'
176
305
  - 'lib/dnsmadeeasy/runner.rb'
177
306
 
178
- # Offense count: 8
179
- # Cop supports --auto-correct.
180
- # Configuration parameters: AllowAsExpressionSeparator.
181
- Style/Semicolon:
307
+ # Configuration parameters: AllowedClasses.
308
+ Style/OneClassPerFile:
182
309
  Exclude:
310
+ - 'spec/**/*'
311
+ - 'test/**/*'
183
312
  - 'lib/dnsmadeeasy.rb'
184
313
 
185
- # Offense count: 2
186
- # Cop supports --auto-correct.
187
- # Configuration parameters: EnforcedStyle.
188
- # SupportedStyles: only_raise, only_fail, semantic
189
- Style/SignalException:
314
+ # Configuration parameters: AllowedMethods.
315
+ # AllowedMethods: respond_to_missing?
316
+ Style/OptionalBooleanParameter:
190
317
  Exclude:
318
+ - 'lib/dnsmadeeasy.rb'
191
319
  - 'lib/dnsmadeeasy/api/client.rb'
192
320
 
193
- # Offense count: 1
194
- # Cop supports --auto-correct.
195
- Style/StderrPuts:
321
+ # This cop supports unsafe autocorrection (--autocorrect-all).
322
+ Style/SelectByRegexp:
196
323
  Exclude:
324
+ - 'lib/dnsmadeeasy/api/client.rb'
197
325
  - 'lib/dnsmadeeasy/runner.rb'
198
326
 
199
- # Offense count: 5
200
- # Cop supports --auto-correct.
201
- # Configuration parameters: EnforcedStyle, ConsistentQuotesInMultiline.
202
- # SupportedStyles: single_quotes, double_quotes
203
- Style/StringLiterals:
204
- Exclude:
205
- - 'Gemfile'
206
- - 'Rakefile'
207
- - 'lib/dnsmadeeasy/credentials/api_keys.rb'
208
- - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
209
-
210
- # Offense count: 1
211
- # Cop supports --auto-correct.
212
- # Configuration parameters: EnforcedStyleForMultiline.
213
- # SupportedStylesForMultiline: comma, consistent_comma, no_comma
214
- Style/TrailingCommaInArrayLiteral:
215
- Exclude:
216
- - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
217
-
218
- # Offense count: 1
219
- # Cop supports --auto-correct.
220
- # Configuration parameters: EnforcedStyleForMultiline.
221
- # SupportedStylesForMultiline: comma, consistent_comma, no_comma
222
- Style/TrailingCommaInHashLiteral:
327
+ # This cop supports unsafe autocorrection (--autocorrect-all).
328
+ # Configuration parameters: Mode.
329
+ Style/StringConcatenation:
223
330
  Exclude:
331
+ - 'lib/dnsmadeeasy/credentials.rb'
332
+ - 'lib/dnsmadeeasy/runner.rb'
224
333
  - 'spec/lib/dnsmadeeasy/api/client_spec.rb'
225
334
 
226
- # Offense count: 96
227
- # Cop supports --auto-correct.
228
- # Configuration parameters: AutoCorrect, AllowHeredoc, AllowURI, URISchemes, IgnoreCopDirectives, IgnoredPatterns.
335
+ # This cop supports safe autocorrection (--autocorrect).
336
+ # Configuration parameters: AllowHeredoc, AllowURI, AllowQualifiedName, URISchemes, AllowRBSInlineAnnotation, AllowCopDirectives, AllowedPatterns, SplitStrings.
229
337
  # URISchemes: http, https
230
338
  Layout/LineLength:
231
- Max: 305
339
+ Max: 300
data/CLAUDE.md ADDED
@@ -0,0 +1,67 @@
1
+ # CLAUDE.md
2
+
3
+ This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.
4
+
5
+ ## Project Overview
6
+
7
+ Ruby gem (`dnsmadeeasy`) — a REST API client and CLI for the DnsMadeEasy DNS provider (API v2.0). Requires Ruby ~> 4.0. Version 1.0 is **not backwards compatible** with 0.x: the executable was renamed from `dme` to `dmez` (`exe/dme` is now a deprecation stub), and the headline feature is a Terraform-style `export → plan → apply` workflow over standard DNS zone files.
8
+
9
+ ## Commands
10
+
11
+ ```bash
12
+ bin/setup # install dependencies (bundle install)
13
+ bundle exec rspec # run all tests (order is random; WebMock blocks real HTTP)
14
+ bundle exec rspec spec/lib/dns_made_easy/zone/diff_spec.rb # single spec file
15
+ bundle exec rspec spec/lib/dns_made_easy/zone/diff_spec.rb:42 # single example by line
16
+ bundle exec rubocop # lint (inherits .rubocop_todo.yml; rubocop-rspec plugin)
17
+ bundle exec rake spec # rake alias for the test suite
18
+ bundle exec rake build # build gem (also runs the `permissions` task first)
19
+ bundle exec rake install # install gem locally
20
+ bundle exec rake doc # YARD docs
21
+ bin/console # IRB with the gem loaded
22
+ ```
23
+
24
+ CI (`.github/workflows/ruby.yml`) runs `rspec` and `rubocop` on Ruby 4.0 — both must pass.
25
+
26
+ Running the tests writes a coverage badge to `docs/badges/coverage_badge.svg` via SimpleCov (see `spec/spec_helper.rb`).
27
+
28
+ ## Architecture
29
+
30
+ The gem is built on the dry-rb stack: `dry-cli` (CLI), `dry-struct`/`dry-types` (value objects), `dry-monads` (`Success`/`Failure` results). Shared types live in `lib/dnsmadeeasy/types.rb` (`Types::RecordType`, `Types::Ttl`, `DNS_RECORD_TYPES`, etc.).
31
+
32
+ ### Three ways callers reach the API
33
+
34
+ 1. `DnsMadeEasy::Api::Client` — the actual REST client (`lib/dnsmadeeasy/api/client.rb`): HMAC-SHA1-signed requests against production or sandbox base URLs (constants in `lib/dnsmadeeasy.rb`), returning `Hashie::Mash` objects. All domain/record/secondary-domain/ip-set operations live here.
35
+ 1. `DnsMadeEasy` module — holds default credentials and a memoized client; `method_missing` forwards any client method (`DnsMadeEasy.domains`, etc.).
36
+ 1. `DME` — an optional shorthand module (`lib/dnsmadeeasy/dme.rb`, `lib/dme.rb`) that forwards to `DnsMadeEasy`. Only loaded via `require 'dme'` or `require 'dnsmadeeasy/dme'`, never by default.
37
+
38
+ Error classes are defined in `lib/dnsmadeeasy.rb` (all inherit `DnsMadeEasy::Error`).
39
+
40
+ ### Credentials (`lib/dnsmadeeasy/credentials*.rb`)
41
+
42
+ Resolution supports: explicit key/secret, `DNSMADEEASY_API_KEY`/`DNSMADEEASY_API_SECRET` env vars, `~/.dnsmadeeasy/credentials.yml` (single or multi-account YAML with a `default_account` flag), INI format, and values encrypted with the `sym` gem (`encryption_key` may be a file path, keychain name, or env var name). Fixtures for all formats are in `spec/fixtures/`.
43
+
44
+ ### CLI (`exe/dmez` → `lib/dnsmadeeasy/cli/`)
45
+
46
+ `CLI::Launcher` wraps a `Dry::CLI` registry (`cli/commands.rb`) and takes injected stdin/stdout/stderr/kernel so specs can run it in-process. Commands:
47
+
48
+ - `dmez account <operation>` — legacy pass-through to client methods, delegating to `DnsMadeEasy::Runner` (`lib/dnsmadeeasy/runner.rb`), which formats output as json/yaml/pp.
49
+ - `dmez zone export|validate|fmt|plan|apply` — the zone-file workflow (`cli/commands/zone.rb`).
50
+
51
+ ### Zone subsystem (`lib/dnsmadeeasy/zone/`) — the plan/apply pipeline
52
+
53
+ Provider-neutral value objects (`Record`, `RecordSet`, `File`, `ProviderRecord`) are dry-structs. Pipeline stages all return `Dry::Monads` `Success`/`Failure` (Failure carries an array of message strings):
54
+
55
+ 1. `Parser` — zone-file text → `Zone::File`, using the `dns-zonefile` gem. Injects a synthetic SOA when the file lacks one (SOA is otherwise ignored — supported types are in `Parser::SUPPORTED_RECORD_CLASSES`).
56
+ 1. `Serializer` — `Zone::File` → canonical formatted zone text (used by `export` and `fmt`).
57
+ 1. `RemoteAdapter` — DME API record hashes → `RemoteRecords` (`ProviderRecord`s + warnings). HTTPRED records are omitted with a warning; unknown types are a hard `Failure`.
58
+ 1. `Diff` — desired vs. remote record sets → `Plan` with `creates` / `updates` / `skipped_deletes` / `ambiguous` `PlanAction`s. Deliberately conservative: deletes are skipped by default, and identity collisions (multiple records sharing owner/type) become `ambiguous` rather than guessed at.
59
+ 1. `PlanRenderer` — human-readable plan output for the CLI.
60
+ 1. `ApplyExecutor` — executes plan actions against the client in modes `:merge` (default), `:add_only`, `:delete_only`, with a thread pool and injectable tty-spinner factory; returns an `ApplyResult`.
61
+
62
+ ## Testing conventions
63
+
64
+ - RSpec with `rspec-its`; heavy use of `subject`, `let`, and one-line `its(:attr) { is_expected.to ... }` expectations.
65
+ - WebMock is on for everything — API client specs stub HTTP; no real network calls.
66
+ - CLI specs use Aruba in **in-process** mode (`Aruba.configure` in `spec_helper.rb` sets `main_class = DnsMadeEasy::CLI::Launcher`) — `*_aruba_spec.rb` files exercise full command runs without spawning processes.
67
+ - Spec paths are split between two trees for historical reasons: newer zone/CLI specs under `spec/lib/dns_made_easy/`, older specs under `spec/lib/dnsmadeeasy/`. Follow the tree that already contains the spec for the code you touch.
data/Gemfile CHANGED
@@ -1,6 +1,14 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- source "https://rubygems.org"
3
+ source 'https://rubygems.org'
4
4
 
5
5
  # Specify your gem's dependencies in dnsmadeeasy.gemspec
6
6
  gemspec
7
+
8
+ gem 'aruba'
9
+ gem 'coverage-badge'
10
+ gem 'rspec'
11
+ gem 'rspec-its'
12
+ gem 'rubocop'
13
+ gem 'rubocop-rspec'
14
+ gem 'simplecov'