hexx 5.0.0 → 5.1.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
  SHA1:
3
- metadata.gz: 7290018a93943ca2db70630dac37ed9d1b2eabfe
4
- data.tar.gz: 04b3a2c21598e88beda09d3f2a8bcee7622ba105
3
+ metadata.gz: 7a0f508972f47609f09b6b7b303ee55c0268256e
4
+ data.tar.gz: a3c0760ee8824891234b4b6b0c48d29c47c4eecd
5
5
  SHA512:
6
- metadata.gz: e93648cc19a96e0dca81731ce200b443a4d10e394356e329f0995061cf5ea9656758f42a382b65d465125baa6bc38013f94f5d39b2d00ffe3c04922c6317c5db
7
- data.tar.gz: 4169b5355f71c1a1bb1c431edacb47e68d81990c6b74c6164a71aebc5d0b85c098be054f9f6789239c4c371b26144224e4379e78bc3f36b1b5764af7a909a1fd
6
+ metadata.gz: fc2de5bffc7cfc7fd0cdfc75b6a3fad2b2f657cfa80e28e1b90980af0d746d244a546a86ef125164001518fd89f30adb1f3023b3dc7cff09a2d0761ab484bf00
7
+ data.tar.gz: 81442ee8209ef2b7e4c3ac9e5b37f5ff8f94e3a63dbe6dd193dea1d0b9623b2e6f7c90e812a696630cea08f634989a9d154f2c7f822c705cb57be6d572422c08
data/README.rdoc CHANGED
@@ -139,6 +139,32 @@ preparation:
139
139
  user = User.name " Ivan "
140
140
  user.name # => "Ivan"
141
141
 
142
+ == Dependencies
143
+
144
+ The module provides methods +depends_on+ and +config+ to create
145
+ dependency injection framework.
146
+
147
+ Declare gem dependencies (external classes and modules).
148
+
149
+ # lib/my_gem.rb
150
+ module MyGem
151
+ extend Hexx::Dependencies
152
+ depends_on :get_item, :add_item
153
+ end
154
+
155
+ Inject gem dependencies:
156
+
157
+ # config/my_gem.rb
158
+ MyGem.configure do |config|
159
+ config.get_item = AnotherGem::Services::Get # as a constant
160
+ config.add_item = "AnotherGem::Services::Add" # as a name of a constant
161
+ end
162
+
163
+ Use them somewhere in a code:
164
+
165
+ MyGem.get_item # => AnotherGem::Services::Get
166
+ MyGem.add_item # => AnotherGem::Services::Add # the name is constantized
167
+
142
168
  == Relevant Links
143
169
 
144
170
  * Matt Wynne's talk {Hexagonal Rails}[http://www.confreaks.com/videos/977-goruco2012-hexagonal-rails]
@@ -0,0 +1,159 @@
1
+ # encoding: utf-8
2
+
3
+ module Hexx
4
+
5
+ # Contains methods to declare and inject module dependencies.
6
+ #
7
+ # Allows to provide DJ framework for the gem.
8
+ #
9
+ # @example
10
+ # # Declare the dependencies for the gem root module
11
+ #
12
+ # # lib/my_gem.rb
13
+ # module MyGem
14
+ # extend Hexx::Dependencies
15
+ # self.depends_on :get_item, :add_item, :delete_item
16
+ # end
17
+ #
18
+ # # Inject dependencies (as a constant or its name)
19
+ #
20
+ # # config/my_gem.rb
21
+ # MyGem.configure do |config|
22
+ # config.get_item = AnotherGem::Services::Get
23
+ # config.add_item = "AnotherGem::Services::Add"
24
+ # end
25
+ #
26
+ # # Use dependency in the module code (models, services, etc.)
27
+ # # When the dependency hasn't been set, fails with +NotImplementedError+
28
+ #
29
+ # MyGem.get_item # => AnotherGem::Services::Get
30
+ # MyGem.add_item # => AnotherGem::Services::Add
31
+ # MyGem.delete_item # raises #<NotImplementedError ... >
32
+ module Dependencies
33
+
34
+ # Yields a block and gives it self
35
+ #
36
+ # @example
37
+ # module MyGem
38
+ # extend Hexx::Dependencies
39
+ # end
40
+ #
41
+ # MyGem.configure do |config|
42
+ # c # => MyGem
43
+ # end
44
+ #
45
+ # @yield The block.
46
+ # @yieldparam [Dependencies] +self+.
47
+ def configure
48
+ yield(self)
49
+ end
50
+
51
+ # Declares dependency getter and setter.
52
+ #
53
+ # The getter constants, strings and symbols. The setter constantize the
54
+ # assigned value.
55
+ #
56
+ # This allows setting dependency before definition of a corresponding
57
+ # constant.
58
+ #
59
+ # @example
60
+ # module MyGem
61
+ # extend Hexx::Dependencies
62
+ # self.depends_on :some_class
63
+ # end
64
+ #
65
+ # MyGem.some_class = String
66
+ # # => "String"
67
+ # MyGem.some_class # => String
68
+ #
69
+ # MyGem.some_class = "String"
70
+ # # => "String"
71
+ # MyGem.some_class # => String
72
+ #
73
+ # MyGem.some_class = :String
74
+ # # => "String"
75
+ # MyGem.some_class # => String
76
+ #
77
+ # @param [String, Symbol] name The name for dependency.
78
+ def depends_on(*names)
79
+ names.each do |name|
80
+ DependencyName.new(name).validate
81
+ add_dependency_setter name
82
+ add_dependency_getter name
83
+ end
84
+ end
85
+
86
+ private
87
+
88
+ # @api hide
89
+ # Checks the name of the dependency.
90
+ class DependencyName < Struct.new(:name)
91
+
92
+ # @api hide
93
+ # Runs validations and fails in case of any error.
94
+ def validate
95
+ check_type
96
+ check_value
97
+ end
98
+
99
+ private
100
+
101
+ def check_type
102
+ return if [String, Symbol].include? name.class
103
+ fail TypeError.new "#{ name.inspect } is neither a string nor symbol."
104
+ end
105
+
106
+ def check_value
107
+ return unless name.to_s == ""
108
+ fail ArgumentError.new "The dependency name should not be blank."
109
+ end
110
+ end
111
+
112
+ # @api hide
113
+ # Checks the value of the dependency.
114
+ class Dependency < Struct.new(:name, :value)
115
+
116
+ # @api hide
117
+ # Runs validations and fails in case of any error.
118
+ def validate
119
+ check_type
120
+ check_value
121
+ end
122
+
123
+ private
124
+
125
+ def check_type
126
+ return if value.is_a? String
127
+ return if value.is_a? Symbol
128
+ return if value.is_a? Module
129
+ fail TypeError.new "#{ inspect } is not a string, symbol or module."
130
+ end
131
+
132
+ def check_value
133
+ return unless value.to_s == ""
134
+ fail ArgumentError.new "The dependency #{ name } should not be blank."
135
+ end
136
+
137
+ def inspect
138
+ value.inspect
139
+ end
140
+ end
141
+
142
+ def add_dependency_setter(name)
143
+ instance_eval "
144
+ def #{ name }=(value);
145
+ Dependency.new(:#{ name }, value).validate;
146
+ @#{ name }= value.to_s;
147
+ end"
148
+ end
149
+
150
+ def add_dependency_getter(name)
151
+ instance_eval "
152
+ def #{ name };
153
+ value = @#{ name };
154
+ fail NotImplementedError unless value;
155
+ value.constantize;
156
+ end"
157
+ end
158
+ end
159
+ end
data/lib/hexx/version.rb CHANGED
@@ -2,5 +2,5 @@
2
2
  module Hexx
3
3
 
4
4
  # Current release.
5
- VERSION = "5.0.0"
5
+ VERSION = "5.1.0"
6
6
  end
@@ -0,0 +1,87 @@
1
+ require "spec_helper"
2
+
3
+ module Hexx
4
+ describe Dependencies do
5
+
6
+ # Mocks gem core module to test dependencies from
7
+ before { module Test; extend Dependencies; end }
8
+ after { Hexx.send :remove_const, :Test }
9
+ let(:described_module) { Test }
10
+
11
+ describe ".configure" do
12
+
13
+ it "is defined" do
14
+ expect(described_module).to respond_to :configure
15
+ end
16
+
17
+ it "yields block with self" do
18
+ described_module.configure do |config|
19
+ expect(config).to eq described_module
20
+ end
21
+ end
22
+ end
23
+
24
+ describe ".depends_on" do
25
+
26
+ it "is defined" do
27
+ expect(described_module).to respond_to :depends_on
28
+ end
29
+
30
+ it "allows symbolic attributes" do
31
+ expect { described_module.depends_on :item }.not_to raise_error
32
+ end
33
+
34
+ it "allows string attributes" do
35
+ expect { described_module.depends_on "item" }.not_to raise_error
36
+ end
37
+
38
+ it "fails when wrong object given" do
39
+ expect { described_module.depends_on 1 }.to raise_error TypeError
40
+ end
41
+
42
+ it "fails when blank object given" do
43
+ expect { described_module.depends_on "" }.to raise_error ArgumentError
44
+ end
45
+
46
+ it "adds dependencies getters" do
47
+ described_module.depends_on :item, "user"
48
+ expect(described_module).to respond_to :item
49
+ expect(described_module).to respond_to :user
50
+ end
51
+
52
+ it "adds dependencies setters" do
53
+ described_module.depends_on :item, "user"
54
+ expect(described_module).to respond_to :item=
55
+ expect(described_module).to respond_to :user=
56
+ end
57
+
58
+ context ":item" do
59
+
60
+ before { described_module.depends_on :item }
61
+
62
+ it "allows setting string and constantizes it" do
63
+ described_module.item = "String"
64
+ expect(described_module.item).to eq String
65
+ end
66
+
67
+ it "allows setting symbol and constantizes it" do
68
+ described_module.item = :String
69
+ expect(described_module.item).to eq String
70
+ end
71
+
72
+ it "allows setting constant" do
73
+ described_module.item = String
74
+ expect(described_module.item).to eq String
75
+ end
76
+
77
+ it "fails if wrong value type given" do
78
+ expect { described_module.item = 1 }.to raise_error TypeError
79
+ end
80
+
81
+ it "fails if blank string given" do
82
+ expect { described_module.item = "" }.to raise_error ArgumentError
83
+ end
84
+ end
85
+ end
86
+ end
87
+ end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: hexx
3
3
  version: !ruby/object:Gem::Version
4
- version: 5.0.0
4
+ version: 5.1.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Andrew Kozin
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2014-12-20 00:00:00.000000000 Z
11
+ date: 2014-12-22 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: activemodel
@@ -149,6 +149,7 @@ files:
149
149
  - README.rdoc
150
150
  - Rakefile
151
151
  - lib/hexx.rb
152
+ - lib/hexx/dependencies.rb
152
153
  - lib/hexx/models.rb
153
154
  - lib/hexx/models/base_coercer.rb
154
155
  - lib/hexx/null.rb
@@ -158,6 +159,7 @@ files:
158
159
  - lib/hexx/service/parameters.rb
159
160
  - lib/hexx/service/with_callbacks.rb
160
161
  - lib/hexx/version.rb
162
+ - spec/hexx/dependencies_spec.rb
161
163
  - spec/hexx/models_spec.rb
162
164
  - spec/hexx/null_spec.rb
163
165
  - spec/hexx/service/invalid_spec.rb
@@ -196,6 +198,7 @@ summary: Service objects for Rails.
196
198
  test_files:
197
199
  - spec/spec_helper.rb
198
200
  - spec/hexx/service_spec.rb
201
+ - spec/hexx/dependencies_spec.rb
199
202
  - spec/hexx/null_spec.rb
200
203
  - spec/hexx/service/message_spec.rb
201
204
  - spec/hexx/service/invalid_spec.rb