contours 0.1.0 → 0.2.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/README.md +11 -2
- data/Rakefile +7 -0
- data/lib/contours/blended_hash.rb +74 -16
- data/lib/contours/structured_string.rb +68 -0
- data/lib/contours/version.rb +1 -1
- metadata +4 -6
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: e5586515f8a3343dd3facd5738d1bff58a0643b0e630e633d67c374ae077c00c
|
4
|
+
data.tar.gz: d168143703695cddf4fe429502a296dabf85702fd013bc42920bc8270ca365d0
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: e1652a33ebb6e2ec2efbc5b8aa494b60369a181b15970eea362ad264b7812a062830400154a0f8dfc6d78713079672022251ff9660a16f9b87e06953eb581679
|
7
|
+
data.tar.gz: 6088095e1dd8b5c89e9f3cbc456709a553c6260d6d4016e69eda213ec190392a42f35230eccceb4893c50b02d000e743a471eb1842714a161c61e42572f0a4f2
|
data/README.md
CHANGED
@@ -44,7 +44,7 @@ You can specify a custom way to blend the values for the `@blended_keys`
|
|
44
44
|
class Configuration < Contours::BlendedHash
|
45
45
|
@blended_keys = %i[class data]
|
46
46
|
|
47
|
-
blend(:class, with: StructuredString)
|
47
|
+
blend(:class, with: Contours::StructuredString)
|
48
48
|
|
49
49
|
blend :data do |existing, new_value|
|
50
50
|
existing.sum(new_value.sum)
|
@@ -60,7 +60,16 @@ config.to_h # => {class: "test overwrite", data: 21}
|
|
60
60
|
|
61
61
|
After checking out the repo, run `bin/setup` to install dependencies. Then, run `rake test` to run the tests. You can also run `bin/console` for an interactive prompt that will allow you to experiment.
|
62
62
|
|
63
|
-
To install this gem onto your local machine, run `bundle exec rake install`.
|
63
|
+
To install this gem onto your local machine, run `bundle exec rake install`.
|
64
|
+
|
65
|
+
This project is managed with [Reissue](https://github.com/SOFware/reissue).
|
66
|
+
|
67
|
+
To release a new version, make your changes and be sure to update the CHANGELOG.md.
|
68
|
+
|
69
|
+
To release a new version:
|
70
|
+
|
71
|
+
1. `bundle exec rake build:checksum`
|
72
|
+
2. `bundle exec rake release`
|
64
73
|
|
65
74
|
## Contributing
|
66
75
|
|
data/Rakefile
CHANGED
@@ -27,8 +27,6 @@ module Contours
|
|
27
27
|
#
|
28
28
|
# See the source of this #{name} class for more details.
|
29
29
|
class BlendedHash < DelegateClass(Hash)
|
30
|
-
alias_method :to_hash, :__getobj__
|
31
|
-
|
32
30
|
# Ensure that the initial hash is a BlendedHash
|
33
31
|
def self.init(initial_hash)
|
34
32
|
if initial_hash.is_a?(BlendedHash)
|
@@ -44,11 +42,34 @@ module Contours
|
|
44
42
|
# Otherwise, the default implementation will be used where the value of the
|
45
43
|
# with argument is expected to receive 'init' with the original value and
|
46
44
|
# then 'merge' with the extras value.
|
45
|
+
#
|
46
|
+
# @param key [Symbol] the key that should be blended
|
47
|
+
# @param with [BlendedHash] the class that should be used to blend the value
|
48
|
+
# @param block [Proc] the implementation of the blend method
|
49
|
+
#
|
50
|
+
# @example
|
51
|
+
# class CssConfig < BlendedHash
|
52
|
+
# @blended_keys = %i[class]
|
53
|
+
# blend :class do |original, extras|
|
54
|
+
# [original, extras].flatten.compact.uniq.join(" ")
|
55
|
+
# end
|
56
|
+
# end
|
57
|
+
#
|
58
|
+
# CssConfig.new({class: "foo"}).merge({class: "bar"})
|
59
|
+
#
|
60
|
+
# @example
|
61
|
+
# class CssConfig < BlendedHash
|
62
|
+
# @blended_keys = %i[class]
|
63
|
+
# blend :class, with: CssConfig
|
64
|
+
# end
|
65
|
+
#
|
66
|
+
# CssConfig.new({class: "foo"}).merge({class: "bar"})
|
67
|
+
#
|
47
68
|
def self.blend(key, with: nil, &block)
|
48
69
|
if block
|
49
|
-
define_method("blend_#{key}", &block)
|
70
|
+
define_method(:"blend_#{key}", &block)
|
50
71
|
else
|
51
|
-
define_method("blend_#{key}") do |original, extras|
|
72
|
+
define_method(:"blend_#{key}") do |original, extras|
|
52
73
|
with.init(original).merge(extras)
|
53
74
|
end
|
54
75
|
end
|
@@ -57,12 +78,28 @@ module Contours
|
|
57
78
|
# Recursively check for keys that are specified as blended and apply
|
58
79
|
# the blend method to them or execute the blend_#{key} method if it exists
|
59
80
|
# to set the new value.
|
81
|
+
#
|
82
|
+
# @param overrides [Hash] the hash to merge with
|
83
|
+
#
|
84
|
+
# @return [BlendedHash] the new hash
|
85
|
+
#
|
86
|
+
# @example
|
87
|
+
# class CssConfig < BlendedHash
|
88
|
+
# @blended_keys = %i[class]
|
89
|
+
# blend :class do |original, extras|
|
90
|
+
# [original, extras].flatten.compact.uniq.join(" ")
|
91
|
+
# end
|
92
|
+
# end
|
93
|
+
#
|
94
|
+
# config = CssConfig.new({class: "foo"}).merge({class: "bar"})
|
95
|
+
# config[:class] # => "foo bar"
|
96
|
+
#
|
60
97
|
def merge(overrides)
|
61
98
|
return self if overrides.nil? || overrides.empty?
|
62
99
|
self.class.new(overrides.each_with_object(to_hash.dup) do |(key, value), hash|
|
63
100
|
hash[key] = if blended_keys.include?(key)
|
64
|
-
if respond_to?("blend_#{key}")
|
65
|
-
send("blend_#{key}", hash[key], value)
|
101
|
+
if respond_to?(:"blend_#{key}")
|
102
|
+
send(:"blend_#{key}", hash[key], value)
|
66
103
|
else
|
67
104
|
blend(hash[key], value)
|
68
105
|
end
|
@@ -75,26 +112,29 @@ module Contours
|
|
75
112
|
|
76
113
|
# Ensure that the return value of these methods is a BlendedHash
|
77
114
|
def [](...)
|
78
|
-
|
79
|
-
|
115
|
+
super_result = super
|
116
|
+
if super_result.is_a?(Hash)
|
117
|
+
self.class.init(super_result)
|
80
118
|
else
|
81
|
-
|
119
|
+
super_result
|
82
120
|
end
|
83
121
|
end
|
84
122
|
|
85
123
|
def fetch(...)
|
86
|
-
|
87
|
-
|
124
|
+
super_result = super
|
125
|
+
if super_result.is_a?(Hash)
|
126
|
+
self.class.init(super_result)
|
88
127
|
else
|
89
|
-
|
128
|
+
super_result
|
90
129
|
end
|
91
130
|
end
|
92
131
|
|
93
132
|
def dig(...)
|
94
|
-
|
95
|
-
|
133
|
+
super_result = super
|
134
|
+
if super_result.is_a?(Hash)
|
135
|
+
self.class.init(super_result)
|
96
136
|
else
|
97
|
-
|
137
|
+
super_result
|
98
138
|
end
|
99
139
|
end
|
100
140
|
|
@@ -110,7 +150,6 @@ module Contours
|
|
110
150
|
# with a custom blend_#{key} method to customize the blending behavior for a
|
111
151
|
# specific key.
|
112
152
|
#
|
113
|
-
|
114
153
|
def blend(original, extra)
|
115
154
|
case original
|
116
155
|
when BlendedHash, Hash
|
@@ -121,5 +160,24 @@ module Contours
|
|
121
160
|
extra
|
122
161
|
end
|
123
162
|
end
|
163
|
+
|
164
|
+
def to_hash
|
165
|
+
deep_stringify_structured_strings(__getobj__)
|
166
|
+
end
|
167
|
+
|
168
|
+
private
|
169
|
+
|
170
|
+
def deep_stringify_structured_strings(obj)
|
171
|
+
case obj
|
172
|
+
when Hash
|
173
|
+
obj.transform_values { |v| deep_stringify_structured_strings(v) }
|
174
|
+
when Array
|
175
|
+
obj.map { |v| deep_stringify_structured_strings(v) }
|
176
|
+
when StructuredString
|
177
|
+
obj.to_s
|
178
|
+
else
|
179
|
+
obj
|
180
|
+
end
|
181
|
+
end
|
124
182
|
end
|
125
183
|
end
|
@@ -28,6 +28,16 @@ module Contours
|
|
28
28
|
|
29
29
|
# Initialize with base string that is used to build the StructuredString
|
30
30
|
# Other values will be added to the string in the order they are added.
|
31
|
+
#
|
32
|
+
# @param base [String] the initial string
|
33
|
+
# @param separator [String] the separator used to join the parts of the string
|
34
|
+
#
|
35
|
+
# @example
|
36
|
+
# config = StructuredString.new("input")
|
37
|
+
# config << "my-special-class"
|
38
|
+
# config << "input-error"
|
39
|
+
# config.to_s #=> "input my-special-class input-error"
|
40
|
+
#
|
31
41
|
def initialize(base = "", separator: " ")
|
32
42
|
@base = [base]
|
33
43
|
@separator = separator
|
@@ -37,6 +47,14 @@ module Contours
|
|
37
47
|
end
|
38
48
|
|
39
49
|
# Add a value to the beginning of the string
|
50
|
+
#
|
51
|
+
# @param value [String] the value to add
|
52
|
+
#
|
53
|
+
# @example
|
54
|
+
# config = StructuredString.new("input")
|
55
|
+
# config.first("my-special-class")
|
56
|
+
# config.to_s #=> "my-special-class input"
|
57
|
+
#
|
40
58
|
def first(value)
|
41
59
|
@first << value.to_s
|
42
60
|
__setobj__ to_s
|
@@ -44,6 +62,14 @@ module Contours
|
|
44
62
|
end
|
45
63
|
|
46
64
|
# Add a value to the end of the string
|
65
|
+
#
|
66
|
+
# @param value [String] the value to add
|
67
|
+
#
|
68
|
+
# @example
|
69
|
+
# config = StructuredString.new("input")
|
70
|
+
# config.last("input-error")
|
71
|
+
# config.to_s #=> "input input-error"
|
72
|
+
#
|
47
73
|
def last(value)
|
48
74
|
@last << value.to_s
|
49
75
|
__setobj__ to_s
|
@@ -51,6 +77,14 @@ module Contours
|
|
51
77
|
end
|
52
78
|
|
53
79
|
# Add a value to the middle of the string
|
80
|
+
#
|
81
|
+
# @param value [String] the value to add
|
82
|
+
#
|
83
|
+
# @example
|
84
|
+
# config = StructuredString.new("input")
|
85
|
+
# config << "my-special-class"
|
86
|
+
# config.to_s #=> "input my-special-class"
|
87
|
+
#
|
54
88
|
def <<(other)
|
55
89
|
@other << other.to_s
|
56
90
|
__setobj__ to_s
|
@@ -58,6 +92,21 @@ module Contours
|
|
58
92
|
end
|
59
93
|
|
60
94
|
# Read a particular portion of the structured string or raise an error
|
95
|
+
#
|
96
|
+
# @param key [Symbol] the portion of the string to read
|
97
|
+
#
|
98
|
+
# @return [Array] the portion of the string
|
99
|
+
#
|
100
|
+
# @example
|
101
|
+
# config = StructuredString.new("input")
|
102
|
+
# config << "my-special-class"
|
103
|
+
# config.first("first-class")
|
104
|
+
# config.last("last-class")
|
105
|
+
# config.read(:base) #=> ["input"]
|
106
|
+
# config.read(:first) #=> ["first-class"]
|
107
|
+
# config.read(:last) #=> ["last-class"]
|
108
|
+
# config.read(:other) #=> ["my-special-class"]
|
109
|
+
#
|
61
110
|
def read(key)
|
62
111
|
case key
|
63
112
|
when :first
|
@@ -109,6 +158,17 @@ module Contours
|
|
109
158
|
end
|
110
159
|
|
111
160
|
# Return the string representation of the StructuredString
|
161
|
+
#
|
162
|
+
# @return [String] the string
|
163
|
+
#
|
164
|
+
# @example
|
165
|
+
# config = StructuredString.new("input")
|
166
|
+
# config << "my-special-class"
|
167
|
+
# config.last("last-class")
|
168
|
+
# config.first("first-class")
|
169
|
+
# config << "input-error"
|
170
|
+
# config.to_s #=> "first-class input my-special-class input-error last-class"
|
171
|
+
#
|
112
172
|
def to_s
|
113
173
|
[@first, @base, @other, @last]
|
114
174
|
.flatten
|
@@ -120,6 +180,14 @@ module Contours
|
|
120
180
|
alias_method :to_str, :to_s
|
121
181
|
alias_method :inspect, :to_s
|
122
182
|
|
183
|
+
def as_json(*)
|
184
|
+
to_s
|
185
|
+
end
|
186
|
+
|
187
|
+
def to_json(*)
|
188
|
+
to_s.to_json
|
189
|
+
end
|
190
|
+
|
123
191
|
def ==(other)
|
124
192
|
to_s == other.to_s
|
125
193
|
end
|
data/lib/contours/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,13 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: contours
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.2.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Jim Gay
|
8
|
-
autorequire:
|
9
8
|
bindir: bin
|
10
9
|
cert_chain: []
|
11
|
-
date:
|
10
|
+
date: 2025-06-22 00:00:00.000000000 Z
|
12
11
|
dependencies: []
|
13
12
|
description: |
|
14
13
|
Provides objects with which you can define a configuration object
|
@@ -32,7 +31,7 @@ metadata:
|
|
32
31
|
allowed_push_host: https://rubygems.org
|
33
32
|
homepage_uri: https://github.com/SOFware/contours
|
34
33
|
source_code_uri: https://github.com/SOFware/contours.git
|
35
|
-
|
34
|
+
changelog_uri: https://github.com/SOFware/contours/blob/main/CHANGELOG.md
|
36
35
|
rdoc_options: []
|
37
36
|
require_paths:
|
38
37
|
- lib
|
@@ -47,8 +46,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
47
46
|
- !ruby/object:Gem::Version
|
48
47
|
version: '0'
|
49
48
|
requirements: []
|
50
|
-
rubygems_version: 3.
|
51
|
-
signing_key:
|
49
|
+
rubygems_version: 3.6.5
|
52
50
|
specification_version: 4
|
53
51
|
summary: Support for building customizable configuration objects.
|
54
52
|
test_files: []
|