smart_core 0.6.0 → 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.
- checksums.yaml +4 -4
- data/.rspec +1 -1
- data/.rubocop.yml +1 -1
- data/.travis.yml +5 -8
- data/CHANGELOG.md +5 -0
- data/README.md +14 -4
- data/lib/smart_core.rb +2 -2
- data/lib/smart_core/container.rb +49 -56
- data/lib/smart_core/container/arbitary_lock.rb +22 -0
- data/lib/smart_core/container/definition_dsl.rb +105 -55
- data/lib/smart_core/container/{command_set.rb → definition_dsl/command_set.rb} +20 -26
- data/lib/smart_core/container/definition_dsl/commands.rb +12 -0
- data/lib/smart_core/container/{commands → definition_dsl/commands}/base.rb +3 -3
- data/lib/smart_core/container/definition_dsl/commands/definition/compose.rb +46 -0
- data/lib/smart_core/container/definition_dsl/commands/definition/namespace.rb +51 -0
- data/lib/smart_core/container/{commands → definition_dsl/commands/definition}/register.rb +13 -25
- data/lib/smart_core/container/definition_dsl/commands/instantiation/compose.rb +50 -0
- data/lib/smart_core/container/definition_dsl/commands/instantiation/freeze_state.rb +24 -0
- data/lib/smart_core/container/dependency_compatability.rb +3 -3
- data/lib/smart_core/container/dependency_compatability/definition.rb +42 -0
- data/lib/smart_core/container/dependency_compatability/general.rb +61 -0
- data/lib/smart_core/container/dependency_compatability/registry.rb +28 -29
- data/lib/smart_core/container/dependency_resolver.rb +9 -4
- data/lib/smart_core/container/entities.rb +11 -0
- data/lib/smart_core/container/{entity.rb → entities/base.rb} +7 -7
- data/lib/smart_core/container/entities/dependency.rb +38 -0
- data/lib/smart_core/container/entities/dependency_builder.rb +50 -0
- data/lib/smart_core/container/entities/namespace.rb +73 -0
- data/lib/smart_core/container/entities/namespace_builder.rb +41 -0
- data/lib/smart_core/container/errors.rb +43 -0
- data/lib/smart_core/container/key_guard.rb +5 -5
- data/lib/smart_core/container/mixin.rb +20 -16
- data/lib/smart_core/container/registry.rb +224 -201
- data/lib/smart_core/container/registry_builder.rb +38 -5
- data/lib/smart_core/{exceptions.rb → errors.rb} +0 -0
- data/lib/smart_core/operation.rb +3 -1
- data/lib/smart_core/operation/{custom.rb → callback.rb} +7 -7
- data/lib/smart_core/operation/result.rb +1 -1
- data/lib/smart_core/operation/result_interface.rb +3 -3
- data/lib/smart_core/version.rb +1 -1
- data/smart_core.gemspec +6 -5
- metadata +28 -38
- data/lib/smart_core/container/command_definer.rb +0 -117
- data/lib/smart_core/container/commands.rb +0 -9
- data/lib/smart_core/container/commands/namespace.rb +0 -53
- data/lib/smart_core/container/dependency.rb +0 -44
- data/lib/smart_core/container/dependency_builder.rb +0 -48
- data/lib/smart_core/container/dependency_compatability/abstract.rb +0 -59
- data/lib/smart_core/container/dependency_compatability/command_set.rb +0 -35
- data/lib/smart_core/container/exceptions.rb +0 -31
- data/lib/smart_core/container/memoized_dependency.rb +0 -28
- data/lib/smart_core/container/namespace.rb +0 -51
@@ -1,36 +1,35 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
|
-
|
4
|
-
|
5
|
-
|
6
|
-
class
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
3
|
+
# @api private
|
4
|
+
# @since 0.7.0
|
5
|
+
module SmartCore::Container::DependencyCompatability::Registry
|
6
|
+
class << self
|
7
|
+
# @since 0.7.0
|
8
|
+
include SmartCore::Container::DependencyCompatability::General
|
9
|
+
|
10
|
+
# @param registry [SmartCore::Container::Registry]
|
11
|
+
# @param dependency_name [String, Symbol]
|
12
|
+
# @return [Boolean]
|
13
|
+
#
|
14
|
+
# @api private
|
15
|
+
# @since 0.7.0
|
16
|
+
def potential_namespace_overlap?(registry, dependency_name)
|
17
|
+
registry.any? do |(entity_name, entity)|
|
18
|
+
next unless entity.is_a?(SmartCore::Container::Entities::Namespace)
|
19
|
+
entity.namespace_name == dependency_name
|
20
20
|
end
|
21
|
+
end
|
21
22
|
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
registered_dependency.external_name == namespace_name
|
33
|
-
end
|
23
|
+
# @param registry [SmartCore::Container::Registry]
|
24
|
+
# @param namespace_name [String, Symbol]
|
25
|
+
# @return [Boolean]
|
26
|
+
#
|
27
|
+
# @api private
|
28
|
+
# @since 0.7.0
|
29
|
+
def potential_dependency_overlap?(registry, namespace_name)
|
30
|
+
registry.any? do |(entity_name, entity)|
|
31
|
+
next unless entity.is_a?(SmartCore::Container::Entities::Dependency)
|
32
|
+
entity.dependency_name == namespace_name
|
34
33
|
end
|
35
34
|
end
|
36
35
|
end
|
@@ -1,16 +1,21 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
3
|
# @api private
|
4
|
-
# @since 0.
|
4
|
+
# @since 0.7.0
|
5
5
|
module SmartCore::Container::DependencyResolver
|
6
6
|
class << self
|
7
7
|
# @param registry [SmartCore::Container::Registry]
|
8
|
-
# @
|
8
|
+
# @param dependency_path [String, Symbol]
|
9
|
+
# @return [SmartCore::Container, Any]
|
10
|
+
#
|
11
|
+
# @see SmartCore::Container::Registry#resolve
|
12
|
+
# @see SmartCore::Container::Entities::Namespace#resolve
|
13
|
+
# @see SmartCore::Container::Entities::Dependency#resolve
|
9
14
|
#
|
10
15
|
# @api private
|
11
|
-
# @since 0.
|
16
|
+
# @since 0.7.0
|
12
17
|
def resolve(registry, dependency_path)
|
13
|
-
registry.resolve(dependency_path).
|
18
|
+
registry.resolve(dependency_path).resolve
|
14
19
|
end
|
15
20
|
end
|
16
21
|
end
|
@@ -0,0 +1,11 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
# @api private
|
4
|
+
# @since 0.7.0
|
5
|
+
module SmartCore::Container::Entities
|
6
|
+
require_relative 'entities/base'
|
7
|
+
require_relative 'entities/dependency'
|
8
|
+
require_relative 'entities/dependency_builder'
|
9
|
+
require_relative 'entities/namespace'
|
10
|
+
require_relative 'entities/namespace_builder'
|
11
|
+
end
|
@@ -1,26 +1,26 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
3
|
# @api private
|
4
|
-
# @since 0.
|
5
|
-
class SmartCore::Container::
|
4
|
+
# @since 0.7.0
|
5
|
+
class SmartCore::Container::Entities::Base
|
6
6
|
# @return [String]
|
7
7
|
#
|
8
8
|
# @api private
|
9
|
-
# @since 0.
|
9
|
+
# @since 0.7.0
|
10
10
|
attr_reader :external_name
|
11
11
|
|
12
12
|
# @param external_name [String]
|
13
13
|
# @return [void]
|
14
14
|
#
|
15
15
|
# @api private
|
16
|
-
# @since 0.
|
16
|
+
# @since 0.7.0
|
17
17
|
def initialize(external_name)
|
18
18
|
@external_name = external_name
|
19
19
|
end
|
20
20
|
|
21
|
-
# @return [
|
21
|
+
# @return [Any]
|
22
22
|
#
|
23
23
|
# @api private
|
24
|
-
# @since 0.
|
25
|
-
def
|
24
|
+
# @since 0.7.0
|
25
|
+
def resolve; end
|
26
26
|
end
|
@@ -0,0 +1,38 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
# @api private
|
4
|
+
# @since 0.7.0
|
5
|
+
class SmartCore::Container::Entities::Dependency < SmartCore::Container::Entities::Base
|
6
|
+
# @return [String]
|
7
|
+
#
|
8
|
+
# @api private
|
9
|
+
# @sicne 0.7.0
|
10
|
+
alias_method :dependency_name, :external_name
|
11
|
+
|
12
|
+
# @param dependency_name [String]
|
13
|
+
# @param dependency_definition [Proc]
|
14
|
+
# @return [void]
|
15
|
+
#
|
16
|
+
# @api private
|
17
|
+
# @since 0.7.0
|
18
|
+
def initialize(dependency_name, dependency_definition)
|
19
|
+
super(dependency_name)
|
20
|
+
@dependency_definition = dependency_definition
|
21
|
+
end
|
22
|
+
|
23
|
+
# @return [Any]
|
24
|
+
#
|
25
|
+
# @api private
|
26
|
+
# @since 0.7.0
|
27
|
+
def resolve
|
28
|
+
dependency_definition.call
|
29
|
+
end
|
30
|
+
|
31
|
+
private
|
32
|
+
|
33
|
+
# @return [Proc]
|
34
|
+
#
|
35
|
+
# @api private
|
36
|
+
# @since 0.7.0
|
37
|
+
attr_reader :dependency_definition
|
38
|
+
end
|
@@ -0,0 +1,50 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
# @api private
|
4
|
+
# @since 0.7.0
|
5
|
+
class SmartCore::Container::Entities::DependencyBuilder
|
6
|
+
class << self
|
7
|
+
# @param dependency_name [String]
|
8
|
+
# @param dependency_definition [Proc]
|
9
|
+
# @return [SmartCore::Container::Entities::Dependency]
|
10
|
+
#
|
11
|
+
# @api private
|
12
|
+
# @since 0.7.0
|
13
|
+
def build(dependency_name, dependency_definition)
|
14
|
+
new(dependency_name, dependency_definition).build
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
18
|
+
# @param dependency_name [String]
|
19
|
+
# @param dependency_definition [Proc]
|
20
|
+
# @return [void]
|
21
|
+
#
|
22
|
+
# @api private
|
23
|
+
# @since 0.7.0
|
24
|
+
def initialize(dependency_name, dependency_definition)
|
25
|
+
@dependency_name = dependency_name
|
26
|
+
@dependency_definition = dependency_definition
|
27
|
+
end
|
28
|
+
|
29
|
+
# @return [SmartCore::Container::Entities::Dependency]
|
30
|
+
#
|
31
|
+
# @api private
|
32
|
+
# @since 0.7.0
|
33
|
+
def build
|
34
|
+
SmartCore::Container::Entities::Dependency.new(dependency_name, dependency_definition)
|
35
|
+
end
|
36
|
+
|
37
|
+
private
|
38
|
+
|
39
|
+
# @return [String]
|
40
|
+
#
|
41
|
+
# @api private
|
42
|
+
# @since 0.7.0
|
43
|
+
attr_reader :dependency_name
|
44
|
+
|
45
|
+
# @return [Proc]
|
46
|
+
#
|
47
|
+
# @api private
|
48
|
+
# @since 0.7.0
|
49
|
+
attr_reader :dependency_definition
|
50
|
+
end
|
@@ -0,0 +1,73 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
# @api private
|
4
|
+
# @since 0.7.0
|
5
|
+
class SmartCore::Container::Entities::Namespace < SmartCore::Container::Entities::Base
|
6
|
+
# @return [String]
|
7
|
+
#
|
8
|
+
# @api private
|
9
|
+
# @since 0.7.0
|
10
|
+
alias_method :namespace_name, :external_name
|
11
|
+
|
12
|
+
# @param namespace_name [String]
|
13
|
+
# @return [void]
|
14
|
+
#
|
15
|
+
# @api private
|
16
|
+
# @since 0.7.0
|
17
|
+
def initialize(namespace_name)
|
18
|
+
super(namespace_name)
|
19
|
+
@container_klass = Class.new(SmartCore::Container)
|
20
|
+
@container_instance = nil
|
21
|
+
@lock = SmartCore::Container::ArbitaryLock.new
|
22
|
+
end
|
23
|
+
|
24
|
+
# @return [SmartCore::Container]
|
25
|
+
#
|
26
|
+
# @api private
|
27
|
+
# @since 0.7.0
|
28
|
+
def resolve
|
29
|
+
thread_safe { container_instance }
|
30
|
+
end
|
31
|
+
|
32
|
+
# @param dependencies_definition [Proc]
|
33
|
+
# @return [void]
|
34
|
+
#
|
35
|
+
# @api private
|
36
|
+
# @since 0.7.0
|
37
|
+
def append_definitions(dependencies_definition)
|
38
|
+
thread_safe { container_klass.instance_eval(&dependencies_definition) }
|
39
|
+
end
|
40
|
+
|
41
|
+
# @return [void]
|
42
|
+
#
|
43
|
+
# @api private
|
44
|
+
# @since 0.7.0
|
45
|
+
def freeze!
|
46
|
+
thread_safe { container_instance.freeze! }
|
47
|
+
end
|
48
|
+
|
49
|
+
private
|
50
|
+
|
51
|
+
# @return [Class<SmartCore::Container>]
|
52
|
+
#
|
53
|
+
# @api private
|
54
|
+
# @since 0.7.0
|
55
|
+
attr_reader :container_klass
|
56
|
+
|
57
|
+
# @return [SmartCore::Container]
|
58
|
+
#
|
59
|
+
# @api private
|
60
|
+
# @since 0.7.0
|
61
|
+
def container_instance
|
62
|
+
@container_instance ||= container_klass.new
|
63
|
+
end
|
64
|
+
|
65
|
+
# @param block [Block]
|
66
|
+
# @return [Any]
|
67
|
+
#
|
68
|
+
# @api private
|
69
|
+
# @since 0.7.0
|
70
|
+
def thread_safe(&block)
|
71
|
+
@lock.thread_safe(&block)
|
72
|
+
end
|
73
|
+
end
|
@@ -0,0 +1,41 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
# @api private
|
4
|
+
# @since 0.7.0
|
5
|
+
class SmartCore::Container::Entities::NamespaceBuilder
|
6
|
+
class << self
|
7
|
+
# @param namespace_name [String]
|
8
|
+
# @return [SmartCore::Container::Entities::Namespace]
|
9
|
+
#
|
10
|
+
# @api private
|
11
|
+
# @since 0.7.0
|
12
|
+
def build(namespace_name)
|
13
|
+
new(namespace_name).build
|
14
|
+
end
|
15
|
+
end
|
16
|
+
|
17
|
+
# @param namespace_name [String]
|
18
|
+
# @return [void]
|
19
|
+
#
|
20
|
+
# @api private
|
21
|
+
# @since 0.7.0
|
22
|
+
def initialize(namespace_name)
|
23
|
+
@namespace_name = namespace_name
|
24
|
+
end
|
25
|
+
|
26
|
+
# @return [SmartCore::Container::Entities::Namespace]
|
27
|
+
#
|
28
|
+
# @api private
|
29
|
+
# @since 0.7.0
|
30
|
+
def build
|
31
|
+
SmartCore::Container::Entities::Namespace.new(namespace_name)
|
32
|
+
end
|
33
|
+
|
34
|
+
private
|
35
|
+
|
36
|
+
# @return [String]
|
37
|
+
#
|
38
|
+
# @api private
|
39
|
+
# @since 0.7.0
|
40
|
+
attr_reader :namespace_name
|
41
|
+
end
|
@@ -0,0 +1,43 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
class SmartCore::Container
|
4
|
+
# @api public
|
5
|
+
# @since 0.7.0
|
6
|
+
Error = Class.new(SmartCore::Error)
|
7
|
+
|
8
|
+
# @api public
|
9
|
+
# @since 0.7.0
|
10
|
+
ArgumentError = Class.new(SmartCore::ArgumentError)
|
11
|
+
|
12
|
+
# @api public
|
13
|
+
# @since 0.7.0
|
14
|
+
IncompatibleEntityNameError = Class.new(ArgumentError)
|
15
|
+
|
16
|
+
# @see SmartCore::Container::Registry
|
17
|
+
#
|
18
|
+
# @api public
|
19
|
+
# @since 0.7.0
|
20
|
+
FrozenRegistryError = Class.new(SmartCore::FrozenError)
|
21
|
+
|
22
|
+
# @see SmartCore::Container::Registry
|
23
|
+
#
|
24
|
+
# @api public
|
25
|
+
# @since 0.7.0
|
26
|
+
NonexistentEntityError = Class.new(Error)
|
27
|
+
|
28
|
+
# @see SmartCore::Container::DependencyCompatability::General
|
29
|
+
# @see SmartCore::Container::DependencyCompatability::Definition
|
30
|
+
# @see SmartCore::Container::DependencyCompatability::Registry
|
31
|
+
#
|
32
|
+
# @api public
|
33
|
+
# @since 0.7.0
|
34
|
+
DependencyOverNamespaceOverlapError = Class.new(Error)
|
35
|
+
|
36
|
+
# @see SmartCore::Container::DependencyCompatability::General
|
37
|
+
# @see SmartCore::Container::DependencyCompatability::Definition
|
38
|
+
# @see SmartCore::Container::DependencyCompatability::Registry
|
39
|
+
#
|
40
|
+
# @api public
|
41
|
+
# @since 0.7.0
|
42
|
+
NamespaceOverDependencyOverlapError = Class.new(Error)
|
43
|
+
end
|
@@ -1,19 +1,19 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
3
|
# @api priavate
|
4
|
-
# @since 0.
|
4
|
+
# @since 0.7.0
|
5
5
|
module SmartCore::Container::KeyGuard
|
6
6
|
class << self
|
7
7
|
# @param key [Symbol, String]
|
8
8
|
# @return [void]
|
9
9
|
#
|
10
|
-
# @raise [SmartCore::Container::
|
10
|
+
# @raise [SmartCore::Container::IncompatibleEntityNameError]
|
11
11
|
#
|
12
12
|
# @api private
|
13
|
-
# @since 0.
|
13
|
+
# @since 0.7.0
|
14
14
|
def prevent_incomparabilities!(key)
|
15
15
|
raise(
|
16
|
-
SmartCore::Container::
|
16
|
+
SmartCore::Container::IncompatibleEntityNameError,
|
17
17
|
'Namespace/Dependency name should be a symbol or a string'
|
18
18
|
) unless key.is_a?(String) || key.is_a?(Symbol)
|
19
19
|
end
|
@@ -22,7 +22,7 @@ module SmartCore::Container::KeyGuard
|
|
22
22
|
# @return [String]
|
23
23
|
#
|
24
24
|
# @api private
|
25
|
-
# @since 0.
|
25
|
+
# @since 0.7.0
|
26
26
|
def indifferently_accessable_key(key)
|
27
27
|
prevent_incomparabilities!(key)
|
28
28
|
key.to_s
|
@@ -1,18 +1,17 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
3
|
# @api public
|
4
|
-
# @since 0.
|
4
|
+
# @since 0.7.0
|
5
5
|
module SmartCore::Container::Mixin
|
6
6
|
class << self
|
7
7
|
# @param base_klass [Class]
|
8
8
|
# @return [void]
|
9
9
|
#
|
10
10
|
# @api private
|
11
|
-
# @since 0.
|
11
|
+
# @since 0.7.0
|
12
12
|
def included(base_klass)
|
13
13
|
# rubocop:disable Metrics/LineLength
|
14
|
-
base_klass.instance_variable_set(:@__smart_core_container_access_lock__,
|
15
|
-
base_klass.instance_variable_set(:@__smart_core_container_definition_lock__, Mutex.new)
|
14
|
+
base_klass.instance_variable_set(:@__smart_core_container_access_lock__, SmartCore::Container::ArbitaryLock.new)
|
16
15
|
base_klass.instance_variable_set(:@__smart_core_container_klass__, Class.new(SmartCore::Container))
|
17
16
|
base_klass.instance_variable_set(:@__smart_core_container__, nil)
|
18
17
|
# rubocop:enable Metrics/LineLength
|
@@ -24,57 +23,62 @@ module SmartCore::Container::Mixin
|
|
24
23
|
end
|
25
24
|
|
26
25
|
# @api private
|
27
|
-
# @since 0.
|
26
|
+
# @since 0.7.0
|
28
27
|
module ClassInheritance
|
29
28
|
# @param child_klass [CLass]
|
30
29
|
# @return [void]
|
31
30
|
#
|
32
31
|
# @api private
|
33
|
-
# @since 0.
|
32
|
+
# @since 0.7.0
|
34
33
|
def inherited(child_klass)
|
35
34
|
inherited_container_klass = Class.new(@__smart_core_container_klass__)
|
36
35
|
|
37
|
-
|
38
|
-
child_klass.instance_variable_set(:@
|
36
|
+
# rubocop:disable Metrics/LineLength
|
37
|
+
child_klass.instance_variable_set(:@__smart_core_container_access_lock__, SmartCore::Container::ArbitaryLock.new)
|
39
38
|
child_klass.instance_variable_set(:@__smart_core_container_klass__, inherited_container_klass)
|
40
39
|
child_klass.instance_variable_set(:@__smart_core_container__, nil)
|
40
|
+
# rubocop:disable Metrics/LineLength
|
41
41
|
|
42
42
|
super
|
43
43
|
end
|
44
44
|
end
|
45
45
|
|
46
46
|
# @api private
|
47
|
-
# @since 0.
|
47
|
+
# @since 0.7.0
|
48
48
|
module ClassMethods
|
49
|
+
# @param freeze_state [Boolean]
|
49
50
|
# @param block [Proc]
|
50
51
|
# @return [void]
|
51
52
|
#
|
52
53
|
# @api public
|
53
|
-
# @since 0.
|
54
|
-
def dependencies(&block)
|
55
|
-
@
|
54
|
+
# @since 0.7.0
|
55
|
+
def dependencies(freeze_state: false, &block)
|
56
|
+
@__smart_core_container_access_lock__.thread_safe do
|
56
57
|
@__smart_core_container_klass__.instance_eval(&block) if block_given?
|
58
|
+
@__smart_core_container_klass__.instance_eval do
|
59
|
+
freeze_state!
|
60
|
+
end if freeze_state
|
57
61
|
end
|
58
62
|
end
|
59
63
|
|
60
64
|
# @return [SmartCore::Container]
|
61
65
|
#
|
62
66
|
# @api public
|
63
|
-
# @since 0.
|
67
|
+
# @since 0.7.0
|
64
68
|
def container
|
65
|
-
@
|
69
|
+
@__smart_core_container_access_lock__.thread_safe do
|
66
70
|
@__smart_core_container__ ||= @__smart_core_container_klass__.new
|
67
71
|
end
|
68
72
|
end
|
69
73
|
end
|
70
74
|
|
71
75
|
# @api private
|
72
|
-
# @since 0.
|
76
|
+
# @since 0.7.0
|
73
77
|
module InstanceMethods
|
74
78
|
# @return [SmartCore::Container]
|
75
79
|
#
|
76
80
|
# @api public
|
77
|
-
# @since 0.
|
81
|
+
# @since 0.7.0
|
78
82
|
def container
|
79
83
|
self.class.container
|
80
84
|
end
|