Repository navigation
Replace OpenStruct with a lightweight Paddle::Object - #26
Merged
Merged
Conversation
OpenStruct is no longer a default gem, and it's slow to build because it defines singleton methods on every instance. Paddle responses are deeply nested, so every response created many OpenStructs. Paddle::Object now stores attributes in a hash and reads them through method_missing. Dot access, hash access, setters, nil for missing attributes, each_pair and update all work as before. to_h now converts nested objects too, and to_json, as_json, dig and key? have been added. Nested objects are Paddle::Object rather than OpenStruct, and the ostruct dependency has been removed. Building a transaction is around 20x faster and uses around 20x less memory. Dot-access reads are slower, at around 0.3µs each. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
OpenStruct is no longer a default gem, and it's slow to build because it defines singleton methods on every instance. Paddle responses are deeply nested, so every response created many OpenStructs.
This replaces it with a small
Paddle::Objectthat stores attributes in a hash and reads them throughmethod_missing.What stays the same
obj.id), hash access (obj[:id],obj["id"]) and setters (obj.foo =)nilfor missing attributeseach_pair,respond_to?,==and the instanceupdatemethodWhat's new
to_hnow converts nested objects too, so it returns plain hashes all the way downto_jsonreturns real JSON. Before, it returned an inspect stringas_json,digandkey?updateon a model without anupdatemethod now raisesNoMethodErrorrather than a confusingNameErrorostructdependency has been removedPerformance
Benchmarked on a real transaction response from the test cassettes, Ruby 4.0.7, best of 5 runs:
Memory per transaction dropped from 134 KB to 6.8 KB, and allocations to build one went from 2,744 to 56. Dot-access reads are slower because they go through
method_missing, but that's around 0.3µs per read.Compatibility
Nested objects are now
Paddle::Objectrather thanOpenStruct. Code that checksis_a?(OpenStruct)or uses OpenStruct-only methods, such asdelete_fieldorto_hwith a block, will break. A field named after a built-in public method, such ashashorclass, now returns the method's result, so useobj[:hash]for those. This probably warrants a minor version bump and a changelog note.Testing
Added 10 tests for the new object. The full suite passes (188 runs), and RuboCop is clean.
🤖 Generated with Claude Code