awesome_print 1.6.1 → 1.9.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (93) hide show
  1. checksums.yaml +5 -5
  2. data/.gitignore +4 -0
  3. data/Appraisals +45 -22
  4. data/{CHANGELOG → CHANGELOG.md} +83 -18
  5. data/CONTRIBUTING.md +45 -4
  6. data/Gemfile.lock +28 -22
  7. data/LICENSE +16 -19
  8. data/README.md +97 -92
  9. data/Rakefile +5 -5
  10. data/awesome_print.gemspec +33 -0
  11. data/init.rb +1 -0
  12. data/lib/ap.rb +2 -2
  13. data/lib/awesome_print/colorize.rb +24 -0
  14. data/lib/awesome_print/core_ext/{array.rb → awesome_method_array.rb} +16 -18
  15. data/lib/awesome_print/core_ext/class.rb +3 -2
  16. data/lib/awesome_print/core_ext/kernel.rb +1 -1
  17. data/lib/awesome_print/core_ext/logger.rb +1 -1
  18. data/lib/awesome_print/core_ext/method.rb +2 -2
  19. data/lib/awesome_print/core_ext/object.rb +3 -2
  20. data/lib/awesome_print/core_ext/string.rb +3 -3
  21. data/lib/awesome_print/custom_defaults.rb +57 -0
  22. data/lib/awesome_print/ext/action_view.rb +8 -4
  23. data/lib/awesome_print/ext/active_record.rb +45 -12
  24. data/lib/awesome_print/ext/active_support.rb +1 -1
  25. data/lib/awesome_print/ext/mongo_mapper.rb +16 -13
  26. data/lib/awesome_print/ext/mongoid.rb +8 -6
  27. data/lib/awesome_print/ext/nobrainer.rb +52 -0
  28. data/lib/awesome_print/ext/nokogiri.rb +4 -4
  29. data/lib/awesome_print/ext/ostruct.rb +1 -1
  30. data/lib/awesome_print/ext/ripple.rb +5 -6
  31. data/lib/awesome_print/ext/sequel.rb +7 -6
  32. data/lib/awesome_print/formatter.rb +54 -327
  33. data/lib/awesome_print/formatters/array_formatter.rb +139 -0
  34. data/lib/awesome_print/formatters/base_formatter.rb +140 -0
  35. data/lib/awesome_print/formatters/class_formatter.rb +25 -0
  36. data/lib/awesome_print/formatters/dir_formatter.rb +22 -0
  37. data/lib/awesome_print/formatters/file_formatter.rb +22 -0
  38. data/lib/awesome_print/formatters/hash_formatter.rb +106 -0
  39. data/lib/awesome_print/formatters/method_formatter.rb +22 -0
  40. data/lib/awesome_print/formatters/object_formatter.rb +78 -0
  41. data/lib/awesome_print/formatters/simple_formatter.rb +21 -0
  42. data/lib/awesome_print/formatters/struct_formatter.rb +71 -0
  43. data/lib/awesome_print/formatters.rb +15 -0
  44. data/lib/awesome_print/indentator.rb +18 -0
  45. data/lib/awesome_print/inspector.rb +92 -94
  46. data/lib/awesome_print/version.rb +2 -2
  47. data/lib/awesome_print.rb +19 -18
  48. data/spec/active_record_helper.rb +24 -28
  49. data/spec/colors_spec.rb +31 -31
  50. data/spec/core_ext/logger_spec.rb +43 -0
  51. data/spec/core_ext/string_spec.rb +20 -0
  52. data/spec/ext/action_view_spec.rb +21 -0
  53. data/spec/ext/active_record_spec.rb +260 -0
  54. data/spec/ext/active_support_spec.rb +30 -0
  55. data/spec/ext/mongo_mapper_spec.rb +261 -0
  56. data/spec/ext/mongoid_spec.rb +67 -0
  57. data/spec/ext/nobrainer_spec.rb +59 -0
  58. data/spec/ext/nokogiri_spec.rb +46 -0
  59. data/spec/ext/ostruct_spec.rb +22 -0
  60. data/spec/ext/ripple_spec.rb +48 -0
  61. data/spec/formats_spec.rb +251 -184
  62. data/spec/methods_spec.rb +126 -130
  63. data/spec/misc_spec.rb +98 -93
  64. data/spec/objects_spec.rb +162 -27
  65. data/spec/spec_helper.rb +72 -38
  66. data/spec/support/active_record_data/3_2_diana.txt +24 -0
  67. data/spec/support/active_record_data/3_2_diana_legacy.txt +24 -0
  68. data/spec/support/active_record_data/3_2_multi.txt +50 -0
  69. data/spec/support/active_record_data/3_2_multi_legacy.txt +50 -0
  70. data/spec/support/active_record_data/4_0_diana.txt +98 -0
  71. data/spec/support/active_record_data/4_0_multi.txt +198 -0
  72. data/spec/support/active_record_data/4_1_diana.txt +97 -0
  73. data/spec/support/active_record_data/4_1_multi.txt +196 -0
  74. data/spec/support/active_record_data/4_2_diana.txt +109 -0
  75. data/spec/support/active_record_data/4_2_diana_legacy.txt +109 -0
  76. data/spec/support/active_record_data/4_2_multi.txt +220 -0
  77. data/spec/support/active_record_data/4_2_multi_legacy.txt +220 -0
  78. data/spec/support/active_record_data/5_0_diana.txt +105 -0
  79. data/spec/support/active_record_data/5_0_multi.txt +212 -0
  80. data/spec/support/active_record_data/5_1_diana.txt +104 -0
  81. data/spec/support/active_record_data/5_1_multi.txt +210 -0
  82. data/spec/support/active_record_data/5_2_diana.txt +104 -0
  83. data/spec/support/active_record_data/5_2_multi.txt +210 -0
  84. data/spec/support/active_record_data/6_0_diana.txt +104 -0
  85. data/spec/support/active_record_data/6_0_multi.txt +210 -0
  86. data/spec/support/active_record_data/6_1_diana.txt +109 -0
  87. data/spec/support/active_record_data/6_1_multi.txt +220 -0
  88. data/spec/support/active_record_data.rb +20 -0
  89. data/spec/support/ext_verifier.rb +42 -0
  90. data/spec/support/mongoid_versions.rb +26 -0
  91. data/spec/support/rails_versions.rb +55 -0
  92. metadata +104 -15
  93. data/lib/awesome_print/ext/no_brainer.rb +0 -58
@@ -0,0 +1,140 @@
1
+ require_relative '../colorize'
2
+
3
+ module AwesomePrint
4
+ module Formatters
5
+ class BaseFormatter
6
+ include Colorize
7
+
8
+ DEFAULT_LIMIT_SIZE = 7
9
+
10
+ # To support limited output, for example:
11
+ #
12
+ # ap ('a'..'z').to_a, :limit => 3
13
+ # [
14
+ # [ 0] "a",
15
+ # [ 1] .. [24],
16
+ # [25] "z"
17
+ # ]
18
+ #
19
+ # ap (1..100).to_a, :limit => true # Default limit is 7.
20
+ # [
21
+ # [ 0] 1,
22
+ # [ 1] 2,
23
+ # [ 2] 3,
24
+ # [ 3] .. [96],
25
+ # [97] 98,
26
+ # [98] 99,
27
+ # [99] 100
28
+ # ]
29
+ #------------------------------------------------------------------------------
30
+ def should_be_limited?
31
+ options[:limit] or (options[:limit].is_a?(Integer) and options[:limit] > 0)
32
+ end
33
+
34
+ def get_limit_size
35
+ case options[:limit]
36
+ when true
37
+ DEFAULT_LIMIT_SIZE
38
+ else
39
+ options[:limit]
40
+ end
41
+ end
42
+
43
+ def limited(data, width, is_hash = false)
44
+ limit = get_limit_size
45
+ if data.length <= limit
46
+ data
47
+ else
48
+ # Calculate how many elements to be displayed above and below the separator.
49
+ head = limit / 2
50
+ tail = head - (limit - 1) % 2
51
+
52
+ # Add the proper elements to the temp array and format the separator.
53
+ temp = data[0, head] + [nil] + data[-tail, tail]
54
+
55
+ temp[head] = if is_hash
56
+ "#{indent}#{data[head].strip} .. #{data[data.length - tail - 1].strip}"
57
+ else
58
+ "#{indent}[#{head.to_s.rjust(width)}] .. [#{data.length - tail - 1}]"
59
+ end
60
+
61
+ temp
62
+ end
63
+ end
64
+
65
+
66
+ def method_tuple(method)
67
+ if method.respond_to?(:parameters) # Ruby 1.9.2+
68
+ # See http://readruby.chengguangnan.com/methods#method-objects-parameters
69
+ # (mirror: http://archive.is/XguCA#selection-3381.1-3381.11)
70
+ args = method.parameters.inject([]) do |arr, (type, name)|
71
+ name ||= (type == :block ? 'block' : "arg#{arr.size + 1}")
72
+ arr << case type
73
+ when :req then name.to_s
74
+ when :opt, :rest then "*#{name}"
75
+ when :block then "&#{name}"
76
+ else '?'
77
+ end
78
+ end
79
+ else # See http://ruby-doc.org/core/classes/Method.html#M001902
80
+ args = (1..method.arity.abs).map { |i| "arg#{i}" }
81
+ args[-1] = "*#{args[-1]}" if method.arity < 0
82
+ end
83
+
84
+ # method.to_s formats to handle:
85
+ #
86
+ # #<Method: Fixnum#zero?>
87
+ # #<Method: Fixnum(Integer)#years>
88
+ # #<Method: User(#<Module:0x00000103207c00>)#_username>
89
+ # #<Method: User(id: integer, username: string).table_name>
90
+ # #<Method: User(id: integer, username: string)(ActiveRecord::Base).current>
91
+ # #<UnboundMethod: Hello#world>
92
+ #
93
+ if method.to_s =~ /(Unbound)*Method: (.*?)[#\.]/
94
+ unbound = $1 && '(unbound)'
95
+ klass = $2
96
+ if klass && klass =~ /(\(\w+:\s.*?\))/ # Is this ActiveRecord-style class?
97
+ klass.sub!($1, '') # Yes, strip the fields leaving class name only.
98
+ end
99
+ owner = "#{klass}#{unbound}".gsub('(', ' (')
100
+ end
101
+
102
+ [method.name.to_s, "(#{args.join(', ')})", owner.to_s]
103
+ end
104
+
105
+ #
106
+ # Indentation related methods
107
+ #-----------------------------------------
108
+ def indentation
109
+ inspector.current_indentation
110
+ end
111
+
112
+ def indented(&block)
113
+ inspector.increase_indentation(&block)
114
+ end
115
+
116
+ def indent
117
+ ' ' * indentation
118
+ end
119
+
120
+ def outdent
121
+ ' ' * (indentation - options[:indent].abs)
122
+ end
123
+
124
+ def align(value, width)
125
+ if options[:multiline]
126
+ if options[:indent] > 0
127
+ value.rjust(width)
128
+ elsif options[:indent] == 0
129
+ indent + value.ljust(width)
130
+ else
131
+ indent[0, indentation + options[:indent]] + value.ljust(width)
132
+ end
133
+ else
134
+ value
135
+ end
136
+ end
137
+
138
+ end
139
+ end
140
+ end
@@ -0,0 +1,25 @@
1
+ require_relative 'base_formatter'
2
+
3
+ module AwesomePrint
4
+ module Formatters
5
+ class ClassFormatter < BaseFormatter
6
+
7
+ attr_reader :klass, :inspector, :options
8
+
9
+ def initialize(klass, inspector)
10
+ @klass = klass
11
+ @inspector = inspector
12
+ @options = inspector.options
13
+ end
14
+
15
+ def format
16
+ superclass = klass.superclass
17
+ if superclass
18
+ colorize("#{klass.inspect} < #{superclass}", :class)
19
+ else
20
+ colorize(klass.inspect, :class)
21
+ end
22
+ end
23
+ end
24
+ end
25
+ end
@@ -0,0 +1,22 @@
1
+ require_relative 'base_formatter'
2
+ require 'shellwords'
3
+
4
+ module AwesomePrint
5
+ module Formatters
6
+ class DirFormatter < BaseFormatter
7
+
8
+ attr_reader :dir, :inspector, :options
9
+
10
+ def initialize(dir, inspector)
11
+ @dir = dir
12
+ @inspector = inspector
13
+ @options = inspector.options
14
+ end
15
+
16
+ def format
17
+ ls = `ls -alF #{dir.path.shellescape}`
18
+ colorize(ls.empty? ? dir.inspect : "#{dir.inspect}\n#{ls.chop}", :dir)
19
+ end
20
+ end
21
+ end
22
+ end
@@ -0,0 +1,22 @@
1
+ require_relative 'base_formatter'
2
+ require 'shellwords'
3
+
4
+ module AwesomePrint
5
+ module Formatters
6
+ class FileFormatter < BaseFormatter
7
+
8
+ attr_reader :file, :inspector, :options
9
+
10
+ def initialize(file, inspector)
11
+ @file = file
12
+ @inspector = inspector
13
+ @options = inspector.options
14
+ end
15
+
16
+ def format
17
+ ls = File.directory?(file) ? `ls -adlF #{file.path.shellescape}` : `ls -alF #{file.path.shellescape}`
18
+ colorize(ls.empty? ? file.inspect : "#{file.inspect}\n#{ls.chop}", :file)
19
+ end
20
+ end
21
+ end
22
+ end
@@ -0,0 +1,106 @@
1
+ require_relative 'base_formatter'
2
+
3
+ module AwesomePrint
4
+ module Formatters
5
+ class HashFormatter < BaseFormatter
6
+ attr_reader :hash, :inspector, :options
7
+
8
+ def initialize(hash, inspector)
9
+ @hash = hash
10
+ @inspector = inspector
11
+ @options = inspector.options
12
+ end
13
+
14
+ def format
15
+ if hash.empty?
16
+ empty_hash
17
+ elsif multiline_hash?
18
+ multiline_hash
19
+ else
20
+ simple_hash
21
+ end
22
+ end
23
+
24
+ private
25
+
26
+ def empty_hash
27
+ '{}'
28
+ end
29
+
30
+ def multiline_hash?
31
+ options[:multiline]
32
+ end
33
+
34
+ def multiline_hash
35
+ ["{\n", printable_hash.join(",\n"), "\n#{outdent}}"].join
36
+ end
37
+
38
+ def simple_hash
39
+ "{ #{printable_hash.join(', ')} }"
40
+ end
41
+
42
+ def printable_hash
43
+ data = printable_keys
44
+ width = left_width(data)
45
+
46
+ data.map! do |key, value|
47
+ indented do
48
+ if options[:ruby19_syntax] && symbol?(key)
49
+ ruby19_syntax(key, value, width)
50
+ else
51
+ pre_ruby19_syntax(key, value, width)
52
+ end
53
+ end
54
+ end
55
+
56
+ should_be_limited? ? limited(data, width, hash: true) : data
57
+ end
58
+
59
+ def left_width(keys)
60
+ result = max_key_width(keys)
61
+ result += indentation if options[:indent] > 0
62
+ result
63
+ end
64
+
65
+ def max_key_width(keys)
66
+ keys.map { |key, _value| key.size }.max || 0
67
+ end
68
+
69
+ def printable_keys
70
+ keys = hash.keys
71
+
72
+ keys.sort! { |a, b| a.to_s <=> b.to_s } if options[:sort_keys]
73
+
74
+ keys.map! do |key|
75
+ plain_single_line do
76
+ [String.new(inspector.awesome(key)), hash[key]]
77
+ end
78
+ end
79
+ end
80
+
81
+ def symbol?(key)
82
+ key[0] == ':'
83
+ end
84
+
85
+ def ruby19_syntax(key, value, width)
86
+ key[0] = ''
87
+ align(key, width - 1) << colorize(': ', :hash) << inspector.awesome(value)
88
+ end
89
+
90
+ def pre_ruby19_syntax(key, value, width)
91
+ align(key, width) << colorize(' => ', :hash) << inspector.awesome(value)
92
+ end
93
+
94
+ def plain_single_line
95
+ plain = options[:plain]
96
+ multiline = options[:multiline]
97
+ options[:plain] = true
98
+ options[:multiline] = false
99
+ yield
100
+ ensure
101
+ options[:plain] = plain
102
+ options[:multiline] = multiline
103
+ end
104
+ end
105
+ end
106
+ end
@@ -0,0 +1,22 @@
1
+ require_relative 'base_formatter'
2
+
3
+ module AwesomePrint
4
+ module Formatters
5
+ class MethodFormatter < BaseFormatter
6
+
7
+ attr_reader :method, :inspector, :options
8
+
9
+ def initialize(method, inspector)
10
+ @method = method
11
+ @inspector = inspector
12
+ @options = inspector.options
13
+ end
14
+
15
+ def format
16
+ name, args, owner = method_tuple(method)
17
+
18
+ "#{colorize(owner, :class)}##{colorize(name, :method)}#{colorize(args, :args)}"
19
+ end
20
+ end
21
+ end
22
+ end
@@ -0,0 +1,78 @@
1
+ require_relative 'base_formatter'
2
+
3
+ module AwesomePrint
4
+ module Formatters
5
+ class ObjectFormatter < BaseFormatter
6
+
7
+ attr_reader :object, :variables, :inspector, :options
8
+
9
+ def initialize(object, inspector)
10
+ @object = object
11
+ @variables = object.instance_variables
12
+ @inspector = inspector
13
+ @options = inspector.options
14
+ end
15
+
16
+ def format
17
+ vars = variables.map do |var|
18
+ property = var.to_s[1..-1].to_sym # to_s because of some monkey patching done by Puppet.
19
+ accessor = if object.respond_to?(:"#{property}=")
20
+ object.respond_to?(property) ? :accessor : :writer
21
+ else
22
+ object.respond_to?(property) ? :reader : nil
23
+ end
24
+ if accessor
25
+ [String.new("attr_#{accessor} :#{property}"), var]
26
+ else
27
+ [var.to_s, var]
28
+ end
29
+ end
30
+
31
+ data = (options[:sort_vars] ? vars.sort : vars).map do |declaration, var|
32
+ key = left_aligned do
33
+ align(declaration, declaration.size)
34
+ end
35
+
36
+ unless options[:plain]
37
+ if key =~ /(@\w+)/
38
+ key.sub!($1, colorize($1, :variable))
39
+ else
40
+ key.sub!(/(attr_\w+)\s(\:\w+)/, "#{colorize('\\1', :keyword)} #{colorize('\\2', :method)}")
41
+ end
42
+ end
43
+
44
+ indented do
45
+ key << colorize(' = ', :hash) + inspector.awesome(object.instance_variable_get(var))
46
+ end
47
+ end
48
+
49
+ if options[:multiline]
50
+ "#<#{awesome_instance}\n#{data.join(%Q/,\n/)}\n#{outdent}>"
51
+ else
52
+ "#<#{awesome_instance} #{data.join(', ')}>"
53
+ end
54
+ end
55
+
56
+ private
57
+
58
+ def valid_instance_var?(variable_name)
59
+ variable_name.to_s.start_with?('@')
60
+ end
61
+
62
+ def awesome_instance
63
+ str = String.new
64
+ str << object.send(options[:class_name]).to_s
65
+ str << ":0x%08x" % (object.__id__ * 2) if options[:object_id]
66
+ str
67
+ end
68
+
69
+ def left_aligned
70
+ current = options[:indent]
71
+ options[:indent] = 0
72
+ yield
73
+ ensure
74
+ options[:indent] = current
75
+ end
76
+ end
77
+ end
78
+ end
@@ -0,0 +1,21 @@
1
+ require_relative 'base_formatter'
2
+
3
+ module AwesomePrint
4
+ module Formatters
5
+ class SimpleFormatter < BaseFormatter
6
+
7
+ attr_reader :string, :type, :inspector, :options
8
+
9
+ def initialize(string, type, inspector)
10
+ @string = string
11
+ @type = type
12
+ @inspector = inspector
13
+ @options = inspector.options
14
+ end
15
+
16
+ def format
17
+ colorize(string, type)
18
+ end
19
+ end
20
+ end
21
+ end
@@ -0,0 +1,71 @@
1
+ require_relative 'base_formatter'
2
+
3
+ module AwesomePrint
4
+ module Formatters
5
+ class StructFormatter < BaseFormatter
6
+
7
+ attr_reader :struct, :variables, :inspector, :options
8
+
9
+ def initialize(struct, inspector)
10
+ @struct = struct
11
+ @variables = struct.members
12
+ @inspector = inspector
13
+ @options = inspector.options
14
+ end
15
+
16
+ def format
17
+ vars = variables.map do |var|
18
+ property = var.to_s[1..-1].to_sym # to_s because of some monkey patching done by Puppet.
19
+ accessor = if struct.respond_to?(:"#{property}=")
20
+ struct.respond_to?(property) ? :accessor : :writer
21
+ else
22
+ struct.respond_to?(property) ? :reader : nil
23
+ end
24
+ if accessor
25
+ ["attr_#{accessor} :#{property}", var]
26
+ else
27
+ [var.to_s, var]
28
+ end
29
+ end
30
+
31
+ data = vars.sort.map do |declaration, var|
32
+ key = left_aligned do
33
+ align(declaration, declaration.size)
34
+ end
35
+
36
+ unless options[:plain]
37
+ if key =~ /(@\w+)/
38
+ key.sub!($1, colorize($1, :variable))
39
+ else
40
+ key.sub!(/(attr_\w+)\s(\:\w+)/, "#{colorize('\\1', :keyword)} #{colorize('\\2', :method)}")
41
+ end
42
+ end
43
+
44
+ indented do
45
+ key << colorize(' = ', :hash) + inspector.awesome(struct.send(var))
46
+ end
47
+ end
48
+
49
+ if options[:multiline]
50
+ "#<#{awesome_instance}\n#{data.join(%Q/,\n/)}\n#{outdent}>"
51
+ else
52
+ "#<#{awesome_instance} #{data.join(', ')}>"
53
+ end
54
+ end
55
+
56
+ private
57
+
58
+ def awesome_instance
59
+ "#{struct.class.superclass}:#{struct.class}:0x%08x" % (struct.__id__ * 2)
60
+ end
61
+
62
+ def left_aligned
63
+ current = options[:indent]
64
+ options[:indent] = 0
65
+ yield
66
+ ensure
67
+ options[:indent] = current
68
+ end
69
+ end
70
+ end
71
+ end
@@ -0,0 +1,15 @@
1
+ module AwesomePrint
2
+ module Formatters
3
+ require 'awesome_print/formatters/object_formatter'
4
+ require 'awesome_print/formatters/struct_formatter'
5
+ require 'awesome_print/formatters/hash_formatter'
6
+ require 'awesome_print/formatters/array_formatter'
7
+ require 'awesome_print/formatters/simple_formatter'
8
+ require 'awesome_print/formatters/method_formatter'
9
+ require 'awesome_print/formatters/class_formatter'
10
+ require 'awesome_print/formatters/dir_formatter'
11
+ require 'awesome_print/formatters/file_formatter'
12
+ require 'awesome_print/colorize'
13
+ end
14
+ end
15
+
@@ -0,0 +1,18 @@
1
+ module AwesomePrint
2
+ class Indentator
3
+
4
+ attr_reader :shift_width, :indentation
5
+
6
+ def initialize(indentation)
7
+ @indentation = indentation
8
+ @shift_width = indentation.freeze
9
+ end
10
+
11
+ def indent
12
+ @indentation += shift_width
13
+ yield
14
+ ensure
15
+ @indentation -= shift_width
16
+ end
17
+ end
18
+ end