faraday-xml 0.0.1 → 0.2.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 777d8a0d7887223960c5ec14c5be37e7ceb50a8c7cd0abf33a070330f8c57a6d
4
- data.tar.gz: de298ca9f99ff381b232996351d33bcbc72ff8343d3ee8f8ab24cfdaf0f15c32
3
+ metadata.gz: fd31db052ce943d7b8f60e8396449da83c134b70f3fe59f52e105edf1105f20d
4
+ data.tar.gz: 80348c82aa221ff79dbb488bf11b7df6adecbb877887165899a6d057197bc12d
5
5
  SHA512:
6
- metadata.gz: 1933ead1a4cf3a3de25e773c2e3787df00962ae2039a0182051b2dea3fee6abe029901ca3129b66fdf23129f65b309731061a8f3cd2af860e6c134e24e3dfe69
7
- data.tar.gz: 8dd8bcb901bbdcede8df0e077ffc20a1db75d2b9cb78cc973b9a5dbcb26ccd64b7721792c4ee91f2cda4753402a633e32fe16cd7706b15de584e697f0bdd0735
6
+ metadata.gz: 33acfe362ff340f1e39f40a1610c77b98ccd89d7b0e107625fd2d7fc4ef08ed52c34166a3903cdb64514f5861a7420d181495355572d772be0b697870fb5986f
7
+ data.tar.gz: 347b1ab466889029e44fb4cba75d5845bcf959544154d4fc8cb653a2988397f8a7edb19e4e7115d77594e83962ac07a017c0ab15f8fba76339fc3124b6676b23
data/CHANGELOG.md CHANGED
@@ -1,5 +1,11 @@
1
1
  # Changelog
2
2
 
3
- ## Unreleased
3
+ ## [Unreleased](https://github.com/gemhome/faraday-xml/compare/v0.2.0...main)
4
4
 
5
- * Initial release.
5
+ ## [0.2.0](https://github.com/gemhome/faraday-xml/compare/v0.1.0...v0.2.0)
6
+
7
+ * feat: simple Hash -> XML request encoder
8
+
9
+ ## [0.1.0](https://github.com/gemhome/faraday-xml/blob/v0.1.0) (2023-01-12)
10
+
11
+ * feat: Initial release.
data/README.md CHANGED
@@ -29,9 +29,19 @@ gem install faraday-xml
29
29
  ## Usage
30
30
 
31
31
  ```ruby
32
+ require 'faraday'
32
33
  require 'faraday/xml'
33
34
 
34
- # TODO
35
+ conn = Faraday.new do |builder|
36
+ builder.headers.update(
37
+ "Accept" => "application/xml",
38
+ "Content-Type" => "application/xml;charset=UTF-8",
39
+ )
40
+ # or builder.use Faraday::XML::Request
41
+ builder.request :xml # encode Hash as XML
42
+ # or builder.use Faraday::XML::Response
43
+ builder.response :xml # decode response bodies from XML
44
+ end
35
45
  ```
36
46
 
37
47
  ## Development
@@ -0,0 +1,135 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Faraday
4
+ module XML
5
+ # Request middleware that encodes the body as XML.
6
+ #
7
+ # Processes only requests with matching Content-type or those without a type.
8
+ # If a request doesn't have a type but has a body, it sets the Content-type
9
+ # to XML MIME-type.
10
+ #
11
+ # Doesn't try to encode bodies that already are in string form.
12
+ class Request < Middleware # rubocop:disable Metrics/ClassLength
13
+ MIME_TYPE = 'application/xml'
14
+ MIME_TYPE_REGEX = %r{^application/(vnd\..+\+)?xml$}.freeze
15
+
16
+ def initialize(app = nil, options = {})
17
+ super(app)
18
+ @encoder_options = options.fetch(:encoder_options, {})
19
+ end
20
+
21
+ def on_request(env)
22
+ match_content_type(env) do |data|
23
+ env[:body] = encode(data)
24
+ end
25
+ end
26
+
27
+ def encoder
28
+ @encoder ||= nil
29
+ if @encoder.nil?
30
+ @encoder = set_encoder
31
+ @encoder && test_encoder
32
+ end
33
+ @encoder or raise 'Missing dependencies Builder'
34
+ end
35
+
36
+ private
37
+
38
+ def encode(data)
39
+ encoder.call(data)
40
+ end
41
+
42
+ def test_encoder
43
+ encode({ success: true })
44
+ end
45
+
46
+ def set_encoder
47
+ @encoder ||= # rubocop:disable Naming/MemoizedInstanceVariableName
48
+ begin
49
+ require 'builder'
50
+ lambda do |parameter_hash|
51
+ parameters_as_xml(parameter_hash)
52
+ end
53
+ rescue LoadError # rubocop:disable Lint/SuppressedException
54
+ end
55
+ end
56
+
57
+ def match_content_type(env)
58
+ return unless process_request?(env)
59
+
60
+ env[:request_headers][CONTENT_TYPE] ||= MIME_TYPE
61
+ yield env[:body] unless env[:body].respond_to?(:to_str)
62
+ end
63
+
64
+ def process_request?(env)
65
+ type = request_type(env)
66
+ body?(env) && (type.empty? || type.match?(MIME_TYPE_REGEX))
67
+ end
68
+
69
+ def body?(env)
70
+ (body = env[:body]) && !(body.respond_to?(:to_str) && body.empty?)
71
+ end
72
+
73
+ def request_type(env)
74
+ type = env[:request_headers][CONTENT_TYPE].to_s
75
+ type = type.split(';', 2).first if type.index(';')
76
+ type
77
+ end
78
+
79
+ def parameters_as_xml(parameter_hash) # rubocop:disable Metrics/MethodLength
80
+ xml_markup = build_xml_markup(skip_instruct: true)
81
+ parameter_hash.each_pair do |key, value|
82
+ key = key.to_s
83
+ if _parameter_as_xml?(value)
84
+ xml_markup.tag!(key) do
85
+ xml = _parameter_as_xml(value)
86
+ xml_markup << xml
87
+ end
88
+ else
89
+ xml_markup.tag!(key, _parameter_as_xml(value))
90
+ end
91
+ end
92
+ xml_markup.target!
93
+ end
94
+
95
+ def _parameter_as_xml?(value)
96
+ case value
97
+ when Hash, Array then true
98
+ else false
99
+ end
100
+ end
101
+
102
+ def _parameter_as_xml(value)
103
+ case value
104
+ when Hash
105
+ parameters_as_xml(value) # recursive case
106
+ when Array
107
+ _parameter_as_list_xml(value) # recursive case
108
+ else
109
+ value.to_s.encode(xml: :text) # end case
110
+ end
111
+ end
112
+
113
+ def _parameter_as_list_xml(array_of_hashes)
114
+ xml_markup = build_xml_markup(skip_instruct: true)
115
+ array_of_hashes.each do |value|
116
+ xml_markup << parameters_as_xml(value) # recursive case
117
+ end
118
+ xml_markup.target!
119
+ end
120
+
121
+ def build_xml_markup(**options)
122
+ # https://github.com/rails/rails/blob/86fd8d0143b1a0578b359f4b86fea94c718139ae/activesupport/lib/active_support/builder.rb
123
+ # https://github.com/rails/rails/blob/86fd8d0143b1a0578b359f4b86fea94c718139ae/activesupport/lib/active_support/core_ext/hash/conversions.rb
124
+ require 'builder'
125
+ options.merge!(@encoder_options)
126
+ options[:indent] = 2 unless options.key?(:indent)
127
+ xml_markup = ::Builder::XmlMarkup.new(**options)
128
+ if !options.delete(:skip_instruct) # rubocop:disable Style/NegatedIf
129
+ xml_markup.instruct! :xml, version: '1.0', encoding: 'UTF-8'
130
+ end
131
+ xml_markup
132
+ end
133
+ end
134
+ end
135
+ end
@@ -4,11 +4,11 @@ module Faraday
4
4
  module XML
5
5
  # Parse response bodies as XML
6
6
  class Response < Faraday::Middleware
7
- def initialize(app = nil, parser_options: nil, content_type: /\bxml$/, preserve_raw: false)
7
+ def initialize(app = nil, options = {})
8
8
  super(app)
9
- @parser_options = parser_options
10
- @content_types = Array(content_type)
11
- @preserve_raw = preserve_raw
9
+ @parser_options = options[:parser_options]
10
+ @content_types = Array(options.fetch(:content_type, /\bxml$/))
11
+ @preserve_raw = options.fetch(:preserve_raw, false)
12
12
  end
13
13
 
14
14
  # @param env [Faraday::Env] the environment of the response being processed.
@@ -16,6 +16,15 @@ module Faraday
16
16
  process_response(env) if parse_response?(env)
17
17
  end
18
18
 
19
+ def parser
20
+ @parser ||= nil
21
+ if @parser.nil?
22
+ @parser = set_parser
23
+ @parser && test_parser
24
+ end
25
+ @parser or raise 'Missing dependencies ActiveSupport::XmlMini or MultiXml'
26
+ end
27
+
19
28
  private
20
29
 
21
30
  def process_response(env)
@@ -32,19 +41,10 @@ module Faraday
32
41
  end
33
42
 
34
43
  def test_parser
35
- parse("<success>true</success>")
44
+ parse('<success>true</success>')
36
45
  end
37
46
 
38
- def parser # rubocop:disable Metrics/MethodLength
39
- @parser ||= nil
40
- if @parser.nil?
41
- @parser = set_parser
42
- @parser && test_parser
43
- end
44
- @parser or raise 'Missing dependencies ActiveSupport::XmlMini or MultiXml'
45
- end
46
-
47
- def set_parser
47
+ def set_parser # rubocop:disable Metrics/MethodLength
48
48
  @parser ||=
49
49
  begin
50
50
  require 'multi_xml'
@@ -53,10 +53,9 @@ module Faraday
53
53
  end
54
54
  rescue LoadError # rubocop:disable Lint/SuppressedException
55
55
  end
56
- @parser ||=
56
+ @parser ||= # rubocop:disable Naming/MemoizedInstanceVariableName
57
57
  begin
58
58
  require 'active_support'
59
- # require 'active_support/isolated_execution_state'
60
59
  require 'active_support/xml_mini'
61
60
  require 'active_support/core_ext/hash/conversions'
62
61
  require 'active_support/core_ext/array/conversions'
@@ -2,6 +2,6 @@
2
2
 
3
3
  module Faraday
4
4
  module XML
5
- VERSION = '0.0.1'
5
+ VERSION = '0.2.0'
6
6
  end
7
7
  end
data/lib/faraday/xml.rb CHANGED
@@ -1,5 +1,6 @@
1
1
  # frozen_string_literal: true
2
2
 
3
+ require_relative 'xml/request'
3
4
  require_relative 'xml/response'
4
5
  require_relative 'xml/version'
5
6
 
@@ -7,7 +8,12 @@ module Faraday
7
8
  # The Faraday::XML middleware main module
8
9
  module XML
9
10
  # Load middleware with
10
- # conn.response Faraday::XML::Response
11
+ # conn.use Faraday::XML::Request
12
+ # or
13
+ # conn.request :xml
14
+ Faraday::Request.register_middleware(xml: Faraday::XML::Request)
15
+ # Load middleware with
16
+ # conn.use Faraday::XML::Response
11
17
  # or
12
18
  # conn.response :xml
13
19
  Faraday::Response.register_middleware(xml: Faraday::XML::Response)
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: faraday-xml
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.1
4
+ version: 0.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Benjamin Fleischer
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2023-01-12 00:00:00.000000000 Z
11
+ date: 2023-01-23 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: faraday
@@ -155,6 +155,7 @@ files:
155
155
  - LICENSE.md
156
156
  - README.md
157
157
  - lib/faraday/xml.rb
158
+ - lib/faraday/xml/request.rb
158
159
  - lib/faraday/xml/response.rb
159
160
  - lib/faraday/xml/version.rb
160
161
  homepage: https://github.com/gemhome/faraday-xml
@@ -162,8 +163,8 @@ licenses:
162
163
  - MIT
163
164
  metadata:
164
165
  bug_tracker_uri: https://github.com/gemhome/faraday-xml/issues
165
- changelog_uri: https://github.com/gemhome/faraday-xml/blob/v0.0.1/CHANGELOG.md
166
- documentation_uri: http://www.rubydoc.info/gems/faraday-xml/0.0.1
166
+ changelog_uri: https://github.com/gemhome/faraday-xml/blob/v0.2.0/CHANGELOG.md
167
+ documentation_uri: http://www.rubydoc.info/gems/faraday-xml/0.2.0
167
168
  homepage_uri: https://github.com/gemhome/faraday-xml
168
169
  rubygems_mfa_required: 'true'
169
170
  source_code_uri: https://github.com/gemhome/faraday-xml