RIC:1060: Change in PTL
[ric-plt/nodeb-rnib.git] / reader / rNibReader.go
index 49ee38c..6f33273 100644 (file)
@@ -1,6 +1,7 @@
 //
 // Copyright 2019 AT&T Intellectual Property
 // Copyright 2019 Nokia
+// Copyright 2023 Capgemini
 //
 // Licensed under the Apache License, Version 2.0 (the "License");
 // you may not use this file except in compliance with the License.
 // See the License for the specific language governing permissions and
 // limitations under the License.
 
+//  This source code is part of the near-RT RIC (RAN Intelligent Controller)
+//  platform project (RICP).
+
 package reader
 
 import (
+       "encoding/json"
        "gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/common"
        "gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/entities"
-       "gerrit.o-ran-sc.org/r/ric-plt/sdlgo"
        "github.com/golang/protobuf/proto"
-       "github.com/pkg/errors"
        "reflect"
 )
 
-var readerPool *common.Pool
+const E2TAddressesKey = "E2TAddresses"
 
 type rNibReaderInstance struct {
-       sdl       *common.ISdlInstance
-       namespace string
+       sdl        common.ISdlInstance //Deprecated: Will be removed in a future release and replaced by sdlStorage
+       sdlStorage common.ISdlSyncStorage
+       ns         string
 }
 
 /*
@@ -37,71 +41,99 @@ RNibReader interface allows retrieving data from redis BD by various keys
 */
 type RNibReader interface {
        // GetNodeb retrieves responding nodeb entity from redis DB by nodeb inventory name
-       GetNodeb(inventoryName string) (*entities.NodebInfo, common.IRNibError)
+       GetNodeb(inventoryName string) (*entities.NodebInfo, error)
        // GetNodebByGlobalNbId retrieves responding nodeb entity from redis DB by nodeb global Id
-       GetNodebByGlobalNbId(nodeType entities.Node_Type, globalNbId *entities.GlobalNbId) (*entities.NodebInfo, common.IRNibError)
+       GetNodebByGlobalNbId(nodeType entities.Node_Type, globalNbId *entities.GlobalNbId, cuupId string,duid string) (*entities.NodebInfo, error)
        // GetCellList retrieves the list of cell entities belonging to responding nodeb entity from redis DB by nodeb inventory name
-       GetCellList(inventoryName string) (*entities.Cells, common.IRNibError)
+       GetCellList(inventoryName string) (*entities.Cells, error)
        // GetListGnbIds retrieves the list of gNodeb identity entities
-       GetListGnbIds() (*[]*entities.NbIdentity, common.IRNibError)
+       GetListGnbIds() ([]*entities.NbIdentity, error)
        // GetListEnbIds retrieves the list of eNodeb identity entities
-       GetListEnbIds() (*[]*entities.NbIdentity, common.IRNibError)
+       GetListEnbIds() ([]*entities.NbIdentity, error)
        // Close closes reader's pool
-       GetCountGnbList() (int, common.IRNibError)
+       GetCountGnbList() (int, error)
        // GetCell retrieves the cell entity belonging to responding nodeb from redis DB by nodeb inventory name and cell pci
-       GetCell(inventoryName string, pci uint32) (*entities.Cell, common.IRNibError)
+       GetCell(inventoryName string, pci uint32) (*entities.Cell, error)
        // GetCellById retrieves the cell entity from redis DB by cell type and cell Id
-       GetCellById(cellType entities.Cell_Type, cellId string) (*entities.Cell, common.IRNibError)
+       GetCellById(cellType entities.Cell_Type, cellId string) (*entities.Cell, error)
        // GetListNodebIds returns the full list of Nodeb identity entities
-       GetListNodebIds()([]*entities.NbIdentity, common.IRNibError)
+       GetListNodebIds() ([]*entities.NbIdentity, error)
        // GetRanLoadInformation retrieves nodeb load information entity from redis DB by nodeb inventory name
-       GetRanLoadInformation(inventoryName string) (*entities.RanLoadInformation, common.IRNibError)
+       GetRanLoadInformation(inventoryName string) (*entities.RanLoadInformation, error)
+
+       GetE2TInstance(address string) (*entities.E2TInstance, error)
+
+       GetE2TInstances(addresses []string) ([]*entities.E2TInstance, error)
+
+       GetE2TAddresses() ([]string, error)
+
+       GetGeneralConfiguration() (*entities.GeneralConfiguration, error)
+
+        GetRanFunctionDefinition(inventoryName string, Oid string) ([]string, error)
 }
 
-/*
- Init initializes the infrastructure required for the RNibReader instance
-*/
-func Init(namespace string, poolSize int) {
-       initPool(poolSize,
-               func() interface{} {
-                       var sdlI common.ISdlInstance = sdlgo.NewSdlInstance(namespace, sdlgo.NewDatabase())
-                       return &rNibReaderInstance{sdl: &sdlI, namespace: namespace}
-               },
-               func(obj interface{}) {
-                       (*obj.(*rNibReaderInstance).sdl).Close()
-               })
+//GetNewRNibReader returns reference to RNibReader
+func GetNewRNibReader(storage common.ISdlSyncStorage) RNibReader {
+       return &rNibReaderInstance{
+               sdl: nil,
+               sdlStorage: storage,
+               ns:         common.GetRNibNamespace(),
+       }
 }
 
-func initPool(poolSize int, newObj func() interface{}, destroyObj func(interface{})) {
-       readerPool = common.NewPool(poolSize, newObj, destroyObj)
+//GetRanFunctionDefinition from the OID
+func (w *rNibReaderInstance) GetRanFunctionDefinition(inventoryName string, oid string) ([]string, error){
+    nb, err := w.GetNodeb (inventoryName)
+    if (nb.GetGnb() != nil) {
+        ranFunction := nb.GetGnb().RanFunctions
+        functionDefinitionList := make([]string, 0)
+        for _, ranFunction := range ranFunction {
+            if (oid == ranFunction.RanFunctionOid) {
+                functionDefinitionList = append(functionDefinitionList ,ranFunction.RanFunctionDefinition)
+                }
+        }
+        return functionDefinitionList, err
+    }
+    return nil, common.NewResourceNotFoundErrorf("#rNibReader.GetCellList - served cells not found. Responding node RAN name: %    s.", inventoryName)
 }
 
-/*
-GetRNibReader returns RNibReader instance from the pool
-*/
-func GetRNibReader() RNibReader {
-       return readerPool.Get().(RNibReader)
+//GetRNibReader returns reference to RNibReader
+//Deprecated: Will be removed in a future release, please use GetNewRNibReader instead.
+func GetRNibReader(sdl common.ISdlInstance) RNibReader {
+       return &rNibReaderInstance{
+               sdl:        sdl,
+               sdlStorage: nil,
+               ns:         "",
+       }
 }
 
-func (w *rNibReaderInstance) GetNodeb(inventoryName string) (*entities.NodebInfo, common.IRNibError) {
-       defer readerPool.Put(w)
+func (w *rNibReaderInstance) GetNodeb(inventoryName string) (*entities.NodebInfo, error) {
        key, rNibErr := common.ValidateAndBuildNodeBNameKey(inventoryName)
        if rNibErr != nil {
                return nil, rNibErr
        }
-       return w.getNodeb(key)
+       nbInfo := &entities.NodebInfo{}
+       err := w.getByKeyAndUnmarshal(key, nbInfo)
+       if err != nil {
+               return nil, err
+       }
+       return nbInfo, nil
 }
 
-func (w *rNibReaderInstance) GetNodebByGlobalNbId(nodeType entities.Node_Type, globalNbId *entities.GlobalNbId) (*entities.NodebInfo, common.IRNibError) {
-       defer readerPool.Put(w)
-       key, rNibErr := common.ValidateAndBuildNodeBIdKey(nodeType.String(), globalNbId.GetPlmnId(), globalNbId.GetNbId())
+func (w *rNibReaderInstance) GetNodebByGlobalNbId(nodeType entities.Node_Type, globalNbId *entities.GlobalNbId, cuupid string, duid string) (*entities.NodebInfo, error) {
+       key, rNibErr := common.ValidateAndBuildNodeBIdKey(nodeType.String(), globalNbId.GetPlmnId(), globalNbId.GetNbId(), cuupid, duid)
        if rNibErr != nil {
                return nil, rNibErr
        }
-       return w.getNodeb(key)
+       nbInfo := &entities.NodebInfo{}
+       err := w.getByKeyAndUnmarshal(key, nbInfo)
+       if err != nil {
+               return nil, err
+       }
+       return nbInfo, nil
 }
 
-func (w *rNibReaderInstance) GetCellList(inventoryName string) (*entities.Cells, common.IRNibError) {
+func (w *rNibReaderInstance) GetCellList(inventoryName string) (*entities.Cells, error) {
        cells := &entities.Cells{}
        nb, err := w.GetNodeb(inventoryName)
        if err != nil {
@@ -111,148 +143,237 @@ func (w *rNibReaderInstance) GetCellList(inventoryName string) (*entities.Cells,
                cells.Type = entities.Cell_LTE_CELL
                cells.List = &entities.Cells_ServedCellInfos{ServedCellInfos: &entities.ServedCellInfoList{ServedCells: nb.GetEnb().GetServedCells()}}
                return cells, nil
-       } else if nb.GetGnb() != nil && len(nb.GetGnb().GetServedNrCells()) > 0 {
+       }
+       if nb.GetGnb() != nil && len(nb.GetGnb().GetServedNrCells()) > 0 {
                cells.Type = entities.Cell_NR_CELL
                cells.List = &entities.Cells_ServedNrCells{ServedNrCells: &entities.ServedNRCellList{ServedCells: nb.GetGnb().GetServedNrCells()}}
                return cells, nil
        }
-       return nil, common.NewResourceNotFoundError(errors.Errorf("#rNibReader.GetCellList - served cells not found. Responding node RAN name: %s.", inventoryName))
+       return nil, common.NewResourceNotFoundErrorf("#rNibReader.GetCellList - served cells not found. Responding node RAN name: %s.", inventoryName)
 }
 
-func (w *rNibReaderInstance) GetListGnbIds() (*[]*entities.NbIdentity, common.IRNibError) {
-       defer readerPool.Put(w)
+func (w *rNibReaderInstance) GetListGnbIds() ([]*entities.NbIdentity, error) {
        return w.getListNodebIdsByType(entities.Node_GNB.String())
 }
 
-func (w *rNibReaderInstance) GetListEnbIds() (*[]*entities.NbIdentity, common.IRNibError) {
-       defer readerPool.Put(w)
+func (w *rNibReaderInstance) GetListEnbIds() ([]*entities.NbIdentity, error) {
        return w.getListNodebIdsByType(entities.Node_ENB.String())
 }
 
-func (w *rNibReaderInstance) GetCountGnbList() (int, common.IRNibError) {
-       defer readerPool.Put(w)
-       size, err := (*w.sdl).GroupSize(entities.Node_GNB.String())
+func (w *rNibReaderInstance) GetCountGnbList() (int, error) {
+       var size int64
+       var err error
+       if w.sdlStorage != nil {
+               size, err = w.sdlStorage.GroupSize(w.ns, entities.Node_GNB.String())
+       } else {
+               size, err = w.sdl.GroupSize(entities.Node_GNB.String())
+       }
        if err != nil {
                return 0, common.NewInternalError(err)
        }
        return int(size), nil
 }
 
-func (w *rNibReaderInstance) GetCell(inventoryName string, pci uint32) (*entities.Cell, common.IRNibError) {
-       defer readerPool.Put(w)
+func (w *rNibReaderInstance) GetCell(inventoryName string, pci uint32) (*entities.Cell, error) {
        key, rNibErr := common.ValidateAndBuildCellNamePciKey(inventoryName, pci)
        if rNibErr != nil {
                return nil, rNibErr
        }
-       return w.getCellByKey(key)
+       cell := &entities.Cell{}
+       err := w.getByKeyAndUnmarshal(key, cell)
+       if err != nil {
+               return nil, err
+       }
+       return cell, err
 }
 
-func (w *rNibReaderInstance) GetCellById(cellType entities.Cell_Type, cellId string) (*entities.Cell, common.IRNibError) {
-       defer readerPool.Put(w)
+func (w *rNibReaderInstance) GetCellById(cellType entities.Cell_Type, cellId string) (*entities.Cell, error) {
        var key string
-       var rNibErr common.IRNibError
+       var rNibErr error
        if cellType == entities.Cell_LTE_CELL {
                key, rNibErr = common.ValidateAndBuildCellIdKey(cellId)
        } else if cellType == entities.Cell_NR_CELL {
                key, rNibErr = common.ValidateAndBuildNrCellIdKey(cellId)
        } else {
-               return nil, common.NewValidationError(errors.Errorf("#rNibReader.GetCellById - invalid cell type: %v", cellType))
+               return nil, common.NewValidationErrorf("#rNibReader.GetCellById - invalid cell type: %v", cellType)
        }
        if rNibErr != nil {
                return nil, rNibErr
        }
-       return w.getCellByKey(key)
+       cell := &entities.Cell{}
+       err := w.getByKeyAndUnmarshal(key, cell)
+       if err != nil {
+               return nil, err
+       }
+       return cell, err
 }
 
-func (w *rNibReaderInstance) GetListNodebIds()([]*entities.NbIdentity, common.IRNibError){
-       defer readerPool.Put(w)
-       dataEnb, err := (*w.sdl).GetMembers(entities.Node_ENB.String())
-       if err != nil{
-               return nil, common.NewInternalError(err)
+func (w *rNibReaderInstance) GetListNodebIds() ([]*entities.NbIdentity, error) {
+       var dataEnb, dataGnb []string
+       var err error
+       if w.sdlStorage != nil {
+               dataEnb, err = w.sdlStorage.GetMembers(w.ns, entities.Node_ENB.String())
+       } else {
+               dataEnb, err = w.sdl.GetMembers(entities.Node_ENB.String())
        }
-       dataGnb, err := (*w.sdl).GetMembers(entities.Node_GNB.String())
-       if err != nil{
+       if err != nil {
                return nil, common.NewInternalError(err)
        }
-       dataUnknown, err := (*w.sdl).GetMembers(entities.Node_UNKNOWN.String())
-       if err != nil{
+       if w.sdlStorage != nil {
+               dataGnb, err = w.sdlStorage.GetMembers(w.ns, entities.Node_GNB.String())
+       } else {
+               dataGnb, err = w.sdl.GetMembers(entities.Node_GNB.String())
+       }
+       if err != nil {
                return nil, common.NewInternalError(err)
        }
        allIds := append(dataEnb, dataGnb...)
-       allIds = append(allIds, dataUnknown...)
-       data, rnibErr := unmarshalIdentityList(allIds)
-       return *data, rnibErr
+       data, rnibErr := w.unmarshalIdentityList(allIds)
+       return data, rnibErr
 }
 
-func (w *rNibReaderInstance) GetRanLoadInformation(inventoryName string) (*entities.RanLoadInformation, common.IRNibError){
+func (w *rNibReaderInstance) GetRanLoadInformation(inventoryName string) (*entities.RanLoadInformation, error) {
        key, rNibErr := common.ValidateAndBuildRanLoadInformationKey(inventoryName)
        if rNibErr != nil {
                return nil, rNibErr
        }
        loadInfo := &entities.RanLoadInformation{}
        err := w.getByKeyAndUnmarshal(key, loadInfo)
-       if err!= nil{
+       if err != nil {
                return nil, err
        }
        return loadInfo, err
 }
 
-func (w *rNibReaderInstance) getByKeyAndUnmarshal(key string, entity proto.Message)common.IRNibError{
-       data, err := (*w.sdl).Get([]string{key})
+func (w *rNibReaderInstance) GetE2TInstance(address string) (*entities.E2TInstance, error) {
+       key, rNibErr := common.ValidateAndBuildE2TInstanceKey(address)
+       if rNibErr != nil {
+               return nil, rNibErr
+       }
+       e2tInstance := &entities.E2TInstance{}
+       err := w.getByKeyAndUnmarshalJson(key, e2tInstance)
        if err != nil {
-               return common.NewInternalError(err)
+               return nil, err
        }
-       if data != nil && data[key] != nil {
-               err = proto.Unmarshal([]byte(data[key].(string)), entity)
-               if err != nil {
-                       return common.NewInternalError(err)
+       return e2tInstance, err
+}
+
+func (w *rNibReaderInstance) GetE2TInstances(addresses []string) ([]*entities.E2TInstance, error) {
+       var data map[string]interface{}
+       var err error
+
+       keys := common.MapE2TAddressesToKeys(addresses)
+
+       e2tInstances := []*entities.E2TInstance{}
+
+       if w.sdlStorage != nil {
+               data, err = w.sdlStorage.Get(w.ns, keys)
+       } else {
+               data, err = w.sdl.Get(keys)
+       }
+
+       if err != nil {
+               return []*entities.E2TInstance{}, common.NewInternalError(err)
+       }
+
+       if len(data) == 0 {
+               return []*entities.E2TInstance{}, common.NewResourceNotFoundErrorf("#rNibReader.GetE2TInstances - e2t instances not found")
+       }
+
+       for _, v := range keys {
+
+               if data[v] != nil {
+                       var e2tInstance entities.E2TInstance
+                       err = json.Unmarshal([]byte(data[v].(string)), &e2tInstance)
+                       if err != nil {
+                               continue
+                       }
+
+                       e2tInstances = append(e2tInstances, &e2tInstance)
                }
-               return nil
        }
-       return common.NewResourceNotFoundError(errors.Errorf("#rNibReader.getByKeyAndUnmarshal - entity of type %s not found. Key: %s", reflect.TypeOf(entity).String(), key))
+
+       return e2tInstances, nil
 }
 
-func (w *rNibReaderInstance) getNodeb(key string) (*entities.NodebInfo, common.IRNibError) {
-       data, err := (*w.sdl).Get([]string{key})
+func (w *rNibReaderInstance) GetE2TAddresses() ([]string, error) {
+       var e2tAddresses []string
+       err := w.getByKeyAndUnmarshalJson(E2TAddressesKey, &e2tAddresses)
        if err != nil {
-               return nil, common.NewInternalError(err)
+               return nil, err
        }
-       nb := entities.NodebInfo{}
+       return e2tAddresses, err
+}
+
+func (w *rNibReaderInstance) GetGeneralConfiguration() (*entities.GeneralConfiguration, error) {
+       config := &entities.GeneralConfiguration{}
+       key := common.BuildGeneralConfigurationKey()
+
+       err := w.getByKeyAndUnmarshalJson(key, config)
+
+       return config, err
+}
+
+func (w *rNibReaderInstance) getByKeyAndUnmarshalJson(key string, entity interface{}) error {
+       var data map[string]interface{}
+       var err error
+       if w.sdlStorage != nil {
+               data, err = w.sdlStorage.Get(w.ns, []string{key})
+       } else {
+               data, err = w.sdl.Get([]string{key})
+       }
+
+       if err != nil {
+               return common.NewInternalError(err)
+       }
+
        if data != nil && data[key] != nil {
-               err = proto.Unmarshal([]byte(data[key].(string)), &nb)
+               err = json.Unmarshal([]byte(data[key].(string)), entity)
                if err != nil {
-                       return nil, common.NewInternalError(err)
+                       return common.NewInternalError(err)
                }
-               return &nb, nil
+               return nil
        }
-       return nil, common.NewResourceNotFoundError(errors.Errorf("#rNibReader.getNodeb - responding node not found. Key: %s", key))
+       return common.NewResourceNotFoundErrorf("#rNibReader.getByKeyAndUnmarshalJson - entity of type %s not found. Key: %s", reflect.TypeOf(entity).String(), key)
 }
 
-func (w *rNibReaderInstance) getCellByKey(key string) (*entities.Cell, common.IRNibError) {
-       data, err := (*w.sdl).Get([]string{key})
+func (w *rNibReaderInstance) getByKeyAndUnmarshal(key string, entity proto.Message) error {
+       var data map[string]interface{}
+       var err error
+       if w.sdlStorage != nil {
+               data, err = w.sdlStorage.Get(w.ns, []string{key})
+       } else {
+               data, err = w.sdl.Get([]string{key})
+       }
+
        if err != nil {
-               return nil, common.NewInternalError(err)
+               return common.NewInternalError(err)
        }
-       cell := entities.Cell{}
        if data != nil && data[key] != nil {
-               err = proto.Unmarshal([]byte(data[key].(string)), &cell)
+               err = proto.Unmarshal([]byte(data[key].(string)), entity)
                if err != nil {
-                       return nil, common.NewInternalError(err)
+                       return common.NewInternalError(err)
                }
-               return &cell, nil
+               return nil
        }
-       return nil, common.NewResourceNotFoundError(errors.Errorf("#rNibReader.getCellByKey - cell not found, key: %s", key))
+       return common.NewResourceNotFoundErrorf("#rNibReader.getByKeyAndUnmarshal - entity of type %s not found. Key: %s", reflect.TypeOf(entity).String(), key)
 }
 
-func (w *rNibReaderInstance) getListNodebIdsByType(nbType string) (*[]*entities.NbIdentity, common.IRNibError) {
-       data, err := (*w.sdl).GetMembers(nbType)
+func (w *rNibReaderInstance) getListNodebIdsByType(nbType string) ([]*entities.NbIdentity, error) {
+       var data []string
+       var err error
+       if w.sdlStorage != nil {
+               data, err = w.sdlStorage.GetMembers(w.ns, nbType)
+       } else {
+               data, err = w.sdl.GetMembers(nbType)
+       }
        if err != nil {
                return nil, common.NewInternalError(err)
        }
-       return unmarshalIdentityList(data)
+       return w.unmarshalIdentityList(data)
 }
 
-func unmarshalIdentityList(data []string) (*[]*entities.NbIdentity, common.IRNibError) {
+func (w *rNibReaderInstance) unmarshalIdentityList(data []string) ([]*entities.NbIdentity, error) {
        var members []*entities.NbIdentity
        for _, d := range data {
                member := entities.NbIdentity{}
@@ -262,9 +383,10 @@ func unmarshalIdentityList(data []string) (*[]*entities.NbIdentity, common.IRNib
                }
                members = append(members, &member)
        }
-       return &members, nil
+       return members, nil
 }
 
+//Close the reader
 func Close() {
-       readerPool.Close()
-}
\ No newline at end of file
+       // Nothing to do
+}