~nskaggs/+junk/xenial-test

« back to all changes in this revision

Viewing changes to src/github.com/juju/juju/worker/uniter/runner/args.go

  • Committer: Nicholas Skaggs
  • Date: 2016-10-24 20:56:05 UTC
  • Revision ID: nicholas.skaggs@canonical.com-20161024205605-z8lta0uvuhtxwzwl
Initi with beta15

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
// Copyright 2012-2014 Canonical Ltd.
 
2
// Licensed under the AGPLv3, see LICENCE file for details.
 
3
 
 
4
package runner
 
5
 
 
6
import (
 
7
        "fmt"
 
8
        "os"
 
9
        "os/exec"
 
10
        "path/filepath"
 
11
        "strings"
 
12
 
 
13
        "github.com/juju/juju/worker/uniter/runner/context"
 
14
        jujuos "github.com/juju/utils/os"
 
15
)
 
16
 
 
17
var windowsSuffixOrder = []string{
 
18
        ".ps1",
 
19
        ".cmd",
 
20
        ".bat",
 
21
        ".exe",
 
22
}
 
23
 
 
24
func lookPath(hook string) (string, error) {
 
25
        hookFile, err := exec.LookPath(hook)
 
26
        if err != nil {
 
27
                if ee, ok := err.(*exec.Error); ok && os.IsNotExist(ee.Err) {
 
28
                        return "", context.NewMissingHookError(hook)
 
29
                }
 
30
                return "", err
 
31
        }
 
32
        return hookFile, nil
 
33
}
 
34
 
 
35
// searchHook will search, in order, hooks suffixed with extensions
 
36
// in windowsSuffixOrder. As windows cares about extensions to determine
 
37
// how to execute a file, we will allow several suffixes, with powershell
 
38
// being default.
 
39
func searchHook(charmDir, hook string) (string, error) {
 
40
        hookFile := filepath.Join(charmDir, hook)
 
41
        if jujuos.HostOS() != jujuos.Windows {
 
42
                // we are not running on windows,
 
43
                // there is no need to look for suffixed hooks
 
44
                return lookPath(hookFile)
 
45
        }
 
46
        for _, suffix := range windowsSuffixOrder {
 
47
                file := fmt.Sprintf("%s%s", hookFile, suffix)
 
48
                foundHook, err := lookPath(file)
 
49
                if err != nil {
 
50
                        if context.IsMissingHookError(err) {
 
51
                                // look for next suffix
 
52
                                continue
 
53
                        }
 
54
                        return "", err
 
55
                }
 
56
                return foundHook, nil
 
57
        }
 
58
        return "", context.NewMissingHookError(hook)
 
59
}
 
60
 
 
61
// hookCommand constructs an appropriate command to be passed to
 
62
// exec.Command(). The exec package uses cmd.exe as default on windows.
 
63
// cmd.exe does not know how to execute ps1 files by default, and
 
64
// powershell needs a few flags to allow execution (-ExecutionPolicy)
 
65
// and propagate error levels (-File). .cmd and .bat files can be run
 
66
// directly.
 
67
func hookCommand(hook string) []string {
 
68
        if jujuos.HostOS() != jujuos.Windows {
 
69
                // we are not running on windows,
 
70
                // just return the hook name
 
71
                return []string{hook}
 
72
        }
 
73
        if strings.HasSuffix(hook, ".ps1") {
 
74
                return []string{
 
75
                        "powershell.exe",
 
76
                        "-NonInteractive",
 
77
                        "-ExecutionPolicy",
 
78
                        "RemoteSigned",
 
79
                        "-File",
 
80
                        hook,
 
81
                }
 
82
        }
 
83
        return []string{hook}
 
84
}