grape 2.0.0 → 2.2.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 (97) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +96 -1
  3. data/README.md +364 -317
  4. data/UPGRADING.md +205 -7
  5. data/grape.gemspec +7 -7
  6. data/lib/grape/api/instance.rb +14 -11
  7. data/lib/grape/api.rb +19 -10
  8. data/lib/grape/content_types.rb +13 -10
  9. data/lib/grape/cookies.rb +2 -1
  10. data/lib/grape/dry_types.rb +0 -2
  11. data/lib/grape/dsl/desc.rb +22 -20
  12. data/lib/grape/dsl/headers.rb +1 -1
  13. data/lib/grape/dsl/helpers.rb +7 -3
  14. data/lib/grape/dsl/inside_route.rb +51 -15
  15. data/lib/grape/dsl/parameters.rb +5 -4
  16. data/lib/grape/dsl/request_response.rb +14 -18
  17. data/lib/grape/dsl/routing.rb +20 -4
  18. data/lib/grape/dsl/validations.rb +13 -0
  19. data/lib/grape/endpoint.rb +43 -35
  20. data/lib/grape/{util/env.rb → env.rb} +0 -5
  21. data/lib/grape/error_formatter/json.rb +13 -4
  22. data/lib/grape/error_formatter/txt.rb +11 -10
  23. data/lib/grape/error_formatter.rb +13 -25
  24. data/lib/grape/exceptions/base.rb +3 -3
  25. data/lib/grape/exceptions/validation.rb +0 -2
  26. data/lib/grape/exceptions/validation_array_errors.rb +1 -0
  27. data/lib/grape/exceptions/validation_errors.rb +2 -4
  28. data/lib/grape/extensions/hash.rb +5 -1
  29. data/lib/grape/formatter.rb +15 -25
  30. data/lib/grape/http/headers.rb +18 -34
  31. data/lib/grape/{util/json.rb → json.rb} +1 -3
  32. data/lib/grape/locale/en.yml +4 -0
  33. data/lib/grape/middleware/auth/base.rb +0 -2
  34. data/lib/grape/middleware/auth/dsl.rb +0 -2
  35. data/lib/grape/middleware/base.rb +14 -15
  36. data/lib/grape/middleware/error.rb +61 -54
  37. data/lib/grape/middleware/formatter.rb +18 -15
  38. data/lib/grape/middleware/globals.rb +1 -3
  39. data/lib/grape/middleware/stack.rb +4 -5
  40. data/lib/grape/middleware/versioner/accept_version_header.rb +8 -33
  41. data/lib/grape/middleware/versioner/header.rb +62 -123
  42. data/lib/grape/middleware/versioner/param.rb +5 -23
  43. data/lib/grape/middleware/versioner/path.rb +11 -33
  44. data/lib/grape/middleware/versioner.rb +5 -14
  45. data/lib/grape/middleware/versioner_helpers.rb +75 -0
  46. data/lib/grape/namespace.rb +3 -4
  47. data/lib/grape/parser.rb +8 -24
  48. data/lib/grape/path.rb +24 -29
  49. data/lib/grape/request.rb +4 -12
  50. data/lib/grape/router/base_route.rb +39 -0
  51. data/lib/grape/router/greedy_route.rb +20 -0
  52. data/lib/grape/router/pattern.rb +39 -30
  53. data/lib/grape/router/route.rb +22 -59
  54. data/lib/grape/router.rb +32 -37
  55. data/lib/grape/util/base_inheritable.rb +4 -4
  56. data/lib/grape/util/cache.rb +0 -3
  57. data/lib/grape/util/endpoint_configuration.rb +1 -1
  58. data/lib/grape/util/header.rb +13 -0
  59. data/lib/grape/util/inheritable_values.rb +0 -2
  60. data/lib/grape/util/lazy/block.rb +29 -0
  61. data/lib/grape/util/lazy/object.rb +45 -0
  62. data/lib/grape/util/lazy/value.rb +38 -0
  63. data/lib/grape/util/lazy/value_array.rb +21 -0
  64. data/lib/grape/util/lazy/value_enumerable.rb +34 -0
  65. data/lib/grape/util/lazy/value_hash.rb +21 -0
  66. data/lib/grape/util/media_type.rb +70 -0
  67. data/lib/grape/util/reverse_stackable_values.rb +1 -6
  68. data/lib/grape/util/stackable_values.rb +1 -6
  69. data/lib/grape/util/strict_hash_configuration.rb +3 -3
  70. data/lib/grape/validations/attributes_doc.rb +38 -36
  71. data/lib/grape/validations/attributes_iterator.rb +1 -0
  72. data/lib/grape/validations/contract_scope.rb +71 -0
  73. data/lib/grape/validations/params_scope.rb +22 -19
  74. data/lib/grape/validations/types/array_coercer.rb +0 -2
  75. data/lib/grape/validations/types/build_coercer.rb +69 -71
  76. data/lib/grape/validations/types/dry_type_coercer.rb +1 -11
  77. data/lib/grape/validations/types/json.rb +0 -2
  78. data/lib/grape/validations/types/primitive_coercer.rb +0 -2
  79. data/lib/grape/validations/types/set_coercer.rb +0 -3
  80. data/lib/grape/validations/types.rb +0 -3
  81. data/lib/grape/validations/validators/base.rb +1 -0
  82. data/lib/grape/validations/validators/default_validator.rb +5 -1
  83. data/lib/grape/validations/validators/exactly_one_of_validator.rb +1 -1
  84. data/lib/grape/validations/validators/length_validator.rb +49 -0
  85. data/lib/grape/validations/validators/values_validator.rb +6 -1
  86. data/lib/grape/validations.rb +3 -7
  87. data/lib/grape/version.rb +1 -1
  88. data/lib/grape/{util/xml.rb → xml.rb} +1 -1
  89. data/lib/grape.rb +30 -274
  90. metadata +31 -38
  91. data/lib/grape/eager_load.rb +0 -20
  92. data/lib/grape/middleware/versioner/parse_media_type_patch.rb +0 -24
  93. data/lib/grape/router/attribute_translator.rb +0 -63
  94. data/lib/grape/util/lazy_block.rb +0 -27
  95. data/lib/grape/util/lazy_object.rb +0 -43
  96. data/lib/grape/util/lazy_value.rb +0 -91
  97. data/lib/grape/util/registrable.rb +0 -15
@@ -1,20 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- Grape.eager_load!
4
- Grape::Http.eager_load!
5
- Grape::Exceptions.eager_load!
6
- Grape::Extensions.eager_load!
7
- Grape::Extensions::ActiveSupport.eager_load!
8
- Grape::Extensions::Hashie.eager_load!
9
- Grape::Middleware.eager_load!
10
- Grape::Middleware::Auth.eager_load!
11
- Grape::Middleware::Versioner.eager_load!
12
- Grape::Util.eager_load!
13
- Grape::ErrorFormatter.eager_load!
14
- Grape::Formatter.eager_load!
15
- Grape::Parser.eager_load!
16
- Grape::DSL.eager_load!
17
- Grape::API.eager_load!
18
- Grape::Presenters.eager_load!
19
- Grape::ServeStream.eager_load!
20
- Rack::Head # AutoLoads the Rack::Head
@@ -1,24 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- require 'English'
4
- module Rack
5
- module Accept
6
- module Header
7
- ALLOWED_CHARACTERS = %r{^([a-z*]+)/([a-z0-9*&\^\-_#{$ERROR_INFO}.+]+)(?:;([a-z0-9=;]+))?$}.freeze
8
- class << self
9
- # Corrected version of https://github.com/mjackson/rack-accept/blob/master/lib/rack/accept/header.rb#L40-L44
10
- def parse_media_type(media_type)
11
- # see http://tools.ietf.org/html/rfc6838#section-4.2 for allowed characters in media type names
12
- m = media_type&.match(ALLOWED_CHARACTERS)
13
- m ? [m[1], m[2], m[3] || ''] : []
14
- end
15
- end
16
- end
17
-
18
- class MediaType
19
- def parse_media_type(media_type)
20
- Header.parse_media_type(media_type)
21
- end
22
- end
23
- end
24
- end
@@ -1,63 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module Grape
4
- class Router
5
- # this could be an OpenStruct, but doesn't work in Ruby 2.3.0, see https://bugs.ruby-lang.org/issues/12251
6
- class AttributeTranslator
7
- attr_reader :attributes
8
-
9
- ROUTE_ATTRIBUTES = %i[
10
- prefix
11
- version
12
- settings
13
- format
14
- description
15
- http_codes
16
- headers
17
- entity
18
- details
19
- requirements
20
- request_method
21
- namespace
22
- ].freeze
23
-
24
- ROUTER_ATTRIBUTES = %i[pattern index].freeze
25
-
26
- def initialize(**attributes)
27
- @attributes = attributes
28
- end
29
-
30
- (ROUTER_ATTRIBUTES + ROUTE_ATTRIBUTES).each do |attr|
31
- define_method attr do
32
- attributes[attr]
33
- end
34
- end
35
-
36
- def to_h
37
- attributes
38
- end
39
-
40
- def method_missing(method_name, *args)
41
- if setter?(method_name[-1])
42
- attributes[method_name[0..]] = *args
43
- else
44
- attributes[method_name]
45
- end
46
- end
47
-
48
- def respond_to_missing?(method_name, _include_private = false)
49
- if setter?(method_name[-1])
50
- true
51
- else
52
- @attributes.key?(method_name)
53
- end
54
- end
55
-
56
- private
57
-
58
- def setter?(method_name)
59
- method_name[-1] == '='
60
- end
61
- end
62
- end
63
- end
@@ -1,27 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module Grape
4
- module Util
5
- class LazyBlock
6
- def initialize(&new_block)
7
- @block = new_block
8
- end
9
-
10
- def evaluate_from(configuration)
11
- @block.call(configuration)
12
- end
13
-
14
- def evaluate
15
- @block.call({})
16
- end
17
-
18
- def lazy?
19
- true
20
- end
21
-
22
- def to_s
23
- evaluate.to_s
24
- end
25
- end
26
- end
27
- end
@@ -1,43 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- # Based on https://github.com/HornsAndHooves/lazy_object
4
-
5
- module Grape
6
- module Util
7
- class LazyObject < BasicObject
8
- attr_reader :callable
9
-
10
- def initialize(&callable)
11
- @callable = callable
12
- end
13
-
14
- def __target_object__
15
- @__target_object__ ||= callable.call
16
- end
17
-
18
- def ==(other)
19
- __target_object__ == other
20
- end
21
-
22
- def !=(other)
23
- __target_object__ != other
24
- end
25
-
26
- def !
27
- !__target_object__
28
- end
29
-
30
- def method_missing(method_name, *args, &block)
31
- if __target_object__.respond_to?(method_name)
32
- __target_object__.send(method_name, *args, &block)
33
- else
34
- super
35
- end
36
- end
37
-
38
- def respond_to_missing?(method_name, include_priv = false)
39
- __target_object__.respond_to?(method_name, include_priv)
40
- end
41
- end
42
- end
43
- end
@@ -1,91 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module Grape
4
- module Util
5
- class LazyValue
6
- attr_reader :access_keys
7
-
8
- def initialize(value, access_keys = [])
9
- @value = value
10
- @access_keys = access_keys
11
- end
12
-
13
- def evaluate_from(configuration)
14
- matching_lazy_value = configuration.fetch(@access_keys)
15
- matching_lazy_value.evaluate
16
- end
17
-
18
- def evaluate
19
- @value
20
- end
21
-
22
- def lazy?
23
- true
24
- end
25
-
26
- def reached_by(parent_access_keys, access_key)
27
- @access_keys = parent_access_keys + [access_key]
28
- self
29
- end
30
-
31
- def to_s
32
- evaluate.to_s
33
- end
34
- end
35
-
36
- class LazyValueEnumerable < LazyValue
37
- def [](key)
38
- if @value_hash[key].nil?
39
- LazyValue.new(nil).reached_by(access_keys, key)
40
- else
41
- @value_hash[key].reached_by(access_keys, key)
42
- end
43
- end
44
-
45
- def fetch(access_keys)
46
- fetched_keys = access_keys.dup
47
- value = self[fetched_keys.shift]
48
- fetched_keys.any? ? value.fetch(fetched_keys) : value
49
- end
50
-
51
- def []=(key, value)
52
- @value_hash[key] = case value
53
- when Hash
54
- LazyValueHash.new(value)
55
- when Array
56
- LazyValueArray.new(value)
57
- else
58
- LazyValue.new(value)
59
- end
60
- end
61
- end
62
-
63
- class LazyValueArray < LazyValueEnumerable
64
- def initialize(array)
65
- super
66
- @value_hash = []
67
- array.each_with_index do |value, index|
68
- self[index] = value
69
- end
70
- end
71
-
72
- def evaluate
73
- @value_hash.map(&:evaluate)
74
- end
75
- end
76
-
77
- class LazyValueHash < LazyValueEnumerable
78
- def initialize(hash)
79
- super
80
- @value_hash = ActiveSupport::HashWithIndifferentAccess.new
81
- hash.each do |key, value|
82
- self[key] = value
83
- end
84
- end
85
-
86
- def evaluate
87
- @value_hash.transform_values(&:evaluate)
88
- end
89
- end
90
- end
91
- end
@@ -1,15 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module Grape
4
- module Util
5
- module Registrable
6
- def default_elements
7
- @default_elements ||= {}
8
- end
9
-
10
- def register(format, element)
11
- default_elements[format] = element unless default_elements[format]
12
- end
13
- end
14
- end
15
- end