mbrao 1.2.3 → 1.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 (55) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +3 -0
  3. data/CHANGELOG.md +5 -0
  4. data/doc/ActionView/Template/Handlers/MbraoTemplate.html +87 -20
  5. data/doc/ActionView/Template/Handlers.html +1 -1
  6. data/doc/HTML/Pipeline/KramdownFilter.html +1 -1
  7. data/doc/HTML/Pipeline.html +1 -1
  8. data/doc/HTML.html +1 -1
  9. data/doc/Mbrao/Author.html +337 -67
  10. data/doc/Mbrao/Content.html +1268 -444
  11. data/doc/Mbrao/ContentPublicInterface.html +24 -20
  12. data/doc/Mbrao/Exceptions/InvalidDate.html +1 -1
  13. data/doc/Mbrao/Exceptions/InvalidMetadata.html +1 -1
  14. data/doc/Mbrao/Exceptions/Parsing.html +1 -1
  15. data/doc/Mbrao/Exceptions/Rendering.html +1 -1
  16. data/doc/Mbrao/Exceptions/UnavailableLocalization.html +1 -1
  17. data/doc/Mbrao/Exceptions/Unimplemented.html +1 -1
  18. data/doc/Mbrao/Exceptions/UnknownEngine.html +1 -1
  19. data/doc/Mbrao/Exceptions.html +1 -1
  20. data/doc/Mbrao/Parser.html +11 -11
  21. data/doc/Mbrao/ParsingEngines/Base.html +25 -24
  22. data/doc/Mbrao/ParsingEngines/PlainText.html +17 -16
  23. data/doc/Mbrao/ParsingEngines.html +1 -1
  24. data/doc/Mbrao/PublicInterface/ClassMethods.html +312 -19
  25. data/doc/Mbrao/PublicInterface.html +1 -1
  26. data/doc/Mbrao/RenderingEngines/Base.html +7 -7
  27. data/doc/Mbrao/RenderingEngines/HtmlPipeline.html +27 -15
  28. data/doc/Mbrao/RenderingEngines.html +1 -1
  29. data/doc/Mbrao/Validations/ClassMethods.html +21 -21
  30. data/doc/Mbrao/Validations.html +1 -1
  31. data/doc/Mbrao/Version.html +3 -3
  32. data/doc/Mbrao.html +1 -1
  33. data/doc/_index.html +1 -1
  34. data/doc/file.README.html +1 -1
  35. data/doc/index.html +1 -1
  36. data/doc/method_list.html +86 -62
  37. data/doc/top-level-namespace.html +1 -1
  38. data/lib/mbrao/author.rb +18 -4
  39. data/lib/mbrao/content.rb +93 -44
  40. data/lib/mbrao/integrations/rails.rb +12 -5
  41. data/lib/mbrao/parser.rb +23 -0
  42. data/lib/mbrao/parsing_engines/base.rb +12 -11
  43. data/lib/mbrao/parsing_engines/plain_text.rb +29 -23
  44. data/lib/mbrao/rendering_engines/base.rb +4 -4
  45. data/lib/mbrao/rendering_engines/html_pipeline.rb +7 -2
  46. data/lib/mbrao/version.rb +2 -2
  47. data/spec/mbrao/author_spec.rb +32 -16
  48. data/spec/mbrao/content_spec.rb +144 -85
  49. data/spec/mbrao/integrations/rails_spec.rb +14 -0
  50. data/spec/mbrao/parser_spec.rb +19 -19
  51. data/spec/mbrao/parsing_engines/base_spec.rb +12 -12
  52. data/spec/mbrao/parsing_engines/plain_text_spec.rb +21 -21
  53. data/spec/mbrao/rendering_engines/base_spec.rb +2 -2
  54. data/spec/mbrao/rendering_engines/html_pipeline_spec.rb +31 -31
  55. metadata +2 -2
data/lib/mbrao/content.rb CHANGED
@@ -19,7 +19,8 @@ module Mbrao
19
19
  # Gets the title of the content in the desired locales.
20
20
  #
21
21
  # @param locales [String|Array] The desired locales. Can include `*` to match all. If none are specified, the default mbrao locale will be used.
22
- # @return [String|HashWithIndifferentAccess] Return the title of the content in the desired locales. If only one locale is required, then a `String` is returned, else a `HashWithIndifferentAccess` with locales as keys.
22
+ # @return [String|HashWithIndifferentAccess] Return the title of the content in the desired locales. If only one locale is required, then a `String`
23
+ # is returned, else a `HashWithIndifferentAccess` with locales as keys.
23
24
  def get_title(locales = [])
24
25
  filter_attribute_for_locales(@title, locales)
25
26
  end
@@ -28,7 +29,8 @@ module Mbrao
28
29
  #
29
30
  # @param locales [String|Array] The desired locales. Can include `*` to match all. If none are specified, the default mbrao locale will be used.
30
31
  # @param engine [String|Symbol|Object] The engine to use to filter contents.
31
- # @return [String|HashWithIndifferentAccess] Return the body of the content in the desired locales. If only one locale is required, then a `String` is returned, else a `HashWithIndifferentAccess` with locales as keys.
32
+ # @return [String|HashWithIndifferentAccess] Return the body of the content in the desired locales. If only one locale is required, then a `String`
33
+ # is returned, else a `HashWithIndifferentAccess` with locales as keys.
32
34
  def get_body(locales = [], engine = :plain_text)
33
35
  Mbrao::Parser.create_engine(engine).filter_content(self, locales)
34
36
  end
@@ -36,7 +38,8 @@ module Mbrao
36
38
  # Gets the tags of the content in the desired locales.
37
39
  #
38
40
  # @param locales [String|Array] The desired locales. Can include `*` to match all. If none are specified, the default mbrao locale will be used.
39
- # @return [Array|HashWithIndifferentAccess] Return the title of the content in the desired locales. If only one locale is required, then a `Array` is returned, else a `HashWithIndifferentAccess` with locales as keys.
41
+ # @return [Array|HashWithIndifferentAccess] Return the title of the content in the desired locales. If only one locale is required, then a `Array`
42
+ # is returned, else a `HashWithIndifferentAccess` with locales as keys.
40
43
  def get_tags(locales = [])
41
44
  filter_attribute_for_locales(@tags, locales)
42
45
  end
@@ -44,7 +47,8 @@ module Mbrao
44
47
  # Gets the "more link" text of the content in the desired locales.
45
48
  #
46
49
  # @param locales [String|Array] The desired locales. Can include `*` to match all. If none are specified, the default mbrao locale will be used.
47
- # @return [String|HashWithIndifferentAccess] Return the label of the "more link" of the content in the desired locales. If only one locale is required, then a `String` is returned, else a `HashWithIndifferentAccess` with locales as keys.
50
+ # @return [String|HashWithIndifferentAccess] Return the label of the "more link" of the content in the desired locales. If only one locale is required,
51
+ # then a `String` is returned, else a `HashWithIndifferentAccess` with locales as keys.
48
52
  def get_more(locales = [])
49
53
  filter_attribute_for_locales(@more, locales)
50
54
  end
@@ -54,7 +58,8 @@ module Mbrao
54
58
  #
55
59
  # @param attribute [Object|HashWithIndifferentAccess] The desired attribute.
56
60
  # @param locales [String|Array] The desired locales. Can include `*` to match all. If none are specified, the default mbrao locale will be used.
57
- # @return [String|HashWithIndifferentAccess] Return the object for desired locales. If only one locale is available, then only a object is returned, else a `HashWithIndifferentAccess` with locales as keys.
61
+ # @return [String|HashWithIndifferentAccess] Return the object for desired locales. If only one locale is available, then only a object is returned,
62
+ # else a `HashWithIndifferentAccess` with locales as keys.
58
63
  def filter_attribute_for_locales(attribute, locales)
59
64
  locales = ::Mbrao::Content.validate_locales(locales, self)
60
65
 
@@ -70,7 +75,8 @@ module Mbrao
70
75
  #
71
76
  # @param hash [Hash] The hash to handle.
72
77
  # @param locale [String] The list of locale (separated by commas) for which the value is available.
73
- # @param locales [Array] The list of locale for which this value is requested. Can include `*` to match all. If none are specified, the default mbrao locale will be used.
78
+ # @param locales [Array] The list of locale for which this value is requested. Can include `*` to match all. If none are specified, the default mbrao
79
+ # locale will be used.
74
80
  # @param value [Object] The value to add.
75
81
  # @return [Hash] Return the original hash.
76
82
  def append_value_for_locale(hash, locale, locales, value)
@@ -89,13 +95,17 @@ module Mbrao
89
95
  # @attribute locales
90
96
  # @return [Array] A list of locales for this content should be visible. An empty list means that there are no limitations.
91
97
  # @attribute title
92
- # @return [String|HashWithIndifferentAccess] The content's title. Can be a `String` or an `HashWithIndifferentAccess`, if multiple title are specified for multiple locales.
98
+ # @return [String|HashWithIndifferentAccess] The content's title. Can be a `String` or an `HashWithIndifferentAccess`, if multiple title are specified for
99
+ # multiple locales.
93
100
  # @attribute body
94
- # @return [String|HashWithIndifferentAccess] The content's body. Can be a `String` or an `HashWithIndifferentAccess`, if multiple contents are specified for multiple locales.
101
+ # @return [String|HashWithIndifferentAccess] The content's body. Can be a `String` or an `HashWithIndifferentAccess`, if multiple contents are specified
102
+ # for multiple locales.
95
103
  # @attribute tags
96
- # @return [String|HashWithIndifferentAccess] The content's "more link" label. Can be a `String` or an `HashWithIndifferentAccess`, if multiple labels are specified for multiple locales.
104
+ # @return [String|HashWithIndifferentAccess] The content's "more link" label. Can be a `String` or an `HashWithIndifferentAccess`, if multiple labels are
105
+ # specified for multiple locales.
97
106
  # @attribute tags
98
- # @return [Array|HashWithIndifferentAccess] The tags associated with the content. Can be an `Array` or an `HashWithIndifferentAccess`, if multiple tags set are specified for multiple locales.
107
+ # @return [Array|HashWithIndifferentAccess] The tags associated with the content. Can be an `Array` or an `HashWithIndifferentAccess`, if multiple tags set
108
+ # are specified for multiple locales.
99
109
  # @attribute author
100
110
  # @return [Author] The post author.
101
111
  # @attribute created_at
@@ -134,9 +144,10 @@ module Mbrao
134
144
 
135
145
  # Sets the `title` attribute.
136
146
  #
137
- # @param value [String|Hash] The new value for the attribute. If an Hash, keys must be a string with one or locale separated by commas. A empty or "*" will be the default value.
138
- def title=(value)
139
- @title = value.is_a?(Hash) ? value.ensure_hash(:indifferent, nil, :ensure_string) : value.ensure_string
147
+ # @param new_title [String|Hash] The new value for the attribute. If an Hash, keys must be a string with one or locale separated by commas.
148
+ # A empty or "*" will be the default value.
149
+ def title=(new_title)
150
+ @title = is_hash?(new_title) ? new_title.ensure_hash(:indifferent, nil, :ensure_string) : new_title.ensure_string
140
151
  end
141
152
 
142
153
  # Sets the `body` attribute.
@@ -148,33 +159,35 @@ module Mbrao
148
159
 
149
160
  # Sets the `tags` attribute.
150
161
  #
151
- # @param value [Array|Hash] The new value for the attribute. If an Hash, keys must be a string with one or locale separated by commas. A empty or "*" will be the default value.
152
- def tags=(value)
153
- @tags = if value.is_a?(Hash) then
154
- value.ensure_hash(:indifferent) { |v| v.ensure_array(nil, true, true, true, :ensure_string) }
162
+ # @param new_tags [Array|Hash] The new value for the attribute. If an Hash, keys must be a string with one or locale separated by commas.
163
+ # A empty or "*" will be the default value. Tags can also be comma-separated.
164
+ def tags=(new_tags)
165
+ @tags = if is_hash?(new_tags) then
166
+ new_tags.ensure_hash(:indifferent) { |v| parse_tags(v) }
155
167
  else
156
- value.ensure_array(nil, true, true, true, :ensure_string)
168
+ parse_tags(new_tags)
157
169
  end
158
170
  end
159
171
 
160
172
  # Sets the `more` attribute.
161
173
  #
162
- # @param value [String|Hash] The new value for the attribute. If an Hash, keys must be a string with one or locale separated by commas. A empty or "*" will be the default value.
163
- def more=(value)
164
- @more = value.is_a?(Hash) ? value.ensure_hash(:indifferent, nil, :ensure_string) : value.ensure_string
174
+ # @param new_more [String|Hash] The new value for the attribute. If an Hash, keys must be a string with one or locale separated by commas.
175
+ # A empty or "*" will be the default value.
176
+ def more=(new_more)
177
+ @more = is_hash?(new_more) ? new_more.ensure_hash(:indifferent, nil, :ensure_string) : new_more.ensure_string
165
178
  end
166
179
 
167
180
  # Sets the `author` attribute.
168
181
  #
169
- # @param value [Author|Hash|Object] The new value for the attribute.
170
- def author=(value)
171
- if value.is_a?(Mbrao::Author) then
172
- @author = value
173
- elsif value.is_a?(Hash) then
174
- value = value.ensure_hash(:indifferent)
175
- @author = Mbrao::Author.new(value["name"], value["email"], value["website"], value["image"], value["metadata"], value["uid"])
182
+ # @param new_author [Author|Hash|Object|NilClass] The new value for the attribute.
183
+ def author=(new_author)
184
+ if new_author.is_a?(Mbrao::Author) then
185
+ @author = new_author
186
+ elsif is_hash?(new_author) then
187
+ new_author = new_author.ensure_hash(:indifferent)
188
+ @author = Mbrao::Author.create(new_author)
176
189
  else
177
- @author = Mbrao::Author.new(value.ensure_string)
190
+ @author = new_author ? Mbrao::Author.new(new_author.ensure_string) : nil
178
191
  end
179
192
  end
180
193
 
@@ -202,18 +215,32 @@ module Mbrao
202
215
 
203
216
  # Sets the `metadata` attribute.
204
217
  #
205
- # @param value [Hash] The new value for the attribute.
206
- def metadata=(value)
207
- if value.is_a?(Hash) then
208
- @metadata = value.ensure_hash(:indifferent)
218
+ # @param new_metadata [Hash] The new value for the attribute.
219
+ def metadata=(new_metadata)
220
+ if is_hash?(new_metadata) then
221
+ @metadata = new_metadata.ensure_hash(:indifferent)
209
222
  else
210
- @metadata = HashWithIndifferentAccess.new({raw: value})
223
+ @metadata = HashWithIndifferentAccess.new({raw: new_metadata})
211
224
  end
212
225
  end
213
226
 
227
+ # Returns the content as an Hash.
228
+ #
229
+ # @param options [Hash] Options to modify behavior of the serialization.
230
+ # The only supported value are:
231
+ #
232
+ # * `:exclude`, an array of attributes to skip.
233
+ # * `:exclude_empty`, if to exclude nil values. Default is `false`.
234
+ # @return [Hash] An hash with all attributes.
235
+ def as_json(options = {})
236
+ keys = [:uid, :locales, :title, :body, :tags, :more, :author, :created_at, :updated_at, :metadata]
237
+ ::Mbrao::Parser.as_json(self, keys, options)
238
+ end
239
+
214
240
  # Validates locales for attribute retrieval.
215
241
  #
216
- # @param locales [Array] A list of desired locales for an attribute. Can include `*` to match all. If none are specified, the default mbrao locale will be used.
242
+ # @param locales [Array] A list of desired locales for an attribute. Can include `*` to match all. If none are specified, the default mbrao locale will be
243
+ # used.
217
244
  # @param content [Content|nil] An optional content to check for availability
218
245
  # @return [Array] The validated list of locales.
219
246
  def self.validate_locales(locales, content = nil)
@@ -278,21 +305,43 @@ module Mbrao
278
305
  # Extracts a date and time from a value.
279
306
  #
280
307
  # @param value [String|DateTime|Fixnum] The value to parse.
281
- # @return [DateTime] The extract values.
308
+ # @return [DateTime] The extracted value.
282
309
  def extract_datetime(value)
283
310
  begin
284
- if value.is_a?(Date) || value.is_a?(Time) then
285
- value = value.to_datetime
286
- elsif value.to_float > 0 then
287
- value = Time.at(value.to_float).to_datetime
288
- elsif value && !value.is_a?(DateTime) then
289
- value = DateTime.strptime(value.ensure_string, "%Y%m%dT%H%M%S%z")
290
- end
291
-
311
+ value = parse_datetime(value) if value
292
312
  value ? value.utc : nil
293
313
  rescue ArgumentError
294
314
  raise Mbrao::Exceptions::InvalidDate.new
295
315
  end
296
316
  end
317
+
318
+ # Parse a datetime
319
+ # @param value [String|DateTime|Fixnum] The value to parse.
320
+ # @return [DateTime] The extracted value.
321
+ def parse_datetime(value)
322
+ case value.class.to_s
323
+ when "DateTime" then value
324
+ when "Date", "Time" then value.to_datetime
325
+ when "Float", "Fixnum" then
326
+ value.to_float > 0 ? Time.at(value.to_float).to_datetime : nil
327
+ else DateTime.strptime(value.ensure_string, "%Y%m%dT%H%M%S%z")
328
+ end
329
+ end
330
+
331
+ # Extract tags from an array, making sure all the comma separated strings are evaluated.
332
+ #
333
+ # @param value [String|Array] The string or array to parse.
334
+ # @return [Array] The list of tags.
335
+ def parse_tags(value)
336
+ value.ensure_array(nil, true, true, true) { |v| v.ensure_string.split(/\s*,\s*/) }
337
+ end
338
+
339
+ # Check if value is an Hash.
340
+ #
341
+ # @param value [Object] The object to check.
342
+ # @return [Boolean] `true` if value is an Hash, `false` otherwise
343
+ def is_hash?(value)
344
+ value.is_a?(Hash)
345
+ end
297
346
  end
298
347
  end
@@ -17,6 +17,11 @@ module ActionView::Template::Handlers
17
17
  @instance ||= ActionView::Template::Handlers::MbraoTemplate.new
18
18
  end
19
19
 
20
+ # Register Mbrao into Rails.
21
+ def self.register
22
+ ActionView::Template.register_template_handler("emt", instance) if defined?(ActionView) && defined?(Rails) && Rails.version =~ /^[34]/
23
+ end
24
+
20
25
  # Renders a template into a renderer context.
21
26
  #
22
27
  # @param renderer [Object] The renderer context.
@@ -24,11 +29,13 @@ module ActionView::Template::Handlers
24
29
  # @return [String] The rendered template.
25
30
  def render(renderer, template)
26
31
  content = ::Mbrao::Parser.parse(template)
27
- renderer.controller.instance_variable_set(:@mbrao_content, content)
28
- renderer.controller.define_singleton_method(:mbrao_content) { @mbrao_content }
29
- renderer.controller.class.send(:helper_method, :mbrao_content)
32
+ controller = renderer.controller
33
+
34
+ controller.instance_variable_set(:@mbrao_content, content)
35
+ controller.define_singleton_method(:mbrao_content) { @mbrao_content }
36
+ controller.class.send(:helper_method, :mbrao_content)
30
37
 
31
- ::Mbrao::Parser.render(content, {engine: content.metadata[:engine], locale: renderer.controller.params[:locale]})
38
+ ::Mbrao::Parser.render(content, {engine: content.metadata[:engine], locale: controller.params[:locale]})
32
39
  end
33
40
 
34
41
  # Declares support for streaming.
@@ -48,4 +55,4 @@ module ActionView::Template::Handlers
48
55
  end
49
56
  end
50
57
 
51
- ActionView::Template.register_template_handler("emt", ActionView::Template::Handlers::MbraoTemplate.instance) if defined?(ActionView) && defined?(Rails) && Rails.version =~ /^[34]/
58
+ ActionView::Template::Handlers::MbraoTemplate.register
data/lib/mbrao/parser.rb CHANGED
@@ -63,6 +63,29 @@ module Mbrao
63
63
  instance.render(content, options, context)
64
64
  end
65
65
 
66
+ # Returns an object as a JSON compatible hash
67
+ #
68
+ # @param target [Object] The target to serialize.
69
+ # @param keys [Array] The attributes to include in the serialization
70
+ # @param options [Hash] Options to modify behavior of the serialization.
71
+ # The only supported value are:
72
+ #
73
+ # * `:exclude`, an array of attributes to skip.
74
+ # * `:exclude_empty`, if to exclude nil values. Default is `false`.
75
+ # @return [Hash] An hash with all attributes.
76
+ def as_json(target, keys, options = {})
77
+ include_empty = !options[:exclude_empty].to_boolean
78
+ exclude = options[:exclude].ensure_array(nil, true, true, true, :ensure_string)
79
+ keys = keys.ensure_array(nil, true, true, true, :ensure_string)
80
+
81
+ (keys - exclude).reduce({}) {|rv, key|
82
+ value = target.send(key)
83
+ value = value.as_json if value && value.respond_to?(:as_json)
84
+ rv[key] = value if include_empty || !value.is_a?(NilClass)
85
+ rv
86
+ }.deep_stringify_keys
87
+ end
88
+
66
89
  # Instantiates a new engine for rendering or parsing.
67
90
  #
68
91
  # @param cls [String|Symbol|Object] If a `String` or a `Symbol`, then it will be the class of the engine.
@@ -11,29 +11,30 @@ module Mbrao
11
11
  class Base
12
12
  # Parses a whole post content and return its metadata and content parts.
13
13
  #
14
- # @param content [Object] The content to parse.
15
- # @param options [Hash] Options to customize parsing.
14
+ # @param _content [Object] The content to parse.
15
+ # @param _options [Hash] Options to customize parsing.
16
16
  # @return [Array] An array of metadata and contents parts.
17
- def separate_components(content, options = {})
17
+ def separate_components(_content, _options = {})
18
18
  raise Mbrao::Exceptions::Unimplemented.new
19
19
  end
20
20
 
21
21
  # Parses metadata part and returns all valid metadata.
22
22
  #
23
- # @param content [Object] The content to parse.
24
- # @param options [Hash] Options to customize parsing.
23
+ # @param _content [Object] The content to parse.
24
+ # @param _options [Hash] Options to customize parsing.
25
25
  # @return [Hash] All valid metadata for the content.
26
- def parse_metadata(content, options = {})
26
+ def parse_metadata(_content, _options = {})
27
27
  raise Mbrao::Exceptions::Unimplemented.new
28
28
  end
29
29
 
30
30
  # Filters content of a post by locale.
31
31
  #
32
- # @param content [Content] The content to filter.
33
- # @param locales [String|Array] The desired locales. Can include `*` to match all.
34
- # @param options [Hash] Options to customize parsing.
35
- # @return [String|HashWithIndifferentAccess] Return the filtered content in the desired locales. If only one locale is required, then a `String` is returned, else a `HashWithIndifferentAccess` with locales as keys.
36
- def filter_content(content, locales = [], options = {})
32
+ # @param _content [Content] The content to filter.
33
+ # @param _locales [String|Array] The desired locales. Can include `*` to match all.
34
+ # @param _options [Hash] Options to customize parsing.
35
+ # @return [String|HashWithIndifferentAccess] Return the filtered content in the desired locales. If only one locale is required, then a `String` is
36
+ # returned, else a `HashWithIndifferentAccess` with locales as keys.
37
+ def filter_content(_content, _locales = [], _options = {})
37
38
  raise Mbrao::Exceptions::Unimplemented.new
38
39
  end
39
40
 
@@ -15,15 +15,15 @@ module Mbrao
15
15
  # @param options [Hash] Options to customize parsing.
16
16
  # @return [Array] An array of metadata and contents parts.
17
17
  def separate_components(content, options = {})
18
- metadata = nil
19
- content = content.ensure_string.strip
20
- options = sanitize_options(options)
21
- scanner = StringScanner.new(content)
22
- end_tag = options[:meta_tags].last
23
-
24
- if scanner.scan_until(options[:meta_tags].first) && (metadata = scanner.scan_until(end_tag)) then
25
- metadata = metadata.partition(end_tag).first
26
- content = scanner.rest.strip
18
+ metadata, content, scanner, start_tag, end_tag = prepare_for_separation(content, options)
19
+
20
+ if scanner.scan_until(start_tag) then
21
+ metadata = scanner.scan_until(end_tag)
22
+
23
+ if metadata then
24
+ metadata = metadata.partition(end_tag).first
25
+ content = scanner.rest.strip
26
+ end
27
27
  end
28
28
 
29
29
  [metadata.ensure_string.strip, content]
@@ -47,30 +47,31 @@ module Mbrao
47
47
  # @param content [Content] The content to filter.
48
48
  # @param locales [String|Array] The desired locales. Can include `*` to match all. If none are specified, the default Mbrao locale will be requested.
49
49
  # @param options [Hash] Options to customize parsing.
50
- # @return [String|HashWithIndifferentAccess] Return the filtered content in the desired locales. If only one locale is required, then a `String` is returned, else a `HashWithIndifferentAccess` with locales as keys.
50
+ # @return [String|HashWithIndifferentAccess] Return the filtered content in the desired locales. If only one locale is required, then a `String` is
51
+ # returned, else a `HashWithIndifferentAccess` with locales as keys.
51
52
  def filter_content(content, locales = [], options = {})
52
53
  body = content.body.ensure_string.strip
53
- options = sanitize_options(options)
54
+ content_tags = sanitize_tags(options[:content_tags], ["{{content: %ARGS%}}", "{{/content}}"])
54
55
  locales = ::Mbrao::Content.validate_locales(locales, content)
55
56
 
56
57
  # Split the content
57
- result = scan_content(body, options[:content_tags].first, options[:content_tags].last)
58
+ result = scan_content(body, content_tags.first, content_tags.last)
58
59
 
59
60
  # Now filter results
60
61
  perform_filter_content(result, locales)
61
62
  end
62
63
 
63
64
  private
64
- # Sanitizes options.
65
+ # Prepare arguments for separation.
65
66
  #
67
+ # @param content [String] The content to separate.
66
68
  # @param options [Hash] The options to sanitize.
67
- # @return [HashWithIndifferentAccess] The sanitized options.
68
- def sanitize_options(options)
69
- # Tags
70
- options[:meta_tags] = sanitize_tags(options[:meta_tags], ["{{metadata}}", "{{/metadata}}"])
71
- options[:content_tags] = sanitize_tags(options[:content_tags], ["{{content: %ARGS%}}", "{{/content}}"])
69
+ # @return [Array] The sanitized arguments.
70
+ def prepare_for_separation(content, options)
71
+ content = content.ensure_string.strip
72
+ meta_tags = sanitize_tags(options[:meta_tags], ["{{metadata}}", "{{/metadata}}"])
72
73
 
73
- options
74
+ [nil, content.ensure_string.strip, StringScanner.new(content), meta_tags.first, meta_tags.last]
74
75
  end
75
76
 
76
77
  # Sanitizes tag markers.
@@ -135,12 +136,13 @@ module Mbrao
135
136
  def parse_embedded_content(scanner, start_tag, end_tag)
136
137
  rv = ""
137
138
  balance = 1
139
+ embedded_part = scanner.scan_until(end_tag)
138
140
 
139
- while (embedded_part = scanner.scan_until(end_tag)) do
141
+ while balance > 0 && embedded_part do
140
142
  balance += embedded_part.scan(start_tag).count - 1 # -1 Because there is a closure
141
143
  embedded_part = embedded_part.partition(end_tag).first if balance == 0 || !scanner.exist?(end_tag) # This is the last occurrence.
142
144
  rv << embedded_part
143
- break if balance == 0
145
+ embedded_part = scanner.scan_until(end_tag) if balance > 0
144
146
  end
145
147
 
146
148
  rv
@@ -153,10 +155,11 @@ module Mbrao
153
155
  # @return [String|nil] Return the filtered content or `nil` if the content must be hidden.
154
156
  def perform_filter_content(content, locales)
155
157
  content.map { |part|
158
+ part_content = part[0]
156
159
  part_locales = parse_locales(part[1])
157
160
 
158
161
  if locales_valid?(locales, part_locales) then
159
- part[0].is_a?(Array) ? perform_filter_content(part[0], locales) : part[0]
162
+ part_content.is_a?(Array) ? perform_filter_content(part_content, locales) : part_content
160
163
  else
161
164
  nil
162
165
  end
@@ -180,7 +183,10 @@ module Mbrao
180
183
  # @param part_locales[Hash] An hash with valid and invalid locales.
181
184
  # @return [Boolean] `true` if the locales are valid, `false` otherwise.
182
185
  def locales_valid?(locales, part_locales)
183
- locales.include?("*") || part_locales["valid"].include?("*") || ((part_locales["valid"].empty? || (locales & part_locales["valid"]).present?) && (locales & part_locales["invalid"]).blank?)
186
+ valid = part_locales["valid"]
187
+ invalid = part_locales["invalid"]
188
+
189
+ locales.include?("*") || valid.include?("*") || ((valid.empty? || (locales & valid).present?) && (locales & invalid).blank?)
184
190
  end
185
191
  end
186
192
  end
@@ -11,10 +11,10 @@ module Mbrao
11
11
  class Base
12
12
  # Renders a content.
13
13
  #
14
- # @param content [Content|String] The content to parse.
15
- # @param options [Hash] A list of options for renderer.
16
- # @param context [Hash] A context for rendering.
17
- def render(content, options = {}, context = {})
14
+ # @param _content [Content|String] The content to parse.
15
+ # @param _options [Hash] A list of options for renderer.
16
+ # @param _context [Hash] A context for rendering.
17
+ def render(_content, _options = {}, _context = {})
18
18
  raise Mbrao::Exceptions::Unimplemented.new
19
19
  end
20
20
  end
@@ -36,7 +36,9 @@ module Mbrao
36
36
  # A renders which use the [html-pipeline](https://github.com/jch/html-pipeline) gem.
37
37
  #
38
38
  # @attribute default_pipeline
39
- # @return [Array] The default pipeline to use. It should be an array of pairs of `Symbol`, which the first element is the filter (in underscored version and without the filter suffix) and the second is a shortcut to disable the pipeline via options. You can also specify a single element to disable shortcuts.
39
+ # @return [Array] The default pipeline to use. It should be an array of pairs of `Symbol`, which the first element is the filter (in underscored version
40
+ # and without the filter suffix) and the second is a shortcut to disable the pipeline via options.
41
+ # You can also specify a single element to disable shortcuts.
40
42
  # @attribute default_options
41
43
  # @return [Hash] The default options for the renderer.
42
44
  class HtmlPipeline < Mbrao::RenderingEngines::Base
@@ -118,7 +120,10 @@ module Mbrao
118
120
  # @param context [Hash] A context for rendering.
119
121
  # @return [HTML::Pipeline] The pipeline
120
122
  def create_pipeline(options, context)
121
- ::HTML::Pipeline.new(options[:pipeline].map {|f| ::Lazier.find_class(f, "::HTML::Pipeline::%CLASS%Filter", true) }, options[:pipeline_options].merge(context))
123
+ ::HTML::Pipeline.new(
124
+ options[:pipeline].map {|f| ::Lazier.find_class(f, "::HTML::Pipeline::%CLASS%Filter", true) },
125
+ options[:pipeline_options].merge(context)
126
+ )
122
127
  end
123
128
 
124
129
  # Filters pipeline filters basing on the options provided.
data/lib/mbrao/version.rb CHANGED
@@ -14,10 +14,10 @@ module Mbrao
14
14
  MAJOR = 1
15
15
 
16
16
  # The minor version.
17
- MINOR = 2
17
+ MINOR = 3
18
18
 
19
19
  # The patch version.
20
- PATCH = 3
20
+ PATCH = 0
21
21
 
22
22
  # The current version of mbrao.
23
23
  STRING = [MAJOR, MINOR, PATCH].compact.join(".")
@@ -23,40 +23,56 @@ describe Mbrao::Author do
23
23
  end
24
24
 
25
25
  it "creates a author from a hash" do
26
- expect(Mbrao::Author).to receive(:new).with("NAME", "EMAIL", "WEBSITE", "IMAGE", {"other" => "OTHER"}, "UID")
26
+ expect(Mbrao::Author).to receive(:new).with("NAME", "EMAIL", "WEBSITE", "IMAGE", {"other" => "OTHER"}).and_call_original
27
+ expect_any_instance_of(Mbrao::Author).to receive("uid=").with("UID")
27
28
  Mbrao::Author.create({name: "NAME", email: "EMAIL", website: "WEBSITE", image: "IMAGE", other: "OTHER", uid: "UID"})
28
29
  end
29
30
  end
30
31
 
31
32
  describe "#initialize" do
32
33
  it "create a new object" do
33
- reference = Mbrao::Author.new("NAME", "name@example.com", "http://example.com", "http://example.com/image.jpg", {a: {b: :c}})
34
- expect(reference.name).to eq("NAME")
35
- expect(reference.email).to eq("name@example.com")
36
- expect(reference.website).to eq("http://example.com")
37
- expect(reference.image).to eq("http://example.com/image.jpg")
38
- expect(reference.metadata).to eq({"a" => {"b" => :c}})
34
+ subject = Mbrao::Author.new("NAME", "name@example.com", "http://example.com", "http://example.com/image.jpg", {a: {b: :c}})
35
+ expect(subject.name).to eq("NAME")
36
+ expect(subject.email).to eq("name@example.com")
37
+ expect(subject.website).to eq("http://example.com")
38
+ expect(subject.image).to eq("http://example.com/image.jpg")
39
+ expect(subject.metadata).to eq({"a" => {"b" => :c}})
39
40
  end
40
41
 
41
42
  it "make sure that email is valid" do
42
- reference = Mbrao::Author.new("NAME", "INVALID", "http://example.com", "http://example.com/image.jpg", {a: {b: :c}})
43
- expect(reference.email).to be_nil
43
+ subject = Mbrao::Author.new("NAME", "INVALID", "http://example.com", "http://example.com/image.jpg", {a: {b: :c}})
44
+ expect(subject.email).to be_nil
44
45
  end
45
46
 
46
47
  it "make sure that website is a valid URL" do
47
- reference = Mbrao::Author.new("NAME", "name@example.com", "INVALID", "http://example.com/image.jpg", {a: {b: :c}})
48
- expect(reference.website).to be_nil
48
+ subject = Mbrao::Author.new("NAME", "name@example.com", "INVALID", "http://example.com/image.jpg", {a: {b: :c}})
49
+ expect(subject.website).to be_nil
49
50
  end
50
51
 
51
52
  it "make sure that image is a valid URL" do
52
- reference = Mbrao::Author.new("NAME", "name@example.com", "http://example.com", "INVALID", {a: {b: :c}})
53
- expect(reference.image).to be_nil
53
+ subject = Mbrao::Author.new("NAME", "name@example.com", "http://example.com", "INVALID", {a: {b: :c}})
54
+ expect(subject.image).to be_nil
54
55
  end
55
56
 
56
57
  it "make sure that hash is a recursively a HashWithIndifferentAccess" do
57
- reference = Mbrao::Author.new("NAME", "name@example.com", "http://example.com", "http://example.com/image.jpg", {a: {b: :c}})
58
- expect(reference.metadata).to be_a(HashWithIndifferentAccess)
59
- expect(reference.metadata["a"]).to be_a(HashWithIndifferentAccess)
58
+ subject = Mbrao::Author.new("NAME", "name@example.com", "http://example.com", "http://example.com/image.jpg", {a: {b: :c}})
59
+ expect(subject.metadata).to be_a(HashWithIndifferentAccess)
60
+ expect(subject.metadata["a"]).to be_a(HashWithIndifferentAccess)
61
+ end
62
+ end
63
+
64
+ describe "#as_json" do
65
+ it "should return the content as a JSON hash" do
66
+ subject = Mbrao::Author.new("NAME", "name@example.com", "http://example.com", "http://example.com/image.jpg", {a: {b: :c}})
67
+
68
+ expect(subject.as_json).to eq({
69
+ "email" => "name@example.com",
70
+ "image" => "http://example.com/image.jpg",
71
+ "metadata" => {"a" => {"b" => :c}},
72
+ "name" => "NAME",
73
+ "uid" => nil,
74
+ "website" => "http://example.com"
75
+ })
60
76
  end
61
77
  end
62
78
  end