prosereflect 0.1.1 → 0.3.0

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 (158) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/docs.yml +63 -0
  3. data/.github/workflows/links.yml +97 -0
  4. data/.github/workflows/rake.yml +4 -0
  5. data/.github/workflows/release.yml +5 -0
  6. data/.gitignore +4 -0
  7. data/.rubocop.yml +19 -1
  8. data/.rubocop_todo.yml +119 -183
  9. data/CLAUDE.md +78 -0
  10. data/Gemfile +8 -4
  11. data/README.adoc +2 -0
  12. data/Rakefile +3 -3
  13. data/docs/Gemfile +10 -0
  14. data/docs/INDEX.adoc +45 -0
  15. data/docs/_advanced/index.adoc +15 -0
  16. data/docs/_advanced/schema.adoc +112 -0
  17. data/docs/_advanced/step-map.adoc +66 -0
  18. data/docs/_advanced/steps.adoc +88 -0
  19. data/docs/_advanced/test-builder.adoc +61 -0
  20. data/docs/_advanced/transform.adoc +92 -0
  21. data/docs/_config.yml +174 -0
  22. data/docs/_features/html-input.adoc +69 -0
  23. data/docs/_features/html-output.adoc +45 -0
  24. data/docs/_features/index.adoc +15 -0
  25. data/docs/_features/marks.adoc +86 -0
  26. data/docs/_features/node-types.adoc +124 -0
  27. data/docs/_features/user-mentions.adoc +47 -0
  28. data/docs/_guides/custom-nodes.adoc +107 -0
  29. data/docs/_guides/index.adoc +13 -0
  30. data/docs/_guides/round-trip-html.adoc +91 -0
  31. data/docs/_guides/serialization.adoc +109 -0
  32. data/docs/_pages/index.adoc +67 -0
  33. data/docs/_reference/document-api.adoc +49 -0
  34. data/docs/_reference/index.adoc +14 -0
  35. data/docs/_reference/node-api.adoc +79 -0
  36. data/docs/_reference/schema-api.adoc +95 -0
  37. data/docs/_reference/transform-api.adoc +77 -0
  38. data/docs/_understanding/document-model.adoc +65 -0
  39. data/docs/_understanding/fragment.adoc +52 -0
  40. data/docs/_understanding/index.adoc +14 -0
  41. data/docs/_understanding/resolved-position.adoc +53 -0
  42. data/docs/_understanding/slice.adoc +54 -0
  43. data/docs/lychee.toml +63 -0
  44. data/lib/prosereflect/attribute/base.rb +4 -6
  45. data/lib/prosereflect/attribute/bold.rb +2 -4
  46. data/lib/prosereflect/attribute/href.rb +1 -3
  47. data/lib/prosereflect/attribute/id.rb +7 -7
  48. data/lib/prosereflect/attribute.rb +4 -7
  49. data/lib/prosereflect/blockquote.rb +19 -11
  50. data/lib/prosereflect/bullet_list.rb +36 -29
  51. data/lib/prosereflect/code_block.rb +23 -27
  52. data/lib/prosereflect/code_block_wrapper.rb +12 -13
  53. data/lib/prosereflect/document.rb +14 -22
  54. data/lib/prosereflect/fragment.rb +249 -0
  55. data/lib/prosereflect/hard_break.rb +6 -6
  56. data/lib/prosereflect/heading.rb +14 -15
  57. data/lib/prosereflect/horizontal_rule.rb +23 -14
  58. data/lib/prosereflect/image.rb +32 -23
  59. data/lib/prosereflect/input/html.rb +179 -104
  60. data/lib/prosereflect/input.rb +7 -0
  61. data/lib/prosereflect/list_item.rb +11 -12
  62. data/lib/prosereflect/mark/base.rb +9 -11
  63. data/lib/prosereflect/mark/bold.rb +1 -3
  64. data/lib/prosereflect/mark/code.rb +1 -3
  65. data/lib/prosereflect/mark/italic.rb +1 -3
  66. data/lib/prosereflect/mark/link.rb +1 -3
  67. data/lib/prosereflect/mark/strike.rb +1 -3
  68. data/lib/prosereflect/mark/subscript.rb +1 -3
  69. data/lib/prosereflect/mark/superscript.rb +1 -3
  70. data/lib/prosereflect/mark/underline.rb +1 -3
  71. data/lib/prosereflect/mark.rb +9 -5
  72. data/lib/prosereflect/node.rb +171 -33
  73. data/lib/prosereflect/ordered_list.rb +17 -14
  74. data/lib/prosereflect/output/html.rb +279 -50
  75. data/lib/prosereflect/output.rb +7 -0
  76. data/lib/prosereflect/paragraph.rb +11 -13
  77. data/lib/prosereflect/parser.rb +56 -66
  78. data/lib/prosereflect/resolved_pos.rb +256 -0
  79. data/lib/prosereflect/schema/attribute.rb +57 -0
  80. data/lib/prosereflect/schema/content_match.rb +656 -0
  81. data/lib/prosereflect/schema/fragment.rb +166 -0
  82. data/lib/prosereflect/schema/mark.rb +121 -0
  83. data/lib/prosereflect/schema/mark_type.rb +130 -0
  84. data/lib/prosereflect/schema/node.rb +236 -0
  85. data/lib/prosereflect/schema/node_type.rb +274 -0
  86. data/lib/prosereflect/schema/schema_main.rb +190 -0
  87. data/lib/prosereflect/schema/spec.rb +92 -0
  88. data/lib/prosereflect/schema.rb +39 -0
  89. data/lib/prosereflect/table.rb +12 -13
  90. data/lib/prosereflect/table_cell.rb +13 -13
  91. data/lib/prosereflect/table_header.rb +17 -17
  92. data/lib/prosereflect/table_row.rb +12 -12
  93. data/lib/prosereflect/text.rb +35 -11
  94. data/lib/prosereflect/transform/attr_step.rb +157 -0
  95. data/lib/prosereflect/transform/insert_step.rb +115 -0
  96. data/lib/prosereflect/transform/mapping.rb +82 -0
  97. data/lib/prosereflect/transform/mark_step.rb +269 -0
  98. data/lib/prosereflect/transform/replace_around_step.rb +181 -0
  99. data/lib/prosereflect/transform/replace_step.rb +157 -0
  100. data/lib/prosereflect/transform/slice.rb +91 -0
  101. data/lib/prosereflect/transform/step.rb +89 -0
  102. data/lib/prosereflect/transform/step_map.rb +126 -0
  103. data/lib/prosereflect/transform/structure.rb +120 -0
  104. data/lib/prosereflect/transform/transform.rb +341 -0
  105. data/lib/prosereflect/transform.rb +26 -0
  106. data/lib/prosereflect/user.rb +15 -15
  107. data/lib/prosereflect/version.rb +1 -1
  108. data/lib/prosereflect.rb +30 -17
  109. data/prosereflect.gemspec +17 -16
  110. data/spec/fixtures/documents/formatted_text.yaml +14 -0
  111. data/spec/fixtures/documents/heading_paragraph.yaml +16 -0
  112. data/spec/fixtures/documents/lists_doc.yaml +32 -0
  113. data/spec/fixtures/documents/mixed_content.yaml +40 -0
  114. data/spec/fixtures/documents/nested_doc.yaml +20 -0
  115. data/spec/fixtures/documents/simple_doc.yaml +6 -0
  116. data/spec/fixtures/documents/table_doc.yaml +32 -0
  117. data/spec/fixtures/documents/transform_test.yaml +14 -0
  118. data/spec/fixtures/schema/custom_schema.rb +37 -0
  119. data/spec/fixtures/schema/test_schema.rb +46 -0
  120. data/spec/fixtures/test_builder/helpers.rb +212 -0
  121. data/spec/prosereflect/document_spec.rb +332 -330
  122. data/spec/prosereflect/fragment_spec.rb +273 -0
  123. data/spec/prosereflect/hard_break_spec.rb +125 -125
  124. data/spec/prosereflect/input/html_spec.rb +718 -522
  125. data/spec/prosereflect/node_spec.rb +311 -182
  126. data/spec/prosereflect/output/html_spec.rb +105 -105
  127. data/spec/prosereflect/output/whitespace_spec.rb +248 -0
  128. data/spec/prosereflect/paragraph_spec.rb +275 -274
  129. data/spec/prosereflect/parser/round_trip_spec.rb +472 -0
  130. data/spec/prosereflect/parser_spec.rb +185 -180
  131. data/spec/prosereflect/resolved_pos_spec.rb +74 -0
  132. data/spec/prosereflect/schema/conftest.rb +68 -0
  133. data/spec/prosereflect/schema/content_match_spec.rb +237 -0
  134. data/spec/prosereflect/schema/mark_spec.rb +274 -0
  135. data/spec/prosereflect/schema/mark_type_spec.rb +86 -0
  136. data/spec/prosereflect/schema/node_type_spec.rb +142 -0
  137. data/spec/prosereflect/schema/schema_spec.rb +194 -0
  138. data/spec/prosereflect/table_cell_spec.rb +183 -183
  139. data/spec/prosereflect/table_row_spec.rb +149 -149
  140. data/spec/prosereflect/table_spec.rb +320 -318
  141. data/spec/prosereflect/test_builder/marks_spec.rb +127 -0
  142. data/spec/prosereflect/text_spec.rb +133 -132
  143. data/spec/prosereflect/transform/equivalence_spec.rb +487 -0
  144. data/spec/prosereflect/transform/mapping_spec.rb +226 -0
  145. data/spec/prosereflect/transform/replace_spec.rb +832 -0
  146. data/spec/prosereflect/transform/replace_step_spec.rb +157 -0
  147. data/spec/prosereflect/transform/slice_spec.rb +48 -0
  148. data/spec/prosereflect/transform/step_map_spec.rb +70 -0
  149. data/spec/prosereflect/transform/step_spec.rb +211 -0
  150. data/spec/prosereflect/transform/structure_spec.rb +98 -0
  151. data/spec/prosereflect/transform/transform_spec.rb +238 -0
  152. data/spec/prosereflect/user_spec.rb +31 -28
  153. data/spec/prosereflect_spec.rb +28 -26
  154. data/spec/spec_helper.rb +7 -6
  155. data/spec/support/matchers.rb +6 -6
  156. data/spec/support/shared_examples.rb +49 -49
  157. metadata +96 -5
  158. data/spec/prosereflect/version_spec.rb +0 -11
@@ -0,0 +1,238 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "spec_helper"
4
+
5
+ RSpec.describe Prosereflect::Transform::Transform do
6
+ let(:doc) { Prosereflect::Document.new }
7
+
8
+ describe "creation" do
9
+ it "creates transform with document" do
10
+ transform = described_class.new(doc)
11
+ expect(transform.doc).to eq(doc)
12
+ end
13
+
14
+ it "starts with empty steps" do
15
+ transform = described_class.new(doc)
16
+ expect(transform.size).to eq(0)
17
+ end
18
+ end
19
+
20
+ describe "add_mark" do
21
+ it "adds mark step to transform" do
22
+ transform = described_class.new(doc)
23
+ mark = Prosereflect::Mark::Bold.new
24
+ transform.add_mark(0, 10, mark)
25
+ expect(transform.size).to eq(1)
26
+ end
27
+ end
28
+
29
+ describe "remove_mark" do
30
+ it "adds remove mark step to transform" do
31
+ transform = described_class.new(doc)
32
+ mark = Prosereflect::Mark::Bold.new
33
+ transform.remove_mark(0, 10, mark)
34
+ expect(transform.size).to eq(1)
35
+ end
36
+ end
37
+
38
+ describe "insert" do
39
+ it "adds insert step to transform" do
40
+ transform = described_class.new(doc)
41
+ text = Prosereflect::Text.new(text: "hello")
42
+ transform.insert(0, text)
43
+ expect(transform.size).to eq(1)
44
+ end
45
+ end
46
+
47
+ describe "delete" do
48
+ it "adds delete step to transform" do
49
+ transform = described_class.new(doc)
50
+ transform.delete(0, 5)
51
+ expect(transform.size).to eq(1)
52
+ end
53
+ end
54
+
55
+ describe "replace" do
56
+ it "adds replace step to transform" do
57
+ transform = described_class.new(doc)
58
+ slice = Prosereflect::Transform::Slice.empty
59
+ transform.replace(0, 5, slice)
60
+ expect(transform.size).to eq(1)
61
+ end
62
+
63
+ it "defaults to empty slice" do
64
+ transform = described_class.new(doc)
65
+ transform.replace(0, 5)
66
+ expect(transform.size).to eq(1)
67
+ end
68
+ end
69
+
70
+ describe "replace_with" do
71
+ it "adds replace step with nodes" do
72
+ transform = described_class.new(doc)
73
+ text = Prosereflect::Text.new(text: "x")
74
+ transform.replace_with(0, 5, text)
75
+ expect(transform.size).to eq(1)
76
+ end
77
+
78
+ it "accepts multiple nodes" do
79
+ transform = described_class.new(doc)
80
+ t1 = Prosereflect::Text.new(text: "a")
81
+ t2 = Prosereflect::Text.new(text: "b")
82
+ transform.replace_with(0, 5, t1, t2)
83
+ expect(transform.size).to eq(1)
84
+ end
85
+ end
86
+
87
+ describe "set_node_attribute" do
88
+ it "adds attr step to transform" do
89
+ transform = described_class.new(doc)
90
+ transform.set_node_attribute(0, { "level" => 2 })
91
+ expect(transform.size).to eq(1)
92
+ end
93
+ end
94
+
95
+ describe "set_doc_attribute" do
96
+ it "adds doc attr step to transform" do
97
+ transform = described_class.new(doc)
98
+ transform.set_doc_attribute({ "meta" => 1 })
99
+ expect(transform.size).to eq(1)
100
+ end
101
+ end
102
+
103
+ describe "empty?" do
104
+ it "returns true for new transform" do
105
+ transform = described_class.new(doc)
106
+ expect(transform.empty?).to be true
107
+ end
108
+
109
+ it "returns false after adding step" do
110
+ transform = described_class.new(doc)
111
+ transform.delete(0, 5)
112
+ expect(transform.empty?).to be false
113
+ end
114
+ end
115
+
116
+ describe "clone" do
117
+ it "creates new transform with same document" do
118
+ transform = described_class.new(doc)
119
+ cloned = transform.clone
120
+ expect(cloned.doc).to eq(doc)
121
+ end
122
+
123
+ it "clone does not share steps" do
124
+ transform = described_class.new(doc)
125
+ transform.delete(0, 5)
126
+ cloned = transform.clone
127
+ expect(cloned.size).to eq(0)
128
+ end
129
+ end
130
+
131
+ describe "rollback" do
132
+ it "returns self for chaining on empty transform" do
133
+ transform = described_class.new(doc)
134
+ result = transform.rollback
135
+ expect(result).to eq(transform)
136
+ end
137
+ end
138
+
139
+ describe "maps" do
140
+ it "returns empty mapping array for new transform" do
141
+ transform = described_class.new(doc)
142
+ expect(transform.maps).to eq([])
143
+ end
144
+
145
+ it "returns mapping after adding steps" do
146
+ transform = described_class.new(doc)
147
+ transform.delete(0, 5)
148
+ expect(transform.maps.length).to eq(1)
149
+ end
150
+ end
151
+
152
+ describe "size" do
153
+ it "returns number of steps" do
154
+ transform = described_class.new(doc)
155
+ expect(transform.size).to eq(0)
156
+
157
+ transform.delete(0, 5)
158
+ expect(transform.size).to eq(1)
159
+
160
+ transform.delete(0, 5)
161
+ expect(transform.size).to eq(2)
162
+ end
163
+ end
164
+
165
+ describe "add_step" do
166
+ it "returns self for chaining" do
167
+ transform = described_class.new(doc)
168
+ step = Prosereflect::Transform::ReplaceStep.new(0, 5)
169
+ result = transform.add_step(step)
170
+ expect(result).to eq(transform)
171
+ end
172
+
173
+ it "tracks mapping" do
174
+ transform = described_class.new(doc)
175
+ step = Prosereflect::Transform::ReplaceStep.new(0, 5)
176
+ transform.add_step(step)
177
+ expect(transform.maps.length).to eq(1)
178
+ end
179
+ end
180
+
181
+ describe "split" do
182
+ it "adds split step to transform" do
183
+ doc_with_content = Prosereflect::Parser.parse_document({
184
+ "type" => "doc",
185
+ "content" => [
186
+ {
187
+ "type" => "paragraph",
188
+ "content" => [
189
+ { "type" => "text", "text" => "Hello World" },
190
+ ],
191
+ },
192
+ ],
193
+ })
194
+ transform = described_class.new(doc_with_content)
195
+ transform.split(5)
196
+ expect(transform.size).to eq(1)
197
+ end
198
+ end
199
+
200
+ describe "join" do
201
+ it "adds join step to transform" do
202
+ doc_with_two_paras = Prosereflect::Parser.parse_document({
203
+ "type" => "doc",
204
+ "content" => [
205
+ {
206
+ "type" => "paragraph",
207
+ "content" => [
208
+ { "type" => "text", "text" => "Hello" },
209
+ ],
210
+ },
211
+ {
212
+ "type" => "paragraph",
213
+ "content" => [
214
+ { "type" => "text", "text" => "World" },
215
+ ],
216
+ },
217
+ ],
218
+ })
219
+ transform = described_class.new(doc_with_two_paras)
220
+ transform.join(8)
221
+ expect(transform.size).to eq(1)
222
+ end
223
+ end
224
+
225
+ describe "to_s" do
226
+ it "returns string representation" do
227
+ transform = described_class.new(doc)
228
+ expect(transform.to_s).to include("Transform")
229
+ end
230
+ end
231
+
232
+ describe "inspect" do
233
+ it "returns same as to_s" do
234
+ transform = described_class.new(doc)
235
+ expect(transform.inspect).to eq(transform.to_s)
236
+ end
237
+ end
238
+ end
@@ -1,73 +1,76 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'spec_helper'
3
+ require "spec_helper"
4
4
 
5
5
  RSpec.describe Prosereflect::User do
6
6
  let(:user) { described_class.new }
7
7
 
8
- describe '#initialize' do
9
- it 'creates a user mention node with empty content' do
8
+ describe "#initialize" do
9
+ it "creates a user mention node with empty content" do
10
10
  expect(user.content).to eq([])
11
11
  end
12
12
  end
13
13
 
14
- describe '#id' do
15
- it 'gets and sets the user id' do
16
- user.id = '123'
17
- expect(user.id).to eq('123')
14
+ describe "#id" do
15
+ it "gets and sets the user id" do
16
+ user.id = "123"
17
+ expect(user.id).to eq("123")
18
18
  end
19
19
 
20
- it 'gets id from attrs' do
21
- user = described_class.new(attrs: { 'id' => '456' })
22
- expect(user.id).to eq('456')
20
+ it "gets id from attrs" do
21
+ user = described_class.new(attrs: { "id" => "456" })
22
+ expect(user.id).to eq("456")
23
23
  end
24
24
  end
25
25
 
26
- describe '#add_child' do
27
- it 'raises NotImplementedError' do
28
- expect { user.add_child(double) }.to raise_error(NotImplementedError, 'User mention nodes cannot have children')
26
+ describe "#add_child" do
27
+ it "raises NotImplementedError" do
28
+ expect do
29
+ user.add_child(double)
30
+ end.to raise_error(NotImplementedError,
31
+ "User mention nodes cannot have children")
29
32
  end
30
33
  end
31
34
 
32
- describe '#to_h' do
33
- it 'serializes correctly' do
34
- user.id = '789'
35
+ describe "#to_h" do
36
+ it "serializes correctly" do
37
+ user.id = "789"
35
38
  expect(user.to_h).to eq({
36
- 'type' => 'user',
37
- 'attrs' => { 'id' => '789' },
38
- 'content' => []
39
+ "type" => "user",
40
+ "attrs" => { "id" => "789" },
41
+ "content" => [],
39
42
  })
40
43
  end
41
44
  end
42
45
 
43
- describe 'integration with Document' do
44
- it 'can be added to a document' do
46
+ describe "integration with Document" do
47
+ it "can be added to a document" do
45
48
  document = Prosereflect::Document.create
46
- user = document.add_user('123')
49
+ user = document.add_user("123")
47
50
 
48
51
  expect(user).to be_a(described_class)
49
- expect(user.id).to eq('123')
52
+ expect(user.id).to eq("123")
50
53
  expect(document.content.size).to eq(1)
51
54
  expect(document.content.first).to be_a(described_class)
52
55
  end
53
56
  end
54
57
 
55
- describe 'HTML conversion' do
56
- it 'converts to HTML correctly' do
58
+ describe "HTML conversion" do
59
+ it "converts to HTML correctly" do
57
60
  document = Prosereflect::Document.create
58
- document.add_user('123')
61
+ document.add_user("123")
59
62
 
60
63
  html = Prosereflect::Output::Html.convert(document)
61
64
  expect(html).to eq('<user-mention data-id="123"></user-mention>')
62
65
  end
63
66
 
64
- it 'parses from HTML correctly' do
67
+ it "parses from HTML correctly" do
65
68
  html = '<user-mention data-id="123"></user-mention>'
66
69
  document = Prosereflect::Input::Html.parse(html)
67
70
 
68
71
  expect(document.content.size).to eq(1)
69
72
  expect(document.content.first).to be_a(described_class)
70
- expect(document.content.first.id).to eq('123')
73
+ expect(document.content.first.id).to eq("123")
71
74
  end
72
75
  end
73
76
  end
@@ -1,62 +1,64 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'spec_helper'
3
+ require "spec_helper"
4
4
 
5
5
  RSpec.describe Prosereflect do
6
- let(:fixtures_path) { File.join(__dir__, 'fixtures') }
6
+ let(:fixtures_path) { File.join(__dir__, "fixtures") }
7
7
 
8
- it 'has a version number' do
9
- expect(Prosereflect::VERSION).not_to be nil
8
+ it "has a version number" do
9
+ expect(Prosereflect::VERSION).not_to be_nil
10
+ expect(Prosereflect::VERSION).to be_a(String)
11
+ expect(Prosereflect::VERSION).to match(/\d+\.\d+\.\d+/)
10
12
  end
11
13
 
12
14
  # Test YAML parsing for different fixtures
13
- Dir.glob(File.join(__dir__, 'fixtures', '*/*.yaml')).each do |yaml_file|
15
+ Dir.glob(File.join(__dir__, "fixtures", "*/*.yaml")).each do |yaml_file|
14
16
  context "with YAML fixture #{File.basename(yaml_file)}" do
15
17
  let(:file_content) { File.read(yaml_file) }
16
18
 
17
- include_examples 'a parsable format', :yaml
19
+ it_behaves_like "a parsable format", :yaml
18
20
 
19
21
  # Test table functionality for DP fixtures
20
- if yaml_file.include?('DP')
21
- include_examples 'a document with tables'
22
- include_examples 'document traversal'
23
- include_examples 'text content extraction'
22
+ if yaml_file.include?("DP")
23
+ it_behaves_like "a document with tables"
24
+ it_behaves_like "document traversal"
25
+ it_behaves_like "text content extraction"
24
26
  end
25
27
  end
26
28
  end
27
29
 
28
30
  # Test JSON parsing for different fixtures
29
- Dir.glob(File.join(__dir__, 'fixtures', '*/*.json')).each do |json_file|
31
+ Dir.glob(File.join(__dir__, "fixtures", "*/*.json")).each do |json_file|
30
32
  context "with JSON fixture #{File.basename(json_file)}" do
31
33
  let(:file_content) { File.read(json_file) }
32
34
 
33
- include_examples 'a parsable format', :json
35
+ it_behaves_like "a parsable format", :json
34
36
 
35
37
  # Test table functionality for DP fixtures
36
- if json_file.include?('DP')
37
- include_examples 'a document with tables'
38
- include_examples 'document traversal'
39
- include_examples 'text content extraction'
38
+ if json_file.include?("DP")
39
+ it_behaves_like "a document with tables"
40
+ it_behaves_like "document traversal"
41
+ it_behaves_like "text content extraction"
40
42
  end
41
43
  end
42
44
  end
43
45
 
44
- describe 'Document creation' do
45
- include_examples 'document creation'
46
+ describe "Document creation" do
47
+ it_behaves_like "document creation"
46
48
  end
47
49
 
48
- describe 'Round-trip format conversion' do
49
- context 'with YAML format' do
50
- include_examples 'format round-trip', :yaml
50
+ describe "Round-trip format conversion" do
51
+ context "with YAML format" do
52
+ it_behaves_like "format round-trip", :yaml
51
53
  end
52
54
 
53
- context 'with JSON format' do
54
- include_examples 'format round-trip', :json
55
+ context "with JSON format" do
56
+ it_behaves_like "format round-trip", :json
55
57
  end
56
58
 
57
- context 'with HTML format' do
58
- include_examples 'format round-trip', :html
59
- include_examples 'html conversion'
59
+ context "with HTML format" do
60
+ it_behaves_like "format round-trip", :html
61
+ it_behaves_like "html conversion"
60
62
  end
61
63
  end
62
64
  end
data/spec/spec_helper.rb CHANGED
@@ -1,16 +1,17 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'bundler/setup'
4
- require 'yaml'
5
- require 'json'
6
- require 'prosereflect'
3
+ require "bundler/setup"
4
+ require "yaml"
5
+ require "json"
6
+ require "prosereflect"
7
+ require "prosereflect/schema"
7
8
 
8
9
  # Load shared examples
9
- Dir[File.join(__dir__, 'support', '**', '*.rb')].sort.each { |f| require f }
10
+ Dir[File.join(__dir__, "support", "**", "*.rb")].each { |f| require f }
10
11
 
11
12
  RSpec.configure do |config|
12
13
  # Enable flags like --only-failures and --next-failure
13
- config.example_status_persistence_file_path = '.rspec_status'
14
+ config.example_status_persistence_file_path = ".rspec_status"
14
15
 
15
16
  # Disable RSpec exposing methods globally on `Module` and `main`
16
17
  config.disable_monkey_patching!
@@ -1,7 +1,7 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'yaml'
4
- require 'json'
3
+ require "yaml"
4
+ require "json"
5
5
 
6
6
  # Custom RSpec matcher for comparing JSON structures
7
7
  RSpec::Matchers.define :be_equivalent_json do |expected|
@@ -64,7 +64,7 @@ RSpec::Matchers.define :have_equivalent_structure do |expected|
64
64
  # Parse strings if needed
65
65
  expected_data = case expected
66
66
  when String
67
- if expected.strip.start_with?('{', '[')
67
+ if expected.strip.start_with?("{", "[")
68
68
  begin
69
69
  JSON.parse(expected)
70
70
  rescue StandardError
@@ -79,7 +79,7 @@ RSpec::Matchers.define :have_equivalent_structure do |expected|
79
79
 
80
80
  actual_data = case actual
81
81
  when String
82
- if actual.strip.start_with?('{', '[')
82
+ if actual.strip.start_with?("{", "[")
83
83
  begin
84
84
  JSON.parse(actual)
85
85
  rescue StandardError
@@ -98,7 +98,7 @@ RSpec::Matchers.define :have_equivalent_structure do |expected|
98
98
  failure_message do |actual|
99
99
  expected_data = case expected
100
100
  when String
101
- if expected.strip.start_with?('{', '[')
101
+ if expected.strip.start_with?("{", "[")
102
102
  begin
103
103
  JSON.parse(expected)
104
104
  rescue StandardError
@@ -113,7 +113,7 @@ RSpec::Matchers.define :have_equivalent_structure do |expected|
113
113
 
114
114
  actual_data = case actual
115
115
  when String
116
- if actual.strip.start_with?('{', '[')
116
+ if actual.strip.start_with?("{", "[")
117
117
  begin
118
118
  JSON.parse(actual)
119
119
  rescue StandardError