smart_container 0.9.0 → 0.10.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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 6a45cc16a5fa97c52b28570a75115e21765f771b58e43fc1a0bd90d39b3c8abe
4
- data.tar.gz: e956a3ceaa496e4c7e023ac6310b93bc05525959f48619f0c31126d9097f7e83
3
+ metadata.gz: 929c6fcba625ebb836b753d4563082ea2d0aa793abbf840ed97fe6f209a0c7b0
4
+ data.tar.gz: b9cf58d9fc718aff98847e74f986b86da7984c3537f5258a37a2c67f9af611e8
5
5
  SHA512:
6
- metadata.gz: d4d619d75a98601444c55ff7a278169e6b0937f0356ff19f8fcd41ba9c72d9f25c8ec0a077a90b87d77469605e542a5e5081aec5d9b0bf0c1718019902ad8166
7
- data.tar.gz: cb220b711e67c661f7338ff6d49f82048df73861cadc0c1fdc981739d7c64ffec03953d397176c1d9e4e64321cdae078ca624fcb6ac51a8ccb92f4473b92fe83
6
+ metadata.gz: 93e6062a36edf2f06d37132dc53b55c87f5f0aac277eafec6a17572ff60f73e0c164ed4fae53ee5333c10556e605e8d4c9c29b935406f7a9dceb0280e7bfa4df
7
+ data.tar.gz: a653c4ded2e96d9fe4f42292eabe0467ad1cfe3a2633aa3bd4f77506d69f65c0a32703ecffb6875eb5d3de9d3e34592fdebc95c50417257c5a864273b9ae116c
data/.rubocop.yml CHANGED
@@ -5,7 +5,7 @@ inherit_gem:
5
5
  - lib/rubocop.rspec.yml
6
6
 
7
7
  AllCops:
8
- TargetRubyVersion: 3.0.0
8
+ TargetRubyVersion: 3.1
9
9
  NewCops: enable
10
10
  Include:
11
11
  - lib/**/*.rb
data/CHANGELOG.md CHANGED
@@ -1,14 +1,24 @@
1
1
  # Changelog
2
2
  All notable changes to this project will be documented in this file.
3
3
 
4
+ ## [0.10.0] - 2022-10-14
5
+ ### Changed
6
+ - Simple `Mutex`-based locks was replaced with `SmartCore::Engine::ReadWriteLock` in order to decrease
7
+ context switching during method resolving inside RubyVM (to reduce thread locks when it is not necessary);
8
+ - Development progress:
9
+ - Minimal ruby version - **2.5**;
10
+ - Updated development dependencies;
11
+ - Updated `smart_engine` dependency (`~> 0.11` -> `~> 0.17`);
12
+
13
+
4
14
  ## [0.9.0] - 2020-01-17
5
15
  ### Added
6
- - Support for *Ruby@3*;
16
+ - Support for **Ruby@3**;
7
17
  - Updated development dependencies;
8
18
 
9
19
  ### Changed
10
20
  - No more TravisCI (todo: migrate to Github Actions);
11
- - Minimal `smart_engine` version: *0.11.0* (in order to support *Ruby@3*);
21
+ - Minimal `smart_engine` version: **0.11.0** (in order to support **Ruby@3**);
12
22
 
13
23
  ## [0.8.1] - 2020-07-09
14
24
  ### Changed
data/Gemfile.lock CHANGED
@@ -1,104 +1,137 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- smart_container (0.9.0)
5
- smart_engine (~> 0.11)
4
+ smart_container (0.10.0)
5
+ smart_engine (~> 0.17)
6
6
 
7
7
  GEM
8
8
  remote: https://rubygems.org/
9
9
  specs:
10
- activesupport (6.1.1)
10
+ activesupport (7.0.4)
11
11
  concurrent-ruby (~> 1.0, >= 1.0.2)
12
12
  i18n (>= 1.6, < 2)
13
13
  minitest (>= 5.1)
14
14
  tzinfo (~> 2.0)
15
- zeitwerk (~> 2.3)
16
- armitage-rubocop (1.7.0.1)
17
- rubocop (= 1.7.0)
18
- rubocop-performance (= 1.9.1)
19
- rubocop-rails (= 2.9.1)
20
- rubocop-rake (= 0.5.1)
21
- rubocop-rspec (= 2.1.0)
22
- ast (2.4.1)
15
+ armitage-rubocop (1.36.0)
16
+ rubocop (= 1.36.0)
17
+ rubocop-performance (= 1.15.0)
18
+ rubocop-rails (= 2.16.1)
19
+ rubocop-rake (= 0.6.0)
20
+ rubocop-rspec (= 2.13.2)
21
+ ast (2.4.2)
22
+ backport (1.2.0)
23
+ benchmark (0.2.0)
23
24
  coderay (1.1.3)
24
- concurrent-ruby (1.1.7)
25
- diff-lcs (1.4.4)
26
- docile (1.3.5)
27
- i18n (1.8.7)
25
+ concurrent-ruby (1.1.10)
26
+ diff-lcs (1.5.0)
27
+ docile (1.4.0)
28
+ e2mmap (0.1.0)
29
+ i18n (1.12.0)
28
30
  concurrent-ruby (~> 1.0)
31
+ jaro_winkler (1.5.4)
32
+ json (2.6.2)
33
+ kramdown (2.4.0)
34
+ rexml
35
+ kramdown-parser-gfm (1.1.0)
36
+ kramdown (~> 2.0)
29
37
  method_source (1.0.0)
30
- minitest (5.14.3)
31
- parallel (1.20.1)
32
- parser (3.0.0.0)
38
+ minitest (5.16.3)
39
+ nokogiri (1.13.8-arm64-darwin)
40
+ racc (~> 1.4)
41
+ parallel (1.22.1)
42
+ parser (3.1.2.1)
33
43
  ast (~> 2.4.1)
34
- pry (0.13.1)
44
+ pry (0.14.1)
35
45
  coderay (~> 1.1)
36
46
  method_source (~> 1.0)
37
- rack (2.2.3)
38
- rainbow (3.0.0)
39
- rake (13.0.3)
40
- regexp_parser (2.0.3)
41
- rexml (3.2.4)
42
- rspec (3.10.0)
43
- rspec-core (~> 3.10.0)
44
- rspec-expectations (~> 3.10.0)
45
- rspec-mocks (~> 3.10.0)
46
- rspec-core (3.10.1)
47
- rspec-support (~> 3.10.0)
48
- rspec-expectations (3.10.1)
47
+ racc (1.6.0)
48
+ rack (3.0.0)
49
+ rainbow (3.1.1)
50
+ rake (13.0.6)
51
+ regexp_parser (2.6.0)
52
+ reverse_markdown (2.1.1)
53
+ nokogiri
54
+ rexml (3.2.5)
55
+ rspec (3.11.0)
56
+ rspec-core (~> 3.11.0)
57
+ rspec-expectations (~> 3.11.0)
58
+ rspec-mocks (~> 3.11.0)
59
+ rspec-core (3.11.0)
60
+ rspec-support (~> 3.11.0)
61
+ rspec-expectations (3.11.1)
49
62
  diff-lcs (>= 1.2.0, < 2.0)
50
- rspec-support (~> 3.10.0)
51
- rspec-mocks (3.10.1)
63
+ rspec-support (~> 3.11.0)
64
+ rspec-mocks (3.11.1)
52
65
  diff-lcs (>= 1.2.0, < 2.0)
53
- rspec-support (~> 3.10.0)
54
- rspec-support (3.10.1)
55
- rubocop (1.7.0)
66
+ rspec-support (~> 3.11.0)
67
+ rspec-support (3.11.1)
68
+ rubocop (1.36.0)
69
+ json (~> 2.3)
56
70
  parallel (~> 1.10)
57
- parser (>= 2.7.1.5)
71
+ parser (>= 3.1.2.1)
58
72
  rainbow (>= 2.2.2, < 4.0)
59
73
  regexp_parser (>= 1.8, < 3.0)
60
- rexml
61
- rubocop-ast (>= 1.2.0, < 2.0)
74
+ rexml (>= 3.2.5, < 4.0)
75
+ rubocop-ast (>= 1.20.1, < 2.0)
62
76
  ruby-progressbar (~> 1.7)
63
- unicode-display_width (>= 1.4.0, < 2.0)
64
- rubocop-ast (1.4.0)
65
- parser (>= 2.7.1.5)
66
- rubocop-performance (1.9.1)
67
- rubocop (>= 0.90.0, < 2.0)
77
+ unicode-display_width (>= 1.4.0, < 3.0)
78
+ rubocop-ast (1.21.0)
79
+ parser (>= 3.1.1.0)
80
+ rubocop-performance (1.15.0)
81
+ rubocop (>= 1.7.0, < 2.0)
68
82
  rubocop-ast (>= 0.4.0)
69
- rubocop-rails (2.9.1)
83
+ rubocop-rails (2.16.1)
70
84
  activesupport (>= 4.2.0)
71
85
  rack (>= 1.1)
72
- rubocop (>= 0.90.0, < 2.0)
73
- rubocop-rake (0.5.1)
74
- rubocop
75
- rubocop-rspec (2.1.0)
86
+ rubocop (>= 1.33.0, < 2.0)
87
+ rubocop-rake (0.6.0)
76
88
  rubocop (~> 1.0)
77
- rubocop-ast (>= 1.1.0)
89
+ rubocop-rspec (2.13.2)
90
+ rubocop (~> 1.33)
78
91
  ruby-progressbar (1.11.0)
79
92
  simplecov (0.21.2)
80
93
  docile (~> 1.1)
81
94
  simplecov-html (~> 0.11)
82
95
  simplecov_json_formatter (~> 0.1)
83
96
  simplecov-html (0.12.3)
84
- simplecov_json_formatter (0.1.2)
85
- smart_engine (0.11.0)
86
- tzinfo (2.0.4)
97
+ simplecov_json_formatter (0.1.4)
98
+ smart_engine (0.17.0)
99
+ solargraph (0.47.2)
100
+ backport (~> 1.2)
101
+ benchmark
102
+ bundler (>= 1.17.2)
103
+ diff-lcs (~> 1.4)
104
+ e2mmap
105
+ jaro_winkler (~> 1.5)
106
+ kramdown (~> 2.3)
107
+ kramdown-parser-gfm (~> 1.1)
108
+ parser (~> 3.0)
109
+ reverse_markdown (>= 1.0.5, < 3)
110
+ rubocop (>= 0.52)
111
+ thor (~> 1.0)
112
+ tilt (~> 2.0)
113
+ yard (~> 0.9, >= 0.9.24)
114
+ thor (1.2.1)
115
+ tilt (2.0.11)
116
+ tzinfo (2.0.5)
87
117
  concurrent-ruby (~> 1.0)
88
- unicode-display_width (1.7.0)
89
- zeitwerk (2.4.2)
118
+ unicode-display_width (2.3.0)
119
+ webrick (1.7.0)
120
+ yard (0.9.28)
121
+ webrick (~> 1.7.0)
90
122
 
91
123
  PLATFORMS
92
- x86_64-darwin-20
124
+ arm64-darwin-21
93
125
 
94
126
  DEPENDENCIES
95
- armitage-rubocop (~> 1.7)
96
- bundler (~> 2.2)
97
- pry (~> 0.13)
127
+ armitage-rubocop (~> 1.36)
128
+ bundler (~> 2.3)
129
+ pry (~> 0.14)
98
130
  rake (~> 13.0)
99
- rspec (~> 3.10)
131
+ rspec (~> 3.11)
100
132
  simplecov (~> 0.21)
101
133
  smart_container!
134
+ solargraph (~> 0.47)
102
135
 
103
136
  BUNDLED WITH
104
- 2.2.3
137
+ 2.3.23
data/LICENSE.txt CHANGED
@@ -1,6 +1,6 @@
1
1
  The MIT License (MIT)
2
2
 
3
- Copyright (c) 2020 Rustam Ibragimov
3
+ Copyright (c) 2020-2021 Rustam Ibragimov
4
4
 
5
5
  Permission is hereby granted, free of charge, to any person obtaining a copy
6
6
  of this software and associated documentation files (the "Software"), to deal
data/README.md CHANGED
@@ -1,6 +1,14 @@
1
- # SmartCore::Container &middot; [![Gem Version](https://badge.fury.io/rb/smart_container.svg)](https://badge.fury.io/rb/smart_container)
1
+ # SmartCore::Container &middot; <a target="_blank" href="https://github.com/Cado-Labs"><img src="https://github.com/Cado-Labs/cado-labs-logos/raw/main/cado_labs_badge.svg" alt="Supported by Cado Labs" style="max-width: 100%; height: 20px"></a> &middot; [![Gem Version](https://badge.fury.io/rb/smart_container.png)](https://badge.fury.io/rb/smart_container)
2
2
 
3
- Thread-safe semanticaly-defined IoC/DI Container.
3
+ Thread-safe semanticaly-defined IoC/DI Container with a developer-friendly DSL and API.
4
+
5
+ ---
6
+
7
+ <p>
8
+ <a href="https://github.com/Cado-Labs">
9
+ <img src="https://github.com/Cado-Labs/cado-labs-logos/blob/main/cado_labs_supporting.svg" alt="Supported by Cado Labs" />
10
+ </a>
11
+ </p>
4
12
 
5
13
  ---
6
14
 
@@ -370,6 +378,12 @@ end
370
378
 
371
379
  Released under MIT License.
372
380
 
381
+ ## Supporting
382
+
383
+ <a href="https://github.com/Cado-Labs">
384
+ <img src="https://github.com/Cado-Labs/cado-labs-logos/blob/main/cado_labs_logo.png" alt="Supported by Cado Labs" />
385
+ </a>
386
+
373
387
  ## Authors
374
388
 
375
389
  [Rustam Ibragimov](https://github.com/0exp)
@@ -17,7 +17,7 @@ class SmartCore::Container
17
17
  def included(base_klass)
18
18
  base_klass.instance_variable_set(:@__container_definition_commands__, CommandSet.new)
19
19
  base_klass.instance_variable_set(:@__container_instantiation_commands__, CommandSet.new)
20
- base_klass.instance_variable_set(:@__container_definition_lock__, ArbitraryLock.new)
20
+ base_klass.instance_variable_set(:@__container_definition_lock__, SmartCore::Engine::ReadWriteLock.new)
21
21
  base_klass.singleton_class.send(:attr_reader, :__container_definition_commands__)
22
22
  base_klass.singleton_class.send(:attr_reader, :__container_instantiation_commands__)
23
23
  base_klass.extend(ClassMethods)
@@ -36,7 +36,7 @@ class SmartCore::Container
36
36
  def inherited(child_klass)
37
37
  child_klass.instance_variable_set(:@__container_definition_commands__, CommandSet.new)
38
38
  child_klass.instance_variable_set(:@__container_instantiation_commands__, CommandSet.new)
39
- child_klass.instance_variable_set(:@__container_definition_lock__, ArbitraryLock.new)
39
+ child_klass.instance_variable_set(:@__container_definition_lock__, SmartCore::Engine::ReadWriteLock.new)
40
40
  SmartCore::Container::DefinitionDSL::Inheritance.inherit(base: self, child: child_klass)
41
41
  child_klass.singleton_class.prepend(ClassInheritance)
42
42
  super
@@ -53,7 +53,7 @@ class SmartCore::Container
53
53
  # @api public
54
54
  # @since 0.1.0
55
55
  def namespace(namespace_name, &dependencies_definition)
56
- @__container_definition_lock__.thread_safe do
56
+ @__container_definition_lock__.write_sync do
57
57
  DependencyCompatability::Definition.prevent_dependency_overlap!(self, namespace_name)
58
58
 
59
59
  __container_definition_commands__ << Commands::Definition::Namespace.new(
@@ -75,7 +75,7 @@ class SmartCore::Container
75
75
  memoize: SmartCore::Container::Registry::DEFAULT_MEMOIZATION_BEHAVIOR,
76
76
  &dependency_definition
77
77
  )
78
- @__container_definition_lock__.thread_safe do
78
+ @__container_definition_lock__.write_sync do
79
79
  DependencyCompatability::Definition.prevent_namespace_overlap!(self, dependency_name)
80
80
 
81
81
  __container_definition_commands__ << Commands::Definition::Register.new(
@@ -90,7 +90,7 @@ class SmartCore::Container
90
90
  # @api public
91
91
  # @since 0.1.0
92
92
  def compose(container_klass)
93
- @__container_definition_lock__.thread_safe do
93
+ @__container_definition_lock__.write_sync do
94
94
  __container_definition_commands__ << Commands::Definition::Compose.new(
95
95
  container_klass
96
96
  )
@@ -106,7 +106,7 @@ class SmartCore::Container
106
106
  # @api public
107
107
  # @since 0.1.0
108
108
  def freeze_state!
109
- @__container_definition_lock__.thread_safe do
109
+ @__container_definition_lock__.write_sync do
110
110
  __container_instantiation_commands__ << Commands::Instantiation::FreezeState.new
111
111
  end
112
112
  end
@@ -13,7 +13,6 @@ module SmartCore::Container::DependencyCompatability::Definition
13
13
  #
14
14
  # @api private
15
15
  # @since 0.1.0
16
- # rubocop:disable Lint/EmptyBlock
17
16
  def potential_namespace_overlap?(container_klass, dependency_name)
18
17
  anonymous_container = Class.new(container_klass).new
19
18
  anonymous_container.register(dependency_name, &(proc {}))
@@ -21,7 +20,6 @@ module SmartCore::Container::DependencyCompatability::Definition
21
20
  rescue SmartCore::Container::DependencyOverNamespaceOverlapError
22
21
  true
23
22
  end
24
- # rubocop:enable Lint/EmptyBlock
25
23
 
26
24
  # @param container_klass [Class<SmartCore::Container>]
27
25
  # @param namespace_name [String, Symbol]
@@ -29,7 +27,6 @@ module SmartCore::Container::DependencyCompatability::Definition
29
27
  #
30
28
  # @api private
31
29
  # @since 0.1.0
32
- # rubocop:disable Lint/EmptyBlock
33
30
  def potential_dependency_overlap?(container_klass, namespace_name)
34
31
  anonymous_container = Class.new(container_klass).new
35
32
  anonymous_container.namespace(namespace_name, &(proc {}))
@@ -37,6 +34,5 @@ module SmartCore::Container::DependencyCompatability::Definition
37
34
  rescue SmartCore::Container::NamespaceOverDependencyOverlapError
38
35
  true
39
36
  end
40
- # rubocop:enable Lint/EmptyBlock
41
37
  end
42
38
  end
@@ -3,6 +3,7 @@
3
3
  module SmartCore::Container::Entities
4
4
  # @api private
5
5
  # @since 0.2.0
6
+ # @version 0.10.0
6
7
  class MemoizedDependency < Dependency
7
8
  # @param dependency_name [String]
8
9
  # @param dependency_definition [Proc]
@@ -10,9 +11,10 @@ module SmartCore::Container::Entities
10
11
  #
11
12
  # @api private
12
13
  # @since 0.2.0
14
+ # @version 0.10.0
13
15
  def initialize(dependency_name, dependency_definition)
14
16
  super(dependency_name, dependency_definition)
15
- @lock = SmartCore::Container::ArbitraryLock.new
17
+ @lock = SmartCore::Engine::ReadWriteLock.new
16
18
  end
17
19
 
18
20
  # @param host_container [SmartCore::Container, NilClass]
@@ -22,7 +24,7 @@ module SmartCore::Container::Entities
22
24
  # @since 0.2.0
23
25
  # @version 0.8.1
24
26
  def reveal(host_container = SmartCore::Container::NO_HOST_CONTAINER)
25
- @lock.thread_safe do
27
+ @lock.read_sync do
26
28
  unless instance_variable_defined?(:@revealed_dependency)
27
29
  @revealed_dependency = dependency_definition.call
28
30
  else
@@ -2,6 +2,7 @@
2
2
 
3
3
  # @api private
4
4
  # @since 0.1.0
5
+ # @version 0.10.0
5
6
  class SmartCore::Container::Entities::Namespace < SmartCore::Container::Entities::Base
6
7
  # @return [String]
7
8
  #
@@ -21,13 +22,13 @@ class SmartCore::Container::Entities::Namespace < SmartCore::Container::Entities
21
22
  #
22
23
  # @api private
23
24
  # @since 0.1.0
24
- # @version 0.8.1
25
+ # @version 0.10.0
25
26
  def initialize(namespace_name, host_container = SmartCore::Container::NO_HOST_CONTAINER)
26
27
  super(namespace_name)
27
28
  @container_klass = Class.new(SmartCore::Container)
28
29
  @container_instance = nil
29
30
  @host_container = host_container
30
- @lock = SmartCore::Container::ArbitraryLock.new
31
+ @lock = SmartCore::Engine::ReadWriteLock.new
31
32
  end
32
33
 
33
34
  # @param runtime_host_container [SmartCore::Container, NilClass]
@@ -35,26 +36,26 @@ class SmartCore::Container::Entities::Namespace < SmartCore::Container::Entities
35
36
  #
36
37
  # @api private
37
38
  # @since 0.1.0
38
- # @version 0.8.1
39
+ # @version 0.10.0
39
40
  def reveal(runtime_host_container = SmartCore::Container::NO_HOST_CONTAINER)
40
- thread_safe { container_instance(runtime_host_container) }
41
+ @lock.read_sync { container_instance(runtime_host_container) }
41
42
  end
42
43
 
43
44
  # @param dependencies_definition [Proc]
44
45
  # @return [void]
45
46
  #
46
47
  # @api private
47
- # @since 0.1.0
48
+ # @since 0.10.0
48
49
  def append_definitions(dependencies_definition)
49
- thread_safe { container_klass.instance_eval(&dependencies_definition) }
50
+ @lock.write_sync { container_klass.instance_eval(&dependencies_definition) }
50
51
  end
51
52
 
52
53
  # @return [void]
53
54
  #
54
55
  # @api private
55
- # @since 0.1.0
56
+ # @since 0.10.0
56
57
  def freeze!
57
- thread_safe { container_instance.freeze! }
58
+ @lock.write_sync { container_instance.freeze! }
58
59
  end
59
60
 
60
61
  private
@@ -78,13 +79,4 @@ class SmartCore::Container::Entities::Namespace < SmartCore::Container::Entities
78
79
  host_path: @host_container && namespace_name
79
80
  )
80
81
  end
81
-
82
- # @param block [Block]
83
- # @return [Any]
84
- #
85
- # @api private
86
- # @since 0.1.0
87
- def thread_safe(&block)
88
- @lock.thread_safe(&block)
89
- end
90
82
  end
@@ -2,6 +2,7 @@
2
2
 
3
3
  # @api private
4
4
  # @since 0.1.0
5
+ # @version 0.10.0
5
6
  # rubocop:disable Metrics/ClassLength
6
7
  class SmartCore::Container::Registry
7
8
  # @since 0.1.0
@@ -35,9 +36,10 @@ class SmartCore::Container::Registry
35
36
  #
36
37
  # @api private
37
38
  # @since 0.1.0
39
+ # @version 0.10.0
38
40
  def initialize
39
41
  @registry = {}
40
- @access_lock = SmartCore::Container::ArbitraryLock.new
42
+ @lock = SmartCore::Engine::ReadWriteLock.new
41
43
  end
42
44
 
43
45
  # @param entity_path [String, Symbol]
@@ -45,8 +47,9 @@ class SmartCore::Container::Registry
45
47
  #
46
48
  # @api private
47
49
  # @since 0.1.0
50
+ # @version 0.10.0
48
51
  def resolve(entity_path)
49
- thread_safe { fetch_entity(entity_path) }
52
+ @lock.read_sync { fetch_entity(entity_path) }
50
53
  end
51
54
 
52
55
  # @param name [String, Symbol]
@@ -56,9 +59,9 @@ class SmartCore::Container::Registry
56
59
  #
57
60
  # @api private
58
61
  # @since 0.1.0
59
- # @version 0.3.0
62
+ # @version 0.10.0
60
63
  def register_dependency(name, memoize: DEFAULT_MEMOIZATION_BEHAVIOR, &dependency_definition)
61
- thread_safe { add_dependency(name, dependency_definition, memoize) }
64
+ @lock.write_sync { add_dependency(name, dependency_definition, memoize) }
62
65
  end
63
66
 
64
67
  # @param name [String, Symbol]
@@ -68,29 +71,31 @@ class SmartCore::Container::Registry
68
71
  #
69
72
  # @api private
70
73
  # @since 0.1.0
71
- # @version 0.8.1
74
+ # @version 0.10.0
72
75
  def register_namespace(
73
76
  name,
74
77
  host_container = SmartCore::Container::NO_HOST_CONTAINER,
75
78
  &dependencies_definition
76
79
  )
77
- thread_safe { add_namespace(name, host_container, dependencies_definition) }
80
+ @lock.write_sync { add_namespace(name, host_container, dependencies_definition) }
78
81
  end
79
82
 
80
83
  # @return [void]
81
84
  #
82
85
  # @api private
83
86
  # @since 0.1.0
87
+ # @version 0.10.0
84
88
  def freeze!
85
- thread_safe { freeze_state! }
89
+ @lock.write_sync { freeze_state! }
86
90
  end
87
91
 
88
92
  # @return [Boolean]
89
93
  #
90
94
  # @api private
91
95
  # @since 0.1.0
96
+ # @version 0.10.0
92
97
  def frozen?
93
- thread_safe { state_frozen? }
98
+ @lock.read_sync { state_frozen? }
94
99
  end
95
100
 
96
101
  # @param block [Block]
@@ -98,8 +103,9 @@ class SmartCore::Container::Registry
98
103
  #
99
104
  # @api private
100
105
  # @since 0.1.0
106
+ # @version 0.10.0
101
107
  def each(&block)
102
- thread_safe { enumerate(&block) }
108
+ @lock.read_sync { enumerate(&block) }
103
109
  end
104
110
 
105
111
  # @param root_dependency_name [NilClass, String]
@@ -109,12 +115,13 @@ class SmartCore::Container::Registry
109
115
  #
110
116
  # @api private
111
117
  # @since 0.4.0
118
+ # @version 0.10.0
112
119
  def each_dependency(
113
120
  root_dependency_name = nil,
114
121
  yield_all: DEFAULT_ITERATION_YIELD_BEHAVIOUR,
115
122
  &block
116
123
  )
117
- thread_safe { iterate(root_dependency_name, yield_all: yield_all, &block) }
124
+ @lock.read_sync { iterate(root_dependency_name, yield_all: yield_all, &block) }
118
125
  end
119
126
 
120
127
  # @option all_variants [Boolean]
@@ -122,28 +129,24 @@ class SmartCore::Container::Registry
122
129
  #
123
130
  # @api private
124
131
  # @since 0.4.0
132
+ # @version 0.10.0
125
133
  def keys(all_variants: DEFAULT_KEY_EXTRACTION_BEHAVIOUR)
126
- thread_safe { extract_keys(all_variants: all_variants) }
134
+ @lock.read_sync { extract_keys(all_variants: all_variants) }
127
135
  end
128
136
 
129
137
  # @return [Hash<String|Symbol,SmartCore::Container::Entities::Base|Any>]
130
138
  #
131
139
  # @api private
132
140
  # @since 0.1.0
141
+ # @version 0.10.0
133
142
  def hash_tree(resolve_dependencies: false)
134
- thread_safe { build_hash_tree(resolve_dependencies: resolve_dependencies) }
143
+ @lock.read_sync { build_hash_tree(resolve_dependencies: resolve_dependencies) }
135
144
  end
136
145
  alias_method :to_h, :hash_tree
137
146
  alias_method :to_hash, :hash_tree
138
147
 
139
148
  private
140
149
 
141
- # @return [Mutex]
142
- #
143
- # @api private
144
- # @since 0.1.0
145
- attr_reader :lock
146
-
147
150
  # @return [Boolean]
148
151
  #
149
152
  # @api private
@@ -238,7 +241,6 @@ class SmartCore::Container::Registry
238
241
  # @api private
239
242
  # @since 0.1.0
240
243
  # @version 0.8.1
241
- # rubocop:disable Lint/EmptyBlock
242
244
  def add_namespace(namespace_name, host_container, dependencies_definition)
243
245
  if state_frozen?
244
246
  raise(SmartCore::Container::FrozenRegistryError, 'Can not modify frozen registry!')
@@ -256,7 +258,6 @@ class SmartCore::Container::Registry
256
258
  end
257
259
  namespace_entity.tap { namespace_entity.append_definitions(dependencies_definition) }
258
260
  end
259
- # rubocop:enable Lint/EmptyBlock
260
261
 
261
262
  # @param root_dependency_name [String, NilClass]
262
263
  # @param block [Block]
@@ -274,8 +275,8 @@ class SmartCore::Container::Registry
274
275
  final_dependency_name =
275
276
  if root_dependency_name
276
277
  "#{root_dependency_name}" \
277
- "#{SmartCore::Container::DependencyResolver::PATH_PART_SEPARATOR}" \
278
- "#{dependency_name}"
278
+ "#{SmartCore::Container::DependencyResolver::PATH_PART_SEPARATOR}" \
279
+ "#{dependency_name}"
279
280
  else
280
281
  dependency_name
281
282
  end
@@ -342,14 +343,5 @@ class SmartCore::Container::Registry
342
343
  self, namespace_name
343
344
  )
344
345
  end
345
-
346
- # @param block [Proc]
347
- # @return [Any]
348
- #
349
- # @api private
350
- # @since 0.1.0
351
- def thread_safe(&block)
352
- @access_lock.thread_safe(&block)
353
- end
354
346
  end
355
347
  # rubocop:enable Metrics/ClassLength
@@ -2,9 +2,11 @@
2
2
 
3
3
  module SmartCore
4
4
  class Container # rubocop:disable Style/StaticClass
5
+ # @return [String]
6
+ #
5
7
  # @api public
6
8
  # @since 0.1.0
7
- # @version 0.9.0
8
- VERSION = '0.9.0'
9
+ # @version 0.10.0
10
+ VERSION = '0.10.0'
9
11
  end
10
12
  end
@@ -7,10 +7,10 @@ require 'smart_core'
7
7
  module SmartCore
8
8
  # @api public
9
9
  # @since 0.1.0
10
+ # @version 0.10.0
10
11
  class Container # rubocop:disable Metrics/ClassLength
11
12
  require_relative 'container/version'
12
13
  require_relative 'container/errors'
13
- require_relative 'container/arbitrary_lock'
14
14
  require_relative 'container/key_guard'
15
15
  require_relative 'container/entities'
16
16
  require_relative 'container/definition_dsl'
@@ -82,13 +82,13 @@ module SmartCore
82
82
  #
83
83
  # @api public
84
84
  # @since 0.1.0
85
- # @version 0.8.1
85
+ # @version 0.10.0
86
86
  def initialize(host_container: NO_HOST_CONTAINER, host_path: NO_HOST_PATH)
87
87
  @host = SmartCore::Container::Host.build(host_container, host_path)
88
88
  build_registry!
89
89
  @watcher = SmartCore::Container::DependencyWatcher.new(self)
90
90
  @host_path = host_path
91
- @access_lock = ArbitraryLock.new
91
+ @lock = SmartCore::Engine::ReadWriteLock.new
92
92
  end
93
93
 
94
94
  # @param dependency_name [String, Symbol]
@@ -97,13 +97,14 @@ module SmartCore
97
97
  #
98
98
  # @api public
99
99
  # @sicne 0.1.0
100
- # @version 0.8.0
100
+ # @version 0.10.0
101
101
  def register(
102
102
  dependency_name,
103
103
  memoize: SmartCore::Container::Registry::DEFAULT_MEMOIZATION_BEHAVIOR,
104
104
  &dependency_definition
105
105
  )
106
- thread_safe do
106
+
107
+ @lock.write_sync do
107
108
  registry.register_dependency(dependency_name, memoize: memoize, &dependency_definition)
108
109
  watcher.notify(dependency_name)
109
110
  end
@@ -115,9 +116,9 @@ module SmartCore
115
116
  #
116
117
  # @api public
117
118
  # @since 0.1.0
118
- # @version 0.8.0
119
+ # @version 0.10.0
119
120
  def namespace(namespace_name, &dependencies_definition)
120
- thread_safe do
121
+ @lock.write_sync do
121
122
  registry.register_namespace(namespace_name, self, &dependencies_definition)
122
123
  watcher.notify(namespace_name)
123
124
  end
@@ -128,9 +129,9 @@ module SmartCore
128
129
  #
129
130
  # @api public
130
131
  # @since 0.1.0
131
- # @version 0.1.0
132
+ # @version 0.10.0
132
133
  def resolve(dependency_path)
133
- thread_safe { DependencyResolver.resolve(self, dependency_path) }
134
+ @lock.read_sync { DependencyResolver.resolve(self, dependency_path) }
134
135
  end
135
136
  alias_method :[], :resolve
136
137
 
@@ -139,32 +140,36 @@ module SmartCore
139
140
  #
140
141
  # @api public
141
142
  # @since 0.1.0
143
+ # @version 0.10.0
142
144
  def fetch(dependency_path)
143
- thread_safe { DependencyResolver.fetch(self, dependency_path) }
145
+ @lock.read_sync { DependencyResolver.fetch(self, dependency_path) }
144
146
  end
145
147
 
146
148
  # @return [void]
147
149
  #
148
150
  # @api public
149
151
  # @since 0.1.0
152
+ # @version 0.10.0
150
153
  def freeze!
151
- thread_safe { registry.freeze! }
154
+ @lock.write_sync { registry.freeze! }
152
155
  end
153
156
 
154
157
  # @return [Boolean]
155
158
  #
156
159
  # @api public
157
160
  # @since 0.1.0
161
+ # @version 0.10.0
158
162
  def frozen?
159
- thread_safe { registry.frozen? }
163
+ @lock.read_sync { registry.frozen? }
160
164
  end
161
165
 
162
166
  # @return [void]
163
167
  #
164
168
  # @api public
165
169
  # @since 0.1.0
170
+ # @version 0.10.0
166
171
  def reload!
167
- thread_safe { build_registry! }
172
+ @lock.write_sync { build_registry! }
168
173
  end
169
174
 
170
175
  # @option all_variants [Boolean]
@@ -172,8 +177,9 @@ module SmartCore
172
177
  #
173
178
  # @api public
174
179
  # @since 0.4.0
180
+ # @version 0.10.0
175
181
  def keys(all_variants: SmartCore::Container::Registry::DEFAULT_KEY_EXTRACTION_BEHAVIOUR)
176
- thread_safe { registry.keys(all_variants: all_variants) }
182
+ @lock.read_sync { registry.keys(all_variants: all_variants) }
177
183
  end
178
184
 
179
185
  # @param key [String, Symbol]
@@ -181,8 +187,9 @@ module SmartCore
181
187
  #
182
188
  # @api public
183
189
  # @since 0.5.0
190
+ # @version 0.10.0
184
191
  def key?(key)
185
- thread_safe { DependencyResolver.key?(self, key) }
192
+ @lock.read_sync { DependencyResolver.key?(self, key) }
186
193
  end
187
194
 
188
195
  # @param namespace_path [String, Symbol]
@@ -190,8 +197,9 @@ module SmartCore
190
197
  #
191
198
  # @api public
192
199
  # @since 0.5.0
200
+ # @version 0.10.0
193
201
  def namespace?(namespace_path)
194
- thread_safe { DependencyResolver.namespace?(self, namespace_path) }
202
+ @lock.read_sync { DependencyResolver.namespace?(self, namespace_path) }
195
203
  end
196
204
 
197
205
  # @param dependency_path [String, Symbol]
@@ -200,8 +208,9 @@ module SmartCore
200
208
  #
201
209
  # @api public
202
210
  # @since 0.5.0
211
+ # @version 0.10.0
203
212
  def dependency?(dependency_path, memoized: nil)
204
- thread_safe { DependencyResolver.dependency?(self, dependency_path, memoized: memoized) }
213
+ @lock.read_sync { DependencyResolver.dependency?(self, dependency_path, memoized: memoized) }
205
214
  end
206
215
 
207
216
  # @option yield_all [Boolean]
@@ -213,11 +222,12 @@ module SmartCore
213
222
  #
214
223
  # @api public
215
224
  # @since 0.4.0
225
+ # @version 0.10.0
216
226
  def each_dependency(
217
227
  yield_all: SmartCore::Container::Registry::DEFAULT_ITERATION_YIELD_BEHAVIOUR,
218
228
  &block
219
229
  )
220
- thread_safe { registry.each_dependency(yield_all: yield_all, &block) }
230
+ @lock.read_sync { registry.each_dependency(yield_all: yield_all, &block) }
221
231
  end
222
232
  alias_method :each, :each_dependency
223
233
  alias_method :each_pair, :each_dependency
@@ -227,8 +237,9 @@ module SmartCore
227
237
  #
228
238
  # @api public
229
239
  # @since 0.1.0
240
+ # @version 0.10.0
230
241
  def hash_tree(resolve_dependencies: false)
231
- thread_safe { registry.hash_tree(resolve_dependencies: resolve_dependencies) }
242
+ @lock.read_sync { registry.hash_tree(resolve_dependencies: resolve_dependencies) }
232
243
  end
233
244
  alias_method :to_h, :hash_tree
234
245
  alias_method :to_hash, :hash_tree
@@ -242,8 +253,9 @@ module SmartCore
242
253
  #
243
254
  # @api public
244
255
  # @since 0.8.0
256
+ # @version 0.10.0
245
257
  def observe(entity_path, &observer) # TODO: support for pattern-based pathes
246
- thread_safe { watcher.watch(entity_path, &observer) }
258
+ @lock.write_sync { watcher.watch(entity_path, &observer) }
247
259
  end
248
260
  alias_method :subscribe, :observe
249
261
 
@@ -252,8 +264,9 @@ module SmartCore
252
264
  #
253
265
  # @api public
254
266
  # @since 0.8.0
267
+ # @version 0.10.0
255
268
  def unobserve(observer)
256
- thread_safe { watcher.unwatch(observer) }
269
+ @lock.write_sync { watcher.unwatch(observer) }
257
270
  end
258
271
  alias_method :unsubscribe, :unobserve
259
272
 
@@ -262,8 +275,9 @@ module SmartCore
262
275
  #
263
276
  # @api public
264
277
  # @since 0.8.0
278
+ # @version 0.10.0
265
279
  def clear_observers(entity_path = nil) # TODO: support for pattern-based pathes
266
- thread_safe { watcher.clear_listeners(entity_path) }
280
+ @lock.write_sync { watcher.clear_listeners(entity_path) }
267
281
  end
268
282
  alias_method :clear_listeners, :clear_observers
269
283
 
@@ -277,14 +291,5 @@ module SmartCore
277
291
  def build_registry!
278
292
  @registry = RegistryBuilder.build(self)
279
293
  end
280
-
281
- # @param block [Block]
282
- # @return [Any]
283
- #
284
- # @api private
285
- # @since 0.1.0
286
- def thread_safe(&block)
287
- @access_lock.thread_safe(&block)
288
- end
289
294
  end
290
295
  end
@@ -3,7 +3,7 @@
3
3
  require_relative 'lib/smart_core/container/version'
4
4
 
5
5
  Gem::Specification.new do |spec|
6
- spec.required_ruby_version = Gem::Requirement.new('>= 2.4.10')
6
+ spec.required_ruby_version = Gem::Requirement.new('>= 2.5')
7
7
 
8
8
  spec.name = 'smart_container'
9
9
  spec.version = SmartCore::Container::VERSION
@@ -27,12 +27,13 @@ Gem::Specification.new do |spec|
27
27
  spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
28
28
  spec.require_paths = ['lib']
29
29
 
30
- spec.add_dependency 'smart_engine', '~> 0.11'
30
+ spec.add_dependency 'smart_engine', '~> 0.17'
31
31
 
32
- spec.add_development_dependency 'bundler', '~> 2.2'
32
+ spec.add_development_dependency 'solargraph', '~> 0.47'
33
+ spec.add_development_dependency 'bundler', '~> 2.3'
33
34
  spec.add_development_dependency 'rake', '~> 13.0'
34
- spec.add_development_dependency 'rspec', '~> 3.10'
35
- spec.add_development_dependency 'armitage-rubocop', '~> 1.7'
35
+ spec.add_development_dependency 'rspec', '~> 3.11'
36
+ spec.add_development_dependency 'armitage-rubocop', '~> 1.36'
36
37
  spec.add_development_dependency 'simplecov', '~> 0.21'
37
- spec.add_development_dependency 'pry', '~> 0.13'
38
+ spec.add_development_dependency 'pry', '~> 0.14'
38
39
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: smart_container
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.9.0
4
+ version: 0.10.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Rustam Ibragimov
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2021-01-17 00:00:00.000000000 Z
11
+ date: 2022-10-13 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: smart_engine
@@ -16,28 +16,42 @@ dependencies:
16
16
  requirements:
17
17
  - - "~>"
18
18
  - !ruby/object:Gem::Version
19
- version: '0.11'
19
+ version: '0.17'
20
20
  type: :runtime
21
21
  prerelease: false
22
22
  version_requirements: !ruby/object:Gem::Requirement
23
23
  requirements:
24
24
  - - "~>"
25
25
  - !ruby/object:Gem::Version
26
- version: '0.11'
26
+ version: '0.17'
27
+ - !ruby/object:Gem::Dependency
28
+ name: solargraph
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - "~>"
32
+ - !ruby/object:Gem::Version
33
+ version: '0.47'
34
+ type: :development
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - "~>"
39
+ - !ruby/object:Gem::Version
40
+ version: '0.47'
27
41
  - !ruby/object:Gem::Dependency
28
42
  name: bundler
29
43
  requirement: !ruby/object:Gem::Requirement
30
44
  requirements:
31
45
  - - "~>"
32
46
  - !ruby/object:Gem::Version
33
- version: '2.2'
47
+ version: '2.3'
34
48
  type: :development
35
49
  prerelease: false
36
50
  version_requirements: !ruby/object:Gem::Requirement
37
51
  requirements:
38
52
  - - "~>"
39
53
  - !ruby/object:Gem::Version
40
- version: '2.2'
54
+ version: '2.3'
41
55
  - !ruby/object:Gem::Dependency
42
56
  name: rake
43
57
  requirement: !ruby/object:Gem::Requirement
@@ -58,28 +72,28 @@ dependencies:
58
72
  requirements:
59
73
  - - "~>"
60
74
  - !ruby/object:Gem::Version
61
- version: '3.10'
75
+ version: '3.11'
62
76
  type: :development
63
77
  prerelease: false
64
78
  version_requirements: !ruby/object:Gem::Requirement
65
79
  requirements:
66
80
  - - "~>"
67
81
  - !ruby/object:Gem::Version
68
- version: '3.10'
82
+ version: '3.11'
69
83
  - !ruby/object:Gem::Dependency
70
84
  name: armitage-rubocop
71
85
  requirement: !ruby/object:Gem::Requirement
72
86
  requirements:
73
87
  - - "~>"
74
88
  - !ruby/object:Gem::Version
75
- version: '1.7'
89
+ version: '1.36'
76
90
  type: :development
77
91
  prerelease: false
78
92
  version_requirements: !ruby/object:Gem::Requirement
79
93
  requirements:
80
94
  - - "~>"
81
95
  - !ruby/object:Gem::Version
82
- version: '1.7'
96
+ version: '1.36'
83
97
  - !ruby/object:Gem::Dependency
84
98
  name: simplecov
85
99
  requirement: !ruby/object:Gem::Requirement
@@ -100,14 +114,14 @@ dependencies:
100
114
  requirements:
101
115
  - - "~>"
102
116
  - !ruby/object:Gem::Version
103
- version: '0.13'
117
+ version: '0.14'
104
118
  type: :development
105
119
  prerelease: false
106
120
  version_requirements: !ruby/object:Gem::Requirement
107
121
  requirements:
108
122
  - - "~>"
109
123
  - !ruby/object:Gem::Version
110
- version: '0.13'
124
+ version: '0.14'
111
125
  description: Thread-safe semanticaly-defined IoC/DI Container
112
126
  email:
113
127
  - iamdaiver@gmail.com
@@ -128,7 +142,6 @@ files:
128
142
  - bin/console
129
143
  - bin/setup
130
144
  - lib/smart_core/container.rb
131
- - lib/smart_core/container/arbitrary_lock.rb
132
145
  - lib/smart_core/container/definition_dsl.rb
133
146
  - lib/smart_core/container/definition_dsl/command_set.rb
134
147
  - lib/smart_core/container/definition_dsl/commands.rb
@@ -180,14 +193,14 @@ required_ruby_version: !ruby/object:Gem::Requirement
180
193
  requirements:
181
194
  - - ">="
182
195
  - !ruby/object:Gem::Version
183
- version: 2.4.10
196
+ version: '2.5'
184
197
  required_rubygems_version: !ruby/object:Gem::Requirement
185
198
  requirements:
186
199
  - - ">="
187
200
  - !ruby/object:Gem::Version
188
201
  version: '0'
189
202
  requirements: []
190
- rubygems_version: 3.2.3
203
+ rubygems_version: 3.3.11
191
204
  signing_key:
192
205
  specification_version: 4
193
206
  summary: IoC/DI Container
@@ -1,22 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- # @api private
4
- # @since 0.1.0
5
- class SmartCore::Container::ArbitraryLock
6
- # @return [void]
7
- #
8
- # @api private
9
- # @since 0.1.0
10
- def initialize
11
- @lock = Mutex.new
12
- end
13
-
14
- # @param block [Proc]
15
- # @return [Any]
16
- #
17
- # @api private
18
- # @since 0.1.0
19
- def thread_safe(&block)
20
- @lock.owned? ? yield : @lock.synchronize(&block)
21
- end
22
- end