grape-entity 0.6.1 → 0.7.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 (47) hide show
  1. checksums.yaml +5 -5
  2. data/.coveralls.yml +1 -0
  3. data/.gitignore +5 -1
  4. data/.rubocop.yml +31 -0
  5. data/.rubocop_todo.yml +29 -16
  6. data/.travis.yml +15 -10
  7. data/CHANGELOG.md +18 -0
  8. data/Dangerfile +2 -0
  9. data/Gemfile +6 -1
  10. data/README.md +82 -1
  11. data/Rakefile +2 -2
  12. data/bench/serializing.rb +2 -0
  13. data/grape-entity.gemspec +9 -7
  14. data/lib/grape-entity.rb +2 -0
  15. data/lib/grape_entity.rb +2 -0
  16. data/lib/grape_entity/condition.rb +20 -11
  17. data/lib/grape_entity/condition/base.rb +2 -0
  18. data/lib/grape_entity/condition/block_condition.rb +3 -1
  19. data/lib/grape_entity/condition/hash_condition.rb +2 -0
  20. data/lib/grape_entity/condition/symbol_condition.rb +2 -0
  21. data/lib/grape_entity/delegator.rb +10 -9
  22. data/lib/grape_entity/delegator/base.rb +2 -0
  23. data/lib/grape_entity/delegator/fetchable_object.rb +2 -0
  24. data/lib/grape_entity/delegator/hash_object.rb +2 -0
  25. data/lib/grape_entity/delegator/openstruct_object.rb +2 -0
  26. data/lib/grape_entity/delegator/plain_object.rb +2 -0
  27. data/lib/grape_entity/entity.rb +49 -29
  28. data/lib/grape_entity/exposure.rb +58 -41
  29. data/lib/grape_entity/exposure/base.rb +14 -3
  30. data/lib/grape_entity/exposure/block_exposure.rb +2 -0
  31. data/lib/grape_entity/exposure/delegator_exposure.rb +2 -0
  32. data/lib/grape_entity/exposure/formatter_block_exposure.rb +2 -0
  33. data/lib/grape_entity/exposure/formatter_exposure.rb +2 -0
  34. data/lib/grape_entity/exposure/nesting_exposure.rb +34 -30
  35. data/lib/grape_entity/exposure/nesting_exposure/nested_exposures.rb +23 -14
  36. data/lib/grape_entity/exposure/nesting_exposure/output_builder.rb +5 -2
  37. data/lib/grape_entity/exposure/represent_exposure.rb +3 -1
  38. data/lib/grape_entity/options.rb +41 -56
  39. data/lib/grape_entity/version.rb +3 -1
  40. data/spec/grape_entity/entity_spec.rb +202 -47
  41. data/spec/grape_entity/exposure/nesting_exposure/nested_exposures_spec.rb +6 -4
  42. data/spec/grape_entity/exposure/represent_exposure_spec.rb +2 -0
  43. data/spec/grape_entity/exposure_spec.rb +14 -2
  44. data/spec/grape_entity/hash_spec.rb +2 -0
  45. data/spec/grape_entity/options_spec.rb +66 -0
  46. data/spec/spec_helper.rb +11 -0
  47. metadata +28 -39
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
- SHA1:
3
- metadata.gz: 04e39a2c99114bcf750f4ca63fa6119ffa0cd5ca
4
- data.tar.gz: 1875a1693ff3de51c40db11a8c755464a93f09bd
2
+ SHA256:
3
+ metadata.gz: ecd89442adb3e014be540761d005b20920e8aa847691a69a6c4e166d1ed63f21
4
+ data.tar.gz: c556531fdea49f03dfea0ce4d1388016736c7d3987db0957be30b27a82e21e40
5
5
  SHA512:
6
- metadata.gz: 3cc6b4795400645718b1228affae6067dabb1214a13d033f0b979e096d649d03d9b05897df537c7e7d0cba2991914e958fe3d26f96b58c4ae62bfc51a63a42e7
7
- data.tar.gz: 2cec009315195a548380c46fa057036a21f8e25b7da03a368f150a3cfe2a3e290c5c67b56ccce262db8a485a51b6b130d3d760e992a6aa7d863033af3a4494d7
6
+ metadata.gz: 5a48af786a0d681229aecd0765eccfafb9f28f6178dc5ade649d54b255df13e82f24f4f5243de7cdff9d45a423d101b851137ffb7920e3853529d88fbe23f67b
7
+ data.tar.gz: b9b89ee602c3804470c57e6519244e59b78fa5b10470fb2a5d0f1581e821847ab8a6f66145fcf57445090d654c442d33cfc6fa94c6eaea9e36f15ce1038eb362
@@ -0,0 +1 @@
1
+ service_name: travis-ci
data/.gitignore CHANGED
@@ -31,9 +31,13 @@ pkg
31
31
  dist
32
32
  Gemfile.lock
33
33
  tmp
34
+ coverage/
35
+ .byebug_history
36
+ .ruby-version
37
+ .ruby-gemset
34
38
 
35
39
  ## Rubinius
36
40
  .rbx
37
41
 
38
42
  ## PROJECT::SPECIFIC
39
- .project
43
+ .project
@@ -1,6 +1,37 @@
1
1
  AllCops:
2
+ TargetRubyVersion: 2.4
3
+ Include:
4
+ - Dangerfile
5
+
2
6
  Exclude:
3
7
  - vendor/**/*
8
+ - bin/**/*
4
9
  - Guardfile
5
10
 
6
11
  inherit_from: .rubocop_todo.yml
12
+
13
+ Gemspec/RequiredRubyVersion:
14
+ Enabled: false
15
+
16
+ Naming/FileName:
17
+ Exclude:
18
+ - 'Gemfile'
19
+ - 'Rakefile'
20
+ - 'grape-entity.gemspec'
21
+ - 'lib/grape-entity.rb'
22
+
23
+ Style/Documentation:
24
+ Enabled: false
25
+
26
+ Style/MultilineIfModifier:
27
+ Enabled: false
28
+
29
+ Style/RaiseArgs:
30
+ Enabled: false
31
+
32
+ Lint/BooleanSymbol:
33
+ Exclude:
34
+ - 'spec/grape_entity/exposure_spec.rb'
35
+
36
+ Lint/UnneededDisable:
37
+ Enabled: false
@@ -1,31 +1,35 @@
1
1
  # This configuration was generated by
2
2
  # `rubocop --auto-gen-config`
3
- # on 2016-11-20 10:04:42 -0500 using RuboCop version 0.45.0.
3
+ # on 2018-01-11 18:20:10 +0100 using RuboCop version 0.52.1.
4
4
  # The point is for the user to remove these configuration records
5
5
  # one by one as the offenses are removed from the code base.
6
6
  # Note that changes in the inspected code, or installation of new
7
7
  # versions of RuboCop, may require this file to be generated again.
8
8
 
9
+ # Offense count: 1
10
+ Lint/AmbiguousBlockAssociation:
11
+ Exclude:
12
+ - 'spec/grape_entity/exposure/represent_exposure_spec.rb'
13
+
9
14
  # Offense count: 6
10
15
  Metrics/AbcSize:
11
16
  Max: 32
12
17
 
18
+ # Offense count: 35
19
+ # Configuration parameters: CountComments, ExcludedMethods.
20
+ Metrics/BlockLength:
21
+ Max: 1625
22
+
13
23
  # Offense count: 2
14
24
  # Configuration parameters: CountComments.
15
25
  Metrics/ClassLength:
16
- Max: 208
26
+ Max: 210
17
27
 
18
- # Offense count: 3
28
+ # Offense count: 2
19
29
  Metrics/CyclomaticComplexity:
20
30
  Max: 11
21
31
 
22
- # Offense count: 237
23
- # Configuration parameters: AllowHeredoc, AllowURI, URISchemes, IgnoreCopDirectives.
24
- # URISchemes: http, https
25
- Metrics/LineLength:
26
- Max: 146
27
-
28
- # Offense count: 6
32
+ # Offense count: 7
29
33
  # Configuration parameters: CountComments.
30
34
  Metrics/MethodLength:
31
35
  Max: 28
@@ -34,12 +38,21 @@ Metrics/MethodLength:
34
38
  Metrics/PerceivedComplexity:
35
39
  Max: 13
36
40
 
37
- # Offense count: 33
38
- Style/Documentation:
39
- Enabled: false
41
+ # Offense count: 1
42
+ Style/EvalWithLocation:
43
+ Exclude:
44
+ - 'lib/grape_entity/exposure/nesting_exposure/nested_exposures.rb'
40
45
 
41
46
  # Offense count: 1
42
- # Configuration parameters: ExpectMatchingDefinition, Regex, IgnoreExecutableScripts.
43
- Style/FileName:
47
+ # Cop supports --auto-correct.
48
+ # Configuration parameters: IgnoredMethods.
49
+ # IgnoredMethods: respond_to, define_method
50
+ Style/SymbolProc:
44
51
  Exclude:
45
- - 'lib/grape-entity.rb'
52
+ - 'spec/grape_entity/entity_spec.rb'
53
+
54
+ # Offense count: 250
55
+ # Configuration parameters: AllowHeredoc, AllowURI, URISchemes, IgnoreCopDirectives, IgnoredPatterns.
56
+ # URISchemes: http, https
57
+ Metrics/LineLength:
58
+ Max: 146
@@ -2,24 +2,29 @@ sudo: false
2
2
 
3
3
  language: ruby
4
4
 
5
- cache: bundler
6
- bundler_args: --without test
5
+ before_install:
6
+ - gem update --system
7
+ - gem install bundler
8
+
9
+ after_success:
10
+ - coveralls
11
+ - bundle exec danger
12
+
13
+ rvm:
14
+ - 2.5.0
15
+ - 2.4.3
7
16
 
8
17
  matrix:
18
+ fast_finish: true
19
+
9
20
  include:
10
- - rvm: 2.4.0
11
- script:
12
- - bundle exec danger
13
- - rvm: 2.4.0
14
- - rvm: 2.3.3
15
- - rvm: 2.2.6
21
+ - rvm: 2.3.6
16
22
  - rvm: ruby-head
17
- - rvm: jruby-9.1.6.0
18
23
  - rvm: jruby-head
19
24
  - rvm: rbx-2
20
25
 
21
26
  allow_failures:
27
+ - rvm: 2.3.6
22
28
  - rvm: ruby-head
23
- - rvm: jruby-9.1.6.0
24
29
  - rvm: jruby-head
25
30
  - rvm: rbx-2
@@ -8,6 +8,24 @@
8
8
 
9
9
  * Your contribution here.
10
10
 
11
+ ### 0.7.0 (2018-01-25)
12
+
13
+ #### Features
14
+
15
+ * [#287](https://github.com/ruby-grape/grape-entity/pull/287): Adds ruby 2.5, drops ruby 2.2 support - [@LeFnord](https://github.com/LeFnord).
16
+ * [#277](https://github.com/ruby-grape/grape-entity/pull/277): Provide grape::entity::options#dig - [@kachick](https://github.com/kachick).
17
+ * [#265](https://github.com/ruby-grape/grape-entity/pull/265): Adds ability to provide a proc to as: - [@james2m](https://github.com/james2m).
18
+ * [#264](https://github.com/ruby-grape/grape-entity/pull/264): Adds Rubocop config and todo list - [@james2m](https://github.com/james2m).
19
+ * [#255](https://github.com/ruby-grape/grape-entity/pull/255): Adds code coverage w/ coveralls - [@LeFnord](https://github.com/LeFnord).
20
+ * [#268](https://github.com/ruby-grape/grape-entity/pull/268): Loosens the version dependency for activesupport - [@anakinj](https://github.com/anakinj).
21
+ * [#293](https://github.com/ruby-grape/grape-entity/pull/293): Adds expose_nil option - [@b-boogaard](https://github.com/b-boogaard).
22
+
23
+ #### Fixes
24
+
25
+ * [#288](https://github.com/ruby-grape/grape-entity/pull/288): Fix wrong argument exception when `&:block` passed to the expose method - [@DmitryTsepelev](https://github.com/DmitryTsepelev).
26
+ * [#291](https://github.com/ruby-grape/grape-entity/pull/291): Refactor and simplify various classes and modules - [@DmitryTsepelev](https://github.com/DmitryTsepelev).
27
+ * [#292](https://github.com/ruby-grape/grape-entity/pull/292): Allow replace non-conditional non-nesting exposures in child classes (fixes [#286](https://github.com/ruby-grape/grape-entity/issues/286)) - [@DmitryTsepelev](https://github.com/DmitryTsepelev).
28
+
11
29
  ### 0.6.1 (2017-01-09)
12
30
 
13
31
  #### Features
data/Dangerfile CHANGED
@@ -1 +1,3 @@
1
+ # frozen_string_literal: true
2
+
1
3
  danger.import_dangerfile(gem: 'ruby-grape-danger')
data/Gemfile CHANGED
@@ -1,15 +1,20 @@
1
+ # frozen_string_literal: true
2
+
1
3
  source 'http://rubygems.org'
2
4
 
3
5
  gemspec
4
6
 
5
7
  group :development, :test do
6
- gem 'ruby-grape-danger', '~> 0.1.1', require: false
8
+ gem 'rubocop', '~> 0.51', require: false
7
9
  end
8
10
 
9
11
  group :test do
12
+ gem 'coveralls', require: false
10
13
  gem 'growl'
11
14
  gem 'guard'
12
15
  gem 'guard-bundler'
13
16
  gem 'guard-rspec'
14
17
  gem 'rb-fsevent'
18
+ gem 'ruby-grape-danger', '~> 0.1.1', require: false
19
+ gem 'simplecov', require: false
15
20
  end
data/README.md CHANGED
@@ -2,6 +2,7 @@
2
2
 
3
3
  [![Gem Version](http://img.shields.io/gem/v/grape-entity.svg)](http://badge.fury.io/rb/grape-entity)
4
4
  [![Build Status](http://img.shields.io/travis/ruby-grape/grape-entity.svg)](https://travis-ci.org/ruby-grape/grape-entity)
5
+ [![Coverage Status](https://coveralls.io/repos/github/ruby-grape/grape-entity/badge.svg?branch=master)](https://coveralls.io/github/ruby-grape/grape-entity?branch=master)
5
6
  [![Dependency Status](https://gemnasium.com/ruby-grape/grape-entity.svg)](https://gemnasium.com/ruby-grape/grape-entity)
6
7
  [![Code Climate](https://codeclimate.com/github/ruby-grape/grape-entity.svg)](https://codeclimate.com/github/ruby-grape/grape-entity)
7
8
 
@@ -320,7 +321,7 @@ module Entities
320
321
  with_options(format_with: :iso_timestamp) do
321
322
  expose :created_at
322
323
  expose :updated_at
323
- end
324
+ end
324
325
  end
325
326
  end
326
327
  ```
@@ -349,6 +350,86 @@ module Entities
349
350
  end
350
351
  ```
351
352
 
353
+ #### Expose Nil
354
+
355
+ By default, exposures that contain `nil` values will be represented in the resulting JSON as `null`.
356
+
357
+ As an example, a hash with the following values:
358
+
359
+ ```ruby
360
+ {
361
+ name: nil,
362
+ age: 100
363
+ }
364
+ ```
365
+
366
+ will result in a JSON object that looks like:
367
+
368
+ ```javascript
369
+ {
370
+ "name": null,
371
+ "age": 100
372
+ }
373
+ ```
374
+
375
+ There are also times when, rather than displaying an attribute with a `null` value, it is more desirable to not display the attribute at all. Using the hash from above the desired JSON would look like:
376
+
377
+ ```javascript
378
+ {
379
+ "age": 100
380
+ }
381
+ ```
382
+
383
+ In order to turn on this behavior for an as-exposure basis, the option `expose_nil` can be used. By default, `expose_nil` is considered to be `true`, meaning that `nil` values will be represented in JSON as `null`. If `false` is provided, then attributes with `nil` values will be omitted from the resulting JSON completely.
384
+
385
+ ```ruby
386
+ module Entities
387
+ class MyModel < Grape::Entity
388
+ expose :name, expose_nil: false
389
+ expose :age, expose_nil: false
390
+ end
391
+ end
392
+ ```
393
+
394
+ `expose_nil` is per exposure, so you can suppress exposures from resulting in `null` or express `null` values on a per exposure basis as you need:
395
+
396
+ ```ruby
397
+ module Entities
398
+ class MyModel < Grape::Entity
399
+ expose :name, expose_nil: false
400
+ expose :age # since expose_nil is omitted nil values will be rendered as null
401
+ end
402
+ end
403
+ ```
404
+
405
+ It is also possible to use `expose_nil` with `with_options` if you want to add the configuration to multiple exposures at once.
406
+
407
+ ```ruby
408
+ module Entities
409
+ class MyModel < Grape::Entity
410
+ # None of the exposures in the with_options block will render nil values as null
411
+ with_options(expose_nil: false) do
412
+ expose :name
413
+ expose :age
414
+ end
415
+ end
416
+ end
417
+ ```
418
+
419
+ When using `with_options`, it is possible to again override which exposures will render `nil` as `null` by adding the option on a specific exposure.
420
+
421
+ ```ruby
422
+ module Entities
423
+ class MyModel < Grape::Entity
424
+ # None of the exposures in the with_options block will render nil values as null
425
+ with_options(expose_nil: false) do
426
+ expose :name
427
+ expose :age, expose_nil: true # nil values would be rendered as null in the JSON
428
+ end
429
+ end
430
+ end
431
+ ```
432
+
352
433
  #### Documentation
353
434
 
354
435
  Expose documentation with the field. Gets bubbled up when used with Grape and various API documentation systems.
data/Rakefile CHANGED
@@ -1,4 +1,4 @@
1
- # encoding: utf-8
1
+ # frozen_string_literal: true
2
2
 
3
3
  require 'rubygems'
4
4
  require 'bundler'
@@ -17,4 +17,4 @@ RSpec::Core::RakeTask.new(:spec)
17
17
  require 'rubocop/rake_task'
18
18
  RuboCop::RakeTask.new(:rubocop)
19
19
 
20
- task default: [:spec, :rubocop]
20
+ task default: %i[spec rubocop]
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
2
4
  require 'grape-entity'
3
5
  require 'benchmark'
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  $LOAD_PATH.push File.expand_path('../lib', __FILE__)
2
4
  require 'grape_entity/version'
3
5
 
@@ -12,22 +14,22 @@ Gem::Specification.new do |s|
12
14
  s.description = 'Extracted from Grape, A Ruby framework for rapid API development with great conventions.'
13
15
  s.license = 'MIT'
14
16
 
15
- s.required_ruby_version = '>= 2.2.6'
17
+ s.required_ruby_version = '>= 2.3'
16
18
 
17
19
  s.rubyforge_project = 'grape-entity'
18
20
 
21
+ s.add_runtime_dependency 'activesupport', '>=4.0'
22
+ # FIXME: remove dependecy
19
23
  s.add_runtime_dependency 'multi_json', '>= 1.3.2'
20
- s.add_runtime_dependency 'activesupport', '>= 5.0.0'
21
24
 
22
25
  s.add_development_dependency 'bundler'
23
- s.add_development_dependency 'rake'
24
- s.add_development_dependency 'rubocop', '~> 0.40'
25
- s.add_development_dependency 'rspec', '~> 3.0'
26
- s.add_development_dependency 'rack-test'
27
26
  s.add_development_dependency 'maruku'
28
- s.add_development_dependency 'yard'
29
27
  s.add_development_dependency 'pry' unless RUBY_PLATFORM.eql?('java') || RUBY_ENGINE.eql?('rbx')
30
28
  s.add_development_dependency 'pry-byebug' unless RUBY_PLATFORM.eql?('java') || RUBY_ENGINE.eql?('rbx')
29
+ s.add_development_dependency 'rack-test'
30
+ s.add_development_dependency 'rake'
31
+ s.add_development_dependency 'rspec', '~> 3.0'
32
+ s.add_development_dependency 'yard'
31
33
 
32
34
  s.files = `git ls-files`.split("\n")
33
35
  s.test_files = `git ls-files -- {test,spec}/*`.split("\n")
@@ -1 +1,3 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'grape_entity'
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'active_support/version'
2
4
  require 'active_support/core_ext/string/inflections'
3
5
  require 'active_support/core_ext/hash/reverse_merge'
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'grape_entity/condition/base'
2
4
  require 'grape_entity/condition/block_condition'
3
5
  require 'grape_entity/condition/hash_condition'
@@ -6,19 +8,26 @@ require 'grape_entity/condition/symbol_condition'
6
8
  module Grape
7
9
  class Entity
8
10
  module Condition
9
- def self.new_if(arg)
10
- case arg
11
- when Hash then HashCondition.new false, arg
12
- when Proc then BlockCondition.new false, &arg
13
- when Symbol then SymbolCondition.new false, arg
11
+ class << self
12
+ def new_if(arg)
13
+ condition(false, arg)
14
14
  end
15
- end
16
15
 
17
- def self.new_unless(arg)
18
- case arg
19
- when Hash then HashCondition.new true, arg
20
- when Proc then BlockCondition.new true, &arg
21
- when Symbol then SymbolCondition.new true, arg
16
+ def new_unless(arg)
17
+ condition(true, arg)
18
+ end
19
+
20
+ private
21
+
22
+ def condition(inverse, arg)
23
+ condition_klass =
24
+ case arg
25
+ when Hash then HashCondition
26
+ when Proc then BlockCondition
27
+ when Symbol then SymbolCondition
28
+ end
29
+
30
+ condition_klass.new(inverse, arg)
22
31
  end
23
32
  end
24
33
  end