rfix 1.2.2
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 +7 -0
- data/.github/workflows/main.yml +38 -0
- data/.gitignore +43 -0
- data/.rspec +2 -0
- data/.rubocop.yml +87 -0
- data/.travis.yml +37 -0
- data/Gemfile +2 -0
- data/Gemfile.base +14 -0
- data/Gemfile.base.lock +172 -0
- data/Gemfile.lock +181 -0
- data/Guardfile +16 -0
- data/LICENSE.txt +21 -0
- data/Makefile +4 -0
- data/README.md +92 -0
- data/Rakefile +27 -0
- data/bin/bundle +114 -0
- data/bin/console +29 -0
- data/bin/guard +29 -0
- data/bin/rake +29 -0
- data/bin/rfix +29 -0
- data/bin/rspec +29 -0
- data/bin/setup +29 -0
- data/ci/Gemfile.rubocop-0.80 +2 -0
- data/ci/Gemfile.rubocop-0.80.lock +170 -0
- data/ci/Gemfile.rubocop-0.81 +2 -0
- data/ci/Gemfile.rubocop-0.81.lock +170 -0
- data/ci/Gemfile.rubocop-0.82 +2 -0
- data/ci/Gemfile.rubocop-0.82.lock +170 -0
- data/ci/Gemfile.rubocop-0.83 +2 -0
- data/ci/Gemfile.rubocop-0.83.lock +168 -0
- data/ci/Gemfile.rubocop-0.84 +2 -0
- data/ci/Gemfile.rubocop-0.84.lock +171 -0
- data/ci/Gemfile.rubocop-0.85 +2 -0
- data/ci/Gemfile.rubocop-0.85.1 +2 -0
- data/ci/Gemfile.rubocop-0.85.1.lock +173 -0
- data/ci/Gemfile.rubocop-0.85.lock +173 -0
- data/exe/rfix +30 -0
- data/lib/rfix.rb +34 -0
- data/lib/rfix/box.rb +112 -0
- data/lib/rfix/branch.rb +31 -0
- data/lib/rfix/branches/base.rb +29 -0
- data/lib/rfix/branches/head.rb +13 -0
- data/lib/rfix/branches/main.rb +34 -0
- data/lib/rfix/branches/name.rb +23 -0
- data/lib/rfix/branches/reference.rb +21 -0
- data/lib/rfix/branches/upstream.rb +13 -0
- data/lib/rfix/cmd.rb +39 -0
- data/lib/rfix/commands/branch.rb +15 -0
- data/lib/rfix/commands/extensions/options.rb +8 -0
- data/lib/rfix/commands/help.rb +7 -0
- data/lib/rfix/commands/helper/args.rb +137 -0
- data/lib/rfix/commands/helper/help.rb +6 -0
- data/lib/rfix/commands/helper/loader.rb +6 -0
- data/lib/rfix/commands/helper/option.rb +0 -0
- data/lib/rfix/commands/helper/params.rb +0 -0
- data/lib/rfix/commands/helper/rubocop.rb +17 -0
- data/lib/rfix/commands/info.rb +30 -0
- data/lib/rfix/commands/lint.rb +23 -0
- data/lib/rfix/commands/local.rb +12 -0
- data/lib/rfix/commands/origin.rb +19 -0
- data/lib/rfix/commands/setup.rb +29 -0
- data/lib/rfix/commands/welcome.rb +24 -0
- data/lib/rfix/deleted.rb +13 -0
- data/lib/rfix/error.rb +2 -0
- data/lib/rfix/extensions/extensions.rb +18 -0
- data/lib/rfix/extensions/offense.rb +78 -0
- data/lib/rfix/extensions/string.rb +8 -0
- data/lib/rfix/file.rb +46 -0
- data/lib/rfix/file_cache.rb +59 -0
- data/lib/rfix/formatter.rb +126 -0
- data/lib/rfix/git_helper.rb +59 -0
- data/lib/rfix/log.rb +131 -0
- data/lib/rfix/no_file.rb +13 -0
- data/lib/rfix/rake/paths.rb +50 -0
- data/lib/rfix/rake/support.rb +75 -0
- data/lib/rfix/repository.rb +204 -0
- data/lib/rfix/rfix.rb +34 -0
- data/lib/rfix/tracked.rb +72 -0
- data/lib/rfix/tracked_file.rb +16 -0
- data/lib/rfix/untracked.rb +13 -0
- data/lib/rfix/version.rb +5 -0
- data/resources/ps.png +0 -0
- data/rfix.gemspec +68 -0
- data/tasks/bump.rake +11 -0
- data/tasks/bundle.rake +17 -0
- data/tasks/complex.rake +54 -0
- data/tasks/execute.rake +38 -0
- data/tasks/libgit2.rake +33 -0
- data/tasks/simple.rake +62 -0
- data/tasks/travis.rake +74 -0
- data/tasks/vendor.rake +34 -0
- metadata +350 -0
data/lib/rfix/deleted.rb
ADDED
data/lib/rfix/error.rb
ADDED
@@ -0,0 +1,18 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "rubocop"
|
4
|
+
require "rainbow"
|
5
|
+
require "rfix/log"
|
6
|
+
|
7
|
+
module Rfix::Ext
|
8
|
+
module CommentConfig
|
9
|
+
include Rfix::Log # TODO: Remove
|
10
|
+
# Called by RuboCop on every line to see
|
11
|
+
# if its suppose to run against it or not
|
12
|
+
def cop_enabled_at_line?(_cop, line)
|
13
|
+
Rfix.enabled?(processed_source.file_path, line) && super
|
14
|
+
rescue StandardError
|
15
|
+
say_abort "[Rfix::Enabled] #{$ERROR_INFO}"
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
@@ -0,0 +1,78 @@
|
|
1
|
+
module Rfix::Ext
|
2
|
+
module Offense
|
3
|
+
def where
|
4
|
+
line.to_s + ":" + real_column.to_s
|
5
|
+
end
|
6
|
+
|
7
|
+
def info
|
8
|
+
message.split(": ", 2).last.delete("\n")
|
9
|
+
end
|
10
|
+
|
11
|
+
def msg
|
12
|
+
CLI::UI.resolve_text("{{italic:#{info}}}", truncate_to: CLI::UI::Terminal.width - 10)
|
13
|
+
end
|
14
|
+
|
15
|
+
def code
|
16
|
+
message.split(": ", 2).first
|
17
|
+
end
|
18
|
+
|
19
|
+
def star
|
20
|
+
Rainbow("⭑")
|
21
|
+
end
|
22
|
+
|
23
|
+
def cross
|
24
|
+
Rainbow("✗").red
|
25
|
+
end
|
26
|
+
|
27
|
+
def check
|
28
|
+
Rainbow("✓").green
|
29
|
+
end
|
30
|
+
|
31
|
+
def circle
|
32
|
+
Rainbow("⍟")
|
33
|
+
end
|
34
|
+
|
35
|
+
def relative_path
|
36
|
+
# TODO: Fix this, do not use Dir.getwd, use git root
|
37
|
+
location.source_buffer.name.sub(File.join(Dir.getwd, "/"), "")
|
38
|
+
end
|
39
|
+
|
40
|
+
def clickable_path
|
41
|
+
"{{italic:#{relative_path}:#{where}}}"
|
42
|
+
end
|
43
|
+
|
44
|
+
def clickable_plain_severity
|
45
|
+
to_url("https://www.rubydoc.info/gems/rubocop/RuboCop/Cop/#{code}", code)
|
46
|
+
end
|
47
|
+
|
48
|
+
def clickable_severity
|
49
|
+
"{{#{severity.code}}} {{italic:#{clickable_plain_severity}}}"
|
50
|
+
end
|
51
|
+
|
52
|
+
def icon
|
53
|
+
return check.green if corrected?
|
54
|
+
return star.yellow if correctable?
|
55
|
+
|
56
|
+
cross.red
|
57
|
+
end
|
58
|
+
|
59
|
+
def to_clickable(url, title)
|
60
|
+
esc = CLI::UI::ANSI::ESC
|
61
|
+
cmd = esc + "]8;;"
|
62
|
+
slash = "\x07"
|
63
|
+
cmd + "#{escape(url)}#{slash}#{escape(title)}" + cmd + slash
|
64
|
+
end
|
65
|
+
|
66
|
+
def to_path(path, title)
|
67
|
+
to_clickable("file://#{path}", title)
|
68
|
+
end
|
69
|
+
|
70
|
+
def to_url(url, title)
|
71
|
+
to_clickable(url, title)
|
72
|
+
end
|
73
|
+
|
74
|
+
def escape(str)
|
75
|
+
Shellwords.escape(str)
|
76
|
+
end
|
77
|
+
end
|
78
|
+
end
|
data/lib/rfix/file.rb
ADDED
@@ -0,0 +1,46 @@
|
|
1
|
+
require "rugged"
|
2
|
+
require "shellwords"
|
3
|
+
require "digest"
|
4
|
+
require "listen"
|
5
|
+
|
6
|
+
class Rfix::File < Struct.new(:path, :repo, :ref)
|
7
|
+
include Rfix::Log
|
8
|
+
|
9
|
+
def initialize(path, repo, ref)
|
10
|
+
# check_absolute!(path)
|
11
|
+
super(path, repo, ref)
|
12
|
+
end
|
13
|
+
|
14
|
+
def check_absolute!(path)
|
15
|
+
if Pathname.new(path).absolute?
|
16
|
+
say_abort "Path must be relative #{path}"
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
20
|
+
def include?(_)
|
21
|
+
raise Rfix::Error.new("#include? not implemented")
|
22
|
+
end
|
23
|
+
|
24
|
+
def refresh!
|
25
|
+
raise Rfix::Error.new("#refresh! not implemented")
|
26
|
+
end
|
27
|
+
|
28
|
+
def inspect
|
29
|
+
raise Rfix::Error.new("#inspect not implemented")
|
30
|
+
end
|
31
|
+
|
32
|
+
def git_path
|
33
|
+
@git_path ||= Pathname.new(repo.workdir)
|
34
|
+
end
|
35
|
+
|
36
|
+
def absolute_path
|
37
|
+
path
|
38
|
+
# @absolute_path ||= to_abs(path)
|
39
|
+
end
|
40
|
+
|
41
|
+
def to_abs(path)
|
42
|
+
File.join(repo.workdir, path)
|
43
|
+
end
|
44
|
+
|
45
|
+
alias to_s path
|
46
|
+
end
|
@@ -0,0 +1,59 @@
|
|
1
|
+
class FileCache
|
2
|
+
attr_reader :root_path
|
3
|
+
include Rfix::Log
|
4
|
+
|
5
|
+
def initialize(path)
|
6
|
+
@files = Hash.new
|
7
|
+
@paths = Hash.new
|
8
|
+
@root_path = path
|
9
|
+
end
|
10
|
+
|
11
|
+
def add(file)
|
12
|
+
key = normalized_file_path(file)
|
13
|
+
|
14
|
+
if @files.key?(key)
|
15
|
+
return say_debug("File already exists with path {{error:#{file.path}}} using #{key}")
|
16
|
+
end
|
17
|
+
|
18
|
+
say_debug("Adding file with path {{green:#{file.path}}} using key {{info:#{key}}}")
|
19
|
+
@files[key] = file
|
20
|
+
end
|
21
|
+
|
22
|
+
def get(path)
|
23
|
+
key = normalize_path(path)
|
24
|
+
|
25
|
+
if file = @files[key]
|
26
|
+
say_debug("Found file #{file} with path #{path}")
|
27
|
+
return file
|
28
|
+
end
|
29
|
+
|
30
|
+
say_debug("Could {{error:NOT}} find path #{path}")
|
31
|
+
nil
|
32
|
+
end
|
33
|
+
|
34
|
+
def pluck(&block)
|
35
|
+
@files.values.map(&block)
|
36
|
+
end
|
37
|
+
|
38
|
+
private
|
39
|
+
|
40
|
+
def normalized_file_path(file)
|
41
|
+
normalize_path(file.absolute_path)
|
42
|
+
end
|
43
|
+
|
44
|
+
def to_abs(path)
|
45
|
+
File.join(root_path, path)
|
46
|
+
end
|
47
|
+
|
48
|
+
def normalize_path(path)
|
49
|
+
if cached = @paths[path]
|
50
|
+
return cached
|
51
|
+
end
|
52
|
+
|
53
|
+
if Pathname.new(path).absolute?
|
54
|
+
@paths[path] = File.realdirpath(path)
|
55
|
+
else
|
56
|
+
@paths[path] = File.realdirpath(to_abs(path))
|
57
|
+
end
|
58
|
+
end
|
59
|
+
end
|
@@ -0,0 +1,126 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "rubocop"
|
4
|
+
require "rouge"
|
5
|
+
require "rainbow"
|
6
|
+
require "shellwords"
|
7
|
+
|
8
|
+
module Rfix
|
9
|
+
class Formatter < RuboCop::Formatter::SimpleTextFormatter
|
10
|
+
include Rfix::Log
|
11
|
+
|
12
|
+
def started(files)
|
13
|
+
theme = Rouge::Themes::Gruvbox.new
|
14
|
+
@formatter = Rouge::Formatters::TerminalTruecolor.new(theme)
|
15
|
+
@current = 0
|
16
|
+
@total = files.count
|
17
|
+
@files = {}
|
18
|
+
@lexer = Rouge::Lexers::Ruby.new
|
19
|
+
@pg = CLI::UI::Progress.new
|
20
|
+
@all_files = files
|
21
|
+
end
|
22
|
+
|
23
|
+
def truncate(path)
|
24
|
+
path.sub(::File.join(Dir.getwd, "/"), "")
|
25
|
+
end
|
26
|
+
|
27
|
+
def render_files(files)
|
28
|
+
return unless Rfix.test?
|
29
|
+
|
30
|
+
files.each do |file|
|
31
|
+
offenses = @files.fetch(file)
|
32
|
+
corrected = offenses.select(&:corrected?)
|
33
|
+
|
34
|
+
if offenses.empty?
|
35
|
+
say truncate(file)
|
36
|
+
elsif offenses.count == corrected.count
|
37
|
+
say truncate(file)
|
38
|
+
else
|
39
|
+
say_error truncate(file)
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
43
|
+
|
44
|
+
def finished(files)
|
45
|
+
render_files(files)
|
46
|
+
|
47
|
+
files.each do |file|
|
48
|
+
render_file(file, @files.fetch(file))
|
49
|
+
end
|
50
|
+
|
51
|
+
offenses = @files.values.flatten
|
52
|
+
corrected = offenses.select(&:corrected?)
|
53
|
+
out("\n") unless @total.zero?
|
54
|
+
report_summary(files.size, offenses.count, corrected.count)
|
55
|
+
end
|
56
|
+
|
57
|
+
def render_file(file, offenses)
|
58
|
+
return if offenses.empty?
|
59
|
+
|
60
|
+
offenses.each do |offense|
|
61
|
+
out("\n\n")
|
62
|
+
CLI::UI::Frame.open("#{offense.icon} #{offense.msg}", color: :reset)
|
63
|
+
report_line(file, offense, offense.location, offense.highlighted_area)
|
64
|
+
CLI::UI::Frame.close("#{offense.clickable_severity} » #{offense.clickable_path}", color: :reset)
|
65
|
+
end
|
66
|
+
end
|
67
|
+
|
68
|
+
def mark
|
69
|
+
CLI::UI::ANSI::ESC + "]1337;SetMark" + "\x07"
|
70
|
+
end
|
71
|
+
|
72
|
+
def file_finished(file, offenses)
|
73
|
+
out("\n") if @current == 0.0
|
74
|
+
@current += 1.0
|
75
|
+
unless Rfix.test?
|
76
|
+
@pg.tick(set_percent: (@current / @total))
|
77
|
+
end
|
78
|
+
@files[file] = offenses
|
79
|
+
end
|
80
|
+
|
81
|
+
def out(msg, format: true)
|
82
|
+
CLI::UI.puts(msg, to: output, format: format)
|
83
|
+
end
|
84
|
+
|
85
|
+
def fmt(msg)
|
86
|
+
CLI::UI.fmt(msg, enable_color: true)
|
87
|
+
end
|
88
|
+
|
89
|
+
def dim(value)
|
90
|
+
Rainbow(value).lightgray
|
91
|
+
end
|
92
|
+
|
93
|
+
def highlighted_source_line(offense)
|
94
|
+
source_before_highlight(offense) +
|
95
|
+
hightlight_source_tag(offense) +
|
96
|
+
source_after_highlight(offense)
|
97
|
+
end
|
98
|
+
|
99
|
+
def hightlight_source_tag(offense)
|
100
|
+
offense.highlighted_area.source
|
101
|
+
end
|
102
|
+
|
103
|
+
def source_before_highlight(offense)
|
104
|
+
source_line = offense.location.source_line
|
105
|
+
source_line[0...offense.highlighted_area.begin_pos]
|
106
|
+
end
|
107
|
+
|
108
|
+
def source_after_highlight(offense)
|
109
|
+
source_line = offense.location.source_line
|
110
|
+
source_line[offense.highlighted_area.end_pos..-1]
|
111
|
+
end
|
112
|
+
|
113
|
+
def report_line(_file, offense, _location, highlighted_area)
|
114
|
+
extra = " "
|
115
|
+
src = highlighted_source_line(offense).lines.map { |line| extra + line }.join("\n")
|
116
|
+
lines = @formatter.format(@lexer.lex(src)).gsub('\\e', CLI::UI::ANSI::ESC).lines.map(&:chomp)
|
117
|
+
out("\n\n")
|
118
|
+
out(lines.join("\n"), format: false)
|
119
|
+
b_pos = highlighted_area.begin_pos + extra.length
|
120
|
+
e_pos = highlighted_area.end_pos + extra.length
|
121
|
+
size = e_pos - b_pos
|
122
|
+
out((" " * b_pos) + Rainbow((" " * size)).underline.bold)
|
123
|
+
out("\n\n")
|
124
|
+
end
|
125
|
+
end
|
126
|
+
end
|
@@ -0,0 +1,59 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "open3"
|
4
|
+
require "rfix"
|
5
|
+
require "rfix/log"
|
6
|
+
require "rfix/cmd"
|
7
|
+
require "shellwords"
|
8
|
+
|
9
|
+
module Rfix::GitHelper
|
10
|
+
include Rfix::Log
|
11
|
+
include Rfix::Cmd
|
12
|
+
|
13
|
+
def git(*params, root: Dir.pwd, quiet: false, &block)
|
14
|
+
args = split_args(params)
|
15
|
+
args.unshift *["--git-dir", File.join(root, ".git")]
|
16
|
+
args.unshift *["--work-tree", root]
|
17
|
+
cmd("git", *args, quiet: quiet, &block)
|
18
|
+
end
|
19
|
+
|
20
|
+
def split_args(params)
|
21
|
+
return if params.empty?
|
22
|
+
return split(params.first) if params.count == 1
|
23
|
+
return params
|
24
|
+
end
|
25
|
+
|
26
|
+
def split(str)
|
27
|
+
Shellwords.split(str)
|
28
|
+
end
|
29
|
+
|
30
|
+
def has_branch?(branch)
|
31
|
+
cmd_succeeded?("git", "cat-file", "-t", branch)
|
32
|
+
end
|
33
|
+
|
34
|
+
def dirty?(path)
|
35
|
+
Dir.chdir(path) do
|
36
|
+
!cmd_succeeded?("git diff --quiet")
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
def params
|
41
|
+
[
|
42
|
+
"--word-diff-regex=[^[:space:]]",
|
43
|
+
"--no-renames",
|
44
|
+
"--no-merges",
|
45
|
+
"--first-parent",
|
46
|
+
"--find-renames",
|
47
|
+
"--find-copies",
|
48
|
+
"--diff-filter=AMCR",
|
49
|
+
"-U0",
|
50
|
+
"--no-color",
|
51
|
+
"-p"
|
52
|
+
]
|
53
|
+
end
|
54
|
+
end
|
55
|
+
|
56
|
+
# TODO: Rename above to just ::Git
|
57
|
+
module Rfix::Git
|
58
|
+
extend Rfix::GitHelper
|
59
|
+
end
|
data/lib/rfix/log.rb
ADDED
@@ -0,0 +1,131 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "rfix"
|
4
|
+
require "cli/ui"
|
5
|
+
|
6
|
+
module Rfix::Log
|
7
|
+
extend self
|
8
|
+
def say(message)
|
9
|
+
prt("{{v}} #{message}")
|
10
|
+
end
|
11
|
+
|
12
|
+
def say_error(message)
|
13
|
+
prt("{{x}} #{message}")
|
14
|
+
end
|
15
|
+
|
16
|
+
def say_error_sub(message)
|
17
|
+
prt(message.to_s)
|
18
|
+
end
|
19
|
+
|
20
|
+
def error_box(title)
|
21
|
+
box(title, color: :red) { yield }
|
22
|
+
end
|
23
|
+
|
24
|
+
def abort_box(title)
|
25
|
+
error_box(title) { yield }
|
26
|
+
exit 1
|
27
|
+
end
|
28
|
+
|
29
|
+
def say_test(message)
|
30
|
+
prt("{{i}} #{strip(message)}")
|
31
|
+
end
|
32
|
+
|
33
|
+
def say_debug(message)
|
34
|
+
if debug? or test?
|
35
|
+
prt("{{i}} #{strip(message)}", to: $stderr)
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
def say_abort(message)
|
40
|
+
prt("{{x}} #{message}")
|
41
|
+
exit 1
|
42
|
+
end
|
43
|
+
|
44
|
+
def debug?
|
45
|
+
return false unless defined?(RSpec)
|
46
|
+
return RSpec.configuration.debug?
|
47
|
+
end
|
48
|
+
|
49
|
+
def test?
|
50
|
+
Rfix.test?
|
51
|
+
end
|
52
|
+
|
53
|
+
def say_exit(message)
|
54
|
+
prt("{{v}} #{message}")
|
55
|
+
exit 0
|
56
|
+
end
|
57
|
+
|
58
|
+
def say_plain(message)
|
59
|
+
prt(message)
|
60
|
+
end
|
61
|
+
|
62
|
+
def debug_box(title)
|
63
|
+
unless_debug do
|
64
|
+
box(title) { yield }
|
65
|
+
end
|
66
|
+
end
|
67
|
+
|
68
|
+
def prt(*args)
|
69
|
+
CLI::UI.puts(*args)
|
70
|
+
end
|
71
|
+
|
72
|
+
def fmt(*args)
|
73
|
+
CLI::UI.fmt(*args)
|
74
|
+
end
|
75
|
+
|
76
|
+
alias ftm fmt
|
77
|
+
|
78
|
+
def log_items(items, title:)
|
79
|
+
box("#{title} (#{items.count})") do
|
80
|
+
return margin(2) do
|
81
|
+
prt "{{warning:No items found}}"
|
82
|
+
end if items.empty?
|
83
|
+
|
84
|
+
items.each do |item|
|
85
|
+
if block_given?
|
86
|
+
say strip(yield item)
|
87
|
+
else
|
88
|
+
say strip(item.to_s)
|
89
|
+
end
|
90
|
+
end
|
91
|
+
end
|
92
|
+
end
|
93
|
+
|
94
|
+
def box(title, color: :reset)
|
95
|
+
margin do
|
96
|
+
CLI::UI::Frame.open(title, color: color) do
|
97
|
+
margin(2) do
|
98
|
+
yield
|
99
|
+
end
|
100
|
+
end
|
101
|
+
end
|
102
|
+
end
|
103
|
+
|
104
|
+
def strip(msg)
|
105
|
+
msg
|
106
|
+
# msg.gsub(current_path, "").gsub(Dir.pwd, ".").chomp
|
107
|
+
end
|
108
|
+
|
109
|
+
def current_path
|
110
|
+
File.join(Dir.pwd, "/")
|
111
|
+
end
|
112
|
+
|
113
|
+
def div(title, **args)
|
114
|
+
CLI::UI::Frame.divider(title, **args)
|
115
|
+
margin { yield }
|
116
|
+
end
|
117
|
+
|
118
|
+
def margin(n = 1)
|
119
|
+
new_line(n)
|
120
|
+
yield
|
121
|
+
new_line(n)
|
122
|
+
end
|
123
|
+
|
124
|
+
def new_line(n = 1)
|
125
|
+
say_plain("\n" * n)
|
126
|
+
end
|
127
|
+
|
128
|
+
def unless_debug
|
129
|
+
yield unless Rfix.debug?
|
130
|
+
end
|
131
|
+
end
|