dry-types 0.9.2 → 0.9.3
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.
- checksums.yaml +4 -4
- data/.travis.yml +10 -6
- data/.yardopts +5 -0
- data/CHANGELOG.md +9 -1
- data/Gemfile +4 -1
- data/Rakefile +4 -0
- data/dry-types.gemspec +2 -1
- data/lib/dry/types.rb +25 -0
- data/lib/dry/types/array.rb +2 -0
- data/lib/dry/types/array/member.rb +16 -2
- data/lib/dry/types/builder.rb +17 -2
- data/lib/dry/types/coercions.rb +14 -2
- data/lib/dry/types/coercions/form.rb +18 -0
- data/lib/dry/types/coercions/json.rb +2 -0
- data/lib/dry/types/constrained.rb +21 -0
- data/lib/dry/types/constrained/coercible.rb +5 -0
- data/lib/dry/types/constraints.rb +3 -0
- data/lib/dry/types/constructor.rb +28 -0
- data/lib/dry/types/decorator.rb +19 -0
- data/lib/dry/types/default.rb +14 -0
- data/lib/dry/types/definition.rb +31 -4
- data/lib/dry/types/enum.rb +10 -1
- data/lib/dry/types/errors.rb +14 -2
- data/lib/dry/types/extensions/maybe.rb +19 -2
- data/lib/dry/types/hash.rb +18 -0
- data/lib/dry/types/hash/schema.rb +69 -0
- data/lib/dry/types/options.rb +6 -0
- data/lib/dry/types/result.rb +10 -0
- data/lib/dry/types/safe.rb +9 -0
- data/lib/dry/types/sum.rb +20 -0
- data/lib/dry/types/version.rb +1 -1
- metadata +23 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: b5aba3a0d92022b867e134a072196692b4f0d837
|
4
|
+
data.tar.gz: d2a5c7e8b8c489ec5b507a92f92be026e7337d78
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: b5c1a092cf9a157bdcbecc6aec42fa6731ab1e9a9067c81bb7e109a7516393128c0c183ceb4d589258bea87631da55735e38a4b44860f005ea2230b43985e406
|
7
|
+
data.tar.gz: 706d91386ba41582d7eb927237790bf51c0790fc909b248b9a70c851070fb0f49e897e54098f51891fcd5afdd2ee7311fffb6deff7e8b9061b1b6b2135802743
|
data/.travis.yml
CHANGED
@@ -1,21 +1,25 @@
|
|
1
1
|
language: ruby
|
2
|
-
|
2
|
+
dist: trusty
|
3
|
+
sudo: required
|
3
4
|
cache: bundler
|
4
5
|
bundler_args: --without benchmarks tools
|
6
|
+
after_success:
|
7
|
+
- '[ "$TRAVIS_RUBY_VERSION" = "2.3.1" ] && [ "$TRAVIS_BRANCH" = "master" ] && bundle exec codeclimate-test-reporter'
|
5
8
|
script:
|
6
9
|
- bundle exec rake
|
7
10
|
rvm:
|
8
|
-
- 2.1
|
9
|
-
- 2.2
|
10
|
-
- 2.3
|
11
|
+
- 2.1
|
12
|
+
- 2.2
|
13
|
+
- 2.3
|
11
14
|
- jruby-9.1.5.0
|
12
|
-
- rbx-3
|
15
|
+
- rbx-3
|
13
16
|
env:
|
14
17
|
global:
|
18
|
+
- COVERAGE=true
|
15
19
|
- JRUBY_OPTS='--dev -J-Xmx1024M'
|
16
20
|
matrix:
|
17
21
|
allow_failures:
|
18
|
-
- rvm: rbx-3
|
22
|
+
- rvm: rbx-3
|
19
23
|
notifications:
|
20
24
|
email: false
|
21
25
|
webhooks:
|
data/.yardopts
ADDED
data/CHANGELOG.md
CHANGED
@@ -1,4 +1,12 @@
|
|
1
|
-
# v0.9.
|
1
|
+
# v0.9.3 2016-12-03
|
2
|
+
|
3
|
+
## Fixed
|
4
|
+
|
5
|
+
* Updated to dry-core >= 0.2.1 (ruby warnings are gone) (flash-gordon)
|
6
|
+
|
7
|
+
[Compare v0.9.2...v0.9.3](https://github.com/dryrb/dry-types/compare/v0.9.2...v0.9.3)
|
8
|
+
|
9
|
+
# v0.9.2 2016-11-13
|
2
10
|
|
3
11
|
## Added
|
4
12
|
|
data/Gemfile
CHANGED
@@ -3,7 +3,10 @@ source 'https://rubygems.org'
|
|
3
3
|
gemspec
|
4
4
|
|
5
5
|
group :test do
|
6
|
-
|
6
|
+
platform :mri do
|
7
|
+
gem "codeclimate-test-reporter", require: false
|
8
|
+
gem 'simplecov', require: false
|
9
|
+
end
|
7
10
|
end
|
8
11
|
|
9
12
|
group :tools do
|
data/Rakefile
CHANGED
data/dry-types.gemspec
CHANGED
@@ -29,7 +29,7 @@ Gem::Specification.new do |spec|
|
|
29
29
|
spec.required_ruby_version = ">= 2.1.0"
|
30
30
|
|
31
31
|
spec.add_runtime_dependency 'concurrent-ruby', '~> 1.0'
|
32
|
-
spec.add_runtime_dependency 'dry-core', '~> 0.2'
|
32
|
+
spec.add_runtime_dependency 'dry-core', '~> 0.2', '>= 0.2.1'
|
33
33
|
spec.add_runtime_dependency 'dry-container', '~> 0.3'
|
34
34
|
spec.add_runtime_dependency 'dry-equalizer', '~> 0.2'
|
35
35
|
spec.add_runtime_dependency 'dry-configurable', '~> 0.1'
|
@@ -40,4 +40,5 @@ Gem::Specification.new do |spec|
|
|
40
40
|
spec.add_development_dependency "rake", "~> 11.0"
|
41
41
|
spec.add_development_dependency "rspec", "~> 3.3"
|
42
42
|
spec.add_development_dependency 'dry-monads', '~> 0.2'
|
43
|
+
spec.add_development_dependency 'yard', '~> 0.9.5'
|
43
44
|
end
|
data/lib/dry/types.rb
CHANGED
@@ -8,6 +8,7 @@ require 'concurrent'
|
|
8
8
|
require 'dry-container'
|
9
9
|
require 'dry-equalizer'
|
10
10
|
require 'dry/core/extensions'
|
11
|
+
require 'dry/core/constants'
|
11
12
|
|
12
13
|
require 'dry/types/version'
|
13
14
|
require 'dry/types/container'
|
@@ -20,17 +21,22 @@ module Dry
|
|
20
21
|
module Types
|
21
22
|
extend Dry::Configurable
|
22
23
|
extend Dry::Core::Extensions
|
24
|
+
include Dry::Core::Constants
|
23
25
|
|
26
|
+
# @!attribute [r] namespace
|
27
|
+
# @return [Container{String => Definition}]
|
24
28
|
setting :namespace, self
|
25
29
|
|
26
30
|
TYPE_SPEC_REGEX = %r[(.+)<(.+)>].freeze
|
27
31
|
|
32
|
+
# @return [Module]
|
28
33
|
def self.module
|
29
34
|
namespace = Module.new
|
30
35
|
define_constants(namespace, type_keys)
|
31
36
|
namespace
|
32
37
|
end
|
33
38
|
|
39
|
+
# @deprecated Include {Dry::Types.module} instead
|
34
40
|
def self.finalize
|
35
41
|
warn 'Dry::Types.finalize and configuring namespace is deprecated. Just'\
|
36
42
|
' do `include Dry::Types.module` in places where you want to have access'\
|
@@ -39,19 +45,30 @@ module Dry
|
|
39
45
|
define_constants(config.namespace, type_keys)
|
40
46
|
end
|
41
47
|
|
48
|
+
# @return [Container{String => Definition}]
|
42
49
|
def self.container
|
43
50
|
@container ||= Container.new
|
44
51
|
end
|
45
52
|
|
53
|
+
# @param [String] name
|
54
|
+
# @param [Definition] type
|
55
|
+
# @param [#call] block
|
56
|
+
# @return [Container{String => Definition}]
|
46
57
|
def self.register(name, type = nil, &block)
|
47
58
|
container.register(name, type || block.call)
|
48
59
|
end
|
49
60
|
|
61
|
+
# Registers given +klass+ in {#container} using +meth+ constructor
|
62
|
+
# @param [Class] klass
|
63
|
+
# @param [Symbol] meth
|
64
|
+
# @return [Container{String => Definition}]
|
50
65
|
def self.register_class(klass, meth = :new)
|
51
66
|
type = Definition.new(klass).constructor(klass.method(meth))
|
52
67
|
container.register(identifier(klass), type)
|
53
68
|
end
|
54
69
|
|
70
|
+
# @param [String] name
|
71
|
+
# @return [Definition]
|
55
72
|
def self.[](name)
|
56
73
|
type_map.fetch_or_store(name) do
|
57
74
|
case name
|
@@ -76,6 +93,9 @@ module Dry
|
|
76
93
|
end
|
77
94
|
end
|
78
95
|
|
96
|
+
# @param [Container{String => Definition}] namespace
|
97
|
+
# @param [<String>] identifiers
|
98
|
+
# @return [<Definition>]
|
79
99
|
def self.define_constants(namespace, identifiers)
|
80
100
|
names = identifiers.map do |id|
|
81
101
|
parts = id.split('.')
|
@@ -91,14 +111,19 @@ module Dry
|
|
91
111
|
end
|
92
112
|
end
|
93
113
|
|
114
|
+
# @param [#to_s] klass
|
115
|
+
# @return [String]
|
94
116
|
def self.identifier(klass)
|
95
117
|
Inflecto.underscore(klass).tr('/', '.')
|
96
118
|
end
|
97
119
|
|
120
|
+
# @return [Concurrent::Map]
|
98
121
|
def self.type_map
|
99
122
|
@type_map ||= Concurrent::Map.new
|
100
123
|
end
|
101
124
|
|
125
|
+
# List of type keys defined in {Dry::Types.container}
|
126
|
+
# @return [<String>]
|
102
127
|
def self.type_keys
|
103
128
|
container._container.keys
|
104
129
|
end
|
data/lib/dry/types/array.rb
CHANGED
@@ -2,22 +2,36 @@ module Dry
|
|
2
2
|
module Types
|
3
3
|
class Array < Definition
|
4
4
|
class Member < Array
|
5
|
+
# @return [Definition]
|
5
6
|
attr_reader :member
|
6
7
|
|
8
|
+
# @param [Class] primitive
|
9
|
+
# @param [Hash] options
|
10
|
+
# @option options [Definition] :member
|
7
11
|
def initialize(primitive, options = {})
|
8
12
|
@member = options.fetch(:member)
|
9
13
|
super
|
10
14
|
end
|
11
15
|
|
16
|
+
# @param [Object] input
|
17
|
+
# @param [Symbol] meth
|
18
|
+
# @return [Array]
|
12
19
|
def call(input, meth = :call)
|
13
20
|
input.map { |el| member.__send__(meth, el) }
|
14
21
|
end
|
15
22
|
alias_method :[], :call
|
16
23
|
|
17
|
-
|
18
|
-
|
24
|
+
# @param [Array, #all?] value
|
25
|
+
# @return [Boolean]
|
26
|
+
def valid?(value)
|
27
|
+
super && value.all? { |el| member.valid?(el) }
|
19
28
|
end
|
20
29
|
|
30
|
+
# @param [Array, Object] input
|
31
|
+
# @param [#call] block
|
32
|
+
# @yieldparam [Failure] failure
|
33
|
+
# @yieldreturn [Result]
|
34
|
+
# @return [Result]
|
21
35
|
def try(input, &block)
|
22
36
|
if input.is_a?(::Array)
|
23
37
|
result = call(input, :try)
|
data/lib/dry/types/builder.rb
CHANGED
@@ -1,27 +1,35 @@
|
|
1
|
-
require 'dry/core/constants'
|
2
|
-
|
3
1
|
module Dry
|
4
2
|
module Types
|
5
3
|
module Builder
|
6
4
|
include Dry::Core::Constants
|
7
5
|
|
6
|
+
# @return [Constrained]
|
8
7
|
def constrained_type
|
9
8
|
Constrained
|
10
9
|
end
|
11
10
|
|
11
|
+
# @param [Definition] other
|
12
|
+
# @return [Sum, Sum::Constrained]
|
12
13
|
def |(other)
|
13
14
|
klass = constrained? && other.constrained? ? Sum::Constrained : Sum
|
14
15
|
klass.new(self, other)
|
15
16
|
end
|
16
17
|
|
18
|
+
# @return [Sum]
|
17
19
|
def optional
|
18
20
|
Types['strict.nil'] | self
|
19
21
|
end
|
20
22
|
|
23
|
+
# @param [Hash] options constraining rule (see {Types.Rule})
|
24
|
+
# @return [Constrained]
|
21
25
|
def constrained(options)
|
22
26
|
constrained_type.new(self, rule: Types.Rule(options))
|
23
27
|
end
|
24
28
|
|
29
|
+
# @param [Object] input
|
30
|
+
# @param [#call] block
|
31
|
+
# @raise [ConstraintError]
|
32
|
+
# @return [Default]
|
25
33
|
def default(input = Undefined, &block)
|
26
34
|
value = input == Undefined ? block : input
|
27
35
|
|
@@ -32,14 +40,21 @@ module Dry
|
|
32
40
|
end
|
33
41
|
end
|
34
42
|
|
43
|
+
# @param [Array] values
|
44
|
+
# @return [Enum]
|
35
45
|
def enum(*values)
|
36
46
|
Enum.new(constrained(included_in: values), values: values)
|
37
47
|
end
|
38
48
|
|
49
|
+
# @return [Safe]
|
39
50
|
def safe
|
40
51
|
Safe.new(self)
|
41
52
|
end
|
42
53
|
|
54
|
+
# @param [#call] constructor
|
55
|
+
# @param [Hash] options
|
56
|
+
# @param [#call] block
|
57
|
+
# @return [Constructor]
|
43
58
|
def constructor(constructor = nil, **options, &block)
|
44
59
|
Constructor.new(with(options), fn: constructor || block)
|
45
60
|
end
|
data/lib/dry/types/coercions.rb
CHANGED
@@ -1,14 +1,17 @@
|
|
1
|
-
require 'dry/core/constants'
|
2
|
-
|
3
1
|
module Dry
|
4
2
|
module Types
|
5
3
|
module Coercions
|
6
4
|
include Dry::Core::Constants
|
7
5
|
|
6
|
+
# @param [String] input
|
7
|
+
# @return [String?]
|
8
8
|
def to_nil(input)
|
9
9
|
input unless empty_str?(input)
|
10
10
|
end
|
11
11
|
|
12
|
+
# @param [#to_str, Object] input
|
13
|
+
# @return [Date, Object]
|
14
|
+
# @see Date.parse
|
12
15
|
def to_date(input)
|
13
16
|
return input unless input.respond_to?(:to_str)
|
14
17
|
Date.parse(input)
|
@@ -16,6 +19,9 @@ module Dry
|
|
16
19
|
input
|
17
20
|
end
|
18
21
|
|
22
|
+
# @param [#to_str, Object] input
|
23
|
+
# @return [DateTime, Object]
|
24
|
+
# @see DateTime.parse
|
19
25
|
def to_date_time(input)
|
20
26
|
return input unless input.respond_to?(:to_str)
|
21
27
|
DateTime.parse(input)
|
@@ -23,6 +29,9 @@ module Dry
|
|
23
29
|
input
|
24
30
|
end
|
25
31
|
|
32
|
+
# @param [#to_str, Object] input
|
33
|
+
# @return [Time, Object]
|
34
|
+
# @see Time.parse
|
26
35
|
def to_time(input)
|
27
36
|
return input unless input.respond_to?(:to_str)
|
28
37
|
Time.parse(input)
|
@@ -32,6 +41,9 @@ module Dry
|
|
32
41
|
|
33
42
|
private
|
34
43
|
|
44
|
+
# Checks whether String is empty
|
45
|
+
# @param [String, Object] value
|
46
|
+
# @return [Boolean]
|
35
47
|
def empty_str?(value)
|
36
48
|
EMPTY_STRING.eql?(value)
|
37
49
|
end
|
@@ -11,14 +11,24 @@ module Dry
|
|
11
11
|
|
12
12
|
extend Coercions
|
13
13
|
|
14
|
+
# @param [String, Object] input
|
15
|
+
# @return [Boolean?]
|
16
|
+
# @see TRUE_VALUES
|
17
|
+
# @see FALSE_VALUES
|
14
18
|
def self.to_true(input)
|
15
19
|
BOOLEAN_MAP.fetch(input.to_s, input)
|
16
20
|
end
|
17
21
|
|
22
|
+
# @param [String, Object] input
|
23
|
+
# @return [Boolean?]
|
24
|
+
# @see TRUE_VALUES
|
25
|
+
# @see FALSE_VALUES
|
18
26
|
def self.to_false(input)
|
19
27
|
BOOLEAN_MAP.fetch(input.to_s, input)
|
20
28
|
end
|
21
29
|
|
30
|
+
# @param [#to_int, #to_i, Object] input
|
31
|
+
# @return [Integer?, Object]
|
22
32
|
def self.to_int(input)
|
23
33
|
if empty_str?(input)
|
24
34
|
nil
|
@@ -29,6 +39,8 @@ module Dry
|
|
29
39
|
input
|
30
40
|
end
|
31
41
|
|
42
|
+
# @param [#to_f, Object] input
|
43
|
+
# @return [Float?, Object]
|
32
44
|
def self.to_float(input)
|
33
45
|
if empty_str?(input)
|
34
46
|
nil
|
@@ -39,6 +51,8 @@ module Dry
|
|
39
51
|
input
|
40
52
|
end
|
41
53
|
|
54
|
+
# @param [#to_d, Object] input
|
55
|
+
# @return [BigDecimal?, Object]
|
42
56
|
def self.to_decimal(input)
|
43
57
|
result = to_float(input)
|
44
58
|
|
@@ -49,10 +63,14 @@ module Dry
|
|
49
63
|
end
|
50
64
|
end
|
51
65
|
|
66
|
+
# @param [Array, '', Object] input
|
67
|
+
# @return [Array, Object]
|
52
68
|
def self.to_ary(input)
|
53
69
|
empty_str?(input) ? [] : input
|
54
70
|
end
|
55
71
|
|
72
|
+
# @param [Hash, '', Object] input
|
73
|
+
# @return [Hash]
|
56
74
|
def self.to_hash(input)
|
57
75
|
empty_str?(input) ? {} : input
|
58
76
|
end
|
@@ -9,13 +9,19 @@ module Dry
|
|
9
9
|
include Decorator
|
10
10
|
include Builder
|
11
11
|
|
12
|
+
# @return [Dry::Logic::Rule]
|
12
13
|
attr_reader :rule
|
13
14
|
|
15
|
+
# @param [Definition] type
|
16
|
+
# @param [Hash] options
|
14
17
|
def initialize(type, options)
|
15
18
|
super
|
16
19
|
@rule = options.fetch(:rule)
|
17
20
|
end
|
18
21
|
|
22
|
+
# @param [Object] input
|
23
|
+
# @return [Object]
|
24
|
+
# @raise [ConstraintError]
|
19
25
|
def call(input)
|
20
26
|
try(input) do |result|
|
21
27
|
raise ConstraintError.new(result, input)
|
@@ -23,6 +29,11 @@ module Dry
|
|
23
29
|
end
|
24
30
|
alias_method :[], :call
|
25
31
|
|
32
|
+
# @param [Object] input
|
33
|
+
# @param [#call] block
|
34
|
+
# @yieldparam [Failure] failure
|
35
|
+
# @yieldreturn [Result]
|
36
|
+
# @return [Result]
|
26
37
|
def try(input, &block)
|
27
38
|
result = rule.(input)
|
28
39
|
|
@@ -34,20 +45,30 @@ module Dry
|
|
34
45
|
end
|
35
46
|
end
|
36
47
|
|
48
|
+
# @param [Object] value
|
49
|
+
# @return [Boolean]
|
37
50
|
def valid?(value)
|
38
51
|
rule.(value).success? && type.valid?(value)
|
39
52
|
end
|
40
53
|
|
54
|
+
# @param [Hash] options
|
55
|
+
# The options hash provided to {Types.Rule} and combined
|
56
|
+
# using {&} with previous {#rule}
|
57
|
+
# @return [Constrained]
|
58
|
+
# @see Dry::Logic::Operators#and
|
41
59
|
def constrained(options)
|
42
60
|
with(rule: rule & Types.Rule(options))
|
43
61
|
end
|
44
62
|
|
63
|
+
# @return [true]
|
45
64
|
def constrained?
|
46
65
|
true
|
47
66
|
end
|
48
67
|
|
49
68
|
private
|
50
69
|
|
70
|
+
# @param [Object] response
|
71
|
+
# @return [Boolean]
|
51
72
|
def decorate?(response)
|
52
73
|
super || response.kind_of?(Constructor)
|
53
74
|
end
|