File: runner.rb

package info (click to toggle)
ruby-launchy 3.1.1-1
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid
  • size: 304 kB
  • sloc: ruby: 1,051; makefile: 6
file content (55 lines) | stat: -rw-r--r-- 1,518 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
# frozen_string_literal: true

require "childprocess"
module Launchy
  # Internal: Run a command in a child process
  #
  class Runner
    def run(cmd, *args)
      unless cmd
        raise Launchy::CommandNotFoundError,
              "No command found to run with args '#{args.join(' ')}'. If this is unexpected, #{Launchy.bug_report_message}"
      end

      if Launchy.dry_run?
        $stdout.puts dry_run(cmd, *args)
      else
        wet_run(cmd, *args)
      end
    end

    def wet_run(cmd, *args)
      argv = shell_commands(cmd, args)
      Launchy.log "ChildProcess: argv => #{argv.inspect}"

      process = ChildProcess.build(*argv)

      process.io.inherit!
      process.leader = true
      process.detach = true
      process.start
    end

    def dry_run(cmd, *args)
      shell_commands(cmd, args).join(" ")
    end

    # cut it down to just the shell commands that will be passed to exec or
    # posix_spawn. The cmd argument is split according to shell rules and the
    # args are not escaped because the whole set is passed to system as *args
    # and in that case system shell escaping rules are not done.
    #
    def shell_commands(cmd, args)
      cmdline = [cmd.to_s.shellsplit]
      cmdline << args.flatten.collect(&:to_s)
      commandline_normalize(cmdline)
    end

    def commandline_normalize(cmdline)
      c = cmdline.flatten!
      c = c.find_all { |a| !a.nil? and a.size.positive? }
      Launchy.log "commandline_normalized => #{c.join(' ')}"
      c
    end
  end
end