oasis-etm 0.1.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 (52) hide show
  1. checksums.yaml +7 -0
  2. data/.github/workflows/rake.yml +15 -0
  3. data/.github/workflows/release.yml +23 -0
  4. data/.gitignore +13 -0
  5. data/.rspec +3 -0
  6. data/.rubocop.yml +14 -0
  7. data/.rubocop_todo.yml +24 -0
  8. data/CODE_OF_CONDUCT.md +132 -0
  9. data/Gemfile +15 -0
  10. data/README.adoc +152 -0
  11. data/Rakefile +12 -0
  12. data/bin/console +11 -0
  13. data/bin/setup +8 -0
  14. data/lib/oasis/etm/colspec.rb +28 -0
  15. data/lib/oasis/etm/entry.rb +39 -0
  16. data/lib/oasis/etm/row.rb +22 -0
  17. data/lib/oasis/etm/table.rb +31 -0
  18. data/lib/oasis/etm/tbody.rb +20 -0
  19. data/lib/oasis/etm/tcol.rb +28 -0
  20. data/lib/oasis/etm/tgroup.rb +37 -0
  21. data/lib/oasis/etm/thead.rb +20 -0
  22. data/lib/oasis/etm/version.rb +7 -0
  23. data/lib/oasis/etm.rb +13 -0
  24. data/lib/oasis-etm.rb +1 -0
  25. data/oasis-etm.gemspec +35 -0
  26. data/oasis-etm_wrapped.txt +1910 -0
  27. data/sig/oasis/etm.rbs +6 -0
  28. data/spec/fixtures/isosts/isosts_tables.cals.01.xml +16 -0
  29. data/spec/fixtures/isosts/isosts_tables.cals.02.xml +45 -0
  30. data/spec/fixtures/isosts/isosts_tables.cals.03.xml +35 -0
  31. data/spec/fixtures/isosts/isosts_tables.cals.04.xml +34 -0
  32. data/spec/fixtures/isosts/isosts_tables.cals.05.xml +63 -0
  33. data/spec/fixtures/isosts/isosts_tables.cals.06.xml +52 -0
  34. data/spec/fixtures/isosts/isosts_tables.cals.07.xml +33 -0
  35. data/spec/fixtures/isosts/isosts_tables.cals.08.xml +37 -0
  36. data/spec/fixtures/isosts/isosts_tables.cals.09.xml +37 -0
  37. data/spec/fixtures/isosts/isosts_tables.cals.10.xml +44 -0
  38. data/spec/fixtures/isosts/isosts_tables.cals.11.xml +43 -0
  39. data/spec/fixtures/isosts/isosts_tables.cals.12.xml +22 -0
  40. data/spec/fixtures/native/docbook_example.xml +47 -0
  41. data/spec/fixtures/niso-jats/niso-jats-table-wrap.xml +78 -0
  42. data/spec/oasis/etm/colspec_spec.rb +49 -0
  43. data/spec/oasis/etm/entry_spec.rb +103 -0
  44. data/spec/oasis/etm/row_spec.rb +43 -0
  45. data/spec/oasis/etm/table_spec.rb +94 -0
  46. data/spec/oasis/etm/tbody_spec.rb +48 -0
  47. data/spec/oasis/etm/tgroup_spec.rb +97 -0
  48. data/spec/oasis/etm/thead_spec.rb +48 -0
  49. data/spec/oasis/etm_spec.rb +81 -0
  50. data/spec/spec_helper.rb +31 -0
  51. data/spec/support/shared_examples/validation_examples.rb +20 -0
  52. metadata +110 -0
@@ -0,0 +1,78 @@
1
+
2
+ <oasis:table frame="all" xmlns:oasis="http://docs.oasis-open.org/ns/oasis-exchange/table">
3
+ <oasis:tgroup cols="7">
4
+ <oasis:colspec colnum="1" colname="col1" align="center" colsep="1"/>
5
+ <oasis:colspec colnum="2" colname="col2" align="center" colsep="1"/>
6
+ <oasis:colspec colnum="3" colname="col3" align="center" colsep="1"/>
7
+ <oasis:colspec colnum="4" colname="col4" align="center" colsep="1"/>
8
+ <oasis:colspec colnum="5" colname="col5" align="center" colsep="1" colwidth="2"/>
9
+ <oasis:colspec colnum="6" colname="col6" align="center" colsep="1"/>
10
+ <oasis:colspec colnum="7" colname="col7" align="char" charoff="30" char="."/>
11
+ <oasis:thead valign="middle">
12
+ <oasis:row>
13
+ <oasis:entry morerows="1"></oasis:entry>
14
+ <oasis:entry namest="col2" nameend="col4" align="center"
15
+ morerows="1">Institutional care</oasis:entry>
16
+ <oasis:entry morerows="1"></oasis:entry>
17
+ <oasis:entry namest="col6" nameend="col7" align="center"
18
+ morerows="1">&#x2003;Bed use (days)</oasis:entry>
19
+ </oasis:row>
20
+ <oasis:row>
21
+ <oasis:entry namest="col2" nameend="col4" rowsep="1"></oasis:entry>
22
+ <oasis:entry namest="col6" nameend="col7" rowsep="1"></oasis:entry>
23
+ </oasis:row>
24
+ <oasis:row>
25
+ <oasis:entry>Control group</oasis:entry>
26
+ <oasis:entry align="center">Day hospital</oasis:entry>
27
+ <oasis:entry align="center">Control</oasis:entry>
28
+ <oasis:entry align="center">Odds ratio (95&#x0025; CI)</oasis:entry>
29
+ <oasis:entry></oasis:entry>
30
+ <oasis:entry align="center">Day hospital</oasis:entry>
31
+ <oasis:entry align="center">Control</oasis:entry>
32
+ </oasis:row>
33
+ </oasis:thead>
34
+ <oasis:tbody valign="middle">
35
+ <oasis:row>
36
+ <oasis:entry namest="col1" nameend="col7" rowsep="1"></oasis:entry>
37
+ </oasis:row>
38
+ <oasis:row>
39
+ <oasis:entry>Comprehensive care (5 trials)</oasis:entry>
40
+ <oasis:entry align="center">151/597<xref ref-type="table-fn"
41
+ rid="TF1-150"></xref></oasis:entry>
42
+ <oasis:entry align="center">159/584</oasis:entry>
43
+ <oasis:entry align="center">0.91 (0.70 to 1.19)</oasis:entry>
44
+ <oasis:entry></oasis:entry>
45
+ <oasis:entry align="center">20.5</oasis:entry>
46
+ <oasis:entry align="char" char="." charoff="30">21.4</oasis:entry>
47
+ </oasis:row>
48
+ <oasis:row>
49
+ <oasis:entry>Domiciliary care (4 trials)</oasis:entry>
50
+ <oasis:entry align="center">20/216</oasis:entry>
51
+ <oasis:entry align="center">&#x2002;19/227</oasis:entry>
52
+ <oasis:entry align="center">1.61 (0.30 to 8.55)</oasis:entry>
53
+ <oasis:entry></oasis:entry>
54
+ <oasis:entry align="center">&#x2002;7.7</oasis:entry>
55
+ <oasis:entry align="char" char="." charoff="30">11.1</oasis:entry>
56
+ </oasis:row>
57
+ <oasis:row>
58
+ <oasis:entry>No comprehensive care (3 trials)</oasis:entry>
59
+ <oasis:entry align="center">37/411</oasis:entry>
60
+ <oasis:entry align="center">&#x2002;66/403</oasis:entry>
61
+ <oasis:entry align="center">0.50<xref ref-type="table-fn"
62
+ rid="TF1-151"></xref> (0.26 to 0.96)</oasis:entry>
63
+ <oasis:entry></oasis:entry>
64
+ <oasis:entry align="center">11.2</oasis:entry>
65
+ <oasis:entry align="char" char="." charoff="30">11.7</oasis:entry>
66
+ </oasis:row>
67
+ <oasis:row>
68
+ <oasis:entry>Total</oasis:entry>
69
+ <oasis:entry align="center">208/1224</oasis:entry>
70
+ <oasis:entry align="center">244/1214</oasis:entry>
71
+ <oasis:entry align="center">0.77 (0.52 to 1.13)</oasis:entry>
72
+ <oasis:entry></oasis:entry>
73
+ <oasis:entry align="center">15.0</oasis:entry>
74
+ <oasis:entry align="char" char="." charoff="30">16.4</oasis:entry>
75
+ </oasis:row>
76
+ </oasis:tbody>
77
+ </oasis:tgroup>
78
+ </oasis:table>
@@ -0,0 +1,49 @@
1
+ RSpec.describe Oasis::Etm::Colspec do
2
+ let(:xml) do
3
+ <<~XML
4
+ <colspec
5
+ colnum="1"
6
+ colname="col1"
7
+ colwidth="1*"
8
+ colsep="1"
9
+ rowsep="1"
10
+ align="center"
11
+ char="."
12
+ charoff="50"/>
13
+ XML
14
+ end
15
+
16
+ describe ".from_xml" do
17
+ subject(:colspec) { described_class.from_xml(xml) }
18
+
19
+ it "parses all attributes" do
20
+ expect(colspec.colnum).to eq(1)
21
+ expect(colspec.colname).to eq("col1")
22
+ expect(colspec.colwidth).to eq("1*")
23
+ expect(colspec.colsep).to eq(1)
24
+ expect(colspec.rowsep).to eq(1)
25
+ expect(colspec.align).to eq("center")
26
+ expect(colspec.char).to eq(".")
27
+ expect(colspec.charoff).to eq("50")
28
+ end
29
+ end
30
+
31
+ describe "#to_xml" do
32
+ subject(:colspec) do
33
+ described_class.new(
34
+ colnum: 1,
35
+ colname: "col1",
36
+ colwidth: "1*",
37
+ colsep: 1,
38
+ rowsep: 1,
39
+ align: "center",
40
+ char: ".",
41
+ charoff: "50",
42
+ )
43
+ end
44
+
45
+ it "generates valid XML" do
46
+ expect(colspec.to_xml).to be_analogous_with(xml)
47
+ end
48
+ end
49
+ end
@@ -0,0 +1,103 @@
1
+ # spec/oasis/etm/entry_spec.rb
2
+ RSpec.describe Oasis::Etm::Entry do
3
+ let(:xml) do
4
+ <<~XML
5
+ <entry
6
+ colname="col1"
7
+ namest="col1"
8
+ nameend="col2"
9
+ morerows="1"
10
+ colsep="1"
11
+ rowsep="1"
12
+ align="center"
13
+ char="."
14
+ charoff="50"
15
+ valign="middle">Cell content</entry>
16
+ XML
17
+ end
18
+
19
+ describe ".from_xml" do
20
+ subject(:entry) { described_class.from_xml(xml) }
21
+
22
+ it "parses attributes" do
23
+ expect(entry.colname).to eq("col1")
24
+ expect(entry.namest).to eq("col1")
25
+ expect(entry.nameend).to eq("col2")
26
+ expect(entry.morerows).to eq(1)
27
+ expect(entry.colsep).to eq(1)
28
+ expect(entry.rowsep).to eq(1)
29
+ expect(entry.align).to eq("center")
30
+ expect(entry.char).to eq(".")
31
+ expect(entry.charoff).to eq("50")
32
+ expect(entry.valign).to eq("middle")
33
+ end
34
+
35
+ it "parses content" do
36
+ expect(entry.content).to eq("Cell content")
37
+ end
38
+ end
39
+
40
+ describe "#to_xml" do
41
+ subject(:entry) do
42
+ described_class.new(
43
+ colname: "col1",
44
+ namest: "col1",
45
+ nameend: "col2",
46
+ morerows: 1,
47
+ colsep: 1,
48
+ rowsep: 1,
49
+ align: "center",
50
+ char: ".",
51
+ charoff: "50",
52
+ valign: "middle",
53
+ content: "Cell content",
54
+ )
55
+ end
56
+
57
+ it "generates valid XML" do
58
+ expect(entry.to_xml).to be_analogous_with(xml)
59
+ end
60
+ end
61
+
62
+ context "with validation" do
63
+ it "validates align values" do
64
+ entry = described_class.new(align: "invalid")
65
+ errors = entry.validate
66
+ expect(errors).to match_array(
67
+ have_attributes(
68
+ message: /align is `invalid`, must be one of the following \[left, right, center, justify, char\]/,
69
+ ),
70
+ )
71
+ end
72
+
73
+ it "validates valign values" do
74
+ entry = described_class.new(valign: "invalid")
75
+ errors = entry.validate
76
+ expect(errors).to match_array(
77
+ have_attributes(
78
+ message: /valign is `invalid`, must be one of the following \[top, middle, bottom\]/,
79
+ ),
80
+ )
81
+ end
82
+
83
+ it "validates colsep values" do
84
+ entry = described_class.new(colsep: 2)
85
+ errors = entry.validate
86
+ expect(errors).to match_array(
87
+ have_attributes(
88
+ message: /colsep is `2`, must be one of the following \[0, 1\]/,
89
+ ),
90
+ )
91
+ end
92
+
93
+ it "validates rowsep values" do
94
+ entry = described_class.new(rowsep: 2)
95
+ errors = entry.validate
96
+ expect(errors).to match_array(
97
+ have_attributes(
98
+ message: /rowsep is `2`, must be one of the following \[0, 1\]/,
99
+ ),
100
+ )
101
+ end
102
+ end
103
+ end
@@ -0,0 +1,43 @@
1
+ RSpec.describe Oasis::Etm::Row do
2
+ let(:xml) do
3
+ <<~XML
4
+ <row rowsep="1" valign="middle">
5
+ <entry>Cell 1</entry>
6
+ <entry>Cell 2</entry>
7
+ <entry>Cell 3</entry>
8
+ </row>
9
+ XML
10
+ end
11
+
12
+ describe ".from_xml" do
13
+ subject(:row) { described_class.from_xml(xml) }
14
+
15
+ it "parses attributes" do
16
+ expect(row.rowsep).to eq(1)
17
+ expect(row.valign).to eq("middle")
18
+ end
19
+
20
+ it "parses entries" do
21
+ expect(row.entries.size).to eq(3)
22
+ expect(row.entries.map(&:content)).to eq(["Cell 1", "Cell 2", "Cell 3"])
23
+ end
24
+ end
25
+
26
+ describe "#to_xml" do
27
+ subject(:row) do
28
+ described_class.new(
29
+ rowsep: 1,
30
+ valign: "middle",
31
+ entries: [
32
+ Oasis::Etm::Entry.new(content: "Cell 1"),
33
+ Oasis::Etm::Entry.new(content: "Cell 2"),
34
+ Oasis::Etm::Entry.new(content: "Cell 3"),
35
+ ],
36
+ )
37
+ end
38
+
39
+ it "generates valid XML" do
40
+ expect(row.to_xml).to be_analogous_with(xml)
41
+ end
42
+ end
43
+ end
@@ -0,0 +1,94 @@
1
+ RSpec.describe Oasis::Etm::Table do
2
+ let(:xml) do
3
+ <<~XML
4
+ <table frame="all" colsep="1" rowsep="1">
5
+ <title>Sample Table</title>
6
+ <tgroup cols="3">
7
+ <colspec colnum="1" colwidth="1*"/>
8
+ <colspec colnum="2" colwidth="2*"/>
9
+ <colspec colnum="3" colwidth="1*"/>
10
+ <thead>
11
+ <row>
12
+ <entry>Header 1</entry>
13
+ <entry>Header 2</entry>
14
+ <entry>Header 3</entry>
15
+ </row>
16
+ </thead>
17
+ <tbody>
18
+ <row>
19
+ <entry>Cell 1</entry>
20
+ <entry>Cell 2</entry>
21
+ <entry>Cell 3</entry>
22
+ </row>
23
+ </tbody>
24
+ </tgroup>
25
+ </table>
26
+ XML
27
+ end
28
+
29
+ describe ".from_xml" do
30
+ subject(:table) { described_class.from_xml(xml) }
31
+
32
+ it "parses table attributes" do
33
+ expect(table.frame).to eq("all")
34
+ expect(table.colsep).to eq(1)
35
+ expect(table.rowsep).to eq(1)
36
+ end
37
+
38
+ it "parses title" do
39
+ expect(table.title).to eq("Sample Table")
40
+ end
41
+
42
+ it "parses tgroup" do
43
+ expect(table.tgroups.size).to eq(1)
44
+ expect(table.tgroups.first.cols).to eq(3)
45
+ end
46
+ end
47
+
48
+ describe "#to_xml" do
49
+ subject(:table) do
50
+ described_class.new(
51
+ frame: "all",
52
+ colsep: 1,
53
+ rowsep: 1,
54
+ title: "Sample Table",
55
+ tgroups: [
56
+ Oasis::Etm::Tgroup.new(
57
+ cols: 3,
58
+ colspecs: [
59
+ Oasis::Etm::Colspec.new(colnum: 1, colwidth: "1*"),
60
+ Oasis::Etm::Colspec.new(colnum: 2, colwidth: "2*"),
61
+ Oasis::Etm::Colspec.new(colnum: 3, colwidth: "1*"),
62
+ ],
63
+ thead: Oasis::Etm::Thead.new(
64
+ rows: [
65
+ Oasis::Etm::Row.new(
66
+ entries: [
67
+ Oasis::Etm::Entry.new(content: "Header 1"),
68
+ Oasis::Etm::Entry.new(content: "Header 2"),
69
+ Oasis::Etm::Entry.new(content: "Header 3"),
70
+ ],
71
+ ),
72
+ ],
73
+ ),
74
+ tbody: Oasis::Etm::Tbody.new(
75
+ rows: [
76
+ Oasis::Etm::Row.new(
77
+ entries: [
78
+ Oasis::Etm::Entry.new(content: "Cell 1"),
79
+ Oasis::Etm::Entry.new(content: "Cell 2"),
80
+ Oasis::Etm::Entry.new(content: "Cell 3"),
81
+ ],
82
+ ),
83
+ ],
84
+ ),
85
+ ),
86
+ ],
87
+ )
88
+ end
89
+
90
+ it "generates valid XML" do
91
+ expect(table.to_xml).to be_analogous_with(xml)
92
+ end
93
+ end
94
+ end
@@ -0,0 +1,48 @@
1
+ RSpec.describe Oasis::Etm::Tbody do
2
+ let(:xml) do
3
+ <<~XML
4
+ <tbody valign="top">
5
+ <row>
6
+ <entry>Cell 1</entry>
7
+ <entry>Cell 2</entry>
8
+ <entry>Cell 3</entry>
9
+ </row>
10
+ </tbody>
11
+ XML
12
+ end
13
+
14
+ describe ".from_xml" do
15
+ subject(:tbody) { described_class.from_xml(xml) }
16
+
17
+ it "parses valign attribute" do
18
+ expect(tbody.valign).to eq("top")
19
+ end
20
+
21
+ it "parses rows" do
22
+ expect(tbody.rows.size).to eq(1)
23
+ expect(tbody.rows.first.entries.size).to eq(3)
24
+ expect(tbody.rows.first.entries.first.content).to eq("Cell 1")
25
+ end
26
+ end
27
+
28
+ describe "#to_xml" do
29
+ subject(:tbody) do
30
+ described_class.new(
31
+ valign: "top",
32
+ rows: [
33
+ Oasis::Etm::Row.new(
34
+ entries: [
35
+ Oasis::Etm::Entry.new(content: "Cell 1"),
36
+ Oasis::Etm::Entry.new(content: "Cell 2"),
37
+ Oasis::Etm::Entry.new(content: "Cell 3"),
38
+ ],
39
+ ),
40
+ ],
41
+ )
42
+ end
43
+
44
+ it "generates valid XML" do
45
+ expect(tbody.to_xml).to be_analogous_with(xml)
46
+ end
47
+ end
48
+ end
@@ -0,0 +1,97 @@
1
+ RSpec.describe Oasis::Etm::Tgroup do
2
+ let(:xml) do
3
+ <<~XML
4
+ <tgroup cols="3" colsep="1" rowsep="1" align="center">
5
+ <colspec colnum="1" colwidth="1*"/>
6
+ <colspec colnum="2" colwidth="2*"/>
7
+ <colspec colnum="3" colwidth="1*"/>
8
+ <thead>
9
+ <row>
10
+ <entry>Header 1</entry>
11
+ <entry>Header 2</entry>
12
+ <entry>Header 3</entry>
13
+ </row>
14
+ </thead>
15
+ <tbody>
16
+ <row>
17
+ <entry>Cell 1</entry>
18
+ <entry>Cell 2</entry>
19
+ <entry>Cell 3</entry>
20
+ </row>
21
+ </tbody>
22
+ </tgroup>
23
+ XML
24
+ end
25
+
26
+ describe ".from_xml" do
27
+ subject(:tgroup) { described_class.from_xml(xml) }
28
+
29
+ it "parses required attributes" do
30
+ expect(tgroup.cols).to eq(3)
31
+ end
32
+
33
+ it "parses optional attributes" do
34
+ expect(tgroup.colsep).to eq(1)
35
+ expect(tgroup.rowsep).to eq(1)
36
+ expect(tgroup.align).to eq("center")
37
+ end
38
+
39
+ it "parses colspecs" do
40
+ expect(tgroup.colspecs.size).to eq(3)
41
+ expect(tgroup.colspecs.first.colnum).to eq(1)
42
+ expect(tgroup.colspecs.first.colwidth).to eq("1*")
43
+ end
44
+
45
+ it "parses thead" do
46
+ expect(tgroup.thead).to be_a(Oasis::Etm::Thead)
47
+ expect(tgroup.thead.rows.size).to eq(1)
48
+ end
49
+
50
+ it "parses tbody" do
51
+ expect(tgroup.tbody).to be_a(Oasis::Etm::Tbody)
52
+ expect(tgroup.tbody.rows.size).to eq(1)
53
+ end
54
+ end
55
+
56
+ describe "#to_xml" do
57
+ subject(:tgroup) do
58
+ described_class.new(
59
+ cols: 3,
60
+ colsep: 1,
61
+ rowsep: 1,
62
+ align: "center",
63
+ colspecs: [
64
+ Oasis::Etm::Colspec.new(colnum: 1, colwidth: "1*"),
65
+ Oasis::Etm::Colspec.new(colnum: 2, colwidth: "2*"),
66
+ Oasis::Etm::Colspec.new(colnum: 3, colwidth: "1*"),
67
+ ],
68
+ thead: Oasis::Etm::Thead.new(
69
+ rows: [
70
+ Oasis::Etm::Row.new(
71
+ entries: [
72
+ Oasis::Etm::Entry.new(content: "Header 1"),
73
+ Oasis::Etm::Entry.new(content: "Header 2"),
74
+ Oasis::Etm::Entry.new(content: "Header 3"),
75
+ ],
76
+ ),
77
+ ],
78
+ ),
79
+ tbody: Oasis::Etm::Tbody.new(
80
+ rows: [
81
+ Oasis::Etm::Row.new(
82
+ entries: [
83
+ Oasis::Etm::Entry.new(content: "Cell 1"),
84
+ Oasis::Etm::Entry.new(content: "Cell 2"),
85
+ Oasis::Etm::Entry.new(content: "Cell 3"),
86
+ ],
87
+ ),
88
+ ],
89
+ ),
90
+ )
91
+ end
92
+
93
+ it "generates valid XML" do
94
+ expect(tgroup.to_xml).to be_analogous_with(xml)
95
+ end
96
+ end
97
+ end
@@ -0,0 +1,48 @@
1
+ RSpec.describe Oasis::Etm::Thead do
2
+ let(:xml) do
3
+ <<~XML
4
+ <thead valign="middle">
5
+ <row>
6
+ <entry>Header 1</entry>
7
+ <entry>Header 2</entry>
8
+ <entry>Header 3</entry>
9
+ </row>
10
+ </thead>
11
+ XML
12
+ end
13
+
14
+ describe ".from_xml" do
15
+ subject(:thead) { described_class.from_xml(xml) }
16
+
17
+ it "parses valign attribute" do
18
+ expect(thead.valign).to eq("middle")
19
+ end
20
+
21
+ it "parses rows" do
22
+ expect(thead.rows.size).to eq(1)
23
+ expect(thead.rows.first.entries.size).to eq(3)
24
+ expect(thead.rows.first.entries.first.content).to eq("Header 1")
25
+ end
26
+ end
27
+
28
+ describe "#to_xml" do
29
+ subject(:thead) do
30
+ described_class.new(
31
+ valign: "middle",
32
+ rows: [
33
+ Oasis::Etm::Row.new(
34
+ entries: [
35
+ Oasis::Etm::Entry.new(content: "Header 1"),
36
+ Oasis::Etm::Entry.new(content: "Header 2"),
37
+ Oasis::Etm::Entry.new(content: "Header 3"),
38
+ ],
39
+ ),
40
+ ],
41
+ )
42
+ end
43
+
44
+ it "generates valid XML" do
45
+ expect(thead.to_xml).to be_analogous_with(xml)
46
+ end
47
+ end
48
+ end
@@ -0,0 +1,81 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "pathname"
4
+
5
+ RSpec.describe Oasis::Etm do
6
+ fixtures_dir = Pathname.new(__dir__).join("../fixtures")
7
+
8
+ describe "XML round-trip conversion" do
9
+ describe "native XML" do
10
+ xml_files = Dir[fixtures_dir.join("native", "*.xml")]
11
+
12
+ xml_files.each do |file_path|
13
+ context "with file #{Pathname.new(file_path).relative_path_from(fixtures_dir)}" do
14
+ let(:xml_string) { File.read(file_path) }
15
+
16
+ it "performs lossless round-trip conversion" do
17
+ parsed = Oasis::Etm::Table.from_xml(xml_string)
18
+ generated = parsed.to_xml(
19
+ pretty: true,
20
+ declaration: true,
21
+ encoding: "utf-8",
22
+ )
23
+
24
+ cleaned_xml_string = xml_string
25
+ .gsub(/^<\?xml.*\n/, "")
26
+
27
+ expect(generated).to be_analogous_with(cleaned_xml_string)
28
+ end
29
+ end
30
+ end
31
+ end
32
+
33
+ describe "namespaced XML (ISOSTS)" do
34
+ xml_files = Dir[fixtures_dir.join("isosts", "*.xml")]
35
+
36
+ xml_files.each do |file_path|
37
+ context "with file #{Pathname.new(file_path).relative_path_from(fixtures_dir)}" do
38
+ let(:xml_string) { File.read(file_path) }
39
+
40
+ it "performs lossless round-trip conversion" do
41
+ parsed = Oasis::Etm::Table.from_xml(xml_string)
42
+ generated = parsed.to_xml(
43
+ pretty: true,
44
+ declaration: true,
45
+ encoding: "utf-8",
46
+ )
47
+
48
+ cleaned_xml_string = xml_string
49
+ .gsub(/^<\?xml.*\n/, "")
50
+
51
+ expect(generated).to be_analogous_with(cleaned_xml_string)
52
+ end
53
+ end
54
+ end
55
+ end
56
+
57
+ describe "namespaced XML (NISO JATS)" do
58
+ xml_files = Dir[fixtures_dir.join("niso-jats", "*.xml")]
59
+
60
+ xml_files.each do |file_path|
61
+ context "with file #{Pathname.new(file_path).relative_path_from(fixtures_dir)}" do
62
+ let(:xml_string) { File.read(file_path) }
63
+
64
+ it "performs lossless round-trip conversion" do
65
+ parsed = Oasis::Etm::Table.from_xml(xml_string)
66
+ generated = parsed.to_xml(
67
+ pretty: true,
68
+ declaration: true,
69
+ encoding: "utf-8",
70
+ )
71
+
72
+ cleaned_xml_string = xml_string
73
+ .gsub(/^<\?xml.*\n/, "")
74
+
75
+ expect(generated).to be_analogous_with(cleaned_xml_string)
76
+ end
77
+ end
78
+ end
79
+ end
80
+ end
81
+ end
@@ -0,0 +1,31 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "oasis-etm"
4
+ require "nokogiri"
5
+ require "xml-c14n"
6
+
7
+ # Require all support files
8
+ Dir[File.join(__dir__, "support", "**", "*.rb")].each { |f| require f }
9
+
10
+ RSpec.configure do |config|
11
+ # Enable flags like --only-failures and --next-failure
12
+ config.example_status_persistence_file_path = ".rspec_status"
13
+
14
+ # Disable RSpec exposing methods globally on `Module` and `main`
15
+ config.disable_monkey_patching!
16
+
17
+ config.expect_with :rspec do |c|
18
+ c.syntax = :expect
19
+ end
20
+ end
21
+
22
+ require "lutaml/model"
23
+ require "lutaml/model/xml_adapter/nokogiri_adapter"
24
+ require "lutaml/model/json_adapter/standard_json_adapter"
25
+ require "lutaml/model/yaml_adapter/standard_yaml_adapter"
26
+
27
+ Lutaml::Model::Config.configure do |config|
28
+ config.xml_adapter = Lutaml::Model::XmlAdapter::NokogiriAdapter
29
+ config.json_adapter = Lutaml::Model::JsonAdapter::StandardJsonAdapter
30
+ config.yaml_adapter = Lutaml::Model::YamlAdapter::StandardYamlAdapter
31
+ end