natty-ui 0.31.0 → 0.32.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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 5b2d8212f4b987cd05c8ce904cdde26e0a0228c9fe360a36dfad04b0e29bd7b6
4
- data.tar.gz: 8a3cd4de41e7ae69e18b6bf4e5437166f0c45fccf329009ebd0ecefd90a72f70
3
+ metadata.gz: 92532c7a8557373cb4e26efb2a0bae197e1da2daddac5853ef40800c7cfbf344
4
+ data.tar.gz: 3da178c8e00a752802e8cf1fc4822ce6d187516fc7af5af31e03b85b123fd348
5
5
  SHA512:
6
- metadata.gz: fe766477cf1ee36fad283300a659ed4bbc5e55a56e4d7b25383359f9e6616bac1179729ddda15a2c95e58a011dd185c3b419595554197a7fae6edf57f1a02b2c
7
- data.tar.gz: 40c4b083965158a22a39f171e897f40d0e2e6ee2d5ff4a601ec0015dfce9a523882e45a68f2b3208aa623effaef7d563287252eca388fb033325fb404064fb3d
6
+ metadata.gz: 0e41a869ea4dfde35449314f95662e2fcb837f50a76ab49cdd9e0f7cc462c5c12481e83e2eec66029468b2ef91d9f05e56f3702e0d488329c0fb3e1ee61f4431
7
+ data.tar.gz: da9d3545c79c99d6d09cc924a2d0dcbff6e697c264228a8ec657103c2fda7fc77583e7a5fb60db04f3a3189fd7161059e9841d155038f83cd9de88f88ee6cf65
data/README.md CHANGED
@@ -4,7 +4,7 @@ This is the beautiful, nice, nifty, fancy, neat, pretty, cool, rich, lovely, nat
4
4
 
5
5
  - Gem: [rubygems.org](https://rubygems.org/gems/natty-ui)
6
6
  - Source: [codeberg.org](https://codeberg.org/mblumtritt/natty-ui)
7
- - Help: [rubydoc.info](https://rubydoc.info/gems/natty-ui/NattyUI)
7
+ - Help: [rubydoc.info](https://rubydoc.info/gems/natty-ui/index)
8
8
 
9
9
  ## Features
10
10
 
@@ -28,7 +28,7 @@ This is the beautiful, nice, nifty, fancy, neat, pretty, cool, rich, lovely, nat
28
28
 
29
29
  ## Help
30
30
 
31
- 📕 See the [online help](https://rubydoc.info/gems/natty-ui/NattyUI) and have a look at the [examples](./examples/) directory to learn from code.
31
+ 📕 See the [online help](https://rubydoc.info/gems/natty-ui/index) and have a look at the [examples](./examples/) directory to learn from code.
32
32
 
33
33
  ### Run Examples
34
34
 
@@ -104,11 +104,11 @@ module NattyUI
104
104
  ansi: Terminal.ansi?,
105
105
  ignore_newline: ignore_newline
106
106
  )
107
-
107
+ tail = options[:tail] and lines = lines.to_a.last(tail)
108
108
  @__eol ||= Terminal.ansi? ? "\e[m\n" : "\n"
109
109
 
110
110
  if (align = options[:align]).nil?
111
- lines.each do |line|
111
+ lines.each do |line, _|
112
112
  Terminal.print(prefix, line, suffix, @__eol, bbcode: false)
113
113
  @lines_written += 1
114
114
  prefix, prefix_next = prefix_next, nil if prefix_next
@@ -578,29 +578,74 @@ module NattyUI
578
578
  block ? __with(progress, &block) : progress
579
579
  end
580
580
 
581
- # Run a shell program
581
+ # Execute a program.
582
+ #
583
+ # @example Execute a simple command
584
+ # ui.sh 'ls'
585
+ #
586
+ # @example Execute a command wih arguments
587
+ # ret = ui.sh('curl', '--version')
588
+ # raise('Curl not found') unless ret&.success?
589
+ #
590
+ # @example Execute shell commands
591
+ # ui.sh "mkdir 'test' && cd 'test'"
582
592
  #
583
- # @return [Process::Status] when command was executed
593
+ # @example Execute a command with environment variables
594
+ # ui.sh({'ENV' => 'test'}, 'rails')
595
+ #
596
+ # @see run
597
+ #
598
+ # @param cmd [String]
599
+ # command and optional arguments
600
+ # @param shell [true,false]
601
+ # whether a seperate shell should be created
602
+ # @param input [IO,#to_io,Array,#each,#to_a,#to_s,nil]
603
+ # input piped to the command
604
+ # @param preserve_spaces [true,false]
605
+ # whether the spaces and tabs of the output should be preserve
606
+ # @return [Process::Status]
607
+ # when command was executed
608
+ # @return [nil]
609
+ # in error case (like command not found)
610
+ def sh(*cmd, shell: false, input: nil, preserve_spaces: false)
611
+ ShellRenderer.sh(self, cmd, shell, input, preserve_spaces)
612
+ end
613
+
614
+ # Execute a shell program and return output. Limit the lines displayed.
615
+ #
616
+ # @example Capture output and error
617
+ # status, out, err = ui.run('ls ./ && ls ./this_does_not_exist')
618
+ # # => #<Process::Status: pid 25562 exit 1>
619
+ # # => [...] # the output of first `ls`
620
+ # # => ["ls: ./this_does_not_exist: No such file or directory"]
621
+ #
622
+ # @see sh
623
+ #
624
+ # @param cmd (see sh)
625
+ # @param shell (see sh)
626
+ # @param input (see sh)
627
+ # @param preserve_spaces (see sh)
628
+ # @param max_lines [Integer] limit of displayed lines
629
+ # @return [[Process::Status, Array<String>, Array<String>]]
630
+ # process status, output and error output when command was executed
584
631
  # @return [nil] in error case (like command not found)
585
- def sh(*cmd, shell: false, input: nil)
586
- m = (theme = Theme.current).mark(:sh_out)
587
- opts_out = {
588
- bbcode: false,
589
- prefix: "#{m}#{theme.sh_out_style}",
590
- prefix_width: m.width
591
- }
592
- m = theme.mark(:sh_err)
593
- opts_err = {
594
- bbcode: false,
595
- prefix: "#{m}#{theme.sh_err_style}",
596
- prefix_width: m.width
597
- }
598
- ShellCommand.call(*cmd, shell: shell, input: input) do |line, kind|
599
- puts(
600
- line.gsub("\t", '    ').gsub(/[[:space:]]/, ' '),
601
- **(kind == :error ? opts_err : opts_out)
632
+ def run(
633
+ *cmd,
634
+ shell: false,
635
+ input: nil,
636
+ preserve_spaces: false,
637
+ max_lines: 10
638
+ )
639
+ result =
640
+ ShellRenderer.run(
641
+ self,
642
+ cmd,
643
+ shell,
644
+ input,
645
+ preserve_spaces,
646
+ max_lines.clamp(1, Terminal.rows)
602
647
  )
603
- end
648
+ result if result[0]
604
649
  end
605
650
 
606
651
  #
@@ -755,7 +800,7 @@ module NattyUI
755
800
  # key code/s a user can input to return negative resault
756
801
  #
757
802
  # @return [true, false]
758
- # wheter the user inputs a positive result
803
+ # whether the user inputs a positive result
759
804
  #
760
805
  # @overload await(yes: 'Enter', no: 'Esc', &block)
761
806
  # @param yes [String, Enumerable<String>]
@@ -767,7 +812,7 @@ module NattyUI
767
812
  # temporary displayed section (section will be erased after input)
768
813
  #
769
814
  # @return [true, false]
770
- # wheter the user inputs a positive result
815
+ # whether the user inputs a positive result
771
816
  # @return nil
772
817
  # in error case
773
818
  #
@@ -836,7 +881,7 @@ module NattyUI
836
881
  # r: 'Rio',
837
882
  # abortable: true
838
883
  # ) { ui.puts 'Which terminal emulator do you like?' }
839
- # # => wheter the user selected: :k, :i, :g, :t, :r
884
+ # # => whether the user selected: :k, :i, :g, :t, :r
840
885
  # # => nil, when the user aborted
841
886
  # @param [#to_s] choices
842
887
  # one or more alternatives to select from
@@ -986,7 +1031,6 @@ module NattyUI
986
1031
  dir = __dir__
987
1032
  autoload :Framed, "#{dir}/framed.rb"
988
1033
  autoload :Section, "#{dir}/section.rb"
989
- autoload :ShellCommand, "#{dir}/shell_command.rb"
990
1034
  autoload :Table, "#{dir}/table.rb"
991
1035
  autoload :Task, "#{dir}/task.rb"
992
1036
  autoload :Temporary, "#{dir}/temporary.rb"
@@ -1003,11 +1047,11 @@ module NattyUI
1003
1047
  autoload :CompactLSRenderer, "#{dir}/ls_renderer.rb"
1004
1048
  autoload :HBarsRenderer, "#{dir}/hbars_renderer.rb"
1005
1049
  autoload :LSRenderer, "#{dir}/ls_renderer.rb"
1050
+ autoload :ShellRenderer, "#{dir}/shell_renderer.rb"
1006
1051
  autoload :VBarsRenderer, "#{dir}/vbars_renderer.rb"
1007
1052
 
1008
1053
  private_constant(
1009
1054
  :Framed,
1010
- :ShellCommand,
1011
1055
  :Utils,
1012
1056
  # -
1013
1057
  :Choice,
@@ -1020,6 +1064,7 @@ module NattyUI
1020
1064
  :CompactLSRenderer,
1021
1065
  :HBarsRenderer,
1022
1066
  :LSRenderer,
1067
+ :ShellRenderer,
1023
1068
  :VBarsRenderer
1024
1069
  )
1025
1070
  end
@@ -5,7 +5,7 @@ module NattyUI
5
5
  options = options.except(:in, :out, :err)
6
6
  env = (cmd[0].is_a?(Hash) ? cmd.shift.dup : {}).freeze
7
7
  if shell
8
- cmd = cmd.map! { _escape(it) }.join(' ')
8
+ cmd = cmd.map! { _escape(_1) }.join(' ')
9
9
  elsif cmd.size == 1 && cmd[0].include?(' ')
10
10
  cmd = cmd[0]
11
11
  end
@@ -119,7 +119,7 @@ module NattyUI
119
119
  if enum.respond_to?(:enum_for)
120
120
  enum.enum_for(:each)
121
121
  else
122
- Enumerator.new { |y| enum.each { y << it } }
122
+ Enumerator.new { |y| enum.each { y << _1 } }
123
123
  end
124
124
  end
125
125
  end
@@ -0,0 +1,92 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative 'theme'
4
+ require_relative 'shell_command'
5
+
6
+ module NattyUI
7
+ module ShellRenderer
8
+ def self.sh(parent, cmd, shell, input, space)
9
+ opts_out, opts_err = opts_fom(Theme.current)
10
+ ShellCommand.call(*cmd, shell: shell, input: input) do |line, kind|
11
+ parent.puts(
12
+ space ? line.gsub("\t", '    ').gsub(/[[:space:]]/, ' ') : line,
13
+ **(kind == :error ? opts_err : opts_out)
14
+ )
15
+ end
16
+ end
17
+
18
+ if Terminal.ansi?
19
+ def self.opts_fom(theme)
20
+ out = theme.mark(:sh_out)
21
+ err = theme.mark(:sh_err)
22
+ [
23
+ {
24
+ bbcode: false,
25
+ prefix: "#{out}#{theme.sh_out_style}",
26
+ prefix_width: out.width
27
+ },
28
+ {
29
+ bbcode: false,
30
+ prefix: "#{err}#{theme.sh_err_style}",
31
+ prefix_width: err.width
32
+ }
33
+ ]
34
+ end
35
+
36
+ def self.run(parent, cmd, shell, input, space, tail)
37
+ theme = Theme.current
38
+ opref = "#{theme.mark(:sh_out)}#{theme.sh_out_style}"
39
+ epref = "#{theme.mark(:sh_err)}#{theme.sh_err_style}"
40
+ out, err, show = [], [], []
41
+ start = NattyUI.lines_written
42
+ [
43
+ ShellCommand.call(*cmd, shell: shell, input: input) do |line, kind|
44
+ start = NattyUI.back_to_line(start)
45
+ ol = space ? line.gsub("\t", '    ').gsub(/[[:space:]]/, ' ') : line
46
+ if kind == :error
47
+ err << line
48
+ show << "#{epref}#{ol}"
49
+ else
50
+ out << line
51
+ show << "#{opref}#{ol}"
52
+ end
53
+ parent.puts(*show, bbcode: false, tail: tail)
54
+ end,
55
+ out,
56
+ err
57
+ ]
58
+ end
59
+ else
60
+ def self.opts_fom(theme)
61
+ out = theme.mark(:sh_out)
62
+ err = theme.mark(:sh_err)
63
+ [
64
+ { bbcode: false, prefix: out, prefix_width: out.width },
65
+ { bbcode: false, prefix: err, prefix_width: err.width }
66
+ ]
67
+ end
68
+
69
+ def self.run(parent, cmd, shell, input, _tail)
70
+ theme = Theme.current
71
+ opref, epref = theme.mark(:sh_out), theme.mark(:sh_err)
72
+ out, err = [], []
73
+ [
74
+ ShellCommand.call(*cmd, shell: shell, input: input) do |line, kind|
75
+ ol = line.gsub("\t", '    ').gsub(/[[:space:]]/, ' ')
76
+ if kind == :error
77
+ err << line
78
+ parent.puts("#{epref}#{ol}", bbcode: false)
79
+ else
80
+ out << line
81
+ parent.puts("#{opref}#{ol}", bbcode: false)
82
+ end
83
+ end,
84
+ out,
85
+ err
86
+ ]
87
+ end
88
+ end
89
+ end
90
+
91
+ private_constant :ShellRenderer
92
+ end
@@ -2,5 +2,5 @@
2
2
 
3
3
  module NattyUI
4
4
  # The version number of the gem.
5
- VERSION = '0.31.0'
5
+ VERSION = '0.32.0'
6
6
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: natty-ui
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.31.0
4
+ version: 0.32.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Mike Blumtritt
@@ -70,6 +70,7 @@ files:
70
70
  - lib/natty-ui/progress.rb
71
71
  - lib/natty-ui/section.rb
72
72
  - lib/natty-ui/shell_command.rb
73
+ - lib/natty-ui/shell_renderer.rb
73
74
  - lib/natty-ui/table.rb
74
75
  - lib/natty-ui/table_renderer.rb
75
76
  - lib/natty-ui/task.rb
@@ -103,7 +104,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
103
104
  - !ruby/object:Gem::Version
104
105
  version: '0'
105
106
  requirements: []
106
- rubygems_version: 3.6.9
107
+ rubygems_version: 3.7.2
107
108
  specification_version: 4
108
109
  summary: This is the beautiful, nice, nifty, fancy, neat, pretty, cool, rich, lovely,
109
110
  natty user interface you like to have for your CLI.