foobara 0.2.3 → 0.2.5

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 (46) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +14 -0
  3. data/README.md +96 -3
  4. data/projects/builtin_types/src/builtin_types.rb +3 -3
  5. data/projects/callback/src/registry/chained_multiple_action.rb +1 -1
  6. data/projects/callback/src/registry/conditioned.rb +1 -1
  7. data/projects/callback/src/registry/multiple_action.rb +1 -1
  8. data/projects/command_connectors/src/command_connector.rb +20 -3
  9. data/projects/command_connectors/src/serializers/errors_serializer.rb +1 -1
  10. data/projects/command_connectors/src/serializers/success_serializer.rb +1 -1
  11. data/projects/common/src/runtime_error.rb +1 -1
  12. data/projects/foobara/lib/foobara/all.rb +0 -1
  13. data/projects/foobara/src/foobara.rb +3 -0
  14. data/projects/namespace/src/namespace.rb +1 -1
  15. data/projects/persistence/src/entity_base/transaction/concerns/state_transitions.rb +1 -0
  16. data/projects/persistence/src/entity_base/transaction_table/concerns/record_tracking.rb +6 -1
  17. data/projects/persistence/src/entity_base/transaction_table.rb +1 -2
  18. data/projects/state_machine/src/state_machine.rb +4 -4
  19. data/projects/type_declarations/src/desugarizer.rb +1 -1
  20. data/projects/type_declarations/src/handlers/extend_array_type_declaration/array_desugarizer.rb +2 -2
  21. data/projects/type_declarations/src/handlers/extend_array_type_declaration/to_type_transformer.rb +2 -2
  22. data/projects/type_declarations/src/handlers/extend_associative_array_type_declaration/to_type_transformer.rb +1 -4
  23. data/projects/type_declarations/src/handlers/extend_associative_array_type_declaration.rb +1 -1
  24. data/projects/type_declarations/src/handlers/extend_attributes_type_declaration/dsl_desugarizer.rb +1 -1
  25. data/projects/type_declarations/src/handlers/extend_attributes_type_declaration/element_type_declarations_desugarizer.rb +3 -3
  26. data/projects/type_declarations/src/handlers/extend_attributes_type_declaration/hash_desugarizer.rb +2 -2
  27. data/projects/type_declarations/src/handlers/extend_attributes_type_declaration/to_type_transformer.rb +2 -2
  28. data/projects/type_declarations/src/handlers/extend_registered_type_declaration/to_type_transformer.rb +2 -2
  29. data/projects/type_declarations/src/handlers/extend_registered_type_declaration.rb +1 -1
  30. data/projects/type_declarations/src/handlers/extend_tuple_type_declaration/array_desugarizer.rb +2 -2
  31. data/projects/type_declarations/src/handlers/extend_tuple_type_declaration/to_type_transformer.rb +2 -2
  32. data/projects/type_declarations/src/handlers/registered_type_declaration/to_type_transformer.rb +1 -1
  33. data/projects/type_declarations/src/handlers/registered_type_declaration.rb +1 -1
  34. data/projects/type_declarations/src/to_type_transformer.rb +1 -1
  35. data/projects/type_declarations/src/type_declaration_handler.rb +1 -1
  36. data/projects/type_declarations/src/type_declarations.rb +2 -2
  37. data/projects/types/src/type.rb +5 -0
  38. data/projects/value/lib/foobara/value.rb +1 -1
  39. data/projects/value/src/processor/casting.rb +1 -1
  40. data/projects/value/src/processor/pipeline.rb +1 -1
  41. data/projects/value/src/processor/selection.rb +2 -2
  42. data/projects/value/src/transformer.rb +1 -1
  43. data/version.rb +1 -1
  44. metadata +3 -6
  45. data/projects/weak_object_hash/lib/foobara/weak_object_hash.rb +0 -3
  46. data/projects/weak_object_hash/src/weak_object_hash.rb +0 -225
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: b8eba3fdf241f3d5a5d1d65eeefc6ccd39175e63c4c6d86ece37af0bfb1126d0
4
- data.tar.gz: 3d398fc443f593da6c7e6348469e1d9fe500eb319e3e7859a57dc046b7b58009
3
+ metadata.gz: e05617e8bea9b7a9ce861246a1a5c664ad3b525630dd1cd7362b80b4d6d809ea
4
+ data.tar.gz: 10bd954f202f83aef9a20f0dec859212766a81e9682f6526ece70e3cd457b6a7
5
5
  SHA512:
6
- metadata.gz: 01bf11b7499124317f6e941f0d0013eec1d0ccdc6132ed97e67b7b73a8a29b6820bb315fbc0c79dee7416cfe91ae7cb9c56c8b70ad197577981ec0288f39f64e
7
- data.tar.gz: fff2fc836bada39c4302ad902462345bb7fcded4f2e74976ee862b24e1fbce66655fcc5f8171b3c2bf8b4d75564f772eb5afa50cdd90d452bb064002660c5753
6
+ metadata.gz: 26fa0c9be295542f963963ac892405a315d5b6f004fadcdf23336bab09ad973cdae843186134c20c1e173be816506c37f2ad34e825c6d84f2c2ef42845262011
7
+ data.tar.gz: efefbce7b11751d240a09ca34bc5e20a182c60daa00cc79399aceee55c74e33b8b1135aca706abd2a8d3e80c39414477a19d3fee05cc28bdd0e13b063d6fda77
data/CHANGELOG.md CHANGED
@@ -1,3 +1,17 @@
1
+ # [0.2.5] - 2025-10-27
2
+
3
+ - Do not allow commands to be connected multiple times via symbol/string
4
+ - Add CommandConnector#all_exposed_command_names
5
+ - pry is again required by default in development/test mode but can be skipped with SKIP_PRY env var
6
+
7
+ # [0.2.4] -2025-10-26
8
+
9
+ - Remove all uses of .require_project_file and deprecate it
10
+ - Replace custom WeakObjectHash with similar standard library ObjectSpace::WeakMap
11
+ - Call #committed only after whole transaction has been fully committed
12
+ - Add/fire a :persisted event for callbacks when an entity receives a primary key and is committed
13
+ - Add Type#add_caster
14
+
1
15
  # [0.2.3] - 2025-10-22
2
16
 
3
17
  - Fix Persistence.register_base bug
data/README.md CHANGED
@@ -2100,11 +2100,11 @@ TODO: give some code examples
2100
2100
  # Additional learning materials/Documentation
2101
2101
 
2102
2102
  * Overview and code demo videos:
2103
- * https://foobara.com/videos
2103
+ * https://foobara.org/videos
2104
2104
  * https://www.youtube.com/@FoobaraFlix
2105
2105
  * YARD Docs
2106
2106
  * All docs combined: https://docs.foobara.com/all/
2107
- * Per-repository docs: https://foobara.com/docs
2107
+ * Per-repository docs: https://foobara.org/docs
2108
2108
 
2109
2109
  # Help
2110
2110
 
@@ -2124,10 +2124,103 @@ the build will fail if test coverage is below 100%.
2124
2124
 
2125
2125
  You should be able to do the typical stuff:
2126
2126
 
2127
+ ### 1. Cloning repository:
2128
+ Fork the repository and run this(Only for SSH):
2129
+
2130
+ ```
2131
+ git clone git@github.com:${your_github_username}/foobara.git
2132
+ ```
2133
+
2134
+ Create a new branch for you to push into
2135
+
2136
+ ```
2137
+ git checkout -b <branch-name>
2138
+ ```
2139
+
2140
+ Now navigate to project directory
2141
+
2127
2142
  ```
2128
- git clone git@github.com:foobara/foobara
2129
2143
  cd foobara
2144
+ ```
2145
+
2146
+ ### 2. Installing mise (LINUX/WSL)
2147
+ Mise is a package manager and helps with managing different versions of ruby. It allows you to switch different versions of ruby.
2148
+
2149
+ The installation docs might be updated by mise so here's the reference to that: [Installation Docs](https://mise.jdx.dev/installing-mise.html)
2150
+
2151
+ ***If you already installed by following mise's docs then, you can skip this section***
2152
+
2153
+ Else to setup mise follow the script given below:
2154
+
2155
+ ```
2156
+ sudo apt update -y && sudo apt install -y gpg wget \
2157
+ build-essential \
2158
+ libssl-dev zlib1g-dev libreadline-dev libyaml-dev libxml2-dev \
2159
+ libxslt1-dev libffi-dev libgdbm-dev autoconf bison
2160
+ wget -qO - https://mise.jdx.dev/gpg-key.pub | gpg --dearmor | sudo tee /etc/apt/keyrings/mise-archive-keyring.gpg 1> /dev/null
2161
+ echo "deb [signed-by=/etc/apt/keyrings/mise-archive-keyring.gpg arch=amd64] https://mise.jdx.dev/deb stable main" | sudo tee /etc/apt/sources.list.d/mise.list
2162
+ sudo apt update
2163
+ sudo apt install -y mise
2164
+ ```
2165
+
2166
+ Verify if it's installed or not by running:
2167
+
2168
+ ```
2169
+ mise -v
2170
+ ```
2171
+
2172
+ It should print out an ascii-art saying "mise-en-place"
2173
+
2174
+ ### 3. Install required ruby version
2175
+ In this project, currently we require ruby version >=3.4 so we can install it manually using the command below
2176
+
2177
+ ```
2178
+ mise use -g ruby@3.4
2179
+ ```
2180
+
2181
+ In case, you want to automatically activate the ruby version whenever you navigate to the directory containing .ruby-version file
2182
+
2183
+ This helps a lot when you have lot of ruby projects with different versions and don't want to switch ruby versions each time manually
2184
+
2185
+ ```
2186
+ mise settings add idiomatic_version_file_enable_tools ruby
2187
+ ```
2188
+
2189
+ ### 4. Activating mise
2190
+ We can activate mise so that it will update the environment variables such that we will use the correct version of ruby.
2191
+
2192
+ ```
2193
+ echo 'eval "$(mise activate bash)"' >> ~/.bashrc
2194
+ ```
2195
+
2196
+ Restart the terminal
2197
+
2198
+ Now environment variables are updated and you can verify it by running:
2199
+
2200
+ ```
2201
+ ruby -v
2202
+ ```
2203
+
2204
+ It will print out the ruby version, which is mentioned in .ruby-version file
2205
+
2206
+ You can list out your mise tools and its versions by running:
2207
+
2208
+ ```
2209
+ mise list
2210
+ ```
2211
+
2212
+ ### 5. Running tests
2213
+ Before running test-suite, we need to install all the dependencies
2214
+
2215
+ Run this to install all the dependencies:
2216
+
2217
+ ```
2130
2218
  bundle
2219
+ ```
2220
+
2221
+ Run the tests now:
2222
+
2223
+ ```
2131
2224
  rake
2132
2225
  ```
2133
2226
 
@@ -1,7 +1,7 @@
1
1
  module Foobara
2
- Foobara.require_project_file("builtin_types", "duck")
3
- Foobara.require_project_file("builtin_types", "atomic_duck")
4
- Foobara.require_project_file("builtin_types", "duckture")
2
+ require_relative "duck"
3
+ require_relative "atomic_duck"
4
+ require_relative "duckture"
5
5
 
6
6
  module BuiltinTypes
7
7
  class << self
@@ -1,4 +1,4 @@
1
- Foobara.require_project_file("callback", "registry/multiple_action")
1
+ require_relative "multiple_action"
2
2
 
3
3
  module Foobara
4
4
  module Callback
@@ -1,4 +1,4 @@
1
- Foobara.require_project_file("callback", "registry/base")
1
+ require_relative "base"
2
2
 
3
3
  module Foobara
4
4
  module Callback
@@ -1,4 +1,4 @@
1
- Foobara.require_project_file("callback", "registry/base")
1
+ require_relative "base"
2
2
 
3
3
  module Foobara
4
4
  module Callback
@@ -1,6 +1,7 @@
1
1
  module Foobara
2
2
  class CommandConnector
3
3
  class UnexpectedSensitiveTypeInManifestError < StandardError; end
4
+ class AlreadyConnectedError < StandardError; end
4
5
 
5
6
  include Concerns::Desugarizers
6
7
 
@@ -116,9 +117,10 @@ module Foobara
116
117
  end
117
118
  end
118
119
 
119
- attr_accessor :command_registry, :authenticator, :capture_unknown_error
120
+ attr_accessor :command_registry, :authenticator, :capture_unknown_error, :name
120
121
 
121
- def initialize(authenticator: nil,
122
+ def initialize(name: nil,
123
+ authenticator: nil,
122
124
  capture_unknown_error: nil,
123
125
  default_serializers: nil,
124
126
  default_pre_commit_transformers: nil)
@@ -127,6 +129,7 @@ module Foobara
127
129
  self.authenticator = authenticator
128
130
  self.command_registry = CommandRegistry.new(authenticator:)
129
131
  self.capture_unknown_error = capture_unknown_error
132
+ self.name = name
130
133
 
131
134
  Util.array(default_serializers).each do |serializer|
132
135
  add_default_serializer(serializer)
@@ -303,7 +306,15 @@ module Foobara
303
306
  end
304
307
 
305
308
  def connect_delayed(registerable_name, *args, **opts)
306
- delayed_connections[registerable_name.to_s] = { args:, opts: }
309
+ key = registerable_name.to_s
310
+
311
+ if delayed_connections.key?(key)
312
+ # :nocov:
313
+ raise AlreadyConnectedError, "Already connected #{key}"
314
+ # :nocov:
315
+ else
316
+ delayed_connections[key] = { args:, opts: }
317
+ end
307
318
  end
308
319
 
309
320
  def delayed_connections
@@ -311,6 +322,8 @@ module Foobara
311
322
  end
312
323
 
313
324
  def process_delayed_connections
325
+ return if delayed_connections.empty?
326
+
314
327
  delayed_connections.each_pair do |registerable_name, arg_hash|
315
328
  args = arg_hash[:args]
316
329
  opts = arg_hash[:opts]
@@ -663,6 +676,10 @@ module Foobara
663
676
  command_registry.foobara_all_command(mode: Namespace::LookupMode::ABSOLUTE_SINGLE_NAMESPACE)
664
677
  end
665
678
 
679
+ def all_exposed_command_names
680
+ all_exposed_commands.map(&:full_command_name)
681
+ end
682
+
666
683
  def all_exposed_type_names
667
684
  # TODO: cache this or better yet cache #foobara_manifest
668
685
  foobara_manifest[:type].keys.sort.map(&:to_s)
@@ -1,5 +1,5 @@
1
1
  module Foobara
2
- require_project_file("command_connectors", "serializer")
2
+ require_relative "../serializer"
3
3
 
4
4
  module CommandConnectors
5
5
  module Serializers
@@ -1,5 +1,5 @@
1
1
  module Foobara
2
- require_project_file("command_connectors", "serializer")
2
+ require_relative "../serializer"
3
3
 
4
4
  module CommandConnectors
5
5
  module Serializers
@@ -1,4 +1,4 @@
1
- Foobara.require_project_file("common", "error")
1
+ require_relative "error"
2
2
 
3
3
  module Foobara
4
4
  # NOTE: annoyingly this will clash with ::RuntimeError if not fully qualified when using
@@ -16,7 +16,6 @@ module Foobara
16
16
  # could be independent projects
17
17
  projects "delegate", # Let's just kill delegate
18
18
  "concerns",
19
- "weak_object_hash",
20
19
  "enumerated",
21
20
  "callback",
22
21
  "state_machine",
@@ -5,7 +5,10 @@ module Foobara
5
5
 
6
6
  class << self
7
7
  def require_project_file(project, path)
8
+ # :nocov:
9
+ warn "DEPRECATION WARNING: require_project_file is deprecated. Use require_relative instead."
8
10
  require_relative("../../#{project}/src/#{path}")
11
+ # :nocov:
9
12
  end
10
13
 
11
14
  attr_accessor :is_installed
@@ -51,7 +51,7 @@ module Foobara
51
51
  end
52
52
 
53
53
  def on_change(object, method_name)
54
- @on_change ||= WeakObjectHash.new
54
+ @on_change ||= ObjectSpace::WeakMap.new
55
55
 
56
56
  @on_change[object] = method_name
57
57
  end
@@ -60,6 +60,7 @@ module Foobara
60
60
  state_machine.commit! do
61
61
  each_table(&:commit!)
62
62
  entity_attributes_crud_driver.commit_transaction(raw_tx)
63
+ each_table(&:committed)
63
64
  each_table(&:transaction_closed)
64
65
  end
65
66
  rescue => e
@@ -86,6 +86,10 @@ module Foobara
86
86
  end
87
87
 
88
88
  def committed
89
+ marked_persisted.each do |record|
90
+ record.fire(:persisted)
91
+ end
92
+
89
93
  closed
90
94
  end
91
95
 
@@ -113,7 +117,8 @@ module Foobara
113
117
  :updated,
114
118
  :hard_deleted,
115
119
  :created,
116
- :loading
120
+ :loading,
121
+ :persisted
117
122
  ]
118
123
 
119
124
  interesting_record_states.each do |state|
@@ -656,6 +656,7 @@ module Foobara
656
656
  record.is_persisted = record.is_loaded = true
657
657
  record.is_created = false
658
658
  record.save_persisted_attributes
659
+ mark_persisted(record)
659
660
  end
660
661
 
661
662
  marked_created.clear
@@ -695,8 +696,6 @@ module Foobara
695
696
  validate!
696
697
  flush_created!
697
698
  flush_updated_and_hard_deleted!
698
-
699
- committed
700
699
  end
701
700
 
702
701
  def revert!
@@ -1,8 +1,8 @@
1
1
  module Foobara
2
- require_project_file("state_machine", "sugar")
3
- require_project_file("state_machine", "callbacks")
4
- require_project_file("state_machine", "validations")
5
- require_project_file("state_machine", "transitions")
2
+ require_relative "sugar"
3
+ require_relative "callbacks"
4
+ require_relative "validations"
5
+ require_relative "transitions"
6
6
 
7
7
  # TODO: allow quick creation of a statemachine either through better options to #initialize or a
8
8
  # .for method.
@@ -1,4 +1,4 @@
1
- Foobara.require_project_file("type_declarations", "with_registries")
1
+ require_relative "with_registries"
2
2
 
3
3
  module Foobara
4
4
  module TypeDeclarations
@@ -1,5 +1,5 @@
1
- Foobara.require_project_file("type_declarations", "desugarizer")
2
- Foobara.require_project_file("type_declarations", "handlers/extend_associative_array_type_declaration")
1
+ require_relative "../../desugarizer"
2
+ require_relative "../extend_associative_array_type_declaration"
3
3
 
4
4
  module Foobara
5
5
  module TypeDeclarations
@@ -1,5 +1,5 @@
1
- Foobara.require_project_file("type_declarations", "handlers/registered_type_declaration/to_type_transformer")
2
- Foobara.require_project_file("type_declarations", "handlers/extend_associative_array_type_declaration")
1
+ require_relative "../registered_type_declaration/to_type_transformer"
2
+ require_relative "../extend_associative_array_type_declaration"
3
3
 
4
4
  module Foobara
5
5
  module TypeDeclarations
@@ -1,7 +1,4 @@
1
- Foobara.require_project_file(
2
- "type_declarations",
3
- "handlers/extend_registered_type_declaration/to_type_transformer"
4
- )
1
+ require_relative "../extend_registered_type_declaration/to_type_transformer"
5
2
 
6
3
  module Foobara
7
4
  module TypeDeclarations
@@ -1,4 +1,4 @@
1
- Foobara.require_project_file("type_declarations", "handlers/extend_registered_type_declaration")
1
+ require_relative "extend_registered_type_declaration"
2
2
 
3
3
  module Foobara
4
4
  module TypeDeclarations
@@ -1,4 +1,4 @@
1
- Foobara.require_project_file("type_declarations", "handlers/extend_attributes_type_declaration/hash_desugarizer")
1
+ require_relative "hash_desugarizer"
2
2
 
3
3
  module Foobara
4
4
  module TypeDeclarations
@@ -1,6 +1,6 @@
1
- Foobara.require_project_file("type_declarations", "desugarizer")
2
- Foobara.require_project_file("type_declarations", "handlers/extend_associative_array_type_declaration")
3
- Foobara.require_project_file("type_declarations", "handlers/extend_attributes_type_declaration/hash_desugarizer")
1
+ require_relative "../../desugarizer"
2
+ require_relative "../extend_associative_array_type_declaration"
3
+ require_relative "hash_desugarizer"
4
4
 
5
5
  module Foobara
6
6
  module TypeDeclarations
@@ -1,5 +1,5 @@
1
- Foobara.require_project_file("type_declarations", "desugarizer")
2
- Foobara.require_project_file("type_declarations", "handlers/extend_associative_array_type_declaration")
1
+ require_relative "../../desugarizer"
2
+ require_relative "../extend_associative_array_type_declaration"
3
3
 
4
4
  module Foobara
5
5
  module TypeDeclarations
@@ -1,5 +1,5 @@
1
- Foobara.require_project_file("type_declarations", "handlers/registered_type_declaration/to_type_transformer")
2
- Foobara.require_project_file("type_declarations", "handlers/extend_associative_array_type_declaration")
1
+ require_relative "../registered_type_declaration/to_type_transformer"
2
+ require_relative "../extend_associative_array_type_declaration"
3
3
 
4
4
  module Foobara
5
5
  module TypeDeclarations
@@ -1,5 +1,5 @@
1
- Foobara.require_project_file("type_declarations", "handlers/registered_type_declaration/to_type_transformer")
2
- Foobara.require_project_file("type_declarations", "handlers/extend_associative_array_type_declaration")
1
+ require_relative "../registered_type_declaration/to_type_transformer"
2
+ require_relative "../extend_associative_array_type_declaration"
3
3
 
4
4
  module Foobara
5
5
  module TypeDeclarations
@@ -1,4 +1,4 @@
1
- Foobara.require_project_file("type_declarations", "handlers/registered_type_declaration")
1
+ require_relative "registered_type_declaration"
2
2
 
3
3
  module Foobara
4
4
  module TypeDeclarations
@@ -1,5 +1,5 @@
1
- Foobara.require_project_file("type_declarations", "desugarizer")
2
- Foobara.require_project_file("type_declarations", "handlers/extend_associative_array_type_declaration")
1
+ require_relative "../../desugarizer"
2
+ require_relative "../extend_associative_array_type_declaration"
3
3
 
4
4
  module Foobara
5
5
  module TypeDeclarations
@@ -1,5 +1,5 @@
1
- Foobara.require_project_file("type_declarations", "handlers/registered_type_declaration/to_type_transformer")
2
- Foobara.require_project_file("type_declarations", "handlers/extend_associative_array_type_declaration")
1
+ require_relative "../registered_type_declaration/to_type_transformer"
2
+ require_relative "../extend_associative_array_type_declaration"
3
3
 
4
4
  module Foobara
5
5
  module TypeDeclarations
@@ -1,4 +1,4 @@
1
- Foobara.require_project_file("type_declarations", "to_type_transformer")
1
+ require_relative "../../to_type_transformer"
2
2
 
3
3
  module Foobara
4
4
  module TypeDeclarations
@@ -1,4 +1,4 @@
1
- Foobara.require_project_file("type_declarations", "type_declaration_handler")
1
+ require_relative "../type_declaration_handler"
2
2
 
3
3
  module Foobara
4
4
  module TypeDeclarations
@@ -1,4 +1,4 @@
1
- Foobara.require_project_file("type_declarations", "transformer")
1
+ require_relative "transformer"
2
2
 
3
3
  module Foobara
4
4
  module TypeDeclarations
@@ -1,4 +1,4 @@
1
- Foobara.require_project_file("type_declarations", "with_registries")
1
+ require_relative "with_registries"
2
2
 
3
3
  module Foobara
4
4
  module TypeDeclarations
@@ -1,8 +1,8 @@
1
1
  require "inheritable_thread_vars"
2
2
 
3
3
  module Foobara
4
- require_project_file("type_declarations", "type_builder")
5
- require_project_file("type_declarations", "error_extension")
4
+ require_relative "type_builder"
5
+ require_relative "error_extension"
6
6
 
7
7
  module TypeDeclarations
8
8
  module Mode
@@ -346,6 +346,11 @@ module Foobara
346
346
  @casters = processors
347
347
  end
348
348
 
349
+ def add_caster(processor)
350
+ casters << processor
351
+ clear_caches
352
+ end
353
+
349
354
  def transformers=(processors)
350
355
  clear_caches
351
356
  @transformers = processors
@@ -3,5 +3,5 @@ module Foobara
3
3
  foobara_domain!
4
4
  end
5
5
 
6
- Foobara.require_project_file("value", "processor")
6
+ require_relative "../../src/processor"
7
7
  end
@@ -1,4 +1,4 @@
1
- Foobara.require_project_file("value", "data_error")
1
+ require_relative "../data_error"
2
2
 
3
3
  module Foobara
4
4
  module Value
@@ -1,4 +1,4 @@
1
- Foobara.require_project_file("value", "processor/multi")
1
+ require_relative "multi"
2
2
 
3
3
  module Foobara
4
4
  module Value
@@ -1,5 +1,5 @@
1
- Foobara.require_project_file("value", "processor/multi")
2
- Foobara.require_project_file("value", "data_error")
1
+ require_relative "multi"
2
+ require_relative "../data_error"
3
3
 
4
4
  module Foobara
5
5
  module Value
@@ -1,6 +1,6 @@
1
1
  require "securerandom"
2
2
 
3
- Foobara.require_project_file("value", "processor/runner")
3
+ require_relative "processor/runner"
4
4
 
5
5
  module Foobara
6
6
  module Value
data/version.rb CHANGED
@@ -1,6 +1,6 @@
1
1
  module Foobara
2
2
  module Version
3
- VERSION = "0.2.3".freeze
3
+ VERSION = "0.2.5".freeze
4
4
  MINIMUM_RUBY_VERSION = ">= 3.4.0".freeze
5
5
  end
6
6
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: foobara
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.3
4
+ version: 0.2.5
5
5
  platform: ruby
6
6
  authors:
7
7
  - Miles Georgi
@@ -491,16 +491,14 @@ files:
491
491
  - projects/value/src/processor/selection.rb
492
492
  - projects/value/src/transformer.rb
493
493
  - projects/value/src/validator.rb
494
- - projects/weak_object_hash/lib/foobara/weak_object_hash.rb
495
- - projects/weak_object_hash/src/weak_object_hash.rb
496
494
  - projects/weak_object_set/lib/foobara/weak_object_set.rb
497
495
  - projects/weak_object_set/src/weak_object_set.rb
498
496
  - version.rb
499
- homepage: https://foobara.com
497
+ homepage: https://foobara.org
500
498
  licenses:
501
499
  - MPL-2.0
502
500
  metadata:
503
- homepage_uri: https://foobara.com
501
+ homepage_uri: https://foobara.org
504
502
  source_code_uri: https://github.com/foobara/foobara
505
503
  changelog_uri: https://github.com/foobara/foobara/blob/main/CHANGELOG.md
506
504
  rubygems_mfa_required: 'true'
@@ -531,7 +529,6 @@ require_paths:
531
529
  - "./projects/type_declarations/lib"
532
530
  - "./projects/types/lib"
533
531
  - "./projects/value/lib"
534
- - "./projects/weak_object_hash/lib"
535
532
  - "./projects/weak_object_set/lib"
536
533
  required_ruby_version: !ruby/object:Gem::Requirement
537
534
  requirements:
@@ -1,3 +0,0 @@
1
- require "weakref"
2
-
3
- class Foobara::WeakObjectHash; end
@@ -1,225 +0,0 @@
1
- require "monitor"
2
-
3
- module Foobara
4
- # TODO: a possible optimization: have a certain number of records before the Weakref approach kicks in
5
- # that way we don't just immediately clear out useful information without any actual memory burden
6
- class WeakObjectHash
7
- class ClosedError < StandardError; end
8
-
9
- def initialize(skip_finalizer: false)
10
- if skip_finalizer
11
- self.skip_finalizer = true
12
- end
13
- self.monitor = Monitor.new
14
- self.object_ids_to_weak_refs_and_values = {}
15
- end
16
-
17
- def []=(object, value)
18
- object_id = object.object_id
19
- weak_ref = WeakRef.new(object)
20
-
21
- if closed?
22
- raise ClosedError, "Cannot add objects to a closed WeakObjectHash"
23
- end
24
-
25
- monitor.synchronize do
26
- delete(object)
27
-
28
- object_ids_to_weak_refs_and_values[object_id] = [weak_ref, value]
29
-
30
- unless skip_finalizer?
31
- ObjectSpace.define_finalizer(object, finalizer_proc)
32
- end
33
-
34
- value
35
- end
36
- end
37
-
38
- def [](object)
39
- object_id = object.object_id
40
-
41
- if closed?
42
- raise ClosedError, "Cannot retrieve objects from a closed WeakObjectHash"
43
- end
44
-
45
- monitor.synchronize do
46
- pair = object_ids_to_weak_refs_and_values[object_id]
47
-
48
- return nil unless pair
49
-
50
- weak_ref, value = pair
51
-
52
- if weak_ref.weakref_alive?
53
- if skip_finalizer?
54
- if weak_ref.__getobj__ == object
55
- value
56
- else
57
- # :nocov:
58
- object_ids_to_weak_refs_and_values.delete(object_id)
59
- nil
60
- # :nocov:
61
- end
62
- else
63
- value
64
- end
65
- else
66
- # Seems unreachable... if it's been garbage collected how could we have a reference to the object
67
- # to pass it in?
68
- # :nocov:
69
- object_ids_to_weak_refs_and_values.delete(object_id)
70
- nil
71
- # :nocov:
72
- end
73
- end
74
- end
75
-
76
- def delete(object)
77
- object_id = object.object_id
78
-
79
- monitor.synchronize do
80
- pair = object_ids_to_weak_refs_and_values.delete(object_id)
81
-
82
- return nil unless pair
83
-
84
- weak_ref, value = pair
85
-
86
- if weak_ref.weakref_alive?
87
-
88
- if skip_finalizer?
89
- if weak_ref.__getobj__ == object
90
- value
91
- end
92
- else
93
- # Hmmm, there's seemingly no safe way to remove the finalizer for the previous entry
94
- # if it exists. This is because we can only remove all finalizers on object. Not only
95
- # the ones we've created.
96
- # We will just do this anyway with that caveat and maybe make this configuratble in the future.
97
- unless skip_finalizer?
98
- ObjectSpace.undefine_finalizer(object)
99
- end
100
-
101
- value
102
- end
103
- end
104
- end
105
- end
106
-
107
- def each_pair
108
- monitor.synchronize do
109
- object_ids_to_weak_refs_and_values.each_pair do |object_id, pair|
110
- weak_ref, value = pair
111
-
112
- if weak_ref.weakref_alive?
113
- yield weak_ref.__getobj__, value
114
- else
115
- object_ids_to_weak_refs_and_values.delete(object_id)
116
- end
117
- end
118
- end
119
-
120
- self
121
- end
122
-
123
- def values
124
- values = []
125
-
126
- monitor.synchronize do
127
- each_pair do |_key, value|
128
- values << value
129
- end
130
- end
131
-
132
- values
133
- end
134
-
135
- def keys
136
- keys = []
137
-
138
- monitor.synchronize do
139
- each_pair do |key, _value|
140
- keys << key
141
- end
142
- end
143
-
144
- keys
145
- end
146
-
147
- def size
148
- size = 0
149
- to_delete = nil
150
-
151
- monitor.synchronize do
152
- object_ids_to_weak_refs_and_values.each_pair do |object_id, pair|
153
- weak_ref = pair.first
154
-
155
- if weak_ref.weakref_alive?
156
- size += 1
157
- else
158
- to_delete ||= []
159
- to_delete << object_id
160
- end
161
- end
162
-
163
- to_delete&.each do |object_id|
164
- object_ids_to_weak_refs_and_values.delete(object_id)
165
- end
166
- end
167
-
168
- size
169
- end
170
-
171
- def empty?
172
- size == 0
173
- end
174
-
175
- def close!
176
- if closed?
177
- raise ClosedError, "Already closed"
178
- end
179
-
180
- monitor.synchronize do
181
- self.closed = true
182
- clear
183
- @finalizer_proc = nil
184
- self.object_ids_to_weak_refs_and_values = nil
185
- self.monitor = nil
186
- end
187
- end
188
-
189
- def clear
190
- monitor.synchronize do
191
- unless skip_finalizer?
192
- object_ids_to_weak_refs_and_values.each_value do |pair|
193
- weak_ref = pair.first
194
-
195
- if weak_ref.weakref_alive?
196
- ObjectSpace.undefine_finalizer(weak_ref.__getobj__)
197
- end
198
- end
199
- end
200
-
201
- object_ids_to_weak_refs_and_values.clear
202
- end
203
- end
204
-
205
- def closed?
206
- closed
207
- end
208
-
209
- def skip_finalizer?
210
- @skip_finalizer
211
- end
212
-
213
- private
214
-
215
- attr_accessor :object_ids_to_weak_refs_and_values, :monitor, :closed, :skip_finalizer
216
-
217
- def finalizer_proc
218
- @finalizer_proc ||= ->(object_id) do
219
- unless closed?
220
- object_ids_to_weak_refs_and_values.delete(object_id)
221
- end
222
- end
223
- end
224
- end
225
- end