rspec-junklet 1.1.0 → 1.1.1

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,15 +1,15 @@
1
1
  ---
2
2
  !binary "U0hBMQ==":
3
3
  metadata.gz: !binary |-
4
- ZWQwYjZkZmNlNjlkNmM0MTE2YTMyNzBmYTEwMjU0MThjMjNlYzUzMA==
4
+ ZGY1MjM2NDliN2U1MWUxYTc0ZWQzYmM1YzgwY2EwOWZmYTI0NmIyMg==
5
5
  data.tar.gz: !binary |-
6
- MjQwNmUwNzQxYTljYWQ1NjhiMTgxNzU0NTk0NzNjNTk4MDhkYjdkNg==
6
+ ZTRmMGFmMWM3MzVkNjQ4N2Q2MmQ1M2U1OTg5ZThhODgyMDQxMGI0MQ==
7
7
  SHA512:
8
8
  metadata.gz: !binary |-
9
- ZTFlNmUzYTRhNzgzNjQyNjViZjA4YWNmYzI5Mjk4NWQ3N2VmNDhkYjZmNzIx
10
- NmM5MWE5MDkzNzk1Y2E2YmM2MTEyM2U2YWI0YTU4NjVkOTA1MTdiYjNhZGFj
11
- MThhZjU2MWY2ZDRhYTI2ODQ4MTI2YzJkZmM1NTM0ODJiM2Q1YmQ=
9
+ ZDU5OTYxZGQwMmY3NWQ1MDM2NDU5MTU3ODA2NzE3OTJhMWMzNTM4OGM2YWVj
10
+ MTE5NTE2MTY4OTZjYTcxMDQ2ZDQ2YTdlOTdjZWUwNmI0ZTRiMDQ2N2M1MjY5
11
+ MjBlYmUxMGJiNmY5ZjlmOGNkYzMxZjE3NjIwMjdiNzJhY2FjNDg=
12
12
  data.tar.gz: !binary |-
13
- OWY2NjNiNmY2ZDM1NTVlNWNmODNmZDIxMGNjODI1N2Y2M2MzMmJkOWY4Nzc4
14
- NDY1NTFjZmFjZjU1NjA2YmJiZWI3NzUyYzQ0ZjZmZjYxNjIxYmJlMThkM2Y5
15
- OTYyMjA0ZjEwMTk5MGU1ZmQ2N2UxYWZjMmVlYjQyZWEyZWM4NDQ=
13
+ MWNlM2E0NzAyNWVhODBkMDBmMjljZDc0MDNkZjViMTZkMTc3ZjRkOWJlYmIw
14
+ ZGJiZWJhZGNjZGQ1MjdiMzBlMjRhZmI4YmJjNDhlZmFhYzEzOWE3YjZiMTcw
15
+ OGYwY2IzYzkwNDE5YTMwZGUwMDdjYTYzNTExNDBmMzM5YTI3NmE=
data/Gemfile.lock CHANGED
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- rspec-junklet (1.0.4)
4
+ rspec-junklet (1.1.0)
5
5
 
6
6
  GEM
7
7
  remote: https://rubygems.org/
data/README.md CHANGED
@@ -232,17 +232,87 @@ key space, junk will cheerfully go into an infinite loop.
232
232
 
233
233
  ### Format
234
234
 
235
- Formats are here, but need documentating! For now: `format: :int` will cast your
236
- junk to an integer by calling `.to_i` on it. Other formats include:
235
+ A format can be applied to junk data after generation. This lets you change the
236
+ class or representation of the junk. For example, this feature was added because
237
+ we needed 6-digit decimal ids... represented as strings. Originally I wrote
238
+
239
+ ```ruby
240
+ let(:drug_id) { junk( ->{ junk(:int, size: 6).to_s } ) }
241
+ ```
242
+
243
+ But now I can just say
244
+
245
+ ```ruby
246
+ let(:drug_id) { junk(:int, size: 6, format: :string) }
247
+ ```
248
+ Here are the available formats:
237
249
 
238
250
  * `format: :int` calls `.to_i` on the junk before returning it
239
251
  * `format: :string` calls `.to_s` on the junk
240
252
  * `format: "%s"` (or any other string) calls sprintf on the junk with the
241
253
  string as the format string
242
254
  * `format: SomeClass` passes the junk to `SomeClass.new`, returning an instance
243
- of `SomeClass`. *Note:* If you plan on combining this with `exclude`, make
244
- sure your class implements the `==` operator.
245
- * `format: ->(x) { ... }` passes the junk to your Proc
255
+ of `SomeClass`. *Important:* This class must implement a `#format` method
256
+ which returns the formatted junk. See the `::Junklet::Formatter` class for an
257
+ example class that simply returns the unmodified junk.
258
+ * `format: ->(x) { ... }` passes the junk to your Proc; whatever you return is
259
+ the value of the junk. This is obviously the most powerful transform as it can
260
+ return anything at all; there's nothing stopping you from using the format
261
+ proc as the generator itself aside from the constraints of good taste. ;-) If
262
+ you _were_ to exhibit poor taste, one conceivable (yet still very strained)
263
+ example might be `junk :int, format: ->(x) { srand(x); rand }` but it's not
264
+ really a very far stretch to generate, say, a random index in the generator
265
+ and use the formatter to map it to a dictionary word or some other very wild
266
+ transformation.
267
+
268
+ ### Formatter Classes
269
+
270
+ The careful reader will have noted by now that you can pass a class name as a
271
+ format. This is intended to be a Formatter class. A Formatter class takes the
272
+ generated junk in its initialize method. If the class implements `#format`, this
273
+ method will be called and the return value of this method will be the junk
274
+ data. If the class does not implement `#format`, the Formatter object itself
275
+ will be returned and you can use it how you see fit. It's probably a good idea
276
+ to implement `#to_s` if your formatter is going to wind up in a string
277
+ somewhere.
278
+
279
+ So for example, let's say you want to generate a ZIP+4 code. That's a 5-digit
280
+ decimal number, a hyphen, and a 4-digit decimal. This whole mess is then
281
+ represented as a string. You could do this with a simple lambda:
282
+
283
+ ```ruby
284
+ let(:zip) { junk :int, size: 9, format: ->(x) { '%d-%d' % [x/10000, x%10000] } }
285
+ ```
286
+
287
+ ...but if you're going to be generating ZIP codes regularly, a formatter class
288
+ is probably in order:
289
+
290
+ ```ruby
291
+ class Format::ZipCode
292
+ attr_reader :code
293
+ def initialize(code)
294
+ @code = code
295
+ end
296
+
297
+ def format
298
+ '%d-%d' % [x/10000, x%10000]
299
+ end
300
+ end
301
+ ```
302
+
303
+ Now your junk uses the class as designed:
304
+
305
+ ```ruby
306
+ let(:zip) { junk :int, size: 9, format: Format::ZipCode }
307
+ ```
308
+
309
+ TODO: Hrm, if I'm going to do to that much trouble, why not have an entire junk
310
+ generation class? E.g. include the generator with the formatter, so that we can
311
+ just say
312
+
313
+ ```ruby
314
+ let(:zip) { junk ZipCode }
315
+ ```
246
316
 
247
317
  # TODO
248
318
 
@@ -0,0 +1,14 @@
1
+ module Junklet
2
+ class Formatter
3
+ attr_reader :input
4
+
5
+ def initialize(input)
6
+ @input = input
7
+ end
8
+
9
+ # You probably want to override this
10
+ def format
11
+ input
12
+ end
13
+ end
14
+ end
data/lib/junklet/junk.rb CHANGED
@@ -1,3 +1,5 @@
1
+ require_relative 'formatter'
2
+
1
3
  module Junklet
2
4
  module Junk
3
5
  def junk(*args)
@@ -26,6 +28,26 @@ module Junklet
26
28
  # the Proc an excludes it if the Proc returns true. This
27
29
  # is implemented except for the proc.
28
30
 
31
+ # FIXME: Would be nice to be able to say, e.g. `junk exclude: bob` but
32
+ # currently this breaks because {exclude: bob} is a Hash which is
33
+ # an Enumerable which means it's a valid generator. I don't want to
34
+ # just disallow hashes as generators here. What's a good workaround
35
+ # for when I really do just want junk with either a format or an
36
+ # exclusion? `junk :junk, exclude: bob` looks bad. `junk _,
37
+ # exclude: bob` is also pretty bad.
38
+ #
39
+ # Hmm, I'm tempted to say "the one enumerable you CAN'T have is a
40
+ # Hash, so it can be the options hash; if you DO want to pass in a
41
+ # hash, you must cast it to an array or yield it from a Proc
42
+ # instead". Given that the hash case is weird and rare enough, I
43
+ # think this is acceptable. Oh, if only I didn't have to maintain
44
+ # backwards compatibility with older Rubies, I could just make
45
+ # these keyword args. Sigh.
46
+
47
+ # FIXME: This whole darn method is outta control, and for the record none
48
+ # of the cool excluders and formatters work with the
49
+ # SecureRandom.hex default. Barf.
50
+
29
51
  # FIXME: Raise Argument error unless *args.size is 0-2
30
52
  # FIXME: If arg 1 is a hash, it's the options hash, raise
31
53
  # ArgumentError unless args.size == 1
@@ -54,10 +76,12 @@ module Junklet
54
76
  ->(x) { x.to_s }
55
77
  when :int
56
78
  ->(x) { x.to_i }
79
+ when Class
80
+ raise "Formatter class must implement #format method" unless
81
+ opts[:format].new(0).respond_to? :format
82
+ ->(x) { opts[:format].new(x).format }
57
83
  when String
58
84
  ->(x) { sprintf(opts[:format], x) }
59
- when Class
60
- ->(x) { opts[:format].new(x) }
61
85
  when Proc
62
86
  opts[:format]
63
87
  else
@@ -1,3 +1,3 @@
1
1
  module Junklet
2
- VERSION = "1.1.0"
2
+ VERSION = "1.1.1"
3
3
  end
@@ -113,24 +113,63 @@ describe JunkSpy do
113
113
  end
114
114
  end
115
115
 
116
- context "when format is a class" do
117
- class Doubler
118
- def initialize(n)
119
- @n = n
116
+ context "when format is a Junklet::Formatter" do
117
+ class HexTripler < Junklet::Formatter
118
+ def value
119
+ input * 3
120
+ end
121
+
122
+ def format
123
+ "0x%02x" % value
124
+ end
125
+ end
126
+
127
+ let(:junk) { subject.junk [4], format: HexTripler }
128
+
129
+ it "delegates to #format" do
130
+ expect(junk).to be_kind_of(String)
131
+ expect(junk).to eq("0x0c")
132
+ end
133
+ end
134
+
135
+ context "when format is a class that quacks like Junklet::Formatter" do
136
+ class HexDoubler
137
+ def initialize(input)
138
+ @n = input
120
139
  end
140
+
121
141
  def value
122
142
  @n * 2
123
143
  end
144
+
145
+ def format
146
+ "0x%04x" % value
147
+ end
124
148
  end
125
149
 
126
- let(:junk) { subject.junk [3], format: Doubler }
150
+ let(:junk) { subject.junk [12], format: HexDoubler }
127
151
 
128
- it "instantiates class with junk value" do
129
- expect(junk).to be_kind_of(Doubler)
130
- expect(junk.value).to eq(6)
152
+ it "works as expected" do
153
+ expect(junk).to be_kind_of(String)
154
+ expect(junk).to eq("0x0018")
131
155
  end
132
156
  end
133
157
 
158
+ context "but does not implement #value" do
159
+ class BadDoublerNoFormat
160
+ def initialize(input)
161
+ end
162
+
163
+ def value
164
+ end
165
+ end
166
+
167
+ let(:junk) { subject.junk [2], format: BadDoublerNoFormat }
168
+
169
+ specify { expect { junk }.to raise_error("Formatter class must implement #format method") }
170
+ end
171
+
172
+
134
173
  context "when format is a Proc" do
135
174
  let(:junk) { subject.junk [3], format: ->(x) { x * 3 } }
136
175
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rspec-junklet
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.1.0
4
+ version: 1.1.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - David Brady
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2015-02-20 00:00:00.000000000 Z
11
+ date: 2015-02-22 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -95,6 +95,7 @@ files:
95
95
  - LICENSE
96
96
  - README.md
97
97
  - lib/junklet.rb
98
+ - lib/junklet/formatter.rb
98
99
  - lib/junklet/junk.rb
99
100
  - lib/junklet/junklet.rb
100
101
  - lib/junklet/version.rb