Moving RMR message reciver into go routine
[ric-plt/a1.git] / a1-go / pkg / resthooks / resthooks.go
1 /*
2 ==================================================================================
3   Copyright (c) 2021 Samsung
4
5    Licensed under the Apache License, Version 2.0 (the "License");
6    you may not use this file except in compliance with the License.
7    You may obtain a copy of the License at
8
9        http://www.apache.org/licenses/LICENSE-2.0
10
11    Unless required by applicable law or agreed to in writing, software
12    distributed under the License is distributed on an "AS IS" BASIS,
13    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14    See the License for the specific language governing permissions and
15    limitations under the License.
16
17    This source code is part of the near-RT RIC (RAN Intelligent Controller)
18    platform project (RICP).
19 ==================================================================================
20 */
21 package resthooks
22
23 import (
24         "encoding/json"
25         "errors"
26         "fmt"
27         "strconv"
28         "strings"
29         "time"
30
31         "gerrit.o-ran-sc.org/r/ric-plt/a1/pkg/a1"
32         "gerrit.o-ran-sc.org/r/ric-plt/a1/pkg/models"
33         "gerrit.o-ran-sc.org/r/ric-plt/a1/pkg/policy"
34         "gerrit.o-ran-sc.org/r/ric-plt/a1/pkg/restapi/operations/a1_mediator"
35         "gerrit.o-ran-sc.org/r/ric-plt/a1/pkg/rmr"
36         "gerrit.o-ran-sc.org/r/ric-plt/sdlgo"
37         "github.com/santhosh-tekuri/jsonschema/v5"
38         "gopkg.in/yaml.v2"
39 )
40
41 const (
42         a1PolicyPrefix           = "a1.policy_type."
43         a1MediatorNs             = "A1m_ns"
44         a1InstancePrefix         = "a1.policy_instance."
45         a1InstanceMetadataPrefix = "a1.policy_inst_metadata."
46         a1HandlerPrefix          = "a1.policy_handler."
47         a1PolicyRequest          = 20010
48         a1EIDataDelivery         = 20017
49 )
50
51 var typeAlreadyError = errors.New("Policy Type already exists")
52 var InstanceAlreadyError = errors.New("Policy Instance already exists")
53 var typeMismatchError = errors.New("Policytype Mismatch")
54 var invalidJsonSchema = errors.New("Invalid Json ")
55 var policyInstanceNotFoundError = errors.New("Policy Instance Not Found")
56 var policyTypeNotFoundError = errors.New("Policy Type Not Found")
57 var policyTypeCanNotBeDeletedError = errors.New("tried to delete a type that isn't empty")
58 var policyInstanceCanNotBeDeletedError = errors.New("tried to delete a Instance that isn't empty")
59
60 func (rh *Resthook) CanPolicyInstanceBeDeleted(err error) bool {
61         return err == policyInstanceCanNotBeDeletedError
62 }
63
64 func (rh *Resthook) CanPolicyTypeBeDeleted(err error) bool {
65         return err == policyTypeCanNotBeDeletedError
66 }
67
68 func (rh *Resthook) IsPolicyTypePresent(err error) bool {
69         return err == policyTypeNotFoundError
70 }
71
72 func (rh *Resthook) IsPolicyInstanceNotFound(err error) bool {
73         return err == policyInstanceNotFoundError
74 }
75
76 func (rh *Resthook) IsTypeAlready(err error) bool {
77         return err == typeAlreadyError
78 }
79 func (rh *Resthook) IsInstanceAlready(err error) bool {
80         return err == InstanceAlreadyError
81 }
82 func (rh *Resthook) IsTypeMismatch(err error) bool {
83         return err == typeMismatchError
84 }
85
86 func (rh *Resthook) IsValidJson(err error) bool {
87         return err == invalidJsonSchema
88 }
89 func NewResthook() *Resthook {
90         sdl := sdlgo.NewSyncStorage()
91         policyManager := policy.NewPolicyManager(sdl)
92         return createResthook(sdl, rmr.NewRMRSender(policyManager))
93 }
94
95 func createResthook(sdlInst iSdl, rmrSenderInst rmr.IRmrSender) *Resthook {
96         rh := &Resthook{
97                 db:             sdlInst,
98                 iRmrSenderInst: rmrSenderInst,
99         }
100
101         return rh
102 }
103
104 func (rh *Resthook) GetA1Health() bool {
105         data, _ := rh.db.GetAll(a1MediatorNs)
106         if data != nil {
107                 a1.Logger.Debug("Database connected and A1 is healthy")
108                 return true
109         }
110         return false
111 }
112
113 func (rh *Resthook) GetAllPolicyType() []models.PolicyTypeID {
114
115         var policyTypeIDs []models.PolicyTypeID
116
117         keys, err := rh.db.GetAll("A1m_ns")
118
119         if err != nil {
120                 a1.Logger.Error("error in retrieving policy. err: %v", err)
121                 return policyTypeIDs
122         }
123         a1.Logger.Debug("keys : %+v", keys)
124
125         for _, key := range keys {
126                 if strings.HasPrefix(strings.TrimLeft(key, " "), a1PolicyPrefix) {
127                         pti := strings.Split(strings.Trim(key, " "), a1PolicyPrefix)[1]
128                         ptii, _ := strconv.ParseInt(pti, 10, 64)
129                         policyTypeIDs = append(policyTypeIDs, models.PolicyTypeID(ptii))
130                 }
131         }
132
133         a1.Logger.Debug("return : %+v", policyTypeIDs)
134         return policyTypeIDs
135 }
136
137 func (rh *Resthook) GetPolicyType(policyTypeId models.PolicyTypeID) *models.PolicyTypeSchema {
138         a1.Logger.Debug("GetPolicyType1")
139
140         var policytypeschema *models.PolicyTypeSchema
141         var keys [1]string
142
143         key := a1PolicyPrefix + strconv.FormatInt((int64(policyTypeId)), 10)
144         keys[0] = key
145
146         a1.Logger.Debug("key : %+v", key)
147
148         valmap, err := rh.db.Get(a1MediatorNs, keys[:])
149
150         a1.Logger.Debug("policytype map : %+v", valmap)
151
152         if len(valmap) == 0 {
153                 a1.Logger.Error("policy type Not Present for policyid : %v", policyTypeId)
154                 return policytypeschema
155         }
156
157         if err != nil {
158                 a1.Logger.Error("error in retrieving policy type. err: %v", err)
159                 return nil
160         }
161
162         if valmap[key] == nil {
163                 a1.Logger.Error("policy type Not Present for policyid : %v", policyTypeId)
164                 return policytypeschema
165         }
166
167         a1.Logger.Debug("keysmap : %+v", valmap[key])
168
169         var item models.PolicyTypeSchema
170         valStr := fmt.Sprint(valmap[key])
171
172         a1.Logger.Debug("Policy type for %+v :  %+v", key, valStr)
173         valkey := "`" + valStr + "`"
174         valToUnmarshall, err := strconv.Unquote(valkey)
175         if err != nil {
176                 a1.Logger.Error("unquote error : %+v", err)
177                 return nil
178         }
179
180         a1.Logger.Debug("Policy type for %+v :  %+v", key, string(valToUnmarshall))
181
182         errunm := json.Unmarshal([]byte(valToUnmarshall), &item)
183
184         a1.Logger.Debug(" Unmarshalled json : %+v", (errunm))
185         a1.Logger.Debug("Policy type Name :  %v", (item.Name))
186
187         return &item
188 }
189
190 func (rh *Resthook) CreatePolicyType(policyTypeId models.PolicyTypeID, httprequest models.PolicyTypeSchema) error {
191         a1.Logger.Debug("CreatePolicyType function")
192         if policyTypeId != models.PolicyTypeID(*httprequest.PolicyTypeID) {
193                 //error message
194                 a1.Logger.Debug("Policytype Mismatch")
195                 return typeMismatchError
196         }
197         key := a1PolicyPrefix + strconv.FormatInt((int64(policyTypeId)), 10)
198         a1.Logger.Debug("key %+v ", key)
199         if data, err := httprequest.MarshalBinary(); err == nil {
200                 a1.Logger.Debug("Marshaled String : %+v", string(data))
201                 success, err1 := rh.db.SetIfNotExists(a1MediatorNs, key, string(data))
202                 a1.Logger.Info("success:%+v", success)
203                 if err1 != nil {
204                         a1.Logger.Error("error :%+v", err1)
205                         return err1
206                 }
207                 if !success {
208                         a1.Logger.Debug("Policy type %+v already exist", policyTypeId)
209                         return typeAlreadyError
210                 }
211         }
212         return nil
213 }
214
215 func toStringKeys(val interface{}) (interface{}, error) {
216         var err error
217         switch val := val.(type) {
218         case map[interface{}]interface{}:
219                 m := make(map[string]interface{})
220                 for k, v := range val {
221                         k, ok := k.(string)
222                         if !ok {
223                                 return nil, errors.New("found non-string key")
224                         }
225                         m[k], err = toStringKeys(v)
226                         if err != nil {
227                                 return nil, err
228                         }
229                 }
230                 return m, nil
231         case []interface{}:
232                 var l = make([]interface{}, len(val))
233                 for i, v := range val {
234                         l[i], err = toStringKeys(v)
235                         if err != nil {
236                                 return nil, err
237                         }
238                 }
239                 return l, nil
240         default:
241                 return val, nil
242         }
243 }
244
245 func validate(httpBodyString string, schemaString string) bool {
246         var m interface{}
247         err := yaml.Unmarshal([]byte(httpBodyString), &m)
248         if err != nil {
249                 a1.Logger.Error("Unmarshal error : %+v", err)
250         }
251         m, err = toStringKeys(m)
252         if err != nil {
253                 a1.Logger.Error("Conversion to string error : %+v", err)
254                 return false
255         }
256         compiler := jsonschema.NewCompiler()
257         if err := compiler.AddResource("schema.json", strings.NewReader(schemaString)); err != nil {
258                 a1.Logger.Error("string reader error : %+v", err)
259                 return false
260         }
261         schema, err := compiler.Compile("schema.json")
262         if err != nil {
263                 a1.Logger.Error("schema json compile error : %+v", err)
264                 return false
265         }
266         if err := schema.Validate(m); err != nil {
267                 a1.Logger.Error("schema validation error : %+v", err)
268                 return false
269         }
270         a1.Logger.Debug("validation successfull")
271         return true
272 }
273
274 func (rh *Resthook) storePolicyInstance(policyTypeId models.PolicyTypeID, policyInstanceID models.PolicyInstanceID, httpBody interface{}) (string, error) {
275         var keys [1]string
276         operation := "CREATE"
277         typekey := a1PolicyPrefix + strconv.FormatInt((int64(policyTypeId)), 10)
278         keys[0] = typekey
279
280         a1.Logger.Debug("key1 : %+v", typekey)
281
282         valmap, err := rh.db.Get(a1MediatorNs, keys[:])
283         if err != nil {
284                 a1.Logger.Error("policy type error : %+v", err)
285         }
286         a1.Logger.Debug("policytype map : %+v", valmap)
287         if valmap[typekey] == nil {
288                 a1.Logger.Error("policy type Not Present for policyid : %v", policyTypeId)
289                 return operation, policyTypeNotFoundError
290         }
291         // TODO : rmr creation_timestamp := time.Now() // will be needed for rmr to notify the creation of instance
292
293         instancekey := a1InstancePrefix + strconv.FormatInt((int64(policyTypeId)), 10) + "." + string(policyInstanceID)
294         keys[0] = typekey
295         instanceMap, err := rh.db.Get(a1MediatorNs, keys[:])
296         if err != nil {
297                 a1.Logger.Error("policy type error : %v", err)
298         }
299         a1.Logger.Debug("policyinstancetype map : %+v", instanceMap)
300
301         if instanceMap[instancekey] != nil {
302                 operation = "UPDATE"
303                 a1.Logger.Debug("UPDATE")
304                 data, _ := json.Marshal(httpBody)
305                 a1.Logger.Debug("Marshaled String : %+v", string(data))
306                 a1.Logger.Debug("key   : %+v", instancekey)
307                 success, err1 := rh.db.SetIf(a1MediatorNs, instancekey, instanceMap[instancekey], string(data))
308                 if err1 != nil {
309                         a1.Logger.Error("error2 :%+v", err1)
310                         return operation, err1
311                 }
312                 if !success {
313                         a1.Logger.Debug("Policy instance %+v already exist", policyInstanceID)
314                         return operation, InstanceAlreadyError
315                 }
316         } else {
317                 data, _ := json.Marshal(httpBody)
318                 a1.Logger.Debug("Marshaled String : %+v", string(data))
319                 a1.Logger.Debug("key   : %+v", instancekey)
320
321                 var instance_map []interface{}
322                 instance_map = append(instance_map, instancekey, string(data))
323                 a1.Logger.Debug("policyinstancetype map : %+v", instance_map[1])
324                 a1.Logger.Debug("policyinstancetype to create : %+v", instance_map)
325
326                 err1 := rh.db.Set(a1MediatorNs, instancekey, string(data))
327                 if err1 != nil {
328                         a1.Logger.Error("error1 :%+v", err1)
329                         return operation, err1
330                 }
331         }
332         a1.Logger.Debug("Policy Instance created ")
333         return operation, nil
334 }
335
336 func (rh *Resthook) storePolicyInstanceMetadata(policyTypeId models.PolicyTypeID, policyInstanceID models.PolicyInstanceID) (bool, error) {
337
338         creation_timestamp := time.Now()
339         instanceMetadataKey := a1InstanceMetadataPrefix + strconv.FormatInt((int64(policyTypeId)), 10) + "." + string(policyInstanceID)
340
341         a1.Logger.Debug("key : %+v", instanceMetadataKey)
342
343         var metadatajson []interface{}
344         metadatajson = append(metadatajson, map[string]string{"created_at": creation_timestamp.Format("2006-01-02 15:04:05"), "has_been_deleted": "False"})
345         metadata, _ := json.Marshal(metadatajson)
346
347         a1.Logger.Debug("policyinstanceMetaData to create : %+v", string(metadata))
348
349         err := rh.db.Set(a1MediatorNs, instanceMetadataKey, string(metadata))
350
351         if err != nil {
352                 a1.Logger.Error("error :%+v", err)
353                 return false, err
354         }
355
356         a1.Logger.Debug("Policy Instance Meta Data created at :%+v", creation_timestamp)
357
358         return true, nil
359 }
360
361 func (rh *Resthook) CreatePolicyInstance(policyTypeId models.PolicyTypeID, policyInstanceID models.PolicyInstanceID, httpBody interface{}) error {
362         a1.Logger.Debug("CreatePolicyInstance function")
363         //  validate the PUT against the schema
364         var policyTypeSchema *models.PolicyTypeSchema
365         policyTypeSchema = rh.GetPolicyType(policyTypeId)
366         schemaStr, err := json.Marshal(policyTypeSchema.CreateSchema)
367         if err != nil {
368                 a1.Logger.Error("Json Marshal error : %+v", err)
369                 return err
370         }
371         a1.Logger.Debug("schema to validate %+v", string(schemaStr))
372         a1.Logger.Debug("httpbody to validate %+v", httpBody)
373         schemaString := fmt.Sprint(string(schemaStr))
374         httpBodyMarshal, err := json.Marshal(httpBody)
375         httpBodyString := string((httpBodyMarshal))
376         a1.Logger.Debug("schema to validate sprint  %+v", (schemaString))
377         a1.Logger.Debug("httpbody to validate sprint %+v", httpBodyString)
378         isvalid := validate(httpBodyString, schemaString)
379         if isvalid {
380                 var operation string
381                 operation, err = rh.storePolicyInstance(policyTypeId, policyInstanceID, httpBody)
382                 if err != nil {
383                         a1.Logger.Error("error :%+v", err)
384                         return err
385                 }
386                 a1.Logger.Debug("policy instance :%+v", operation)
387                 iscreated, errmetadata := rh.storePolicyInstanceMetadata(policyTypeId, policyInstanceID)
388                 if errmetadata != nil {
389                         a1.Logger.Error("error :%+v", errmetadata)
390                         return errmetadata
391                 }
392                 if iscreated {
393                         a1.Logger.Debug("policy instance metadata created")
394                 }
395
396                 message := rmr.Message{}
397                 rmrMessage, err := message.PolicyMessage(strconv.FormatInt((int64(policyTypeId)), 10), string(policyInstanceID), httpBodyString, operation)
398                 if err != nil {
399                         a1.Logger.Error("error : %v", err)
400                         return err
401                 }
402                 isSent := rh.iRmrSenderInst.RmrSendToXapp(rmrMessage, a1PolicyRequest)
403                 if isSent {
404                         a1.Logger.Debug("rmrSendToXapp : message sent")
405                 } else {
406                         a1.Logger.Debug("rmrSendToXapp : message not sent")
407                 }
408
409         } else {
410                 a1.Logger.Error("%+v", invalidJsonSchema)
411                 return invalidJsonSchema
412         }
413
414         return nil
415 }
416
417 func (rh *Resthook) GetPolicyInstance(policyTypeId models.PolicyTypeID, policyInstanceID models.PolicyInstanceID) (interface{}, error) {
418         a1.Logger.Debug("GetPolicyInstance1")
419
420         var keys [1]string
421
422         typekey := a1PolicyPrefix + strconv.FormatInt((int64(policyTypeId)), 10)
423         keys[0] = typekey
424
425         a1.Logger.Debug("key1 : %+v", typekey)
426
427         valmap, err := rh.db.Get(a1MediatorNs, keys[:])
428         if len(valmap) == 0 {
429                 a1.Logger.Debug("policy type Not Present for policyid : %v", policyTypeId)
430                 return "{}", policyTypeNotFoundError
431         }
432
433         if err != nil {
434                 a1.Logger.Error("error in retrieving policy type. err: %v", err)
435                 return "{}", err
436         }
437
438         if valmap[typekey] == nil {
439                 a1.Logger.Debug("policy type Not Present for policyid : %v", policyTypeId)
440                 return "{}", policyTypeNotFoundError
441         }
442
443         a1.Logger.Debug("keysmap : %+v", valmap[typekey])
444
445         instancekey := a1InstancePrefix + strconv.FormatInt((int64(policyTypeId)), 10) + "." + string(policyInstanceID)
446         a1.Logger.Debug("key2 : %+v", instancekey)
447         keys[0] = instancekey
448         instanceMap, err := rh.db.Get(a1MediatorNs, keys[:])
449         if err != nil {
450                 a1.Logger.Error("policy instance error : %v", err)
451         }
452         a1.Logger.Debug("policyinstancetype map : %+v", instanceMap)
453
454         if instanceMap[instancekey] == nil {
455                 a1.Logger.Debug("policy instance Not Present for policyinstaneid : %v", policyInstanceID)
456                 return "{}", policyInstanceNotFoundError
457         }
458
459         valStr := fmt.Sprint(instanceMap[instancekey])
460         return valStr, nil
461 }
462
463 func (rh *Resthook) GetAllPolicyInstance(policyTypeId models.PolicyTypeID) ([]models.PolicyInstanceID, error) {
464         a1.Logger.Debug("GetAllPolicyInstance")
465         var policyTypeInstances = []models.PolicyInstanceID{}
466
467         keys, err := rh.db.GetAll("A1m_ns")
468
469         if err != nil {
470                 a1.Logger.Error("error in retrieving policy. err: %v", err)
471                 return policyTypeInstances, err
472         }
473         a1.Logger.Debug("keys : %+v", keys)
474         typekey := a1InstancePrefix + strconv.FormatInt((int64(policyTypeId)), 10) + "."
475
476         for _, key := range keys {
477                 if strings.HasPrefix(strings.TrimLeft(key, " "), typekey) {
478                         pti := strings.Split(strings.Trim(key, " "), typekey)[1]
479                         a1.Logger.Debug("pti %+v", pti)
480                         policyTypeInstances = append(policyTypeInstances, models.PolicyInstanceID(pti))
481                 }
482         }
483
484         if len(policyTypeInstances) == 0 {
485                 a1.Logger.Debug("policy instance Not Present  ")
486         }
487
488         a1.Logger.Debug("return : %+v", policyTypeInstances)
489         return policyTypeInstances, nil
490 }
491
492 func (rh *Resthook) DeletePolicyType(policyTypeId models.PolicyTypeID) error {
493         a1.Logger.Debug("DeletePolicyType")
494
495         policyinstances, err := rh.GetAllPolicyInstance(policyTypeId)
496         if err != nil {
497                 a1.Logger.Error("error in retrieving policy. err: %v", err)
498                 return err
499         }
500
501         var keys [1]string
502         key := a1PolicyPrefix + strconv.FormatInt((int64(policyTypeId)), 10)
503         keys[0] = key
504         if len(policyinstances) == 0 {
505                 err := rh.db.Remove(a1MediatorNs, keys[:])
506                 if err != nil {
507                         a1.Logger.Error("error in deleting policy type err: %v", err)
508                         return err
509                 }
510         } else {
511                 a1.Logger.Error("tried to delete a type that isn't empty")
512                 return policyTypeCanNotBeDeletedError
513         }
514         return nil
515 }
516
517 func (rh *Resthook) typeValidity(policyTypeId models.PolicyTypeID) error {
518         var keys [1]string
519
520         typekey := a1PolicyPrefix + strconv.FormatInt((int64(policyTypeId)), 10)
521         keys[0] = typekey
522
523         a1.Logger.Debug("key1 : %+v", typekey)
524         valmap, err := rh.db.Get(a1MediatorNs, keys[:])
525         if err != nil {
526                 a1.Logger.Error("error in retrieving policytype err: %v", err)
527                 return err
528         }
529         if len(valmap) == 0 {
530                 a1.Logger.Error("policy type Not Present for policyid : %v", policyTypeId)
531                 return policyTypeNotFoundError
532         }
533         return nil
534 }
535
536 func (rh *Resthook) instanceValidity(policyTypeId models.PolicyTypeID, policyInstanceID models.PolicyInstanceID) error {
537         err := rh.typeValidity(policyTypeId)
538         if err != nil {
539                 return err
540         }
541         policyTypeInstances, err := rh.GetPolicyInstance(policyTypeId, policyInstanceID)
542         if err != nil {
543                 a1.Logger.Error("policy instance error : %v", err)
544                 return err
545         }
546         if len(policyTypeInstances.(string)) == 0 {
547                 a1.Logger.Debug("policy instance Not Present  ")
548                 return policyInstanceNotFoundError
549         }
550         return nil
551 }
552
553 func (rh *Resthook) getMetaData(policyTypeId models.PolicyTypeID, policyInstanceID models.PolicyInstanceID) (map[string]interface{}, error) {
554         instanceMetadataKey := a1InstanceMetadataPrefix + strconv.FormatInt((int64(policyTypeId)), 10) + "." + string(policyInstanceID)
555         a1.Logger.Debug("instanceMetadata key : %+v", instanceMetadataKey)
556         var keys [1]string
557         keys[0] = instanceMetadataKey
558         instanceMetadataMap, err := rh.db.Get(a1MediatorNs, keys[:])
559         if err != nil {
560                 a1.Logger.Error("policy instance error : %v", err)
561         }
562         a1.Logger.Debug("instanceMetadata map : %+v", instanceMetadataMap)
563         if instanceMetadataMap[instanceMetadataKey] == nil {
564                 a1.Logger.Error("policy instance Not Present for policyinstaneid : %v", policyInstanceID)
565                 return map[string]interface{}{}, policyInstanceNotFoundError
566         }
567         return instanceMetadataMap, nil
568 }
569
570 func (rh *Resthook) GetPolicyInstanceStatus(policyTypeId models.PolicyTypeID, policyInstanceID models.PolicyInstanceID) (*a1_mediator.A1ControllerGetPolicyInstanceStatusOKBody, error) {
571         err := rh.instanceValidity(policyTypeId, policyInstanceID)
572         policyInstanceStatus := a1_mediator.A1ControllerGetPolicyInstanceStatusOKBody{}
573         if err != nil && err == policyInstanceNotFoundError || err == policyTypeNotFoundError {
574                 policyInstanceStatus.InstanceStatus = "NOT IN EFFECT"
575                 return &policyInstanceStatus, err
576         }
577         metadata, err := rh.getMetaData(policyTypeId, policyInstanceID)
578         a1.Logger.Debug(" metadata %v", metadata)
579         if err != nil {
580                 a1.Logger.Error("policy instance error : %v", err)
581                 policyInstanceStatus.InstanceStatus = "NOT IN EFFECT"
582                 return &policyInstanceStatus, err
583         }
584         jsonbody, err := json.Marshal(metadata)
585         if err != nil {
586                 a1.Logger.Error("marshal error : %v", err)
587                 return &policyInstanceStatus, err
588         }
589
590         if err := json.Unmarshal(jsonbody, &policyInstanceStatus); err != nil {
591                 a1.Logger.Error("unmarshal error : %v", err)
592                 //this error maps to 503 error but can be mapped to 500: internal error
593                 return &policyInstanceStatus, err
594         }
595         if policyInstanceStatus.HasBeenDeleted == false {
596                 policyInstanceStatus.InstanceStatus = "IN EFFECT"
597         } else {
598                 policyInstanceStatus.InstanceStatus = "NOT IN EFFECT"
599         }
600         return &policyInstanceStatus, nil
601 }
602
603 func (rh *Resthook) storeDeletedPolicyInstanceMetadata(policyTypeId models.PolicyTypeID, policyInstanceID models.PolicyInstanceID, creation_timestamp string) error {
604         deleted_timestamp := time.Now()
605
606         instanceMetadataKey := a1InstanceMetadataPrefix + strconv.FormatInt((int64(policyTypeId)), 10) + "." + string(policyInstanceID)
607
608         a1.Logger.Debug("instanceMetadata Key : %+v", instanceMetadataKey)
609
610         var metadatajson interface{}
611         metadatajson = map[string]string{"created_at": creation_timestamp, "has_been_deleted": "True", "deleted_at": deleted_timestamp.Format("2006-01-02 15:04:05")}
612         a1.Logger.Debug("metadatajson to create : %+v", metadatajson)
613         deletedmetadata, err := json.Marshal(metadatajson)
614
615         a1.Logger.Debug("policyinstanceMetaData to create : %+v", string(deletedmetadata))
616
617         err = rh.db.Set(a1MediatorNs, instanceMetadataKey, string(deletedmetadata))
618         a1.Logger.Debug("deletemetadatacreated")
619         if err != nil {
620                 a1.Logger.Error("error :%+v", err)
621                 return err
622         }
623
624         a1.Logger.Error("Policy Instance Meta Data deleted at :%+v", creation_timestamp)
625
626         return nil
627 }
628
629 func (rh *Resthook) deleteInstancedata(policyTypeId models.PolicyTypeID, policyInstanceID models.PolicyInstanceID) error {
630         var keys [1]string
631         instancekey := a1InstancePrefix + strconv.FormatInt((int64(policyTypeId)), 10) + "." + string(policyInstanceID)
632         keys[0] = instancekey
633         err := rh.db.Remove(a1MediatorNs, keys[:])
634         if err != nil {
635                 a1.Logger.Error("error in deleting policy type err: %v", err)
636                 return err
637         }
638         return nil
639 }
640
641 func (rh *Resthook) deleteMetadata(policyTypeId models.PolicyTypeID, policyInstanceID models.PolicyInstanceID) error {
642         var keys [1]string
643         instanceMetadataKey := a1InstanceMetadataPrefix + strconv.FormatInt((int64(policyTypeId)), 10) + "." + string(policyInstanceID)
644
645         a1.Logger.Debug("instanceMetadata Key : %+v", instanceMetadataKey)
646         keys[0] = instanceMetadataKey
647         err := rh.db.Remove(a1MediatorNs, keys[:])
648         if err != nil {
649                 a1.Logger.Error("error in deleting policy metadata err: %v", err)
650                 return err
651         }
652         return nil
653 }
654
655 func (rh *Resthook) DeletePolicyInstance(policyTypeId models.PolicyTypeID, policyInstanceID models.PolicyInstanceID) error {
656         err := rh.instanceValidity(policyTypeId, policyInstanceID)
657         if err != nil {
658                 a1.Logger.Error("policy instance error : %v", err)
659                 if err == policyInstanceNotFoundError || err == policyTypeNotFoundError {
660                         return err
661                 }
662         }
663
664         createdmetadata, err := rh.getMetaData(policyTypeId, policyInstanceID)
665         if err != nil {
666                 a1.Logger.Error("error : %v", err)
667                 return err
668         }
669         a1.Logger.Debug(" created metadata %v", createdmetadata)
670         instanceMetadataKey := a1InstanceMetadataPrefix + strconv.FormatInt((int64(policyTypeId)), 10) + "." + string(policyInstanceID)
671         creation_metadata := createdmetadata[instanceMetadataKey]
672         var metadata map[string]interface{}
673         if err = json.Unmarshal([]byte(creation_metadata.(string)), &metadata); err != nil {
674                 a1.Logger.Error("unmarshal error : %v", err)
675                 return err
676         }
677
678         a1.Logger.Debug(" created metadata created_at %v", metadata["created_at"])
679         creation_timestamp := metadata["created_at"]
680
681         rh.deleteMetadata(policyTypeId, policyInstanceID)
682
683         rh.deleteInstancedata(policyTypeId, policyInstanceID)
684
685         rh.storeDeletedPolicyInstanceMetadata(policyTypeId, policyInstanceID, creation_timestamp.(string))
686
687         message := rmr.Message{}
688         rmrMessage, err1 := message.PolicyMessage(strconv.FormatInt((int64(policyTypeId)), 10), string(policyInstanceID), "", "DELETE")
689         if err1 != nil {
690                 a1.Logger.Error("error : %v", err1)
691                 return err1
692         }
693         isSent := rh.iRmrSenderInst.RmrSendToXapp(rmrMessage, a1PolicyRequest)
694         if isSent {
695                 a1.Logger.Debug("rmrSendToXapp : message sent")
696         } else {
697                 //TODO:if message not sent need to return error or just log it or retry sending
698                 a1.Logger.Error("rmrSendToXapp : message not sent")
699         }
700
701         return nil
702 }
703
704 func (rh *Resthook) DataDelivery(httpBody interface{}) error {
705         a1.Logger.Debug("httpbody : %+v", httpBody)
706         mymap := httpBody.(map[string]interface{})
707         message := rmr.Message{}
708         rmrMessage, err := message.A1EIMessage(mymap["job"].(string), mymap["payload"].(string))
709         if err != nil {
710                 a1.Logger.Error("error : %v", err)
711                 return err
712         }
713         a1.Logger.Debug("rmrSendToXapp :rmrMessage %+v", rmrMessage)
714         isSent := rh.iRmrSenderInst.RmrSendToXapp(rmrMessage, a1EIDataDelivery)
715         if isSent {
716                 a1.Logger.Debug("rmrSendToXapp : message sent")
717         } else {
718                 a1.Logger.Error("rmrSendToXapp : message not sent")
719         }
720         return nil
721 }