1b630cdd1001b7548c7db299223292c1dae6a11d
[ric-plt/alarm-go.git] / cli / alarm-cli.go
1 package main
2
3 import (
4         "bytes"
5         "encoding/json"
6         "fmt"
7         "io/ioutil"
8         "net/http"
9         "os"
10         "strconv"
11         "sync"
12         "time"
13
14         "gerrit.o-ran-sc.org/r/ric-plt/alarm-go/alarm"
15         clientruntime "github.com/go-openapi/runtime/client"
16         "github.com/go-openapi/strfmt"
17         "github.com/jedib0t/go-pretty/table"
18         "github.com/prometheus/alertmanager/api/v2/client"
19         "github.com/prometheus/alertmanager/api/v2/client/alert"
20         "github.com/prometheus/alertmanager/api/v2/models"
21         "github.com/spf13/viper"
22         "github.com/thatisuday/commando"
23 )
24
25 type CliAlarmDefinitions struct {
26         AlarmDefinitions []*alarm.AlarmDefinition `json:"alarmdefinitions"`
27 }
28
29 type AlarmClient struct {
30         alarmer *alarm.RICAlarm
31 }
32
33 type RicPerfAlarmObjects struct {
34         AlarmObjects []*alarm.Alarm `json:"alarmobjects"`
35 }
36
37 type AlarmNotification struct {
38         alarm.AlarmMessage
39         alarm.AlarmDefinition
40 }
41
42 var CLIPerfAlarmObjects map[int]*alarm.Alarm
43
44 var wg sync.WaitGroup
45
46 var CliPerfAlarmDefinitions CliAlarmDefinitions
47
48 const (
49         Raise             string = "RAISE"
50         Clear             string = "CLEAR"
51         End               string = "END"
52         PeakTestDuration  int    = 60
53         OneSecondDuration int    = 1
54 )
55
56 func main() {
57         alarmManagerHost := "localhost"
58         if h := os.Getenv("ALARM_MANAGER_HOST"); h != "" {
59                 alarmManagerHost = h
60         }
61
62         alertManagerHost := "localhost"
63         if h := os.Getenv("ALERT_MANAGER_HOST"); h != "" {
64                 alertManagerHost = h
65         }
66
67         // configure commando
68         commando.
69                 SetExecutableName("alarm-cli").
70                 SetVersion("1.0.0").
71                 SetDescription("This CLI tool provides management interface to SEP alarm system")
72
73         // Get active alarms
74         commando.
75                 Register("active").
76                 SetShortDescription("Displays the SEP active alarms").
77                 SetDescription("This command displays more information about the SEP active alarms").
78                 AddFlag("host", "Alarm manager host address", commando.String, alarmManagerHost).
79                 AddFlag("port", "Alarm manager host address", commando.String, "8080").
80                 SetAction(func(args map[string]commando.ArgValue, flags map[string]commando.FlagValue) {
81                         displayAlarms(getAlarms(flags, "active"), false)
82                 })
83
84         // Get alarm history
85         commando.
86                 Register("history").
87                 SetShortDescription("Displays the SEP alarm history").
88                 SetDescription("This command displays more information about the SEP alarm history").
89                 AddFlag("host", "Alarm manager host address", commando.String, alarmManagerHost).
90                 AddFlag("port", "Alarm manager host address", commando.String, "8080").
91                 SetAction(func(args map[string]commando.ArgValue, flags map[string]commando.FlagValue) {
92                         displayAlarms(getAlarms(flags, "history"), true)
93                 })
94
95         // Raise an alarm
96         commando.
97                 Register("raise").
98                 SetShortDescription("Raises alarm with given parameters").
99                 AddFlag("moid", "Managed object Id", commando.String, nil).
100                 AddFlag("apid", "Application Id", commando.String, nil).
101                 AddFlag("sp", "Specific problem Id", commando.Int, nil).
102                 AddFlag("severity", "Perceived severity", commando.String, nil).
103                 AddFlag("iinfo", "Application identifying info", commando.String, nil).
104                 AddFlag("aai", "Application additional info", commando.String, "-").
105                 AddFlag("host", "Alarm manager host address", commando.String, alarmManagerHost).
106                 AddFlag("port", "Alarm manager host address", commando.String, "8080").
107                 AddFlag("if", "http or rmr used as interface", commando.String, "http").
108                 SetAction(func(args map[string]commando.ArgValue, flags map[string]commando.FlagValue) {
109                         postAlarm(flags, readAlarmParams(flags, false), alarm.AlarmActionRaise, nil)
110                 })
111
112         // Clear an alarm
113         commando.
114                 Register("clear").
115                 SetShortDescription("Raises alarm with given parameters").
116                 AddFlag("moid", "Managed object Id", commando.String, nil).
117                 AddFlag("apid", "Application Id", commando.String, nil).
118                 AddFlag("sp", "Specific problem Id", commando.Int, nil).
119                 AddFlag("iinfo", "Application identifying info", commando.String, nil).
120                 AddFlag("host", "Alarm manager host address", commando.String, alarmManagerHost).
121                 AddFlag("port", "Alarm manager host address", commando.String, "8080").
122                 AddFlag("if", "http or rmr used as interface", commando.String, "http").
123                 SetAction(func(args map[string]commando.ArgValue, flags map[string]commando.FlagValue) {
124                         postAlarm(flags, readAlarmParams(flags, true), alarm.AlarmActionClear, nil)
125                 })
126
127         // Configure an alarm manager
128         commando.
129                 Register("configure").
130                 SetShortDescription("Configure alarm manager with given parameters").
131                 AddFlag("mal", "max active alarms", commando.Int, nil).
132                 AddFlag("mah", "max alarm history", commando.Int, nil).
133                 AddFlag("host", "Alarm manager host address", commando.String, alarmManagerHost).
134                 AddFlag("port", "Alarm manager host address", commando.String, "8080").
135                 SetAction(func(args map[string]commando.ArgValue, flags map[string]commando.FlagValue) {
136                         postAlarmConfig(flags)
137                 })
138         // Create alarm definition
139         commando.
140                 Register("define").
141                 SetShortDescription("Define alarm with given parameters").
142                 AddFlag("aid", "alarm identifier", commando.Int, nil).
143                 AddFlag("atx", "alarm text", commando.String, nil).
144                 AddFlag("ety", "event type", commando.String, nil).
145                 AddFlag("oin", "operation instructions", commando.String, nil).
146                 AddFlag("rad", "Raise alarm delay", commando.Int, 0).
147                 AddFlag("cad", "Clear alarm delay", commando.Int, 0).
148                 AddFlag("host", "Alarm manager host address", commando.String, alarmManagerHost).
149                 AddFlag("port", "Alarm manager host address", commando.String, "8080").
150                 SetAction(func(args map[string]commando.ArgValue, flags map[string]commando.FlagValue) {
151                         postAlarmDefinition(flags)
152                 })
153                 // Delete alarm definition
154         commando.
155                 Register("undefine").
156                 SetShortDescription("Define alarm with given parameters").
157                 AddFlag("aid", "alarm identifier", commando.Int, nil).
158                 AddFlag("host", "Alarm manager host address", commando.String, alarmManagerHost).
159                 AddFlag("port", "Alarm manager host address", commando.String, "8080").
160                 SetAction(func(args map[string]commando.ArgValue, flags map[string]commando.FlagValue) {
161                         deleteAlarmDefinition(flags)
162                 })
163                 // Conduct performance test for alarm-go
164         commando.
165                 Register("perf").
166                 SetShortDescription("Conduct performance test with given parameters").
167                 AddFlag("prf", "performance profile id", commando.Int, nil).
168                 AddFlag("nal", "number of alarms", commando.Int, nil).
169                 AddFlag("aps", "alarms per sec", commando.Int, nil).
170                 AddFlag("tim", "total time of test", commando.Int, nil).
171                 AddFlag("host", "Alarm manager host address", commando.String, alarmManagerHost).
172                 AddFlag("port", "Alarm manager host address", commando.String, "8080").
173                 AddFlag("if", "http or rmr used as interface", commando.String, "http").
174                 SetAction(func(args map[string]commando.ArgValue, flags map[string]commando.FlagValue) {
175                         conductperformancetest(flags)
176                 })
177
178         // Get alerts from Prometheus Alert Manager
179         commando.
180                 Register("gapam").
181                 SetShortDescription("Get alerts from Prometheus Alert Manager").
182                 AddFlag("active", "Active alerts in Prometheus Alert Manager", commando.Bool, true).
183                 AddFlag("inhibited", "Inhibited alerts in Prometheus Alert Manager", commando.Bool, true).
184                 AddFlag("silenced", "Silenced alerts in Prometheus Alert Manager", commando.Bool, true).
185                 AddFlag("unprocessed", "Unprocessed alerts in Prometheus Alert Manager", commando.Bool, true).
186                 AddFlag("host", "Prometheus Alert Manager host address", commando.String, alertManagerHost).
187                 AddFlag("port", "Prometheus Alert Manager port", commando.String, "9093").
188                 SetAction(func(args map[string]commando.ArgValue, flags map[string]commando.FlagValue) {
189                         displayAlerts(flags)
190                 })
191
192         // parse command-line arguments
193         commando.Parse(nil)
194 }
195
196 func readAlarmParams(flags map[string]commando.FlagValue, clear bool) (a alarm.Alarm) {
197         a.ManagedObjectId, _ = flags["moid"].GetString()
198         a.ApplicationId, _ = flags["apid"].GetString()
199         a.SpecificProblem, _ = flags["sp"].GetInt()
200         a.IdentifyingInfo, _ = flags["iinfo"].GetString()
201
202         if !clear {
203                 s, _ := flags["severity"].GetString()
204                 a.PerceivedSeverity = alarm.Severity(s)
205         }
206
207         if !clear {
208                 a.AdditionalInfo, _ = flags["aai"].GetString()
209         }
210         return
211 }
212
213 func getAlarms(flags map[string]commando.FlagValue, action alarm.AlarmAction) (alarms []AlarmNotification) {
214         host, _ := flags["host"].GetString()
215         port, _ := flags["port"].GetString()
216         targetUrl := fmt.Sprintf("http://%s:%s/ric/v1/alarms/%s", host, port, action)
217         resp, err := http.Get(targetUrl)
218         if err != nil || resp == nil || resp.Body == nil {
219                 fmt.Println("Couldn't fetch active alarm list due to error: ", err)
220                 return alarms
221         }
222
223         defer resp.Body.Close()
224
225         body, err := ioutil.ReadAll(resp.Body)
226         if err != nil {
227                 fmt.Println("ioutil.ReadAll failed: ", err)
228                 return alarms
229         }
230
231         json.Unmarshal([]byte(body), &alarms)
232         return alarms
233 }
234
235 func postAlarmWithRmrIf(a alarm.Alarm, action alarm.AlarmAction, alarmClient *AlarmClient) {
236         if alarmClient == nil {
237                 alarmClient = NewAlarmClient("my-pod", "my-app")
238         }
239         if alarmClient == nil {
240                 return
241         }
242
243         // Wait until RMR is up-and-running
244         for !alarmClient.alarmer.IsRMRReady() {
245                 time.Sleep(100 * time.Millisecond)
246         }
247
248         if action == alarm.AlarmActionRaise {
249                 alarmClient.alarmer.Raise(a)
250         }
251
252         if action == alarm.AlarmActionClear {
253                 alarmClient.alarmer.Clear(a)
254         }
255         return
256 }
257
258 func postAlarmWithHttpIf(targetUrl string, a alarm.Alarm, action alarm.AlarmAction) {
259         m := alarm.AlarmMessage{Alarm: a, AlarmAction: action}
260         jsonData, err := json.Marshal(m)
261         if err != nil {
262                 fmt.Println("json.Marshal failed: ", err)
263                 return
264         }
265
266         resp, err := http.Post(targetUrl, "application/json", bytes.NewBuffer(jsonData))
267         if err != nil || resp == nil {
268                 fmt.Println("Couldn't fetch active alarm list due to error: ", err)
269                 return
270         }
271 }
272
273 func postAlarm(flags map[string]commando.FlagValue, a alarm.Alarm, action alarm.AlarmAction, alarmClient *AlarmClient) {
274         // Check the interface to be used for raise or clear the alarm
275         rmr_or_http, _ := flags["if"].GetString()
276         if rmr_or_http == "rmr" {
277                 postAlarmWithRmrIf(a, action, alarmClient)
278         } else {
279
280                 host, _ := flags["host"].GetString()
281                 port, _ := flags["port"].GetString()
282                 targetUrl := fmt.Sprintf("http://%s:%s/ric/v1/alarms", host, port)
283                 postAlarmWithHttpIf(targetUrl, a, action)
284         }
285         fmt.Println("command executed successfully!")
286 }
287
288 func displayAlarms(alarms []AlarmNotification, isHistory bool) {
289         t := table.NewWriter()
290         t.SetOutputMirror(os.Stdout)
291         if isHistory {
292                 t.AppendHeader(table.Row{"ID", "SP", "MOID", "APPID", "IINFO", "SEVERITY", "AAI", "ACTION", "TIME"})
293         } else {
294                 t.AppendHeader(table.Row{"ID", "SP", "MOID", "APPID", "IINFO", "SEVERITY", "AAI", "TIME"})
295         }
296
297         for _, a := range alarms {
298                 // Do not show alarm before raiseDelay has elapsed
299                 alarmTime := time.Unix(0, a.AlarmTime).Format("02/01/2006, 15:04:05")
300                 if isHistory {
301                         t.AppendRows([]table.Row{
302                                 {a.AlarmId, a.SpecificProblem, a.ManagedObjectId, a.ApplicationId, a.IdentifyingInfo, a.PerceivedSeverity, a.AdditionalInfo, a.AlarmAction, alarmTime},
303                         })
304                 } else {
305                         if a.AlarmDefinition.RaiseDelay == 0 {
306                                 t.AppendRows([]table.Row{
307                                         {a.AlarmId, a.SpecificProblem, a.ManagedObjectId, a.ApplicationId, a.IdentifyingInfo, a.PerceivedSeverity, a.AdditionalInfo, alarmTime},
308                                 })
309                         }
310                 }
311         }
312
313         t.SetStyle(table.StyleColoredBright)
314         t.Render()
315 }
316
317 func postAlarmConfig(flags map[string]commando.FlagValue) {
318         host, _ := flags["host"].GetString()
319         port, _ := flags["port"].GetString()
320         maxactivealarms, _ := flags["mal"].GetInt()
321         maxalarmhistory, _ := flags["mah"].GetInt()
322         targetUrl := fmt.Sprintf("http://%s:%s/ric/v1/alarms/config", host, port)
323
324         m := alarm.AlarmConfigParams{MaxActiveAlarms: maxactivealarms, MaxAlarmHistory: maxalarmhistory}
325         jsonData, err := json.Marshal(m)
326         if err != nil {
327                 fmt.Println("json.Marshal failed: ", err)
328                 return
329         }
330
331         resp, err := http.Post(targetUrl, "application/json", bytes.NewBuffer(jsonData))
332         if err != nil || resp == nil {
333                 fmt.Println("Couldn't fetch post alarm configuration due to error: ", err)
334                 return
335         }
336 }
337
338 func postAlarmDefinition(flags map[string]commando.FlagValue) {
339         host, _ := flags["host"].GetString()
340         port, _ := flags["port"].GetString()
341         alarmid, _ := flags["aid"].GetInt()
342         alarmtxt, _ := flags["atx"].GetString()
343         etype, _ := flags["ety"].GetString()
344         operation, _ := flags["oin"].GetString()
345         raiseDelay, _ := flags["rad"].GetInt()
346         clearDelay, _ := flags["cad"].GetInt()
347
348         targetUrl := fmt.Sprintf("http://%s:%s/ric/v1/alarms/define", host, port)
349
350         var alarmdefinition alarm.AlarmDefinition
351         alarmdefinition.AlarmId = alarmid
352         alarmdefinition.AlarmText = alarmtxt
353         alarmdefinition.EventType = etype
354         alarmdefinition.OperationInstructions = operation
355         alarmdefinition.RaiseDelay = raiseDelay
356         alarmdefinition.ClearDelay = clearDelay
357
358         m := CliAlarmDefinitions{AlarmDefinitions: []*alarm.AlarmDefinition{&alarmdefinition}}
359         jsonData, err := json.Marshal(m)
360         if err != nil {
361                 fmt.Println("json.Marshal failed: ", err)
362                 return
363         }
364
365         resp, err := http.Post(targetUrl, "application/json", bytes.NewBuffer(jsonData))
366         if err != nil || resp == nil {
367                 fmt.Println("Couldn't post alarm definition due to error: ", err)
368                 return
369         }
370 }
371
372 func deleteAlarmDefinition(flags map[string]commando.FlagValue) {
373         host, _ := flags["host"].GetString()
374         port, _ := flags["port"].GetString()
375         alarmid, _ := flags["aid"].GetInt()
376         salarmid := strconv.FormatUint(uint64(alarmid), 10)
377         targetUrl := fmt.Sprintf("http://%s:%s/ric/v1/alarms/define/%s", host, port, salarmid)
378
379         client := &http.Client{}
380         req, err := http.NewRequest("DELETE", targetUrl, nil)
381         if err != nil || req == nil {
382                 fmt.Println("Couldn't make delete request due to error: ", err)
383                 return
384         }
385         resp, errr := client.Do(req)
386         if errr != nil || resp == nil {
387                 fmt.Println("Couldn't send delete request due to error: ", err)
388                 return
389         }
390 }
391
392 // NewAlarmClient returns a new AlarmClient.
393 func NewAlarmClient(moId, appId string) *AlarmClient {
394         alarmInstance, err := alarm.InitAlarm(moId, appId)
395         if err == nil {
396                 return &AlarmClient{
397                         alarmer: alarmInstance,
398                 }
399         }
400         fmt.Println("Failed to create alarmInstance", err)
401         return nil
402 }
403
404 // Conduct performance testing
405 func conductperformancetest(flags map[string]commando.FlagValue) {
406         var readerror error
407         var senderror error
408         var readobjerror error
409         host, _ := flags["host"].GetString()
410         port, _ := flags["port"].GetString()
411         targetUrl := fmt.Sprintf("http://%s:%s/ric/v1/alarms/define", host, port)
412         readerror = readPerfAlarmDefinitionFromJson()
413         if readerror == nil {
414                 senderror = sendPerfAlarmDefinitionToAlarmManager(targetUrl)
415                 if senderror == nil {
416                         fmt.Println("sent performance alarm definitions to alarm manager")
417                         CLIPerfAlarmObjects = make(map[int]*alarm.Alarm)
418                         readobjerror = readPerfAlarmObjectFromJson()
419                         if readobjerror == nil {
420                                 profile, _ := flags["prf"].GetInt()
421                                 if profile == 1 {
422                                         fmt.Println("starting peak performance test")
423                                         peakPerformanceTest(flags)
424                                 } else if profile == 2 {
425                                         fmt.Println("starting endurance test")
426                                         enduranceTest(flags)
427                                 } else {
428                                         fmt.Println("Unknown profile, received profile = ", profile)
429                                 }
430                         } else {
431                                 fmt.Println("reading performance alarm objects from json file failed ")
432                         }
433                 } else {
434                         fmt.Println("sending performance alarm definitions to alarm manager failed ")
435                 }
436
437         } else {
438                 fmt.Println("reading performance alarm definitions from json file failed ")
439         }
440 }
441
442 func peakPerformanceTest(flags map[string]commando.FlagValue) {
443         nalarms, _ := flags["nal"].GetInt()
444         var count int = 0
445         for aid, obj := range CLIPerfAlarmObjects {
446                 count = count + 1
447                 if count <= nalarms {
448                         fmt.Println("peakPerformanceTest: invoking worker routine ", count, aid, *obj)
449                         wg.Add(1)
450                         go raiseClearAlarmOnce(obj, flags)
451                 } else {
452                         break
453                 }
454         }
455         fmt.Println("peakPerformanceTest: Waiting for workers to finish")
456         wg.Wait()
457         fmt.Println("peakPerformanceTest: Wait completed")
458 }
459
460 func enduranceTest(flags map[string]commando.FlagValue) {
461         alarmspersec, _ := flags["aps"].GetInt()
462         var count int = 0
463         for aid, obj := range CLIPerfAlarmObjects {
464                 count = count + 1
465                 if count <= alarmspersec {
466                         fmt.Println("enduranceTest: invoking worker routine ", count, aid, *obj)
467                         wg.Add(1)
468                         go raiseClearAlarmOverPeriod(obj, flags)
469                 } else {
470                         break
471                 }
472         }
473         fmt.Println("enduranceTest: Waiting for workers to finish")
474         wg.Wait()
475         fmt.Println("enduranceTest: Wait completed")
476 }
477
478 func readPerfAlarmObjectFromJson() error {
479
480         filename := os.Getenv("PERF_OBJ_FILE")
481         fmt.Printf("readPerfAlarmObjectFromJson: filename = %s\n", filename)
482
483         file, err := ioutil.ReadFile(filename)
484         if err == nil {
485                 data := RicPerfAlarmObjects{}
486                 err = json.Unmarshal([]byte(file), &data)
487                 if err == nil {
488                         for _, alarmObject := range data.AlarmObjects {
489                                 ricAlarmObject := new(alarm.Alarm)
490                                 ricAlarmObject.ManagedObjectId = alarmObject.ManagedObjectId
491                                 ricAlarmObject.ApplicationId = alarmObject.ApplicationId
492                                 ricAlarmObject.SpecificProblem = alarmObject.SpecificProblem
493                                 ricAlarmObject.PerceivedSeverity = alarmObject.PerceivedSeverity
494                                 ricAlarmObject.AdditionalInfo = alarmObject.AdditionalInfo
495                                 ricAlarmObject.IdentifyingInfo = alarmObject.IdentifyingInfo
496                                 CLIPerfAlarmObjects[alarmObject.SpecificProblem] = ricAlarmObject
497                         }
498                 } else {
499                         fmt.Println("readPerfAlarmObjectFromJson: json.Unmarshal failed with error: ", err)
500                         return err
501                 }
502         } else {
503                 fmt.Printf("readPerfAlarmObjectFromJson: ioutil.ReadFile failed with error: %v, filename: %s\n", err, filename)
504                 fmt.Printf("readPerfAlarmObjectFromJson: current directory: %s\n", getCurrentDirectory())
505                 return err
506         }
507         return nil
508 }
509
510 func readPerfAlarmDefinitionFromJson() error {
511
512         filename := os.Getenv("PERF_DEF_FILE")
513         fmt.Printf("ReadPerfAlarmDefinitionFromJson: filename = %s\n", filename)
514
515         file, err := ioutil.ReadFile(filename)
516         if err == nil {
517                 data := CliAlarmDefinitions{}
518                 err = json.Unmarshal([]byte(file), &data)
519                 if err == nil {
520                         for _, alarmDefinition := range data.AlarmDefinitions {
521                                 _, exists := alarm.RICAlarmDefinitions[alarmDefinition.AlarmId]
522                                 if exists {
523                                         fmt.Println("ReadPerfAlarmDefinitionFromJson: alarm definition already exists for ", alarmDefinition.AlarmId)
524                                 } else {
525                                         fmt.Println("ReadPerfAlarmDefinitionFromJson: alarm ", alarmDefinition.AlarmId)
526                                         ricAlarmDefintion := new(alarm.AlarmDefinition)
527                                         ricAlarmDefintion.AlarmId = alarmDefinition.AlarmId
528                                         ricAlarmDefintion.AlarmText = alarmDefinition.AlarmText
529                                         ricAlarmDefintion.EventType = alarmDefinition.EventType
530                                         ricAlarmDefintion.OperationInstructions = alarmDefinition.OperationInstructions
531                                         ricAlarmDefintion.RaiseDelay = alarmDefinition.RaiseDelay
532                                         ricAlarmDefintion.ClearDelay = alarmDefinition.ClearDelay
533                                         CliPerfAlarmDefinitions.AlarmDefinitions = append(CliPerfAlarmDefinitions.AlarmDefinitions, ricAlarmDefintion)
534                                 }
535                         }
536                 } else {
537                         fmt.Println("ReadPerfAlarmDefinitionFromJson: json.Unmarshal failed with error: ", err)
538                         return err
539                 }
540         } else {
541                 fmt.Printf("ReadPerfAlarmDefinitionFromJson: ioutil.ReadFile failed with error: %v, filename: %s\n", err, filename)
542                 fmt.Printf("ReadPerfAlarmDefinitionFromJson: current directory: %s\n", getCurrentDirectory())
543         
544                 return err
545         }
546         return nil
547 }
548
549 func sendPerfAlarmDefinitionToAlarmManager(targetUrl string) error {
550
551         jsonData, err := json.Marshal(CliPerfAlarmDefinitions)
552         if err != nil {
553                 fmt.Println("sendPerfAlarmDefinitionToAlarmManager: json.Marshal failed: ", err)
554                 return err
555         }
556
557         resp, err := http.Post(targetUrl, "application/json", bytes.NewBuffer(jsonData))
558         if err != nil || resp == nil {
559                 fmt.Println("sendPerfAlarmDefinitionToAlarmManager: Couldn't post alarm definition to targeturl due to error: ", targetUrl, err)
560                 return err
561         }
562         return nil
563 }
564
565 func wakeUpAfterTime(timeinseconds int, chn chan string, action string) {
566         time.Sleep(time.Second * time.Duration(timeinseconds))
567         chn <- action
568 }
569
570 func raiseClearAlarmOnce(alarmobject *alarm.Alarm, flags map[string]commando.FlagValue) {
571         var alarmClient *AlarmClient = nil
572         defer wg.Done()
573         chn := make(chan string, 1)
574         rmr_or_http, _ := flags["if"].GetString()
575         if rmr_or_http == "rmr" {
576                 alarmClient = NewAlarmClient("my-pod", "my-app")
577         }
578         postAlarm(flags, *alarmobject, alarm.AlarmActionRaise, alarmClient)
579         go wakeUpAfterTime(PeakTestDuration, chn, Clear)
580         select {
581         case res := <-chn:
582                 if res == Clear {
583                         postAlarm(flags, *alarmobject, alarm.AlarmActionClear, alarmClient)
584                         go wakeUpAfterTime(PeakTestDuration, chn, End)
585                 } else if res == End {
586                         return
587                 }
588         }
589 }
590
591 func raiseClearAlarmOverPeriod(alarmobject *alarm.Alarm, flags map[string]commando.FlagValue) {
592         var alarmClient *AlarmClient = nil
593         defer wg.Done()
594         timeinminutes, _ := flags["tim"].GetInt()
595         timeinseconds := timeinminutes * 60
596         chn := make(chan string, 1)
597         rmr_or_http, _ := flags["if"].GetString()
598         if rmr_or_http == "rmr" {
599                 alarmClient = NewAlarmClient("my-pod", "my-app")
600         }
601         postAlarm(flags, *alarmobject, alarm.AlarmActionRaise, alarmClient)
602         go wakeUpAfterTime(OneSecondDuration, chn, Clear)
603         go wakeUpAfterTime(timeinseconds, chn, End)
604         for {
605                 select {
606                 case res := <-chn:
607                         if res == Raise {
608                                 postAlarm(flags, *alarmobject, alarm.AlarmActionRaise, alarmClient)
609                                 go wakeUpAfterTime(OneSecondDuration, chn, Clear)
610                         } else if res == Clear {
611                                 postAlarm(flags, *alarmobject, alarm.AlarmActionClear, alarmClient)
612                                 go wakeUpAfterTime(OneSecondDuration, chn, Raise)
613                         } else if res == End {
614                                 return
615                         }
616                 }
617         }
618 }
619
620 func displaySingleAlert(t table.Writer, gettableAlert *models.GettableAlert) {
621         t.AppendRow([]interface{}{"------------------------------------"})
622         for key, item := range gettableAlert.Annotations {
623                 t.AppendRow([]interface{}{key, item})
624         }
625         if gettableAlert.EndsAt != nil {
626                 t.AppendRow([]interface{}{"EndsAt", *gettableAlert.EndsAt})
627         }
628         if gettableAlert.Fingerprint != nil {
629                 t.AppendRow([]interface{}{"Fingerprint", *gettableAlert.Fingerprint})
630         }
631         for key, item := range gettableAlert.Receivers {
632                 if gettableAlert.Receivers != nil {
633                         t.AppendRow([]interface{}{key, *item.Name})
634                 }
635         }
636         if gettableAlert.StartsAt != nil {
637                 t.AppendRow([]interface{}{"StartsAt", *gettableAlert.StartsAt})
638         }
639         if gettableAlert.Status != nil {
640                 t.AppendRow([]interface{}{"InhibitedBy", gettableAlert.Status.InhibitedBy})
641                 t.AppendRow([]interface{}{"SilencedBy", gettableAlert.Status.SilencedBy})
642                 t.AppendRow([]interface{}{"State", *gettableAlert.Status.State})
643         }
644         if gettableAlert.UpdatedAt != nil {
645                 t.AppendRow([]interface{}{"UpdatedAt", *gettableAlert.UpdatedAt})
646         }
647         t.AppendRow([]interface{}{"GeneratorURL", gettableAlert.Alert.GeneratorURL})
648         for key, item := range gettableAlert.Alert.Labels {
649                 t.AppendRow([]interface{}{key, item})
650         }
651 }
652
653 func displayAlerts(flags map[string]commando.FlagValue) {
654         resp, err := getAlerts(flags)
655         if err != nil {
656                 fmt.Println(err)
657                 return
658         }
659
660         if resp == nil {
661                 fmt.Println("resp= nil")
662                 return
663         }
664
665         t := table.NewWriter()
666         t.SetOutputMirror(os.Stdout)
667         t.AppendHeader(table.Row{"Alerts from Prometheus Alert Manager"})
668         for _, gettableAlert := range resp.Payload {
669                 if gettableAlert == nil {
670                         continue
671                 }
672
673                 displaySingleAlert(t, gettableAlert)
674         }
675         t.SetStyle(table.StyleColoredBright)
676         t.Render()
677 }
678
679 func getAlerts(flags map[string]commando.FlagValue) (*alert.GetAlertsOK, error) {
680         active, _ := flags["active"].GetBool()
681         inhibited, _ := flags["inhibited"].GetBool()
682         silenced, _ := flags["silenced"].GetBool()
683         unprocessed, _ := flags["unprocessed"].GetBool()
684         amHost, _ := flags["host"].GetString()
685         amPort, _ := flags["port"].GetString()
686         var amAddress string
687         if amHost == "" {
688                 amAddress = viper.GetString("controls.promAlertManager.address")
689         } else {
690                 amAddress = amHost + ":" + amPort
691         }
692
693         alertParams := alert.NewGetAlertsParams()
694         alertParams.Active = &active
695         alertParams.Inhibited = &inhibited
696         alertParams.Silenced = &silenced
697         alertParams.Unprocessed = &unprocessed
698         amBaseUrl := viper.GetString("controls.promAlertManager.baseUrl")
699         amSchemes := []string{viper.GetString("controls.promAlertManager.schemes")}
700         resp, err := newAlertManagerClient(amAddress, amBaseUrl, amSchemes).Alert.GetAlerts(alertParams)
701         if err != nil {
702                 err = fmt.Errorf("GetAlerts from '%s%s' failed with error: %v", amAddress, amBaseUrl, err)
703         }
704         return resp, err
705 }
706
707 func newAlertManagerClient(amAddress string, amBaseUrl string, amSchemes []string) *client.Alertmanager {
708         cr := clientruntime.New(amAddress, amBaseUrl, amSchemes)
709         return client.New(cr, strfmt.Default)
710 }
711
712 func getCurrentDirectory() string {
713         dir, err := os.Getwd()
714         if err != nil {
715                 fmt.Println(err)
716         }
717         return dir
718 }