func (s *SSHSuite) testSSHCommandHostAddressRetry(c *gc.C, proxy bool) { m := s.makeMachines(1, c, false) ctx := coretesting.Context(c) var called int next := func() bool { called++ return called < 2 } attemptStarter := &callbackAttemptStarter{next: next} s.PatchValue(&sshHostFromTargetAttemptStrategy, attemptStarter) // Ensure that the ssh command waits for a public address, or the attempt // strategy's Done method returns false. args := []string{"--proxy=" + fmt.Sprint(proxy), "0"} code := cmd.Main(&SSHCommand{}, ctx, args) c.Check(code, gc.Equals, 1) c.Assert(called, gc.Equals, 2) called = 0 attemptStarter.next = func() bool { called++ if called > 1 { s.setAddresses(m[0], c) } return true } code = cmd.Main(&SSHCommand{}, ctx, args) c.Check(code, gc.Equals, 0) c.Assert(called, gc.Equals, 2) }
// Main runs the Command specified by req, and fills in resp. A single command // is run at a time. func (j *Jujuc) Main(req Request, resp *exec.ExecResponse) error { if req.CommandName == "" { return badReqErrorf("command not specified") } if !filepath.IsAbs(req.Dir) { return badReqErrorf("Dir is not absolute") } c, err := j.getCmd(req.ContextId, req.CommandName) if err != nil { return badReqErrorf("%s", err) } var stdin, stdout, stderr bytes.Buffer ctx := &cmd.Context{ Dir: req.Dir, Stdin: &stdin, Stdout: &stdout, Stderr: &stderr, } j.mu.Lock() defer j.mu.Unlock() logger.Infof("running hook tool %q %q", req.CommandName, req.Args) logger.Debugf("hook context id %q; dir %q", req.ContextId, req.Dir) resp.Code = cmd.Main(c, ctx, req.Args) resp.Stdout = stdout.Bytes() resp.Stderr = stderr.Bytes() return nil }
func (s *RelationListSuite) TestRelationList(c *gc.C) { for i, t := range relationListTests { c.Logf("test %d: %s", i, t.summary) hctx := s.GetHookContext(c, t.relid, "") setMembers(hctx.rels[0], t.members0) setMembers(hctx.rels[1], t.members1) com, err := jujuc.NewCommand(hctx, "relation-list") c.Assert(err, gc.IsNil) ctx := testing.Context(c) code := cmd.Main(com, ctx, t.args) c.Logf(bufferString(ctx.Stderr)) c.Assert(code, gc.Equals, t.code) if code == 0 { c.Assert(bufferString(ctx.Stderr), gc.Equals, "") expect := t.out if expect != "" { expect = expect + "\n" } c.Assert(bufferString(ctx.Stdout), gc.Equals, expect) } else { c.Assert(bufferString(ctx.Stdout), gc.Equals, "") expect := fmt.Sprintf(`(.|\n)*error: %s\n`, t.out) c.Assert(bufferString(ctx.Stderr), gc.Matches, expect) } } }
func (s *RelationIdsSuite) TestHelp(c *gc.C) { template := ` usage: %s purpose: list all relation ids with the given relation name options: --format (= smart) specify output format (json|smart|yaml) -o, --output (= "") specify an output file %s`[1:] for relid, t := range map[int]struct { usage, doc string }{ -1: {"relation-ids [options] <name>", ""}, 0: {"relation-ids [options] [<name>]", "\nCurrent default relation name is \"x\".\n"}, 3: {"relation-ids [options] [<name>]", "\nCurrent default relation name is \"y\".\n"}, } { c.Logf("relid %d", relid) hctx := s.GetHookContext(c, relid, "") com, err := jujuc.NewCommand(hctx, "relation-ids") c.Assert(err, gc.IsNil) ctx := testing.Context(c) code := cmd.Main(com, ctx, []string{"--help"}) c.Assert(code, gc.Equals, 0) expect := fmt.Sprintf(template, t.usage, t.doc) c.Assert(bufferString(ctx.Stdout), gc.Equals, expect) c.Assert(bufferString(ctx.Stderr), gc.Equals, "") } }
func (s *RelationListSuite) TestRelationListHelp(c *gc.C) { template := ` usage: relation-list [options] purpose: list relation units options: --format (= smart) specify output format (json|smart|yaml) -o, --output (= "") specify an output file -r (= %s) specify a relation by id %s`[1:] for relid, t := range map[int]struct { usage, doc string }{ -1: {"", "\n-r must be specified when not in a relation hook\n"}, 0: {"peer0:0", ""}, } { c.Logf("test relid %d", relid) hctx := s.GetHookContext(c, relid, "") com, err := jujuc.NewCommand(hctx, "relation-list") c.Assert(err, gc.IsNil) ctx := testing.Context(c) code := cmd.Main(com, ctx, []string{"--help"}) c.Assert(code, gc.Equals, 0) expect := fmt.Sprintf(template, t.usage, t.doc) c.Assert(bufferString(ctx.Stdout), gc.Equals, expect) c.Assert(bufferString(ctx.Stderr), gc.Equals, "") } }
// Main registers subcommands for the juju-metadata executable, and hands over control // to the cmd package. This function is not redundant with main, because it // provides an entry point for testing with arbitrary command line arguments. func Main(args []string) { ctx, err := cmd.DefaultContext() if err != nil { fmt.Fprintf(os.Stderr, "error: %v\n", err) os.Exit(2) } if err := juju.InitJujuHome(); err != nil { fmt.Fprintf(os.Stderr, "error: %s\n", err) os.Exit(2) } metadatacmd := cmd.NewSuperCommand(cmd.SuperCommandParams{ Name: "metadata", UsagePrefix: "juju", Doc: metadataDoc, Purpose: "tools for generating and validating image and tools metadata", Log: &cmd.Log{}}) metadatacmd.Register(&ValidateImageMetadataCommand{}) metadatacmd.Register(&ImageMetadataCommand{}) metadatacmd.Register(&ToolsMetadataCommand{}) metadatacmd.Register(&ValidateToolsMetadataCommand{}) metadatacmd.Register(&SignMetadataCommand{}) os.Exit(cmd.Main(metadatacmd, ctx, args[1:])) }
func (s *CmdSuite) TestUnknownOutputFormat(c *gc.C) { ctx := testing.Context(c) result := cmd.Main(&OutputCommand{}, ctx, []string{"--format", "cuneiform"}) c.Check(result, gc.Equals, 2) c.Check(bufferString(ctx.Stdout), gc.Equals, "") c.Check(bufferString(ctx.Stderr), gc.Matches, ".*: unknown format \"cuneiform\"\n") }
func (s *CmdSuite) TestMainSuccess(c *gc.C) { ctx := testing.Context(c) result := cmd.Main(&TestCommand{Name: "verb"}, ctx, []string{"--option", "success!"}) c.Assert(result, gc.Equals, 0) c.Assert(bufferString(ctx.Stdout), gc.Equals, "success!\n") c.Assert(bufferString(ctx.Stderr), gc.Equals, "") }
func (s *CmdSuite) TestMainRunSilentError(c *gc.C) { ctx := testing.Context(c) result := cmd.Main(&TestCommand{Name: "verb"}, ctx, []string{"--option", "silent-error"}) c.Assert(result, gc.Equals, 1) c.Assert(bufferString(ctx.Stdout), gc.Equals, "") c.Assert(bufferString(ctx.Stderr), gc.Equals, "") }
func (s *GetSuite) TestGetConfig(c *gc.C) { sch := s.AddTestingCharm(c, "dummy") svc := s.AddTestingService(c, "dummy-service", sch) err := svc.UpdateConfigSettings(charm.Settings{"title": "Nearly There"}) c.Assert(err, gc.IsNil) for _, t := range getTests { ctx := coretesting.Context(c) code := cmd.Main(&GetCommand{}, ctx, []string{t.service}) c.Check(code, gc.Equals, 0) c.Assert(ctx.Stderr.(*bytes.Buffer).String(), gc.Equals, "") // round trip via goyaml to avoid being sucked into a quagmire of // map[interface{}]interface{} vs map[string]interface{}. This is // also required if we add json support to this command. buf, err := goyaml.Marshal(t.expected) c.Assert(err, gc.IsNil) expected := make(map[string]interface{}) err = goyaml.Unmarshal(buf, &expected) c.Assert(err, gc.IsNil) actual := make(map[string]interface{}) err = goyaml.Unmarshal(ctx.Stdout.(*bytes.Buffer).Bytes(), &actual) c.Assert(err, gc.IsNil) c.Assert(actual, gc.DeepEquals, expected) } }
func (s *SSHSuite) TestSSHCommand(c *gc.C) { m := s.makeMachines(3, c, true) ch := coretesting.Charms.Dir("dummy") curl := charm.MustParseURL( fmt.Sprintf("local:quantal/%s-%d", ch.Meta().Name, ch.Revision()), ) bundleURL, err := url.Parse("http://bundles.testing.invalid/dummy-1") c.Assert(err, gc.IsNil) dummy, err := s.State.AddCharm(ch, curl, bundleURL, "dummy-1-sha256") c.Assert(err, gc.IsNil) srv := s.AddTestingService(c, "mysql", dummy) s.addUnit(srv, m[0], c) srv = s.AddTestingService(c, "mongodb", dummy) s.addUnit(srv, m[1], c) s.addUnit(srv, m[2], c) for i, t := range sshTests { c.Logf("test %d: %s -> %s\n", i, t.about, t.args) ctx := coretesting.Context(c) jujucmd := cmd.NewSuperCommand(cmd.SuperCommandParams{}) jujucmd.Register(&SSHCommand{}) code := cmd.Main(jujucmd, ctx, t.args) c.Check(code, gc.Equals, 0) c.Check(ctx.Stderr.(*bytes.Buffer).String(), gc.Equals, "") c.Check(ctx.Stdout.(*bytes.Buffer).String(), gc.Equals, t.result) } }
func runCmdLine(c *gc.C, com cmd.Command, args ...string) (code int, stdout, stderr string) { ctx := coretesting.Context(c) code = cmd.Main(com, ctx, args) stdout = ctx.Stdout.(*bytes.Buffer).String() stderr = ctx.Stderr.(*bytes.Buffer).String() c.Logf("args: %#v\ncode: %d\nstdout: %q\nstderr: %q", args, code, stdout, stderr) return }
func (s *SuperCommandSuite) TestDescription(c *gc.C) { jc := cmd.NewSuperCommand(cmd.SuperCommandParams{Name: "jujutest", Purpose: "blow up the death star"}) jc.Register(&TestCommand{Name: "blah"}) ctx := testing.Context(c) code := cmd.Main(jc, ctx, []string{"blah", "--description"}) c.Assert(code, gc.Equals, 0) c.Assert(bufferString(ctx.Stdout), gc.Equals, "blow up the death star\n") }
// assertSetSuccess sets configuration options and checks the expected settings. func assertSetSuccess(c *gc.C, dir string, svc *state.Service, args []string, expect charm.Settings) { ctx := coretesting.ContextForDir(c, dir) code := cmd.Main(&SetCommand{}, ctx, append([]string{"dummy-service"}, args...)) c.Check(code, gc.Equals, 0) settings, err := svc.ConfigSettings() c.Assert(err, gc.IsNil) c.Assert(settings, gc.DeepEquals, expect) }
func (s *ConfigGetSuite) TestAllPlusKey(c *gc.C) { hctx := s.GetHookContext(c, -1, "") com, err := jujuc.NewCommand(hctx, "config-get") c.Assert(err, gc.IsNil) ctx := testing.Context(c) code := cmd.Main(com, ctx, []string{"--all", "--format", "json", "monsters"}) c.Assert(code, gc.Equals, 2) c.Assert(bufferString(ctx.Stderr), gc.Equals, "error: cannot use argument --all together with key \"monsters\"\n") }
func (s *CmdSuite) TestMainHelp(c *gc.C) { for _, arg := range []string{"-h", "--help"} { ctx := testing.Context(c) result := cmd.Main(&TestCommand{Name: "verb"}, ctx, []string{arg}) c.Assert(result, gc.Equals, 0) c.Assert(bufferString(ctx.Stdout), gc.Equals, fullHelp) c.Assert(bufferString(ctx.Stderr), gc.Equals, "") } }
func (s *ToolsMetadataSuite) TestNoTools(c *gc.C) { ctx := coretesting.Context(c) code := cmd.Main(&ToolsMetadataCommand{}, ctx, nil) c.Assert(code, gc.Equals, 1) stdout := ctx.Stdout.(*bytes.Buffer).String() c.Assert(stdout, gc.Matches, "Finding tools in .*\n") stderr := ctx.Stderr.(*bytes.Buffer).String() c.Assert(stderr, gc.Matches, "error: no tools available\n") }
func (s *CmdSuite) TestStdin(c *gc.C) { const phrase = "Do you, Juju?" ctx := testing.Context(c) ctx.Stdin = bytes.NewBuffer([]byte(phrase)) result := cmd.Main(&TestCommand{Name: "verb"}, ctx, []string{"--option", "echo"}) c.Assert(result, gc.Equals, 0) c.Assert(bufferString(ctx.Stdout), gc.Equals, phrase) c.Assert(bufferString(ctx.Stderr), gc.Equals, "") }
func (s *SuperCommandSuite) TestHelpWithPrefix(c *gc.C) { jc := cmd.NewSuperCommand(cmd.SuperCommandParams{Name: "jujutest", UsagePrefix: "juju"}) jc.Register(&TestCommand{Name: "blah"}) ctx := testing.Context(c) code := cmd.Main(jc, ctx, []string{"blah", "--help"}) c.Assert(code, gc.Equals, 0) stripped := strings.Replace(bufferString(ctx.Stdout), "\n", "", -1) c.Assert(stripped, gc.Matches, ".*usage: juju jujutest blah.*blah-doc.*") }
func (s *BootstrapSuite) TestMissingToolsError(c *gc.C) { s.setupAutoUploadTest(c, "1.8.3", "precise") context := coretesting.Context(c) code := cmd.Main(&BootstrapCommand{}, context, nil) c.Assert(code, gc.Equals, 1) errText := context.Stderr.(*bytes.Buffer).String() expectedErrText := "error: cannot upload bootstrap tools: Juju cannot bootstrap because no tools are available for your environment(.|\n)*" c.Assert(errText, gc.Matches, expectedErrText) }
// Main registers subcommands for the juju-local executable. func Main(args []string) { ctx, err := cmd.DefaultContext() if err != nil { logger.Debugf("error: %v\n", err) os.Exit(2) } plugin := jujuLocalPlugin() os.Exit(cmd.Main(plugin, ctx, args[1:])) }
func (s *EndpointSuite) TestEndpoint(c *gc.C) { ctx := coretesting.Context(c) code := cmd.Main(&EndpointCommand{}, ctx, []string{}) c.Check(code, gc.Equals, 0) c.Assert(ctx.Stderr.(*bytes.Buffer).String(), gc.Equals, "") output := string(ctx.Stdout.(*bytes.Buffer).Bytes()) info := s.APIInfo(c) c.Assert(output, gc.Equals, fmt.Sprintf("%s\n", info.Addrs[0])) }
func (s *OwnerGetSuite) TestOutputFormat(c *gc.C) { for _, t := range ownerGetTests { com := s.createCommand(c) ctx := testing.Context(c) code := cmd.Main(com, ctx, t.args) c.Assert(code, gc.Equals, 0) c.Assert(bufferString(ctx.Stderr), gc.Equals, "") c.Assert(bufferString(ctx.Stdout), gc.Matches, t.out) } }
func (s *CmdSuite) TestMainInitError(c *gc.C) { for _, t := range initErrorTests { ctx := testing.Context(c) result := cmd.Main(t.c, ctx, []string{"--unknown"}) c.Assert(result, gc.Equals, 2) c.Assert(bufferString(ctx.Stdout), gc.Equals, "") expected := "error: flag provided but not defined: --unknown\n" c.Assert(bufferString(ctx.Stderr), gc.Equals, expected) } }
func (s *SuperCommandSuite) TestLogging(c *gc.C) { jc := cmd.NewSuperCommand(cmd.SuperCommandParams{Name: "jujutest", Log: &cmd.Log{}}) jc.Register(&TestCommand{Name: "blah"}) ctx := testing.Context(c) code := cmd.Main(jc, ctx, []string{"blah", "--option", "error", "--debug"}) c.Assert(code, gc.Equals, 1) c.Assert(bufferString(ctx.Stderr), gc.Matches, `^.* running juju-.* .* ERROR .* BAM! `) }
func (s *ValidateToolsMetadataSuite) TestOpenstackLocalMetadataNoMatch(c *gc.C) { s.makeLocalMetadata(c, "1.11.4", "region-2", "raring", "some-auth-url") ctx := coretesting.Context(c) code := cmd.Main( &ValidateToolsMetadataCommand{}, ctx, []string{ "-p", "openstack", "-s", "precise", "-r", "region-2", "-u", "some-auth-url", "-d", s.metadataDir}, ) c.Assert(code, gc.Equals, 1) code = cmd.Main( &ValidateToolsMetadataCommand{}, ctx, []string{ "-p", "openstack", "-s", "raring", "-r", "region-3", "-u", "some-auth-url", "-d", s.metadataDir}, ) c.Assert(code, gc.Equals, 1) errOut := ctx.Stderr.(*bytes.Buffer).String() strippedOut := strings.Replace(errOut, "\n", "", -1) c.Check(strippedOut, gc.Matches, `.*Resolve Metadata:.*`) }
func (s *ValidateToolsMetadataSuite) TestEc2LocalMetadataNoMatch(c *gc.C) { s.setupEc2LocalMetadata(c, "us-east-1") ctx := coretesting.Context(c) code := cmd.Main( &ValidateToolsMetadataCommand{}, ctx, []string{ "-p", "ec2", "-s", "raring", "-r", "us-west-1", "-u", "https://ec2.us-west-1.amazonaws.com", "-d", s.metadataDir}, ) c.Assert(code, gc.Equals, 1) code = cmd.Main( &ValidateToolsMetadataCommand{}, ctx, []string{ "-p", "ec2", "-s", "precise", "-r", "region", "-u", "https://ec2.region.amazonaws.com", "-d", s.metadataDir}, ) c.Assert(code, gc.Equals, 1) errOut := ctx.Stderr.(*bytes.Buffer).String() strippedOut := strings.Replace(errOut, "\n", "", -1) c.Check(strippedOut, gc.Matches, `.*Resolve Metadata:.*`) }
func (s *OwnerGetSuite) TestOutputPath(c *gc.C) { com := s.createCommand(c) ctx := testing.Context(c) code := cmd.Main(com, ctx, []string{"--output", "some-file", "tag"}) c.Assert(code, gc.Equals, 0) c.Assert(bufferString(ctx.Stderr), gc.Equals, "") c.Assert(bufferString(ctx.Stdout), gc.Equals, "") content, err := ioutil.ReadFile(filepath.Join(ctx.Dir, "some-file")) c.Assert(err, gc.IsNil) c.Assert(string(content), gc.Equals, "test-owner\n") }
func (s *ValidateToolsMetadataSuite) TestEc2LocalMetadataUsingEnvironment(c *gc.C) { s.setupEc2LocalMetadata(c, "us-east-1") ctx := coretesting.Context(c) code := cmd.Main( &ValidateToolsMetadataCommand{}, ctx, []string{"-e", "ec2", "-j", "1.11.4", "-d", s.metadataDir}, ) c.Assert(code, gc.Equals, 0) errOut := ctx.Stdout.(*bytes.Buffer).String() strippedOut := strings.Replace(errOut, "\n", "", -1) c.Check(strippedOut, gc.Matches, `Matching Tools Versions:.*Resolve Metadata.*`) }
func (s *ValidateToolsMetadataSuite) TestJustDirectory(c *gc.C) { s.makeLocalMetadata(c, version.Current.Number.String(), "region-2", "raring", "some-auth-url") ctx := coretesting.Context(c) code := cmd.Main( &ValidateToolsMetadataCommand{}, ctx, []string{"-s", "raring", "-d", s.metadataDir}, ) c.Assert(code, gc.Equals, 0) errOut := ctx.Stdout.(*bytes.Buffer).String() strippedOut := strings.Replace(errOut, "\n", "", -1) c.Check(strippedOut, gc.Matches, `Matching Tools Versions:.*Resolve Metadata.*`) }