github.com/bugraaydogar/snapd@v0.0.0-20210315170335-8c70bb858939/overlord/servicestate/servicestate_test.go (about) 1 // -*- Mode: Go; indent-tabs-mode: t -*- 2 3 /* 4 * Copyright (C) 2015-2020 Canonical Ltd 5 * 6 * This program is free software: you can redistribute it and/or modify 7 * it under the terms of the GNU General Public License version 3 as 8 * published by the Free Software Foundation. 9 * 10 * This program is distributed in the hope that it will be useful, 11 * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 * GNU General Public License for more details. 14 * 15 * You should have received a copy of the GNU General Public License 16 * along with this program. If not, see <http://www.gnu.org/licenses/>. 17 * 18 */ 19 20 package servicestate_test 21 22 import ( 23 "bytes" 24 "fmt" 25 "os" 26 "path/filepath" 27 "strings" 28 29 . "gopkg.in/check.v1" 30 31 "github.com/snapcore/snapd/client" 32 "github.com/snapcore/snapd/dirs" 33 "github.com/snapcore/snapd/overlord/servicestate" 34 "github.com/snapcore/snapd/snap" 35 "github.com/snapcore/snapd/systemd" 36 ) 37 38 type statusDecoratorSuite struct{} 39 40 var _ = Suite(&statusDecoratorSuite{}) 41 42 func (s *statusDecoratorSuite) TestDecorateWithStatus(c *C) { 43 dirs.SetRootDir(c.MkDir()) 44 defer dirs.SetRootDir("") 45 snp := &snap.Info{ 46 SideInfo: snap.SideInfo{ 47 RealName: "foo", 48 Revision: snap.R(1), 49 }, 50 } 51 err := os.MkdirAll(snp.MountDir(), 0755) 52 c.Assert(err, IsNil) 53 err = os.Symlink(snp.Revision.String(), filepath.Join(filepath.Dir(snp.MountDir()), "current")) 54 c.Assert(err, IsNil) 55 56 disabled := false 57 r := systemd.MockSystemctl(func(args ...string) (buf []byte, err error) { 58 switch args[0] { 59 case "show": 60 c.Assert(args[0], Equals, "show") 61 unit := args[2] 62 activeState, unitState := "active", "enabled" 63 if disabled { 64 activeState = "inactive" 65 unitState = "disabled" 66 } 67 if strings.HasSuffix(unit, ".timer") || strings.HasSuffix(unit, ".socket") { 68 return []byte(fmt.Sprintf(`Id=%s 69 ActiveState=%s 70 UnitFileState=%s 71 `, args[2], activeState, unitState)), nil 72 } else { 73 return []byte(fmt.Sprintf(`Id=%s 74 Type=simple 75 ActiveState=%s 76 UnitFileState=%s 77 `, args[2], activeState, unitState)), nil 78 } 79 case "--user": 80 c.Assert(args[1], Equals, "--global") 81 c.Assert(args[2], Equals, "is-enabled") 82 unitState := "enabled\n" 83 if disabled { 84 unitState = "disabled\n" 85 } 86 return bytes.Repeat([]byte(unitState), len(args)-3), nil 87 default: 88 c.Errorf("unexpected systemctl command: %v", args) 89 return nil, fmt.Errorf("should not be reached") 90 } 91 }) 92 defer r() 93 94 sd := servicestate.NewStatusDecorator(nil) 95 96 // not a service 97 app := &client.AppInfo{ 98 Snap: "foo", 99 Name: "app", 100 } 101 snapApp := &snap.AppInfo{Snap: snp, Name: "app"} 102 103 err = sd.DecorateWithStatus(app, snapApp) 104 c.Assert(err, IsNil) 105 106 for _, enabled := range []bool{true, false} { 107 disabled = !enabled 108 109 // service only 110 app = &client.AppInfo{ 111 Snap: snp.InstanceName(), 112 Name: "svc", 113 Daemon: "simple", 114 } 115 snapApp = &snap.AppInfo{ 116 Snap: snp, 117 Name: "svc", 118 Daemon: "simple", 119 DaemonScope: snap.SystemDaemon, 120 } 121 122 err = sd.DecorateWithStatus(app, snapApp) 123 c.Assert(err, IsNil) 124 c.Check(app.Active, Equals, enabled) 125 c.Check(app.Enabled, Equals, enabled) 126 127 // service + timer 128 app = &client.AppInfo{ 129 Snap: snp.InstanceName(), 130 Name: "svc", 131 Daemon: "simple", 132 } 133 snapApp = &snap.AppInfo{ 134 Snap: snp, 135 Name: "svc", 136 Daemon: "simple", 137 DaemonScope: snap.SystemDaemon, 138 } 139 snapApp.Timer = &snap.TimerInfo{ 140 App: snapApp, 141 Timer: "10:00", 142 } 143 144 err = sd.DecorateWithStatus(app, snapApp) 145 c.Assert(err, IsNil) 146 c.Check(app.Active, Equals, enabled) 147 c.Check(app.Enabled, Equals, enabled) 148 c.Check(app.Activators, DeepEquals, []client.AppActivator{ 149 {Name: "svc", Type: "timer", Active: enabled, Enabled: enabled}, 150 }) 151 152 // service with socket 153 app = &client.AppInfo{ 154 Snap: snp.InstanceName(), 155 Name: "svc", 156 Daemon: "simple", 157 } 158 snapApp = &snap.AppInfo{ 159 Snap: snp, 160 Name: "svc", 161 Daemon: "simple", 162 DaemonScope: snap.SystemDaemon, 163 } 164 snapApp.Sockets = map[string]*snap.SocketInfo{ 165 "socket1": { 166 App: snapApp, 167 Name: "socket1", 168 ListenStream: "a.socket", 169 }, 170 } 171 172 err = sd.DecorateWithStatus(app, snapApp) 173 c.Assert(err, IsNil) 174 c.Check(app.Active, Equals, enabled) 175 c.Check(app.Enabled, Equals, enabled) 176 c.Check(app.Activators, DeepEquals, []client.AppActivator{ 177 {Name: "socket1", Type: "socket", Active: enabled, Enabled: enabled}, 178 }) 179 180 // service with D-Bus activation 181 app = &client.AppInfo{ 182 Snap: snp.InstanceName(), 183 Name: "svc", 184 Daemon: "simple", 185 } 186 snapApp = &snap.AppInfo{ 187 Snap: snp, 188 Name: "svc", 189 Daemon: "simple", 190 DaemonScope: snap.SystemDaemon, 191 } 192 snapApp.ActivatesOn = []*snap.SlotInfo{ 193 { 194 Snap: snp, 195 Name: "dbus-slot", 196 Interface: "dbus", 197 Attrs: map[string]interface{}{ 198 "bus": "system", 199 "name": "org.example.Svc", 200 }, 201 }, 202 } 203 204 err = sd.DecorateWithStatus(app, snapApp) 205 c.Assert(err, IsNil) 206 c.Check(app.Active, Equals, enabled) 207 c.Check(app.Enabled, Equals, enabled) 208 c.Check(app.Activators, DeepEquals, []client.AppActivator{ 209 {Name: "org.example.Svc", Type: "dbus", Active: true, Enabled: true}, 210 }) 211 212 // No state is currently extracted for user daemons 213 app = &client.AppInfo{ 214 Snap: snp.InstanceName(), 215 Name: "svc", 216 Daemon: "simple", 217 } 218 snapApp = &snap.AppInfo{ 219 Snap: snp, 220 Name: "svc", 221 Daemon: "simple", 222 DaemonScope: snap.UserDaemon, 223 } 224 snapApp.Sockets = map[string]*snap.SocketInfo{ 225 "socket1": { 226 App: snapApp, 227 Name: "socket1", 228 ListenStream: "a.socket", 229 }, 230 } 231 snapApp.Timer = &snap.TimerInfo{ 232 App: snapApp, 233 Timer: "10:00", 234 } 235 snapApp.ActivatesOn = []*snap.SlotInfo{ 236 { 237 Snap: snp, 238 Name: "dbus-slot", 239 Interface: "dbus", 240 Attrs: map[string]interface{}{ 241 "bus": "session", 242 "name": "org.example.Svc", 243 }, 244 }, 245 } 246 247 err = sd.DecorateWithStatus(app, snapApp) 248 c.Assert(err, IsNil) 249 c.Check(app.Active, Equals, false) 250 c.Check(app.Enabled, Equals, enabled) 251 c.Check(app.Activators, DeepEquals, []client.AppActivator{ 252 {Name: "socket1", Type: "socket", Active: false, Enabled: enabled}, 253 {Name: "svc", Type: "timer", Active: false, Enabled: enabled}, 254 {Name: "org.example.Svc", Type: "dbus", Active: true, Enabled: true}, 255 }) 256 } 257 }