shale 0.6.0 → 0.8.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -1,6 +1,8 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  require_relative '../error'
4
+ require_relative '../mapping/group/dict_grouping'
5
+ require_relative '../mapping/group/xml_grouping'
4
6
  require_relative 'value'
5
7
 
6
8
  module Shale
@@ -16,11 +18,14 @@ module Shale
16
18
  # Convert Hash to Object using Hash/JSON/YAML/TOML mapping
17
19
  #
18
20
  # @param [Hash] hash Hash to convert
21
+ # @param [Array<Symbol>] only
22
+ # @param [Array<Symbol>] except
23
+ # @param [any] context
19
24
  #
20
- # @return [Shale::Mapper]
25
+ # @return [model instance]
21
26
  #
22
27
  # @api public
23
- def of_#{format}(hash)
28
+ def of_#{format}(hash, only: nil, except: nil, context: nil)
24
29
  instance = model.new
25
30
 
26
31
  attributes
@@ -29,72 +34,166 @@ module Shale
29
34
  .each { |attr| instance.send(attr.setter, attr.default.call) }
30
35
 
31
36
  mapping_keys = #{format}_mapping.keys
37
+ grouping = Shale::Mapping::Group::DictGrouping.new
38
+
39
+ only = to_partial_render_attributes(only)
40
+ except = to_partial_render_attributes(except)
32
41
 
33
42
  hash.each do |key, value|
34
43
  mapping = mapping_keys[key]
35
44
  next unless mapping
36
45
 
37
- if mapping.method_from
38
- new.send(mapping.method_from, instance, value)
46
+ if mapping.group
47
+ grouping.add(mapping, value)
48
+ elsif mapping.method_from
49
+ mapper = new
50
+
51
+ if mapper.method(mapping.method_from).arity == 3
52
+ mapper.send(mapping.method_from, instance, value, context)
53
+ else
54
+ mapper.send(mapping.method_from, instance, value)
55
+ end
39
56
  else
40
57
  attribute = attributes[mapping.attribute]
41
58
  next unless attribute
42
59
 
60
+ if only
61
+ attribute_only = only[attribute.name]
62
+ next unless only.key?(attribute.name)
63
+ end
64
+
65
+ if except
66
+ attribute_except = except[attribute.name]
67
+ next if except.key?(attribute.name) && attribute_except.nil?
68
+ end
69
+
43
70
  if value.nil?
44
71
  instance.send(attribute.setter, nil)
45
72
  elsif attribute.collection?
46
73
  [*value].each do |val|
47
- val = val ? attribute.type.of_#{format}(val) : val
74
+ if val
75
+ val = attribute.type.of_#{format}(
76
+ val,
77
+ only: attribute_only,
78
+ except: attribute_except,
79
+ context: context
80
+ )
81
+ end
82
+
48
83
  instance.send(attribute.name) << attribute.type.cast(val)
49
84
  end
50
85
  else
51
- val = attribute.type.of_#{format}(value)
86
+ val = attribute.type.of_#{format}(
87
+ value,
88
+ only: attribute_only,
89
+ except: attribute_except,
90
+ context: context
91
+ )
52
92
  instance.send(attribute.setter, attribute.type.cast(val))
53
93
  end
54
94
  end
55
95
  end
56
96
 
97
+ grouping.each do |group|
98
+ mapper = new
99
+
100
+ if mapper.method(group.method_from).arity == 3
101
+ mapper.send(group.method_from, instance, group.dict, context)
102
+ else
103
+ mapper.send(group.method_from, instance, group.dict)
104
+ end
105
+ end
106
+
57
107
  instance
58
108
  end
59
109
 
60
110
  # Convert Object to Hash using Hash/JSON/YAML/TOML mapping
61
111
  #
62
112
  # @param [any] instance Object to convert
113
+ # @param [Array<Symbol>] only
114
+ # @param [Array<Symbol>] except
115
+ # @param [any] context
63
116
  #
64
117
  # @raise [IncorrectModelError]
65
118
  #
66
119
  # @return [Hash]
67
120
  #
68
121
  # @api public
69
- def as_#{format}(instance)
122
+ def as_#{format}(instance, only: nil, except: nil, context: nil)
70
123
  unless instance.is_a?(model)
71
124
  msg = "argument is a '\#{instance.class}' but should be a '\#{model}'"
72
125
  raise IncorrectModelError, msg
73
126
  end
74
127
 
75
128
  hash = {}
129
+ grouping = Shale::Mapping::Group::DictGrouping.new
130
+
131
+ only = to_partial_render_attributes(only)
132
+ except = to_partial_render_attributes(except)
76
133
 
77
134
  #{format}_mapping.keys.each_value do |mapping|
78
- if mapping.method_to
79
- hash[mapping.name] = new.send(mapping.method_to, instance)
135
+ if mapping.group
136
+ grouping.add(mapping, nil)
137
+ elsif mapping.method_to
138
+ mapper = new
139
+
140
+ if mapper.method(mapping.method_to).arity == 3
141
+ mapper.send(mapping.method_to, instance, hash, context)
142
+ else
143
+ mapper.send(mapping.method_to, instance, hash)
144
+ end
80
145
  else
81
146
  attribute = attributes[mapping.attribute]
82
147
  next unless attribute
83
148
 
149
+ if only
150
+ attribute_only = only[attribute.name]
151
+ next unless only.key?(attribute.name)
152
+ end
153
+
154
+ if except
155
+ attribute_except = except[attribute.name]
156
+ next if except.key?(attribute.name) && attribute_except.nil?
157
+ end
158
+
84
159
  value = instance.send(attribute.name)
85
160
 
86
161
  if value.nil?
87
- hash[mapping.name] = nil
162
+ hash[mapping.name] = nil if mapping.render_nil?
88
163
  elsif attribute.collection?
89
- hash[mapping.name] = [*value].map do |v|
90
- v ? attribute.type.as_#{format}(v) : v
164
+ hash[mapping.name] = [*value].map do |val|
165
+ if val
166
+ attribute.type.as_#{format}(
167
+ val,
168
+ only: attribute_only,
169
+ except: attribute_except,
170
+ context: context
171
+ )
172
+ else
173
+ val
174
+ end
91
175
  end
92
176
  else
93
- hash[mapping.name] = attribute.type.as_#{format}(value)
177
+ hash[mapping.name] = attribute.type.as_#{format}(
178
+ value,
179
+ only: attribute_only,
180
+ except: attribute_except,
181
+ context: context
182
+ )
94
183
  end
95
184
  end
96
185
  end
97
186
 
187
+ grouping.each do |group|
188
+ mapper = new
189
+
190
+ if mapper.method(group.method_to).arity == 3
191
+ mapper.send(group.method_to, instance, hash, context)
192
+ else
193
+ mapper.send(group.method_to, instance, hash)
194
+ end
195
+ end
196
+
98
197
  hash
99
198
  end
100
199
  RUBY
@@ -107,80 +206,123 @@ module Shale
107
206
  # Convert JSON to Object
108
207
  #
109
208
  # @param [String] json JSON to convert
209
+ # @param [Array<Symbol>] only
210
+ # @param [Array<Symbol>] except
211
+ # @param [any] context
110
212
  #
111
- # @return [Shale::Mapper]
213
+ # @return [model instance]
112
214
  #
113
215
  # @api public
114
- def from_json(json)
115
- of_json(Shale.json_adapter.load(json))
216
+ def from_json(json, only: nil, except: nil, context: nil)
217
+ of_json(
218
+ Shale.json_adapter.load(json),
219
+ only: only,
220
+ except: except,
221
+ context: context
222
+ )
116
223
  end
117
224
 
118
225
  # Convert Object to JSON
119
226
  #
120
- # @param [Shale::Mapper] instance Object to convert
121
- # @param [Array<Symbol>] options
227
+ # @param [model instance] instance Object to convert
228
+ # @param [Array<Symbol>] only
229
+ # @param [Array<Symbol>] except
230
+ # @param [any] context
231
+ # @param [true, false] pretty
122
232
  #
123
233
  # @return [String]
124
234
  #
125
235
  # @api public
126
- def to_json(instance, *options)
127
- Shale.json_adapter.dump(as_json(instance), *options)
236
+ def to_json(instance, only: nil, except: nil, context: nil, pretty: false)
237
+ Shale.json_adapter.dump(
238
+ as_json(instance, only: only, except: except, context: context),
239
+ pretty: pretty
240
+ )
128
241
  end
129
242
 
130
243
  # Convert YAML to Object
131
244
  #
132
245
  # @param [String] yaml YAML to convert
246
+ # @param [Array<Symbol>] only
247
+ # @param [Array<Symbol>] except
248
+ # @param [any] context
133
249
  #
134
- # @return [Shale::Mapper]
250
+ # @return [model instance]
135
251
  #
136
252
  # @api public
137
- def from_yaml(yaml)
138
- of_yaml(Shale.yaml_adapter.load(yaml))
253
+ def from_yaml(yaml, only: nil, except: nil, context: nil)
254
+ of_yaml(
255
+ Shale.yaml_adapter.load(yaml),
256
+ only: only,
257
+ except: except,
258
+ context: context
259
+ )
139
260
  end
140
261
 
141
262
  # Convert Object to YAML
142
263
  #
143
- # @param [Shale::Mapper] instance Object to convert
264
+ # @param [model instance] instance Object to convert
265
+ # @param [Array<Symbol>] only
266
+ # @param [Array<Symbol>] except
267
+ # @param [any] context
144
268
  #
145
269
  # @return [String]
146
270
  #
147
271
  # @api public
148
- def to_yaml(instance)
149
- Shale.yaml_adapter.dump(as_yaml(instance))
272
+ def to_yaml(instance, only: nil, except: nil, context: nil)
273
+ Shale.yaml_adapter.dump(
274
+ as_yaml(instance, only: only, except: except, context: context)
275
+ )
150
276
  end
151
277
 
152
278
  # Convert TOML to Object
153
279
  #
154
280
  # @param [String] toml TOML to convert
281
+ # @param [Array<Symbol>] only
282
+ # @param [Array<Symbol>] except
283
+ # @param [any] context
155
284
  #
156
- # @return [Shale::Mapper]
285
+ # @return [model instance]
157
286
  #
158
287
  # @api public
159
- def from_toml(toml)
288
+ def from_toml(toml, only: nil, except: nil, context: nil)
160
289
  validate_toml_adapter
161
- of_toml(Shale.toml_adapter.load(toml))
290
+ of_toml(
291
+ Shale.toml_adapter.load(toml),
292
+ only: only,
293
+ except: except,
294
+ context: context
295
+ )
162
296
  end
163
297
 
164
298
  # Convert Object to TOML
165
299
  #
166
- # @param [Shale::Mapper] instance Object to convert
300
+ # @param [model instance] instance Object to convert
301
+ # @param [Array<Symbol>] only
302
+ # @param [Array<Symbol>] except
303
+ # @param [any] context
167
304
  #
168
305
  # @return [String]
169
306
  #
170
307
  # @api public
171
- def to_toml(instance)
308
+ def to_toml(instance, only: nil, except: nil, context: nil)
172
309
  validate_toml_adapter
173
- Shale.toml_adapter.dump(as_toml(instance))
310
+ Shale.toml_adapter.dump(
311
+ as_toml(instance, only: only, except: except, context: context)
312
+ )
174
313
  end
175
314
 
176
315
  # Convert XML document to Object
177
316
  #
178
- # @param [Shale::Adapter::<XML adapter>::Node] xml XML to convert
317
+ # @param [Shale::Adapter::<XML adapter>::Node] element
318
+ # @param [Array<Symbol>] only
319
+ # @param [Array<Symbol>] except
320
+ # @param [any] context
179
321
  #
180
- # @return [Shale::Mapper]
322
+ # @return [model instance]
181
323
  #
182
324
  # @api public
183
- def of_xml(element)
325
+ def of_xml(element, only: nil, except: nil, context: nil)
184
326
  instance = model.new
185
327
 
186
328
  attributes
@@ -188,16 +330,32 @@ module Shale
188
330
  .select { |attr| attr.default }
189
331
  .each { |attr| instance.send(attr.setter, attr.default.call) }
190
332
 
333
+ grouping = Shale::Mapping::Group::XmlGrouping.new
334
+
335
+ only = to_partial_render_attributes(only)
336
+ except = to_partial_render_attributes(except)
337
+
191
338
  element.attributes.each do |key, value|
192
339
  mapping = xml_mapping.attributes[key.to_s]
193
340
  next unless mapping
194
341
 
195
- if mapping.method_from
196
- new.send(mapping.method_from, instance, value)
342
+ if mapping.group
343
+ grouping.add(mapping, :attribute, value)
344
+ elsif mapping.method_from
345
+ mapper = new
346
+
347
+ if mapper.method(mapping.method_from).arity == 3
348
+ mapper.send(mapping.method_from, instance, value, context)
349
+ else
350
+ mapper.send(mapping.method_from, instance, value)
351
+ end
197
352
  else
198
353
  attribute = attributes[mapping.attribute]
199
354
  next unless attribute
200
355
 
356
+ next if only && !only.key?(attribute.name)
357
+ next if except&.key?(attribute.name)
358
+
201
359
  if attribute.collection?
202
360
  instance.send(attribute.name) << attribute.type.cast(value)
203
361
  else
@@ -209,14 +367,31 @@ module Shale
209
367
  content_mapping = xml_mapping.content
210
368
 
211
369
  if content_mapping
212
- if content_mapping.method_from
213
- new.send(content_mapping.method_from, instance, element)
370
+ if content_mapping.group
371
+ grouping.add(content_mapping, :content, element)
372
+ elsif content_mapping.method_from
373
+ mapper = new
374
+
375
+ if mapper.method(content_mapping.method_from).arity == 3
376
+ mapper.send(content_mapping.method_from, instance, element, context)
377
+ else
378
+ mapper.send(content_mapping.method_from, instance, element)
379
+ end
214
380
  else
215
381
  attribute = attributes[content_mapping.attribute]
216
382
 
217
383
  if attribute
218
- value = attribute.type.of_xml(element)
219
- instance.send(attribute.setter, attribute.type.cast(value))
384
+ skip = false
385
+
386
+ # rubocop:disable Metrics/BlockNesting
387
+ skip = true if only && !only.key?(attribute.name)
388
+ skip = true if except&.key?(attribute.name)
389
+
390
+ unless skip
391
+ value = attribute.type.of_xml(element)
392
+ instance.send(attribute.setter, attribute.type.cast(value))
393
+ end
394
+ # rubocop:enable Metrics/BlockNesting
220
395
  end
221
396
  end
222
397
  end
@@ -225,13 +400,36 @@ module Shale
225
400
  mapping = xml_mapping.elements[node.name]
226
401
  next unless mapping
227
402
 
228
- if mapping.method_from
229
- new.send(mapping.method_from, instance, node)
403
+ if mapping.group
404
+ grouping.add(mapping, :element, node)
405
+ elsif mapping.method_from
406
+ mapper = new
407
+
408
+ if mapper.method(mapping.method_from).arity == 3
409
+ mapper.send(mapping.method_from, instance, node, context)
410
+ else
411
+ mapper.send(mapping.method_from, instance, node)
412
+ end
230
413
  else
231
414
  attribute = attributes[mapping.attribute]
232
415
  next unless attribute
233
416
 
234
- value = attribute.type.of_xml(node)
417
+ if only
418
+ attribute_only = only[attribute.name]
419
+ next unless only.key?(attribute.name)
420
+ end
421
+
422
+ if except
423
+ attribute_except = except[attribute.name]
424
+ next if except.key?(attribute.name) && attribute_except.nil?
425
+ end
426
+
427
+ value = attribute.type.of_xml(
428
+ node,
429
+ only: attribute_only,
430
+ except: attribute_except,
431
+ context: context
432
+ )
235
433
 
236
434
  if attribute.collection?
237
435
  instance.send(attribute.name) << attribute.type.cast(value)
@@ -241,21 +439,39 @@ module Shale
241
439
  end
242
440
  end
243
441
 
442
+ grouping.each do |group|
443
+ mapper = new
444
+
445
+ if mapper.method(group.method_from).arity == 3
446
+ mapper.send(group.method_from, instance, group.dict, context)
447
+ else
448
+ mapper.send(group.method_from, instance, group.dict)
449
+ end
450
+ end
451
+
244
452
  instance
245
453
  end
246
454
 
247
455
  # Convert XML to Object
248
456
  #
249
457
  # @param [String] xml XML to convert
458
+ # @param [Array<Symbol>] only
459
+ # @param [Array<Symbol>] except
460
+ # @param [any] context
250
461
  #
251
462
  # @raise [AdapterError]
252
463
  #
253
- # @return [Shale::Mapper]
464
+ # @return [model instance]
254
465
  #
255
466
  # @api public
256
- def from_xml(xml)
467
+ def from_xml(xml, only: nil, except: nil, context: nil)
257
468
  validate_xml_adapter
258
- of_xml(Shale.xml_adapter.load(xml))
469
+ of_xml(
470
+ Shale.xml_adapter.load(xml),
471
+ only: only,
472
+ except: except,
473
+ context: context
474
+ )
259
475
  end
260
476
 
261
477
  # Convert Object to XML document
@@ -263,13 +479,24 @@ module Shale
263
479
  # @param [any] instance Object to convert
264
480
  # @param [String, nil] node_name XML node name
265
481
  # @param [Shale::Adapter::<xml adapter>::Document, nil] doc Object to convert
482
+ # @param [Array<Symbol>] only
483
+ # @param [Array<Symbol>] except
484
+ # @param [any] context
266
485
  #
267
486
  # @raise [IncorrectModelError]
268
487
  #
269
488
  # @return [::REXML::Document, ::Nokogiri::Document, ::Ox::Document]
270
489
  #
271
490
  # @api public
272
- def as_xml(instance, node_name = nil, doc = nil, _cdata = nil)
491
+ def as_xml(
492
+ instance,
493
+ node_name = nil,
494
+ doc = nil,
495
+ _cdata = nil,
496
+ only: nil,
497
+ except: nil,
498
+ context: nil
499
+ )
273
500
  unless instance.is_a?(model)
274
501
  msg = "argument is a '#{instance.class}' but should be a '#{model}'"
275
502
  raise IncorrectModelError, msg
@@ -277,7 +504,17 @@ module Shale
277
504
 
278
505
  unless doc
279
506
  doc = Shale.xml_adapter.create_document
280
- doc.add_element(doc.doc, as_xml(instance, xml_mapping.prefixed_root, doc))
507
+
508
+ element = as_xml(
509
+ instance,
510
+ xml_mapping.prefixed_root,
511
+ doc,
512
+ only: only,
513
+ except: except,
514
+ context: context
515
+ )
516
+ doc.add_element(doc.doc, element)
517
+
281
518
  return doc.doc
282
519
  end
283
520
 
@@ -288,37 +525,69 @@ module Shale
288
525
  xml_mapping.default_namespace.name
289
526
  )
290
527
 
528
+ grouping = Shale::Mapping::Group::XmlGrouping.new
529
+
530
+ only = to_partial_render_attributes(only)
531
+ except = to_partial_render_attributes(except)
532
+
291
533
  xml_mapping.attributes.each_value do |mapping|
292
- if mapping.method_to
293
- new.send(mapping.method_to, instance, element, doc)
534
+ if mapping.group
535
+ grouping.add(mapping, :attribute, nil)
536
+ elsif mapping.method_to
537
+ mapper = new
538
+
539
+ if mapper.method(mapping.method_to).arity == 4
540
+ mapper.send(mapping.method_to, instance, element, doc, context)
541
+ else
542
+ mapper.send(mapping.method_to, instance, element, doc)
543
+ end
294
544
  else
295
545
  attribute = attributes[mapping.attribute]
296
546
  next unless attribute
297
547
 
548
+ next if only && !only.key?(attribute.name)
549
+ next if except&.key?(attribute.name)
550
+
298
551
  value = instance.send(attribute.name)
299
- next if value.nil?
300
552
 
301
- doc.add_namespace(mapping.namespace.prefix, mapping.namespace.name)
302
- doc.add_attribute(element, mapping.prefixed_name, value)
553
+ if mapping.render_nil? || !value.nil?
554
+ doc.add_namespace(mapping.namespace.prefix, mapping.namespace.name)
555
+ doc.add_attribute(element, mapping.prefixed_name, value)
556
+ end
303
557
  end
304
558
  end
305
559
 
306
560
  content_mapping = xml_mapping.content
307
561
 
308
562
  if content_mapping
309
- if content_mapping.method_to
310
- new.send(content_mapping.method_to, instance, element, doc)
563
+ if content_mapping.group
564
+ grouping.add(content_mapping, :content, nil)
565
+ elsif content_mapping.method_to
566
+ mapper = new
567
+
568
+ if mapper.method(content_mapping.method_to).arity == 4
569
+ mapper.send(content_mapping.method_to, instance, element, doc, context)
570
+ else
571
+ mapper.send(content_mapping.method_to, instance, element, doc)
572
+ end
311
573
  else
312
574
  attribute = attributes[content_mapping.attribute]
313
575
 
314
576
  if attribute
315
- value = instance.send(attribute.name)
577
+ skip = false
316
578
 
317
579
  # rubocop:disable Metrics/BlockNesting
318
- if content_mapping.cdata
319
- doc.create_cdata(value.to_s, element)
320
- else
321
- doc.add_text(element, value.to_s)
580
+ skip = true if only && !only.key?(attribute.name)
581
+ skip = true if except&.key?(attribute.name)
582
+
583
+ unless skip
584
+ value = instance.send(attribute.name)
585
+
586
+ if content_mapping.cdata
587
+ doc.create_cdata(value.to_s, element)
588
+ else
589
+ doc.add_text(element, value.to_s)
590
+ end
322
591
  end
323
592
  # rubocop:enable Metrics/BlockNesting
324
593
  end
@@ -326,46 +595,111 @@ module Shale
326
595
  end
327
596
 
328
597
  xml_mapping.elements.each_value do |mapping|
329
- if mapping.method_to
330
- new.send(mapping.method_to, instance, element, doc)
598
+ if mapping.group
599
+ grouping.add(mapping, :element, nil)
600
+ elsif mapping.method_to
601
+ mapper = new
602
+
603
+ if mapper.method(mapping.method_to).arity == 4
604
+ mapper.send(mapping.method_to, instance, element, doc, context)
605
+ else
606
+ mapper.send(mapping.method_to, instance, element, doc)
607
+ end
331
608
  else
332
609
  attribute = attributes[mapping.attribute]
333
610
  next unless attribute
334
611
 
612
+ if only
613
+ attribute_only = only[attribute.name]
614
+ next unless only.key?(attribute.name)
615
+ end
616
+
617
+ if except
618
+ attribute_except = except[attribute.name]
619
+ next if except.key?(attribute.name) && attribute_except.nil?
620
+ end
621
+
335
622
  value = instance.send(attribute.name)
336
- next if value.nil?
337
623
 
338
- doc.add_namespace(mapping.namespace.prefix, mapping.namespace.name)
624
+ if mapping.render_nil? || !value.nil?
625
+ doc.add_namespace(mapping.namespace.prefix, mapping.namespace.name)
626
+ end
339
627
 
340
- if attribute.collection?
628
+ if value.nil?
629
+ if mapping.render_nil?
630
+ child = doc.create_element(mapping.prefixed_name)
631
+ doc.add_element(element, child)
632
+ end
633
+ elsif attribute.collection?
341
634
  [*value].each do |v|
342
635
  next if v.nil?
343
- child = attribute.type.as_xml(v, mapping.prefixed_name, doc, mapping.cdata)
636
+ child = attribute.type.as_xml(
637
+ v,
638
+ mapping.prefixed_name,
639
+ doc,
640
+ mapping.cdata,
641
+ only: attribute_only,
642
+ except: attribute_except,
643
+ context: context
644
+ )
344
645
  doc.add_element(element, child)
345
646
  end
346
647
  else
347
- child = attribute.type.as_xml(value, mapping.prefixed_name, doc, mapping.cdata)
648
+ child = attribute.type.as_xml(
649
+ value,
650
+ mapping.prefixed_name,
651
+ doc,
652
+ mapping.cdata,
653
+ only: attribute_only,
654
+ except: attribute_except,
655
+ context: context
656
+ )
348
657
  doc.add_element(element, child)
349
658
  end
350
659
  end
351
660
  end
352
661
 
662
+ grouping.each do |group|
663
+ mapper = new
664
+
665
+ if mapper.method(group.method_to).arity == 4
666
+ mapper.send(group.method_to, instance, element, doc, context)
667
+ else
668
+ mapper.send(group.method_to, instance, element, doc)
669
+ end
670
+ end
671
+
353
672
  element
354
673
  end
355
674
 
356
675
  # Convert Object to XML
357
676
  #
358
- # @param [Shale::Mapper] instance Object to convert
359
- # @param [Array<Symbol>] options
677
+ # @param [model instance] instance Object to convert
678
+ # @param [Array<Symbol>] only
679
+ # @param [Array<Symbol>] except
680
+ # @param [any] context
681
+ # @param [true, false] pretty
682
+ # @param [true, false] declaration
360
683
  #
361
684
  # @raise [AdapterError]
362
685
  #
363
686
  # @return [String]
364
687
  #
365
688
  # @api public
366
- def to_xml(instance, *options)
689
+ def to_xml(
690
+ instance,
691
+ only: nil,
692
+ except: nil,
693
+ context: nil,
694
+ pretty: false,
695
+ declaration: false
696
+ )
367
697
  validate_xml_adapter
368
- Shale.xml_adapter.dump(as_xml(instance), *options)
698
+ Shale.xml_adapter.dump(
699
+ as_xml(instance, only: only, except: except, context: context),
700
+ pretty: pretty,
701
+ declaration: declaration
702
+ )
369
703
  end
370
704
 
371
705
  private
@@ -387,55 +721,106 @@ module Shale
387
721
  def validate_xml_adapter
388
722
  raise AdapterError, XML_ADAPTER_NOT_SET_MESSAGE unless Shale.xml_adapter
389
723
  end
724
+
725
+ # Convert array with attributes to a hash
726
+ #
727
+ # @param [Array] ary
728
+ #
729
+ # @return [Hash, nil]
730
+ #
731
+ # @api private
732
+ def to_partial_render_attributes(ary)
733
+ return unless ary
734
+
735
+ ary.each_with_object([]) do |e, obj|
736
+ if e.is_a?(Hash)
737
+ obj.push(*e.to_a)
738
+ else
739
+ obj.push([e, nil])
740
+ end
741
+ end.to_h
742
+ end
390
743
  end
391
744
 
392
745
  # Convert Object to Hash
393
746
  #
747
+ # @param [Array<Symbol>] only
748
+ # @param [Array<Symbol>] except
749
+ # @param [any] context
750
+ #
394
751
  # @return [Hash]
395
752
  #
396
753
  # @api public
397
- def to_hash
398
- self.class.to_hash(self)
754
+ def to_hash(only: nil, except: nil, context: nil)
755
+ self.class.to_hash(self, only: only, except: except, context: context)
399
756
  end
400
757
 
401
758
  # Convert Object to JSON
402
759
  #
403
- # @param [Array<Symbol>] options
760
+ # @param [Array<Symbol>] only
761
+ # @param [Array<Symbol>] except
762
+ # @param [any] context
763
+ # @param [true, false] pretty
404
764
  #
405
765
  # @return [String]
406
766
  #
407
767
  # @api public
408
- def to_json(*options)
409
- self.class.to_json(self, *options)
768
+ def to_json(only: nil, except: nil, context: nil, pretty: false)
769
+ self.class.to_json(
770
+ self,
771
+ only: only,
772
+ except: except,
773
+ context: context,
774
+ pretty: pretty
775
+ )
410
776
  end
411
777
 
412
778
  # Convert Object to YAML
413
779
  #
780
+ # @param [Array<Symbol>] only
781
+ # @param [Array<Symbol>] except
782
+ # @param [any] context
783
+ #
414
784
  # @return [String]
415
785
  #
416
786
  # @api public
417
- def to_yaml
418
- self.class.to_yaml(self)
787
+ def to_yaml(only: nil, except: nil, context: nil)
788
+ self.class.to_yaml(self, only: only, except: except, context: context)
419
789
  end
420
790
 
421
791
  # Convert Object to TOML
422
792
  #
793
+ # @param [Array<Symbol>] only
794
+ # @param [Array<Symbol>] except
795
+ # @param [any] context
796
+ #
423
797
  # @return [String]
424
798
  #
425
799
  # @api public
426
- def to_toml
427
- self.class.to_toml(self)
800
+ def to_toml(only: nil, except: nil, context: nil)
801
+ self.class.to_toml(self, only: only, except: except, context: context)
428
802
  end
429
803
 
430
804
  # Convert Object to XML
431
805
  #
432
- # @param [Array<Symbol>] options
806
+ # @param [Array<Symbol>] only
807
+ # @param [Array<Symbol>] except
808
+ # @param [any] context
809
+ # @param [true, false] pretty
810
+ # @param [true, false] declaration
433
811
  #
434
812
  # @return [String]
435
813
  #
436
814
  # @api public
437
- def to_xml(*options)
438
- self.class.to_xml(self, *options)
815
+ def to_xml(only: nil, except: nil, context: nil, pretty: false, declaration: false)
816
+ self.class.to_xml(
817
+ self,
818
+ only: only,
819
+ except: except,
820
+ context: context,
821
+ pretty: pretty,
822
+ declaration: declaration
823
+ )
439
824
  end
440
825
  end
441
826
  end