rubysl-prettyprint 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 78e95b38fd94672e7efdb1f94896fe42b7008da5
4
+ data.tar.gz: 6cf7a850b5d76adb9d20f2a7e51cc5bc599ece4d
5
+ SHA512:
6
+ metadata.gz: bbc1cd6a0302e419f429a5ad3cb46b2eef5226683bce571e28f57a135cb622c10fc0776ae9366d4b85812eb2ba977194ef8c006c5a283fa3d30dcf37f5362cd1
7
+ data.tar.gz: a2ac3668484c636c0dbb77c10a22e08ff198259d9b100424a958532023daa7c2fd677a91684b00696745a59423b932e3c4f39d2c2224259462d59986f6a7de2f
@@ -0,0 +1,17 @@
1
+ *.gem
2
+ *.rbc
3
+ .bundle
4
+ .config
5
+ .yardoc
6
+ Gemfile.lock
7
+ InstalledFiles
8
+ _yardoc
9
+ coverage
10
+ doc/
11
+ lib/bundler/man
12
+ pkg
13
+ rdoc
14
+ spec/reports
15
+ test/tmp
16
+ test/version_tmp
17
+ tmp
@@ -0,0 +1,7 @@
1
+ language: ruby
2
+ env:
3
+ - RUBYLIB=lib
4
+ script: bundle exec mspec
5
+ rvm:
6
+ - 1.8.7
7
+ - rbx-nightly-18mode
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in rubysl-prettyprint.gemspec
4
+ gemspec
data/LICENSE ADDED
@@ -0,0 +1,25 @@
1
+ Copyright (c) 2013, Brian Shirai
2
+ All rights reserved.
3
+
4
+ Redistribution and use in source and binary forms, with or without
5
+ modification, are permitted provided that the following conditions are met:
6
+
7
+ 1. Redistributions of source code must retain the above copyright notice, this
8
+ list of conditions and the following disclaimer.
9
+ 2. Redistributions in binary form must reproduce the above copyright notice,
10
+ this list of conditions and the following disclaimer in the documentation
11
+ and/or other materials provided with the distribution.
12
+ 3. Neither the name of the library nor the names of its contributors may be
13
+ used to endorse or promote products derived from this software without
14
+ specific prior written permission.
15
+
16
+ THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17
+ AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18
+ IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19
+ DISCLAIMED. IN NO EVENT SHALL <COPYRIGHT HOLDER> BE LIABLE FOR ANY DIRECT,
20
+ INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
21
+ BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
22
+ DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
23
+ OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
24
+ NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
25
+ EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
@@ -0,0 +1,29 @@
1
+ # Rubysl::Prettyprint
2
+
3
+ TODO: Write a gem description
4
+
5
+ ## Installation
6
+
7
+ Add this line to your application's Gemfile:
8
+
9
+ gem 'rubysl-prettyprint'
10
+
11
+ And then execute:
12
+
13
+ $ bundle
14
+
15
+ Or install it yourself as:
16
+
17
+ $ gem install rubysl-prettyprint
18
+
19
+ ## Usage
20
+
21
+ TODO: Write usage instructions here
22
+
23
+ ## Contributing
24
+
25
+ 1. Fork it
26
+ 2. Create your feature branch (`git checkout -b my-new-feature`)
27
+ 3. Commit your changes (`git commit -am 'Add some feature'`)
28
+ 4. Push to the branch (`git push origin my-new-feature`)
29
+ 5. Create new Pull Request
@@ -0,0 +1 @@
1
+ require "bundler/gem_tasks"
@@ -0,0 +1 @@
1
+ require "rubysl/prettyprint"
@@ -0,0 +1 @@
1
+ require "rubysl/prettyprint/prettyprint"
@@ -0,0 +1,2 @@
1
+ require "rubysl/prettyprint/version"
2
+ require "rubysl/prettyprint/pp"
@@ -0,0 +1,654 @@
1
+ # == Pretty-printer for Ruby objects.
2
+ #
3
+ # = Which seems better?
4
+ #
5
+ # non-pretty-printed output by #p is:
6
+ # #<PP:0x81fedf0 @genspace=#<Proc:0x81feda0>, @group_queue=#<PrettyPrint::GroupQueue:0x81fed3c @queue=[[#<PrettyPrint::Group:0x81fed78 @breakables=[], @depth=0, @break=false>], []]>, @buffer=[], @newline="\n", @group_stack=[#<PrettyPrint::Group:0x81fed78 @breakables=[], @depth=0, @break=false>], @buffer_width=0, @indent=0, @maxwidth=79, @output_width=2, @output=#<IO:0x8114ee4>>
7
+ #
8
+ # pretty-printed output by #pp is:
9
+ # #<PP:0x81fedf0
10
+ # @buffer=[],
11
+ # @buffer_width=0,
12
+ # @genspace=#<Proc:0x81feda0>,
13
+ # @group_queue=
14
+ # #<PrettyPrint::GroupQueue:0x81fed3c
15
+ # @queue=
16
+ # [[#<PrettyPrint::Group:0x81fed78 @break=false, @breakables=[], @depth=0>],
17
+ # []]>,
18
+ # @group_stack=
19
+ # [#<PrettyPrint::Group:0x81fed78 @break=false, @breakables=[], @depth=0>],
20
+ # @indent=0,
21
+ # @maxwidth=79,
22
+ # @newline="\n",
23
+ # @output=#<IO:0x8114ee4>,
24
+ # @output_width=2>
25
+ #
26
+ # I like the latter. If you do too, this library is for you.
27
+ #
28
+ # = Usage
29
+ #
30
+ # pp(obj)
31
+ #
32
+ # output +obj+ to +$>+ in pretty printed format.
33
+ #
34
+ # It returns +nil+.
35
+ #
36
+ # = Output Customization
37
+ # To define your customized pretty printing function for your classes,
38
+ # redefine a method #pretty_print(+pp+) in the class.
39
+ # It takes an argument +pp+ which is an instance of the class PP.
40
+ # The method should use PP#text, PP#breakable, PP#nest, PP#group and
41
+ # PP#pp to print the object.
42
+ #
43
+ # = Author
44
+ # Tanaka Akira <akr@m17n.org>
45
+
46
+ require 'prettyprint'
47
+
48
+ module Kernel
49
+ # returns a pretty printed object as a string.
50
+ def pretty_inspect
51
+ PP.pp(self, '')
52
+ end
53
+
54
+ private
55
+ # prints arguments in pretty form.
56
+ #
57
+ # pp returns nil.
58
+ def pp(*objs) # :doc:
59
+ objs.each {|obj|
60
+ PP.pp(obj)
61
+ }
62
+ nil
63
+ end
64
+ module_function :pp
65
+ end
66
+
67
+ class PP < PrettyPrint
68
+ # Outputs +obj+ to +out+ in pretty printed format of
69
+ # +width+ columns in width.
70
+ #
71
+ # If +out+ is omitted, +$>+ is assumed.
72
+ # If +width+ is omitted, 79 is assumed.
73
+ #
74
+ # PP.pp returns +out+.
75
+ def PP.pp(obj, out=$>, width=79)
76
+ q = PP.new(out, width)
77
+ q.guard_inspect_key {q.pp obj}
78
+ q.flush
79
+ #$pp = q
80
+ out << "\n"
81
+ end
82
+
83
+ # Outputs +obj+ to +out+ like PP.pp but with no indent and
84
+ # newline.
85
+ #
86
+ # PP.singleline_pp returns +out+.
87
+ def PP.singleline_pp(obj, out=$>)
88
+ q = SingleLine.new(out)
89
+ q.guard_inspect_key {q.pp obj}
90
+ q.flush
91
+ out
92
+ end
93
+
94
+ # :stopdoc:
95
+ def PP.mcall(obj, mod, meth, *args, &block)
96
+ mod.instance_method(meth).bind(obj).call(*args, &block)
97
+ end
98
+ # :startdoc:
99
+
100
+ @sharing_detection = false
101
+ class << self
102
+ # Returns the sharing detection flag as a boolean value.
103
+ # It is false by default.
104
+ attr_accessor :sharing_detection
105
+ end
106
+
107
+ module PPMethods
108
+ InspectKey = :__inspect_key__
109
+
110
+ def guard_inspect_key
111
+ if Thread.current[InspectKey] == nil
112
+ Thread.current[InspectKey] = []
113
+ end
114
+
115
+ save = Thread.current[InspectKey]
116
+
117
+ begin
118
+ Thread.current[InspectKey] = []
119
+ yield
120
+ ensure
121
+ Thread.current[InspectKey] = save
122
+ end
123
+ end
124
+
125
+ # Adds +obj+ to the pretty printing buffer
126
+ # using Object#pretty_print or Object#pretty_print_cycle.
127
+ #
128
+ # Object#pretty_print_cycle is used when +obj+ is already
129
+ # printed, a.k.a the object reference chain has a cycle.
130
+ def pp(obj)
131
+ id = obj.__id__
132
+
133
+ if Thread.current[InspectKey].include? id
134
+ group {obj.pretty_print_cycle self}
135
+ return
136
+ end
137
+
138
+ begin
139
+ Thread.current[InspectKey] << id
140
+ group {obj.pretty_print self}
141
+ ensure
142
+ Thread.current[InspectKey].pop unless PP.sharing_detection
143
+ end
144
+ end
145
+
146
+ # A convenience method which is same as follows:
147
+ #
148
+ # group(1, '#<' + obj.class.name, '>') { ... }
149
+ def object_group(obj, &block) # :yield:
150
+ group(1, '#<' + obj.class.name, '>', &block)
151
+ end
152
+
153
+ def object_address_group(obj, &block)
154
+ id = "%x" % (obj.__id__ * 2)
155
+ id.sub!(/\Af(?=[[:xdigit:]]{2}+\z)/, '') if id.sub!(/\A\.\./, '')
156
+ group(1, "\#<#{obj.class}:0x#{id}", '>', &block)
157
+ end
158
+
159
+ # A convenience method which is same as follows:
160
+ #
161
+ # text ','
162
+ # breakable
163
+ def comma_breakable
164
+ text ','
165
+ breakable
166
+ end
167
+
168
+ # Adds a separated list.
169
+ # The list is separated by comma with breakable space, by default.
170
+ #
171
+ # #seplist iterates the +list+ using +iter_method+.
172
+ # It yields each object to the block given for #seplist.
173
+ # The procedure +separator_proc+ is called between each yields.
174
+ #
175
+ # If the iteration is zero times, +separator_proc+ is not called at all.
176
+ #
177
+ # If +separator_proc+ is nil or not given,
178
+ # +lambda { comma_breakable }+ is used.
179
+ # If +iter_method+ is not given, :each is used.
180
+ #
181
+ # For example, following 3 code fragments has similar effect.
182
+ #
183
+ # q.seplist([1,2,3]) {|v| xxx v }
184
+ #
185
+ # q.seplist([1,2,3], lambda { comma_breakable }, :each) {|v| xxx v }
186
+ #
187
+ # xxx 1
188
+ # q.comma_breakable
189
+ # xxx 2
190
+ # q.comma_breakable
191
+ # xxx 3
192
+ def seplist(list, sep=nil, iter_method=:each) # :yield: element
193
+ sep ||= lambda { comma_breakable }
194
+ first = true
195
+ list.__send__(iter_method) {|*v|
196
+ if first
197
+ first = false
198
+ else
199
+ sep.call
200
+ end
201
+ yield(*v)
202
+ }
203
+ end
204
+
205
+ def pp_object(obj)
206
+ object_address_group(obj) {
207
+ seplist(obj.pretty_print_instance_variables, lambda { text ',' }) {|v|
208
+ breakable
209
+ v = v.to_s if Symbol === v
210
+ text v
211
+ text '='
212
+ group(1) {
213
+ breakable ''
214
+ pp(obj.instance_eval(v))
215
+ }
216
+ }
217
+ }
218
+ end
219
+
220
+ def pp_hash(obj)
221
+ group(1, '{', '}') {
222
+ seplist(obj, nil, :each_pair) {|k, v|
223
+ group {
224
+ pp k
225
+ text '=>'
226
+ group(1) {
227
+ breakable ''
228
+ pp v
229
+ }
230
+ }
231
+ }
232
+ }
233
+ end
234
+ end
235
+
236
+ include PPMethods
237
+
238
+ class SingleLine < PrettyPrint::SingleLine
239
+ include PPMethods
240
+ end
241
+
242
+ module ObjectMixin
243
+ # 1. specific pretty_print
244
+ # 2. specific inspect
245
+ # 3. specific to_s if instance variable is empty
246
+ # 4. generic pretty_print
247
+
248
+ # A default pretty printing method for general objects.
249
+ # It calls #pretty_print_instance_variables to list instance variables.
250
+ #
251
+ # If +self+ has a customized (redefined) #inspect method,
252
+ # the result of self.inspect is used but it obviously has no
253
+ # line break hints.
254
+ #
255
+ # This module provides predefined #pretty_print methods for some of
256
+ # the most commonly used built-in classes for convenience.
257
+ def pretty_print(q)
258
+ if /\(Kernel\)#/ !~ Object.instance_method(:method).bind(self).call(:inspect).inspect
259
+ q.text self.inspect
260
+ elsif /\(Kernel\)#/ !~ Object.instance_method(:method).bind(self).call(:to_s).inspect && instance_variables.empty?
261
+ q.text self.to_s
262
+ else
263
+ q.pp_object(self)
264
+ end
265
+ end
266
+
267
+ # A default pretty printing method for general objects that are
268
+ # detected as part of a cycle.
269
+ def pretty_print_cycle(q)
270
+ q.object_address_group(self) {
271
+ q.breakable
272
+ q.text '...'
273
+ }
274
+ end
275
+
276
+ # Returns a sorted array of instance variable names.
277
+ #
278
+ # This method should return an array of names of instance variables as symbols or strings as:
279
+ # +[:@a, :@b]+.
280
+ def pretty_print_instance_variables
281
+ instance_variables.sort
282
+ end
283
+
284
+ # Is #inspect implementation using #pretty_print.
285
+ # If you implement #pretty_print, it can be used as follows.
286
+ #
287
+ # alias inspect pretty_print_inspect
288
+ #
289
+ # However, doing this requires that every class that #inspect is called on
290
+ # implement #pretty_print, or a RuntimeError will be raised.
291
+ def pretty_print_inspect
292
+ if /\(PP::ObjectMixin\)#/ =~ Object.instance_method(:method).bind(self).call(:pretty_print).inspect
293
+ raise "pretty_print is not overridden for #{self.class}"
294
+ end
295
+ PP.singleline_pp(self, '')
296
+ end
297
+ end
298
+ end
299
+
300
+ class Array
301
+ def pretty_print(q)
302
+ q.group(1, '[', ']') {
303
+ q.seplist(self) {|v|
304
+ q.pp v
305
+ }
306
+ }
307
+ end
308
+
309
+ def pretty_print_cycle(q)
310
+ q.text(empty? ? '[]' : '[...]')
311
+ end
312
+ end
313
+
314
+ class Hash
315
+ def pretty_print(q)
316
+ q.pp_hash self
317
+ end
318
+
319
+ def pretty_print_cycle(q)
320
+ q.text(empty? ? '{}' : '{...}')
321
+ end
322
+ end
323
+
324
+ class << ENV
325
+ def pretty_print(q)
326
+ q.pp_hash self
327
+ end
328
+ end
329
+
330
+ class Struct
331
+ def pretty_print(q)
332
+ q.group(1, '#<struct ' + PP.mcall(self, Kernel, :class).name, '>') {
333
+ q.seplist(PP.mcall(self, Struct, :members), lambda { q.text "," }) {|member|
334
+ q.breakable
335
+ q.text member.to_s
336
+ q.text '='
337
+ q.group(1) {
338
+ q.breakable ''
339
+ q.pp self[member]
340
+ }
341
+ }
342
+ }
343
+ end
344
+
345
+ def pretty_print_cycle(q)
346
+ q.text sprintf("#<struct %s:...>", PP.mcall(self, Kernel, :class).name)
347
+ end
348
+ end
349
+
350
+ class Range
351
+ def pretty_print(q)
352
+ q.pp self.begin
353
+ q.breakable ''
354
+ q.text(self.exclude_end? ? '...' : '..')
355
+ q.breakable ''
356
+ q.pp self.end
357
+ end
358
+ end
359
+
360
+ class File
361
+ class Stat
362
+ def pretty_print(q)
363
+ require 'etc.so'
364
+ q.object_group(self) {
365
+ q.breakable
366
+ q.text sprintf("dev=0x%x", self.dev); q.comma_breakable
367
+ q.text "ino="; q.pp self.ino; q.comma_breakable
368
+ q.group {
369
+ m = self.mode
370
+ q.text sprintf("mode=0%o", m)
371
+ q.breakable
372
+ q.text sprintf("(%s %c%c%c%c%c%c%c%c%c)",
373
+ self.ftype,
374
+ (m & 0400 == 0 ? ?- : ?r),
375
+ (m & 0200 == 0 ? ?- : ?w),
376
+ (m & 0100 == 0 ? (m & 04000 == 0 ? ?- : ?S) :
377
+ (m & 04000 == 0 ? ?x : ?s)),
378
+ (m & 0040 == 0 ? ?- : ?r),
379
+ (m & 0020 == 0 ? ?- : ?w),
380
+ (m & 0010 == 0 ? (m & 02000 == 0 ? ?- : ?S) :
381
+ (m & 02000 == 0 ? ?x : ?s)),
382
+ (m & 0004 == 0 ? ?- : ?r),
383
+ (m & 0002 == 0 ? ?- : ?w),
384
+ (m & 0001 == 0 ? (m & 01000 == 0 ? ?- : ?T) :
385
+ (m & 01000 == 0 ? ?x : ?t)))
386
+ }
387
+ q.comma_breakable
388
+ q.text "nlink="; q.pp self.nlink; q.comma_breakable
389
+ q.group {
390
+ q.text "uid="; q.pp self.uid
391
+ begin
392
+ pw = Etc.getpwuid(self.uid)
393
+ rescue ArgumentError
394
+ end
395
+ if pw
396
+ q.breakable; q.text "(#{pw.name})"
397
+ end
398
+ }
399
+ q.comma_breakable
400
+ q.group {
401
+ q.text "gid="; q.pp self.gid
402
+ begin
403
+ gr = Etc.getgrgid(self.gid)
404
+ rescue ArgumentError
405
+ end
406
+ if gr
407
+ q.breakable; q.text "(#{gr.name})"
408
+ end
409
+ }
410
+ q.comma_breakable
411
+ q.group {
412
+ q.text sprintf("rdev=0x%x", self.rdev)
413
+ q.breakable
414
+ q.text sprintf('(%d, %d)', self.rdev_major, self.rdev_minor)
415
+ }
416
+ q.comma_breakable
417
+ q.text "size="; q.pp self.size; q.comma_breakable
418
+ q.text "blksize="; q.pp self.blksize; q.comma_breakable
419
+ q.text "blocks="; q.pp self.blocks; q.comma_breakable
420
+ q.group {
421
+ t = self.atime
422
+ q.text "atime="; q.pp t
423
+ q.breakable; q.text "(#{t.tv_sec})"
424
+ }
425
+ q.comma_breakable
426
+ q.group {
427
+ t = self.mtime
428
+ q.text "mtime="; q.pp t
429
+ q.breakable; q.text "(#{t.tv_sec})"
430
+ }
431
+ q.comma_breakable
432
+ q.group {
433
+ t = self.ctime
434
+ q.text "ctime="; q.pp t
435
+ q.breakable; q.text "(#{t.tv_sec})"
436
+ }
437
+ }
438
+ end
439
+ end
440
+ end
441
+
442
+ class MatchData
443
+ def pretty_print(q)
444
+ q.object_group(self) {
445
+ q.breakable
446
+ q.seplist(1..self.size, lambda { q.breakable }) {|i|
447
+ q.pp self[i-1]
448
+ }
449
+ }
450
+ end
451
+ end
452
+
453
+ class Object
454
+ include PP::ObjectMixin
455
+ end
456
+
457
+ [Numeric, Symbol, FalseClass, TrueClass, NilClass, Module].each {|c|
458
+ c.class_eval {
459
+ def pretty_print_cycle(q)
460
+ q.text inspect
461
+ end
462
+ }
463
+ }
464
+
465
+ [Numeric, FalseClass, TrueClass, Module].each {|c|
466
+ c.class_eval {
467
+ def pretty_print(q)
468
+ q.text inspect
469
+ end
470
+ }
471
+ }
472
+
473
+ # :enddoc:
474
+ if __FILE__ == $0
475
+ require 'test/unit'
476
+
477
+ class PPTest < Test::Unit::TestCase
478
+ def test_list0123_12
479
+ assert_equal("[0, 1, 2, 3]\n", PP.pp([0,1,2,3], '', 12))
480
+ end
481
+
482
+ def test_list0123_11
483
+ assert_equal("[0,\n 1,\n 2,\n 3]\n", PP.pp([0,1,2,3], '', 11))
484
+ end
485
+
486
+ OverriddenStruct = Struct.new("OverriddenStruct", :members, :class)
487
+ def test_struct_override_members # [ruby-core:7865]
488
+ a = OverriddenStruct.new(1,2)
489
+ assert_equal("#<struct Struct::OverriddenStruct members=1, class=2>\n", PP.pp(a, ''))
490
+ end
491
+
492
+ def test_redefined_method
493
+ o = ""
494
+ def o.method
495
+ end
496
+ assert_equal(%(""\n), PP.pp(o, ""))
497
+ end
498
+ end
499
+
500
+ class HasInspect
501
+ def initialize(a)
502
+ @a = a
503
+ end
504
+
505
+ def inspect
506
+ return "<inspect:#{@a.inspect}>"
507
+ end
508
+ end
509
+
510
+ class HasPrettyPrint
511
+ def initialize(a)
512
+ @a = a
513
+ end
514
+
515
+ def pretty_print(q)
516
+ q.text "<pretty_print:"
517
+ q.pp @a
518
+ q.text ">"
519
+ end
520
+ end
521
+
522
+ class HasBoth
523
+ def initialize(a)
524
+ @a = a
525
+ end
526
+
527
+ def inspect
528
+ return "<inspect:#{@a.inspect}>"
529
+ end
530
+
531
+ def pretty_print(q)
532
+ q.text "<pretty_print:"
533
+ q.pp @a
534
+ q.text ">"
535
+ end
536
+ end
537
+
538
+ class PrettyPrintInspect < HasPrettyPrint
539
+ alias inspect pretty_print_inspect
540
+ end
541
+
542
+ class PrettyPrintInspectWithoutPrettyPrint
543
+ alias inspect pretty_print_inspect
544
+ end
545
+
546
+ class PPInspectTest < Test::Unit::TestCase
547
+ def test_hasinspect
548
+ a = HasInspect.new(1)
549
+ assert_equal("<inspect:1>\n", PP.pp(a, ''))
550
+ end
551
+
552
+ def test_hasprettyprint
553
+ a = HasPrettyPrint.new(1)
554
+ assert_equal("<pretty_print:1>\n", PP.pp(a, ''))
555
+ end
556
+
557
+ def test_hasboth
558
+ a = HasBoth.new(1)
559
+ assert_equal("<pretty_print:1>\n", PP.pp(a, ''))
560
+ end
561
+
562
+ def test_pretty_print_inspect
563
+ a = PrettyPrintInspect.new(1)
564
+ assert_equal("<pretty_print:1>", a.inspect)
565
+ a = PrettyPrintInspectWithoutPrettyPrint.new
566
+ assert_raise(RuntimeError) { a.inspect }
567
+ end
568
+
569
+ def test_proc
570
+ a = proc {1}
571
+ assert_equal("#{a.inspect}\n", PP.pp(a, ''))
572
+ end
573
+
574
+ def test_to_s_with_iv
575
+ a = Object.new
576
+ def a.to_s() "aaa" end
577
+ a.instance_eval { @a = nil }
578
+ result = PP.pp(a, '')
579
+ assert_equal("#{a.inspect}\n", result)
580
+ assert_match(/\A#<Object.*>\n\z/m, result)
581
+ a = 1.0
582
+ a.instance_eval { @a = nil }
583
+ result = PP.pp(a, '')
584
+ assert_equal("#{a.inspect}\n", result)
585
+ end
586
+
587
+ def test_to_s_without_iv
588
+ a = Object.new
589
+ def a.to_s() "aaa" end
590
+ result = PP.pp(a, '')
591
+ assert_equal("#{a.inspect}\n", result)
592
+ assert_equal("aaa\n", result)
593
+ end
594
+ end
595
+
596
+ class PPCycleTest < Test::Unit::TestCase
597
+ def test_array
598
+ a = []
599
+ a << a
600
+ assert_equal("[[...]]\n", PP.pp(a, ''))
601
+ assert_equal("#{a.inspect}\n", PP.pp(a, ''))
602
+ end
603
+
604
+ def test_hash
605
+ a = {}
606
+ a[0] = a
607
+ assert_equal("{0=>{...}}\n", PP.pp(a, ''))
608
+ assert_equal("#{a.inspect}\n", PP.pp(a, ''))
609
+ end
610
+
611
+ S = Struct.new("S", :a, :b)
612
+ def test_struct
613
+ a = S.new(1,2)
614
+ a.b = a
615
+ assert_equal("#<struct Struct::S a=1, b=#<struct Struct::S:...>>\n", PP.pp(a, ''))
616
+ assert_equal("#{a.inspect}\n", PP.pp(a, ''))
617
+ end
618
+
619
+ def test_object
620
+ a = Object.new
621
+ a.instance_eval {@a = a}
622
+ assert_equal(a.inspect + "\n", PP.pp(a, ''))
623
+ end
624
+
625
+ def test_anonymous
626
+ a = Class.new.new
627
+ assert_equal(a.inspect + "\n", PP.pp(a, ''))
628
+ end
629
+
630
+ def test_withinspect
631
+ a = []
632
+ a << HasInspect.new(a)
633
+ assert_equal("[<inspect:[...]>]\n", PP.pp(a, ''))
634
+ assert_equal("#{a.inspect}\n", PP.pp(a, ''))
635
+ end
636
+
637
+ def test_share_nil
638
+ begin
639
+ PP.sharing_detection = true
640
+ a = [nil, nil]
641
+ assert_equal("[nil, nil]\n", PP.pp(a, ''))
642
+ ensure
643
+ PP.sharing_detection = false
644
+ end
645
+ end
646
+ end
647
+
648
+ class PPSingleLineTest < Test::Unit::TestCase
649
+ def test_hash
650
+ assert_equal("{1=>1}", PP.singleline_pp({ 1 => 1}, '')) # [ruby-core:02699]
651
+ assert_equal("[1#{', 1'*99}]", PP.singleline_pp([1]*100, ''))
652
+ end
653
+ end
654
+ end