github.com/niedbalski/juju@v0.0.0-20190215020005-8ff100488e47/cmd/juju/action/status_test.go (about) 1 // Copyright 2014-2015 Canonical Ltd. 2 // Licensed under the AGPLv3, see LICENCE file for details. 3 4 package action_test 5 6 import ( 7 "bytes" 8 "time" 9 10 "github.com/juju/cmd" 11 "github.com/juju/cmd/cmdtesting" 12 jc "github.com/juju/testing/checkers" 13 gc "gopkg.in/check.v1" 14 15 "github.com/juju/juju/apiserver/params" 16 "github.com/juju/juju/cmd/juju/action" 17 ) 18 19 type StatusSuite struct { 20 BaseActionSuite 21 subcommand cmd.Command 22 } 23 24 var _ = gc.Suite(&StatusSuite{}) 25 26 func (s *StatusSuite) SetUpTest(c *gc.C) { 27 s.BaseActionSuite.SetUpTest(c) 28 s.subcommand, _ = action.NewStatusCommandForTest(s.store) 29 } 30 31 func (s *StatusSuite) TestRun(c *gc.C) { 32 prefix := "deadbeef" 33 fakeid := prefix + "-0000-4000-8000-feedfacebeef" 34 fakeid2 := prefix + "-0001-4000-8000-feedfacebeef" 35 faketag := "action-" + fakeid 36 faketag2 := "action-" + fakeid2 37 38 emptyArgs := []string{} 39 emptyPrefixArgs := []string{} 40 prefixArgs := []string{prefix} 41 result1 := []params.ActionResult{{Status: "some-random-status", Action: ¶ms.Action{Tag: faketag, Name: "fakeName"}}} 42 result2 := []params.ActionResult{{Status: "a status", Action: ¶ms.Action{Tag: faketag2, Name: "fakeName2"}}, {Status: "another status"}} 43 errResult := []params.ActionResult{{Status: "", Error: ¶ms.Error{Message: "an error"}}} 44 45 errNotFound := "no actions found" 46 errNotFoundForPrefix := `no actions found matching prefix "` + prefix + `"` 47 errFoundTagButNoResults := `identifier "` + prefix + `" matched action\(s\) \[.*\], but found no results` 48 49 nameArgs := []string{"--name", "action_name"} 50 resultMany := params.ActionsByNames{[]params.ActionsByName{{ 51 Name: "1", 52 }, { 53 Name: "2", 54 }}} 55 56 resultOne := params.ActionsByNames{[]params.ActionsByName{{ 57 Name: "action_name", 58 Actions: result1, 59 }}} 60 61 errNames := ¶ms.Error{ 62 Message: "whoops:", 63 } 64 65 resultOneError := params.ActionsByNames{[]params.ActionsByName{{ 66 Error: errNames, 67 }}} 68 69 tests := []statusTestCase{ 70 {expectError: errNotFound}, 71 {args: emptyArgs, expectError: errNotFound}, 72 {args: emptyArgs, tags: tagsForIdPrefix("", faketag, faketag2), results: result2}, 73 {args: emptyPrefixArgs, expectError: errNotFound}, 74 {args: emptyPrefixArgs, tags: tagsForIdPrefix("", faketag, faketag2), results: result2}, 75 {args: prefixArgs, expectError: errNotFoundForPrefix}, 76 {args: prefixArgs, expectError: errNotFoundForPrefix, tags: tagsForIdPrefix(prefix)}, 77 {args: prefixArgs, expectError: errNotFoundForPrefix, tags: tagsForIdPrefix(prefix, "bb", "bc")}, 78 {args: prefixArgs, expectError: errFoundTagButNoResults, tags: tagsForIdPrefix(prefix, faketag, faketag2)}, 79 {args: prefixArgs, expectError: errFoundTagButNoResults, tags: tagsForIdPrefix(prefix, faketag)}, 80 {args: prefixArgs, tags: tagsForIdPrefix(prefix, faketag), results: result1}, 81 {args: prefixArgs, tags: tagsForIdPrefix(prefix, faketag, faketag2), results: result2}, 82 {args: nameArgs, actionsByNames: resultMany, expectError: "expected one result got 2"}, 83 {args: nameArgs, actionsByNames: resultOneError, expectError: errNames.Message}, 84 {args: nameArgs, actionsByNames: params.ActionsByNames{[]params.ActionsByName{{Name: "action_name"}}}, expectError: "no actions were found for name action_name"}, 85 {args: nameArgs, actionsByNames: resultOne, results: result1}, 86 {args: prefixArgs, tags: tagsForIdPrefix(prefix, faketag), results: errResult}, 87 } 88 89 for i, test := range tests { 90 c.Logf("iteration %d, test case %+v", i, test) 91 s.runTestCase(c, test) 92 } 93 } 94 95 func (s *StatusSuite) runTestCase(c *gc.C, tc statusTestCase) { 96 for _, modelFlag := range s.modelFlags { 97 fakeClient := makeFakeClient( 98 0*time.Second, // No API delay 99 5*time.Second, // 5 second test timeout 100 tc.tags, 101 tc.results, 102 tc.actionsByNames, 103 "", // No API error 104 ) 105 106 restore := s.patchAPIClient(fakeClient) 107 defer restore() 108 109 s.subcommand, _ = action.NewStatusCommandForTest(s.store) 110 args := append([]string{modelFlag, "admin"}, tc.args...) 111 ctx, err := cmdtesting.RunCommand(c, s.subcommand, args...) 112 if tc.expectError == "" { 113 c.Assert(err, jc.ErrorIsNil) 114 } else { 115 c.Assert(err, gc.ErrorMatches, tc.expectError) 116 } 117 if len(tc.results) > 0 { 118 out := &bytes.Buffer{} 119 checkActionResultsMap(c, tc.results) 120 err := cmd.FormatYaml(out, action.ActionResultsToMap(tc.results)) 121 c.Check(err, jc.ErrorIsNil) 122 c.Check(ctx.Stdout.(*bytes.Buffer).String(), gc.Equals, out.String()) 123 c.Check(ctx.Stderr.(*bytes.Buffer).String(), gc.Equals, "") 124 } 125 } 126 } 127 128 func checkActionResultsMap(c *gc.C, results []params.ActionResult) { 129 requiredOutputFields := []string{"status", "completed at"} 130 actionFields := []string{"action", "id", "unit"} 131 132 actionResults := action.ActionResultsToMap(results) 133 134 for i, result := range results { 135 a := actionResults["actions"].([]map[string]interface{})[i] 136 137 for _, field := range requiredOutputFields { 138 c.Logf("checking for presence of result output field: %s", field) 139 c.Check(a[field], gc.NotNil) 140 } 141 142 if result.Action != nil { 143 for _, field := range actionFields { 144 c.Logf("checking for presence of action output field: %s", field) 145 c.Check(a[field], gc.NotNil) 146 } 147 } 148 149 if result.Error != nil { 150 c.Check(a["error"], gc.NotNil) 151 } 152 } 153 } 154 155 type statusTestCase struct { 156 args []string 157 expectError string 158 tags params.FindTagsResults 159 results []params.ActionResult 160 actionsByNames params.ActionsByNames 161 }