From 724ebdc039d3d5ffaa39844d9eb8ecf31cfed455 Mon Sep 17 00:00:00 2001 From: Radu Ioan Fericean Date: Mon, 17 Mar 2014 21:23:47 +0200 Subject: [PATCH] split rating profile and account aliases --- apier/apier.go | 39 ++++++++++------ apier/apier_local_test.go | 3 ++ cmd/cgr-engine/cgr-engine.go | 2 +- cmd/cgr-loader/cgr-loader.go | 5 ++- engine/calldesc.go | 6 +-- engine/loader_csv.go | 54 ++++++++++++++++------ engine/loader_csv_test.go | 28 +++++++----- engine/loader_db.go | 40 ++++++++++++----- engine/storage_interface.go | 14 +++--- engine/storage_map.go | 69 +++++++++++++++++++++------- engine/storage_redis.go | 87 ++++++++++++++++++++++++++++++------ engine/storage_test.go | 2 +- utils/apitpdata.go | 3 +- 13 files changed, 261 insertions(+), 91 deletions(-) diff --git a/apier/apier.go b/apier/apier.go index 5bc3b4381..4ff3b8693 100644 --- a/apier/apier.go +++ b/apier/apier.go @@ -450,7 +450,7 @@ func (self *ApierV1) LoadAccountActions(attrs utils.TPAccountActions, reply *str } // ToDo: Get the action keys loaded by dbReader so we reload only these in cache // Need to do it before scheduler otherwise actions to run will be unknown - if err := self.AccountDb.CacheAccounting(nil, nil); err != nil { + if err := self.AccountDb.CacheAccounting(nil, nil, nil); err != nil { return err } if self.Sched != nil { @@ -473,7 +473,7 @@ func (self *ApierV1) ReloadScheduler(input string, reply *string) error { } func (self *ApierV1) ReloadCache(attrs utils.ApiReloadCache, reply *string) error { - var dstKeys, rpKeys, rpfKeys, actKeys, shgKeys, alsKeys []string + var dstKeys, rpKeys, rpfKeys, actKeys, shgKeys, rpAlsKeys, accAlsKeys []string if len(attrs.DestinationIds) > 0 { dstKeys = make([]string, len(attrs.DestinationIds)) for idx, dId := range attrs.DestinationIds { @@ -504,16 +504,22 @@ func (self *ApierV1) ReloadCache(attrs utils.ApiReloadCache, reply *string) erro shgKeys[idx] = engine.SHARED_GROUP_PREFIX + shgId } } - if len(attrs.Aliases) > 0 { - alsKeys = make([]string, len(attrs.Aliases)) - for idx, alias := range attrs.Aliases { - alsKeys[idx] = engine.ALIAS_PREFIX + alias + if len(attrs.RpAliases) > 0 { + rpAlsKeys = make([]string, len(attrs.RpAliases)) + for idx, alias := range attrs.RpAliases { + rpAlsKeys[idx] = engine.RP_ALIAS_PREFIX + alias } } - if err := self.RatingDb.CacheRating(dstKeys, rpKeys, rpfKeys, alsKeys); err != nil { + if len(attrs.AccAliases) > 0 { + accAlsKeys = make([]string, len(attrs.AccAliases)) + for idx, alias := range attrs.AccAliases { + accAlsKeys[idx] = engine.ACC_ALIAS_PREFIX + alias + } + } + if err := self.RatingDb.CacheRating(dstKeys, rpKeys, rpfKeys, rpAlsKeys); err != nil { return err } - if err := self.AccountDb.CacheAccounting(actKeys, shgKeys); err != nil { + if err := self.AccountDb.CacheAccounting(actKeys, shgKeys, accAlsKeys); err != nil { return err } *reply = "OK" @@ -608,15 +614,20 @@ func (self *ApierV1) LoadTariffPlanFromFolder(attrs utils.AttrLoadTpFromFolder, for idx, shgId := range shgIds { shgKeys[idx] = engine.SHARED_GROUP_PREFIX + shgId } - aliases, _ := loader.GetLoadedIds(engine.ALIAS_PREFIX) - alsKeys := make([]string, len(aliases)) - for idx, alias := range aliases { - alsKeys[idx] = engine.ALIAS_PREFIX + alias + rpAliases, _ := loader.GetLoadedIds(engine.RP_ALIAS_PREFIX) + rpAlsKeys := make([]string, len(rpAliases)) + for idx, alias := range rpAliases { + rpAlsKeys[idx] = engine.RP_ALIAS_PREFIX + alias } - if err := self.RatingDb.CacheRating(dstKeys, rpKeys, rpfKeys, alsKeys); err != nil { + accAliases, _ := loader.GetLoadedIds(engine.ACC_ALIAS_PREFIX) + accAlsKeys := make([]string, len(accAliases)) + for idx, alias := range accAliases { + accAlsKeys[idx] = engine.ACC_ALIAS_PREFIX + alias + } + if err := self.RatingDb.CacheRating(dstKeys, rpKeys, rpfKeys, rpAlsKeys); err != nil { return err } - if err := self.AccountDb.CacheAccounting(actKeys, shgKeys); err != nil { + if err := self.AccountDb.CacheAccounting(actKeys, shgKeys, accAliases); err != nil { return err } if self.Sched != nil { diff --git a/apier/apier_local_test.go b/apier/apier_local_test.go index 7369ac0d8..9e488dd9a 100644 --- a/apier/apier_local_test.go +++ b/apier/apier_local_test.go @@ -1217,6 +1217,9 @@ func TestTriggersExecute(t *testing.T) { // Start fresh before loading from folder func TestResetDataBeforeLoadFromFolder(t *testing.T) { + if !*testLocal { + return + } TestInitDataDb(t) reply := "" arc := new(utils.ApiReloadCache) diff --git a/cmd/cgr-engine/cgr-engine.go b/cmd/cgr-engine/cgr-engine.go index 5d82fbc2d..2f74c6c68 100644 --- a/cmd/cgr-engine/cgr-engine.go +++ b/cmd/cgr-engine/cgr-engine.go @@ -79,7 +79,7 @@ func cacheData(ratingDb engine.RatingStorage, accountDb engine.AccountingStorage exitChan <- true return } - if err := accountDb.CacheAccounting(nil, nil); err != nil { + if err := accountDb.CacheAccounting(nil, nil, nil); err != nil { engine.Logger.Crit(fmt.Sprintf("Cache accounting error: %s", err.Error())) exitChan <- true return diff --git a/cmd/cgr-loader/cgr-loader.go b/cmd/cgr-loader/cgr-loader.go index 4b01cdb93..751975397 100644 --- a/cmd/cgr-loader/cgr-loader.go +++ b/cmd/cgr-loader/cgr-loader.go @@ -188,12 +188,13 @@ func main() { rpfIds, _ := loader.GetLoadedIds(engine.RATING_PROFILE_PREFIX) actIds, _ := loader.GetLoadedIds(engine.ACTION_PREFIX) shgIds, _ := loader.GetLoadedIds(engine.SHARED_GROUP_PREFIX) - aliases, _ := loader.GetLoadedIds(engine.ALIAS_PREFIX) + rpAliases, _ := loader.GetLoadedIds(engine.RP_ALIAS_PREFIX) + accAliases, _ := loader.GetLoadedIds(engine.ACC_ALIAS_PREFIX) // Reload cache first since actions could be calling info from within if *verbose { log.Print("Reloading cache") } - if err = rater.Call("ApierV1.ReloadCache", utils.ApiReloadCache{dstIds, rplIds, rpfIds, actIds, shgIds, aliases}, &reply); err != nil { + if err = rater.Call("ApierV1.ReloadCache", utils.ApiReloadCache{dstIds, rplIds, rpfIds, actIds, shgIds, rpAliases, accAliases}, &reply); err != nil { log.Fatalf("Got error on cache reload: %s", err.Error()) } actTmgIds, _ := loader.GetLoadedIds(engine.ACTION_TIMING_PREFIX) diff --git a/engine/calldesc.go b/engine/calldesc.go index 928133e6b..c1bb509f2 100644 --- a/engine/calldesc.go +++ b/engine/calldesc.go @@ -138,7 +138,7 @@ func (cd *CallDescriptor) GetAccountKey() string { subj := cd.Subject if cd.Account != "" { // check if subject is alias - if realSubject, err := cache2go.GetCached(ALIAS_PREFIX + RATING_PROFILE_PREFIX + subj); err == nil { + if realSubject, err := cache2go.GetCached(ACC_ALIAS_PREFIX + subj); err == nil { cd.Account = realSubject.(string) } subj = cd.Account @@ -286,7 +286,7 @@ func (cd *CallDescriptor) addRatingInfos(ris RatingInfos) bool { // The prefixLen is limiting the length of the destination prefix. func (cd *CallDescriptor) GetKey(subject string) string { // check if subject is alias - if rs, err := cache2go.GetCached(ALIAS_PREFIX + RATING_PROFILE_PREFIX + subject); err == nil { + if rs, err := cache2go.GetCached(RP_ALIAS_PREFIX + subject); err == nil { realSubject := rs.(string) subject = realSubject cd.Subject = realSubject @@ -630,7 +630,7 @@ func (cd *CallDescriptor) FlushCache() (err error) { cache2go.XFlush() cache2go.Flush() dataStorage.CacheRating(nil, nil, nil, nil) - accountingStorage.CacheAccounting(nil, nil) + accountingStorage.CacheAccounting(nil, nil, nil) return nil } diff --git a/engine/loader_csv.go b/engine/loader_csv.go index 2e6f08ad1..59abc7457 100644 --- a/engine/loader_csv.go +++ b/engine/loader_csv.go @@ -38,9 +38,11 @@ type CSVReader struct { actions map[string][]*Action actionsTimings map[string][]*ActionTiming actionsTriggers map[string][]*ActionTrigger - aliases map[string]string + rpAliases map[string]string + accAliases map[string]string accountActions map[string]*Account - dirtyAliases []string // used to clean aliases that might have changed + dirtyRpAliases []string // used to clean aliases that might have changed + dirtyAccAliases []string // used to clean aliases that might have changed destinations []*Destination timings map[string]*utils.TPTiming rates map[string]*utils.TPRate @@ -69,7 +71,8 @@ func NewFileCSVReader(dataStorage RatingStorage, accountingStorage AccountingSto c.ratingProfiles = make(map[string]*RatingProfile) c.sharedGroups = make(map[string]*SharedGroup) c.readerFunc = openFileCSVReader - c.aliases = make(map[string]string) + c.rpAliases = make(map[string]string) + c.accAliases = make(map[string]string) c.destinationsFn, c.timingsFn, c.ratesFn, c.destinationratesFn, c.destinationratetimingsFn, c.ratingprofilesFn, c.sharedgroupsFn, c.actionsFn, c.actiontimingsFn, c.actiontriggersFn, c.accountactionsFn = destinationsFn, timingsFn, ratesFn, destinationratesFn, destinationratetimingsFn, ratingprofilesFn, sharedgroupsFn, actionsFn, actiontimingsFn, actiontriggersFn, accountactionsFn @@ -249,13 +252,28 @@ func (csvr *CSVReader) WriteToDatabase(flush, verbose bool) (err error) { } } if verbose { - log.Print("Aliases") + log.Print("Rating profile liases") } - if err := dataStorage.RemoveAccountAliases(csvr.dirtyAliases); err != nil { + if err := dataStorage.RemoveRpAliases(csvr.dirtyRpAliases); err != nil { return err } - for key, alias := range csvr.aliases { - err = dataStorage.SetAlias(key, alias) + for key, alias := range csvr.rpAliases { + err = dataStorage.SetRpAlias(key, alias) + if err != nil { + return err + } + if verbose { + log.Print(key) + } + } + if verbose { + log.Print("Account aliases") + } + if err := accountingStorage.RemoveAccAliases(csvr.dirtyAccAliases); err != nil { + return err + } + for key, alias := range csvr.accAliases { + err = accountingStorage.SetAccAlias(key, alias) if err != nil { return err } @@ -448,13 +466,13 @@ func (csvr *CSVReader) LoadRatingProfiles() (err error) { if err != nil { return fmt.Errorf("Cannot parse activation time from %v", record[4]) } - csvr.dirtyAliases = append(csvr.dirtyAliases, subject) + csvr.dirtyRpAliases = append(csvr.dirtyRpAliases, subject) // extract aliases from subject aliases := strings.Split(subject, ";") if len(aliases) > 1 { subject = aliases[0] for _, alias := range aliases[1:] { - csvr.aliases[RATING_PROFILE_PREFIX+alias] = subject + csvr.rpAliases[alias] = subject } } key := fmt.Sprintf("%s:%s:%s:%s", direction, tenant, tor, subject) @@ -667,13 +685,13 @@ func (csvr *CSVReader) LoadAccountActions() (err error) { } for record, err := csvReader.Read(); err == nil; record, err = csvReader.Read() { tenant, account, direction := record[0], record[1], record[2] - csvr.dirtyAliases = append(csvr.dirtyAliases, account) + csvr.dirtyAccAliases = append(csvr.dirtyAccAliases, account) // extract aliases from subject aliases := strings.Split(account, ";") if len(aliases) > 1 { account = aliases[0] for _, alias := range aliases[1:] { - csvr.aliases[ACCOUNT_PREFIX+alias] = account + csvr.accAliases[alias] = account } } tag := fmt.Sprintf("%s:%s:%s", direction, tenant, account) @@ -782,10 +800,18 @@ func (csvr *CSVReader) GetLoadedIds(categ string) ([]string, error) { i++ } return keys, nil - case ALIAS_PREFIX: // aliases - keys := make([]string, len(csvr.aliases)) + case RP_ALIAS_PREFIX: // aliases + keys := make([]string, len(csvr.rpAliases)) i := 0 - for k := range csvr.aliases { + for k := range csvr.rpAliases { + keys[i] = k + i++ + } + return keys, nil + case ACC_ALIAS_PREFIX: // aliases + keys := make([]string, len(csvr.accAliases)) + i := 0 + for k := range csvr.accAliases { keys[i] = k i++ } diff --git a/engine/loader_csv_test.go b/engine/loader_csv_test.go index f05ed6bf1..a0b0c9044 100644 --- a/engine/loader_csv_test.go +++ b/engine/loader_csv_test.go @@ -169,7 +169,7 @@ func init() { csvr.LoadAccountActions() csvr.WriteToDatabase(false, false) dataStorage.CacheRating(nil, nil, nil, nil) - accountingStorage.CacheAccounting(nil, nil) + accountingStorage.CacheAccounting(nil, nil, nil) } func TestLoadDestinations(t *testing.T) { @@ -786,16 +786,24 @@ func TestLoadAccountActions(t *testing.T) { } } -func TestLoadAliases(t *testing.T) { - if len(csvr.aliases) != 5 { - t.Error("Failed to load aliases: ", csvr.aliases) +func TestLoadRpAliases(t *testing.T) { + if len(csvr.rpAliases) != 3 { + t.Error("Failed to load rp aliases: ", csvr.rpAliases) } - if csvr.aliases[RATING_PROFILE_PREFIX+"a1"] != "minu" || - csvr.aliases[RATING_PROFILE_PREFIX+"a2"] != "minu" || - csvr.aliases[RATING_PROFILE_PREFIX+"a3"] != "minu" || - csvr.aliases[ACCOUNT_PREFIX+"a1"] != "minitsboy" || - csvr.aliases[ACCOUNT_PREFIX+"a2"] != "minitsboy" { - t.Error("Error loading aliases: ", csvr.aliases) + if csvr.rpAliases["a1"] != "minu" || + csvr.rpAliases["a2"] != "minu" || + csvr.rpAliases["a3"] != "minu" { + t.Error("Error loading rp aliases: ", csvr.rpAliases) + } +} + +func TestLoadAccAliases(t *testing.T) { + if len(csvr.accAliases) != 2 { + t.Error("Failed to load acc aliases: ", csvr.accAliases) + } + if csvr.accAliases["a1"] != "minitsboy" || + csvr.accAliases["a2"] != "minitsboy" { + t.Error("Error loading acc aliases: ", csvr.accAliases) } } diff --git a/engine/loader_db.go b/engine/loader_db.go index 16e34c22b..d0c54ebca 100644 --- a/engine/loader_db.go +++ b/engine/loader_db.go @@ -36,9 +36,11 @@ type DbReader struct { actionsTimings map[string][]*ActionTiming actionsTriggers map[string][]*ActionTrigger accountActions map[string]*Account - dirtyAliases []string // used to clean aliases that might have changed + dirtyRpAliases []string // used to clean aliases that might have changed + dirtyAccAliases []string // used to clean aliases that might have changed destinations []*Destination - aliases map[string]string + rpAliases map[string]string + accAliases map[string]string timings map[string]*utils.TPTiming rates map[string]*utils.TPRate destinationRates map[string]*utils.TPDestinationRate @@ -59,7 +61,8 @@ func NewDbReader(storDB LoadStorage, ratingDb RatingStorage, accountDb Accountin c.ratingPlans = make(map[string]*RatingPlan) c.ratingProfiles = make(map[string]*RatingProfile) c.sharedGroups = make(map[string]*SharedGroup) - c.aliases = make(map[string]string) + c.rpAliases = make(map[string]string) + c.accAliases = make(map[string]string) c.accountActions = make(map[string]*Account) return c } @@ -194,13 +197,28 @@ func (dbr *DbReader) WriteToDatabase(flush, verbose bool) (err error) { } } if verbose { - log.Print("Aliases") + log.Print("Rating profile aliases") } - if err := storage.RemoveAccountAliases(dbr.dirtyAliases); err != nil { + if err := storage.RemoveRpAliases(dbr.dirtyRpAliases); err != nil { return err } - for key, alias := range dbr.aliases { - err = storage.SetAlias(key, alias) + for key, alias := range dbr.rpAliases { + err = storage.SetRpAlias(key, alias) + if err != nil { + return err + } + if verbose { + log.Println(key) + } + } + if verbose { + log.Print("Account aliases") + } + if err := accountingStorage.RemoveAccAliases(dbr.dirtyAccAliases); err != nil { + return err + } + for key, alias := range dbr.accAliases { + err = accountingStorage.SetAccAlias(key, alias) if err != nil { return err } @@ -292,13 +310,13 @@ func (dbr *DbReader) LoadRatingProfiles() error { return err } for _, tpRpf := range mpTpRpfs { - dbr.dirtyAliases = append(dbr.dirtyAliases, tpRpf.Subject) + dbr.dirtyRpAliases = append(dbr.dirtyRpAliases, tpRpf.Subject) // extract aliases from subject aliases := strings.Split(tpRpf.Subject, ";") if len(aliases) > 1 { tpRpf.Subject = aliases[0] for _, alias := range aliases[1:] { - dbr.aliases[RATING_PLAN_PREFIX+alias] = tpRpf.Subject + dbr.rpAliases[alias] = tpRpf.Subject } } rpf := &RatingProfile{Id: tpRpf.KeyId()} @@ -522,13 +540,13 @@ func (dbr *DbReader) LoadAccountActions() (err error) { if _, alreadyDefined := dbr.accountActions[aa.KeyId()]; alreadyDefined { return fmt.Errorf("Duplicate account action found: %s", aa.KeyId()) } - dbr.dirtyAliases = append(dbr.dirtyAliases, aa.Account) + dbr.dirtyAccAliases = append(dbr.dirtyAccAliases, aa.Account) // extract aliases from subject aliases := strings.Split(aa.Account, ";") if len(aliases) > 1 { aa.Account = aliases[0] for _, alias := range aliases[1:] { - dbr.aliases[ACCOUNT_PREFIX+alias] = aa.Account + dbr.accAliases[alias] = aa.Account } } aTriggers, exists := dbr.actionsTriggers[aa.ActionTriggersId] diff --git a/engine/storage_interface.go b/engine/storage_interface.go index dc0b2b0fd..10298939d 100644 --- a/engine/storage_interface.go +++ b/engine/storage_interface.go @@ -35,7 +35,8 @@ const ( ACTION_TIMING_PREFIX = "apl_" RATING_PLAN_PREFIX = "rpl_" RATING_PROFILE_PREFIX = "rpf_" - ALIAS_PREFIX = "als_" + RP_ALIAS_PREFIX = "ral_" + ACC_ALIAS_PREFIX = "aal_" ACTION_PREFIX = "act_" SHARED_GROUP_PREFIX = "shg_" ACCOUNT_PREFIX = "ubl_" @@ -76,9 +77,9 @@ type RatingStorage interface { SetRatingPlan(*RatingPlan) error GetRatingProfile(string, bool) (*RatingProfile, error) SetRatingProfile(*RatingProfile) error - GetAlias(string, bool) (string, error) - SetAlias(string, string) error - RemoveAccountAliases([]string) error + GetRpAlias(string, bool) (string, error) + SetRpAlias(string, string) error + RemoveRpAliases([]string) error GetDestination(string) (*Destination, error) SetDestination(*Destination) error } @@ -86,13 +87,16 @@ type RatingStorage interface { type AccountingStorage interface { Storage HasData(string, string) (bool, error) - CacheAccounting([]string, []string) error + CacheAccounting([]string, []string, []string) error GetActions(string, bool) (Actions, error) SetActions(string, Actions) error GetSharedGroup(string, bool) (*SharedGroup, error) SetSharedGroup(string, *SharedGroup) error GetAccount(string) (*Account, error) SetAccount(*Account) error + GetAccAlias(string, bool) (string, error) + SetAccAlias(string, string) error + RemoveAccAliases([]string) error GetActionTimings(string) (ActionPlan, error) SetActionTimings(string, ActionPlan) error GetAllActionTimings() (map[string]ActionPlan, error) diff --git a/engine/storage_map.go b/engine/storage_map.go index b0fb2aa9f..844859f13 100644 --- a/engine/storage_map.go +++ b/engine/storage_map.go @@ -59,7 +59,7 @@ func (ms *MapStorage) CacheRating(dKeys, rpKeys, rpfKeys, alsKeys []string) erro cache2go.RemPrefixKey(RATING_PROFILE_PREFIX) } if alsKeys == nil { - cache2go.RemPrefixKey(ALIAS_PREFIX) + cache2go.RemPrefixKey(RP_ALIAS_PREFIX) } for k, _ := range ms.dict { if strings.HasPrefix(k, DESTINATION_PREFIX) { @@ -79,9 +79,9 @@ func (ms *MapStorage) CacheRating(dKeys, rpKeys, rpfKeys, alsKeys []string) erro return err } } - if strings.HasPrefix(k, ALIAS_PREFIX) { + if strings.HasPrefix(k, RP_ALIAS_PREFIX) { cache2go.RemKey(k) - if _, err := ms.GetAlias(k[len(ALIAS_PREFIX):], true); err != nil { + if _, err := ms.GetRpAlias(k[len(RP_ALIAS_PREFIX):], true); err != nil { return err } } @@ -89,10 +89,16 @@ func (ms *MapStorage) CacheRating(dKeys, rpKeys, rpfKeys, alsKeys []string) erro return nil } -func (ms *MapStorage) CacheAccounting(actKeys, shgKeys []string) error { +func (ms *MapStorage) CacheAccounting(actKeys, shgKeys, alsKeys []string) error { if actKeys == nil { cache2go.RemPrefixKey(ACTION_PREFIX) // Forced until we can fine tune it } + if shgKeys == nil { + cache2go.RemPrefixKey(SHARED_GROUP_PREFIX) // Forced until we can fine tune it + } + if alsKeys == nil { + cache2go.RemPrefixKey(ACC_ALIAS_PREFIX) + } for k, _ := range ms.dict { if strings.HasPrefix(k, ACTION_PREFIX) { cache2go.RemKey(k) @@ -100,17 +106,18 @@ func (ms *MapStorage) CacheAccounting(actKeys, shgKeys []string) error { return err } } - } - if shgKeys == nil { - cache2go.RemPrefixKey(SHARED_GROUP_PREFIX) // Forced until we can fine tune it - } - for k, _ := range ms.dict { if strings.HasPrefix(k, SHARED_GROUP_PREFIX) { cache2go.RemKey(k) if _, err := ms.GetSharedGroup(k[len(SHARED_GROUP_PREFIX):], true); err != nil { return err } } + if strings.HasPrefix(k, ACC_ALIAS_PREFIX) { + cache2go.RemKey(k) + if _, err := ms.GetAccAlias(k[len(ACC_ALIAS_PREFIX):], true); err != nil { + return err + } + } } return nil } @@ -198,8 +205,8 @@ func (ms *MapStorage) SetRatingProfile(rpf *RatingProfile) (err error) { return } -func (ms *MapStorage) GetAlias(key string, checkDb bool) (alias string, err error) { - key = ALIAS_PREFIX + key +func (ms *MapStorage) GetRpAlias(key string, checkDb bool) (alias string, err error) { + key = RP_ALIAS_PREFIX + key if x, err := cache2go.GetCached(key); err == nil { return x.(string), nil } @@ -215,15 +222,47 @@ func (ms *MapStorage) GetAlias(key string, checkDb bool) (alias string, err erro return } -func (ms *MapStorage) SetAlias(key, alias string) (err error) { - ms.dict[ALIAS_PREFIX+key] = []byte(alias) +func (ms *MapStorage) SetRpAlias(key, alias string) (err error) { + ms.dict[RP_ALIAS_PREFIX+key] = []byte(alias) //cache2go.Cache(ALIAS_PREFIX+key, alias) return } -func (ms *MapStorage) RemoveAccountAliases(accounts []string) (err error) { +func (ms *MapStorage) RemoveRpAliases(accounts []string) (err error) { for key, value := range ms.dict { - if strings.HasPrefix(key, ALIAS_PREFIX) && utils.IsSliceMember(accounts, string(value)) { + if strings.HasPrefix(key, RP_ALIAS_PREFIX) && utils.IsSliceMember(accounts, string(value)) { + delete(ms.dict, key) + } + } + return +} + +func (ms *MapStorage) GetAccAlias(key string, checkDb bool) (alias string, err error) { + key = ACC_ALIAS_PREFIX + key + if x, err := cache2go.GetCached(key); err == nil { + return x.(string), nil + } + if !checkDb { + return "", errors.New(utils.ERR_NOT_FOUND) + } + if values, ok := ms.dict[key]; ok { + alias = string(values) + cache2go.Cache(key, alias) + } else { + return "", errors.New("not found") + } + return +} + +func (ms *MapStorage) SetAccAlias(key, alias string) (err error) { + ms.dict[ACC_ALIAS_PREFIX+key] = []byte(alias) + //cache2go.Cache(ALIAS_PREFIX+key, alias) + return +} + +func (ms *MapStorage) RemoveAccAliases(accounts []string) (err error) { + for key, value := range ms.dict { + if strings.HasPrefix(key, ACC_ALIAS_PREFIX) && utils.IsSliceMember(accounts, string(value)) { delete(ms.dict, key) } } diff --git a/engine/storage_redis.go b/engine/storage_redis.go index cf0aa29f8..a04e271a3 100644 --- a/engine/storage_redis.go +++ b/engine/storage_redis.go @@ -122,27 +122,27 @@ func (rs *RedisStorage) CacheRating(dKeys, rpKeys, rpfKeys, alsKeys []string) (e Logger.Info("Finished rating profile caching.") } if alsKeys == nil { - Logger.Info("Caching all aliases") - if alsKeys, err = rs.db.Keys(ALIAS_PREFIX + "*"); err != nil { + Logger.Info("Caching rating profile aliases") + if alsKeys, err = rs.db.Keys(RP_ALIAS_PREFIX + "*"); err != nil { return } - cache2go.RemPrefixKey(ALIAS_PREFIX) + cache2go.RemPrefixKey(RP_ALIAS_PREFIX) } else if len(alsKeys) != 0 { - Logger.Info(fmt.Sprintf("Caching aliases: %v", alsKeys)) + Logger.Info(fmt.Sprintf("Caching rating profile aliases: %v", alsKeys)) } for _, key := range alsKeys { cache2go.RemKey(key) - if _, err = rs.GetAlias(key[len(ALIAS_PREFIX):], true); err != nil { + if _, err = rs.GetRpAlias(key[len(RP_ALIAS_PREFIX):], true); err != nil { return err } } if len(alsKeys) != 0 { - Logger.Info("Finished aliases caching.") + Logger.Info("Finished rating profile aliases caching.") } return } -func (rs *RedisStorage) CacheAccounting(actKeys, shgKeys []string) (err error) { +func (rs *RedisStorage) CacheAccounting(actKeys, shgKeys, alsKeys []string) (err error) { if actKeys == nil { cache2go.RemPrefixKey(ACTION_PREFIX) } @@ -183,6 +183,24 @@ func (rs *RedisStorage) CacheAccounting(actKeys, shgKeys []string) (err error) { if len(shgKeys) != 0 { Logger.Info("Finished shared groups caching.") } + if alsKeys == nil { + Logger.Info("Caching account aliases") + if alsKeys, err = rs.db.Keys(ACC_ALIAS_PREFIX + "*"); err != nil { + return + } + cache2go.RemPrefixKey(ACC_ALIAS_PREFIX) + } else if len(alsKeys) != 0 { + Logger.Info(fmt.Sprintf("Caching account aliases: %v", alsKeys)) + } + for _, key := range alsKeys { + cache2go.RemKey(key) + if _, err = rs.GetAccAlias(key[len(ACC_ALIAS_PREFIX):], true); err != nil { + return err + } + } + if len(alsKeys) != 0 { + Logger.Info("Finished account aliases caching.") + } return nil } @@ -265,8 +283,8 @@ func (rs *RedisStorage) SetRatingProfile(rpf *RatingProfile) (err error) { return } -func (rs *RedisStorage) GetAlias(key string, checkDb bool) (alias string, err error) { - key = ALIAS_PREFIX + key +func (rs *RedisStorage) GetRpAlias(key string, checkDb bool) (alias string, err error) { + key = RP_ALIAS_PREFIX + key if x, err := cache2go.GetCached(key); err == nil { return x.(string), nil } @@ -281,18 +299,59 @@ func (rs *RedisStorage) GetAlias(key string, checkDb bool) (alias string, err er return } -func (rs *RedisStorage) SetAlias(key, alias string) (err error) { - err = rs.db.Set(ALIAS_PREFIX+key, []byte(alias)) +func (rs *RedisStorage) SetRpAlias(key, alias string) (err error) { + err = rs.db.Set(RP_ALIAS_PREFIX+key, []byte(alias)) + return +} + +func (rs *RedisStorage) RemoveRpAliases(accounts []string) (err error) { + if alsKeys, err := rs.db.Keys(RP_ALIAS_PREFIX + "*"); err != nil { + return err + } else { + for _, key := range alsKeys { + alias, err := rs.GetRpAlias(key[len(RP_ALIAS_PREFIX):], true) + if err != nil { + return err + } + if utils.IsSliceMember(accounts, alias) { + if _, err = rs.db.Del(key); err != nil { + return err + } + } + } + } + + return +} + +func (rs *RedisStorage) GetAccAlias(key string, checkDb bool) (alias string, err error) { + key = ACC_ALIAS_PREFIX + key + if x, err := cache2go.GetCached(key); err == nil { + return x.(string), nil + } + if !checkDb { + return "", errors.New(utils.ERR_NOT_FOUND) + } + var values []byte + if values, err = rs.db.Get(key); err == nil { + alias = string(values) + cache2go.Cache(key, alias) + } + return +} + +func (rs *RedisStorage) SetAccAlias(key, alias string) (err error) { + err = rs.db.Set(ACC_ALIAS_PREFIX+key, []byte(alias)) //cache2go.Cache(ALIAS_PREFIX+key, alias) return } -func (rs *RedisStorage) RemoveAccountAliases(accounts []string) (err error) { - if alsKeys, err := rs.db.Keys(ALIAS_PREFIX + "*"); err != nil { +func (rs *RedisStorage) RemoveAccAliases(accounts []string) (err error) { + if alsKeys, err := rs.db.Keys(ACC_ALIAS_PREFIX + "*"); err != nil { return err } else { for _, key := range alsKeys { - alias, err := rs.GetAlias(key, true) + alias, err := rs.GetAccAlias(key[len(ACC_ALIAS_PREFIX):], true) if err != nil { return err } diff --git a/engine/storage_test.go b/engine/storage_test.go index 857bde3ae..e67d9e437 100644 --- a/engine/storage_test.go +++ b/engine/storage_test.go @@ -110,7 +110,7 @@ func TestCacheRefresh(t *testing.T) { } func TestCacheAliases(t *testing.T) { - if subj, err := cache2go.GetCached(ALIAS_PREFIX + RATING_PROFILE_PREFIX + "a3"); err != nil || subj != "minu" { + if subj, err := cache2go.GetCached(RP_ALIAS_PREFIX + "a3"); err != nil || subj != "minu" { t.Error("Error caching alias: ", subj, err) } } diff --git a/utils/apitpdata.go b/utils/apitpdata.go index 17f80bfe6..5e66b1766 100644 --- a/utils/apitpdata.go +++ b/utils/apitpdata.go @@ -283,7 +283,8 @@ type ApiReloadCache struct { RatingProfileIds []string ActionIds []string SharedGroupIds []string - Aliases []string + RpAliases []string + AccAliases []string } type AttrCacheStats struct { // Add in the future filters here maybe so we avoid counting complete cache