mirror of
https://github.com/cgrates/cgrates.git
synced 2026-02-24 16:48:45 +05:00
fixes for user indexes
tests pending
This commit is contained in:
@@ -82,6 +82,8 @@ func executeCommand(command string) {
|
||||
switch param.(type) {
|
||||
case *console.StringWrapper:
|
||||
param = param.(*console.StringWrapper).Item
|
||||
case *console.StringSliceWrapper:
|
||||
param = param.(*console.StringSliceWrapper).Items
|
||||
}
|
||||
//log.Printf("Param: %+v", param)
|
||||
|
||||
|
||||
@@ -58,6 +58,6 @@ func (self *CmdUserShowIndexes) PostprocessRpcParams() error {
|
||||
}
|
||||
|
||||
func (self *CmdUserShowIndexes) RpcResult() interface{} {
|
||||
s := []string{}
|
||||
s := map[string][]string{}
|
||||
return &s
|
||||
}
|
||||
|
||||
155
engine/users.go
155
engine/users.go
@@ -1,6 +1,7 @@
|
||||
package engine
|
||||
|
||||
import (
|
||||
"log"
|
||||
"strings"
|
||||
|
||||
"github.com/cgrates/cgrates/utils"
|
||||
@@ -33,13 +34,14 @@ type UserService interface {
|
||||
UpdateUser(UserProfile, *string) error
|
||||
GetUsers(UserProfile, *[]*UserProfile) error
|
||||
AddIndex([]string, *string) error
|
||||
GetIndexes(string, *[]string) error
|
||||
GetIndexes(string, *map[string][]string) error
|
||||
}
|
||||
|
||||
type UserMap struct {
|
||||
table map[string]map[string]string
|
||||
index map[string][]string
|
||||
ratingDb RatingStorage
|
||||
table map[string]map[string]string
|
||||
index map[string]map[string]bool
|
||||
indexKeys []string
|
||||
ratingDb RatingStorage
|
||||
}
|
||||
|
||||
func NewUserMap(ratingDb RatingStorage) (*UserMap, error) {
|
||||
@@ -58,27 +60,29 @@ func NewUserMap(ratingDb RatingStorage) (*UserMap, error) {
|
||||
func newUserMap(ratingDb RatingStorage) *UserMap {
|
||||
return &UserMap{
|
||||
table: make(map[string]map[string]string),
|
||||
index: make(map[string][]string),
|
||||
index: make(map[string]map[string]bool),
|
||||
ratingDb: ratingDb,
|
||||
}
|
||||
}
|
||||
|
||||
func (um *UserMap) SetUser(up UserProfile, reply *string) error {
|
||||
um.table[up.GetId()] = up.Profile
|
||||
if err := um.ratingDb.SetUser(&up); err != nil {
|
||||
*reply = err.Error()
|
||||
return err
|
||||
}
|
||||
um.table[up.GetId()] = up.Profile
|
||||
um.addIndex(&up)
|
||||
*reply = utils.OK
|
||||
return nil
|
||||
}
|
||||
|
||||
func (um *UserMap) RemoveUser(up UserProfile, reply *string) error {
|
||||
delete(um.table, up.GetId())
|
||||
if err := um.ratingDb.RemoveUser(up.GetId()); err != nil {
|
||||
*reply = err.Error()
|
||||
return err
|
||||
}
|
||||
delete(um.table, up.GetId())
|
||||
um.deleteIndex(&up)
|
||||
*reply = utils.OK
|
||||
return nil
|
||||
}
|
||||
@@ -90,20 +94,32 @@ func (um *UserMap) UpdateUser(up UserProfile, reply *string) error {
|
||||
return utils.ErrNotFound
|
||||
}
|
||||
if m == nil {
|
||||
um.table[up.GetId()] = make(map[string]string, 0)
|
||||
m = make(map[string]string)
|
||||
}
|
||||
oldM := make(map[string]string, len(m))
|
||||
for k, v := range m {
|
||||
oldM[k] = v
|
||||
}
|
||||
oldUp := &UserProfile{
|
||||
Tenant: up.Tenant,
|
||||
UserName: up.UserName,
|
||||
Profile: oldM,
|
||||
}
|
||||
for key, value := range up.Profile {
|
||||
um.table[up.GetId()][key] = value
|
||||
m[key] = value
|
||||
}
|
||||
finalUp := &UserProfile{
|
||||
Tenant: up.Tenant,
|
||||
UserName: up.UserName,
|
||||
Profile: um.table[up.GetId()],
|
||||
Profile: m,
|
||||
}
|
||||
if err := um.ratingDb.SetUser(finalUp); err != nil {
|
||||
*reply = err.Error()
|
||||
return err
|
||||
}
|
||||
um.table[up.GetId()] = m
|
||||
um.deleteIndex(oldUp)
|
||||
um.addIndex(finalUp)
|
||||
*reply = utils.OK
|
||||
return nil
|
||||
}
|
||||
@@ -115,21 +131,21 @@ func (um *UserMap) GetUsers(up UserProfile, results *[]*UserProfile) error {
|
||||
// search index
|
||||
if up.Tenant != "" {
|
||||
if keys, found := um.index[utils.ConcatenatedKey("Tenant", up.Tenant)]; found {
|
||||
for _, key := range keys {
|
||||
for key := range keys {
|
||||
indexUnionKeys[key] = true
|
||||
}
|
||||
}
|
||||
}
|
||||
if up.UserName != "" {
|
||||
if keys, found := um.index[utils.ConcatenatedKey("UserName", up.UserName)]; found {
|
||||
for _, key := range keys {
|
||||
for key := range keys {
|
||||
indexUnionKeys[key] = true
|
||||
}
|
||||
}
|
||||
}
|
||||
for k, v := range up.Profile {
|
||||
if keys, found := um.index[utils.ConcatenatedKey(k, v)]; found {
|
||||
for _, key := range keys {
|
||||
for key := range keys {
|
||||
indexUnionKeys[key] = true
|
||||
}
|
||||
}
|
||||
@@ -172,38 +188,97 @@ func (um *UserMap) GetUsers(up UserProfile, results *[]*UserProfile) error {
|
||||
}
|
||||
|
||||
func (um *UserMap) AddIndex(indexes []string, reply *string) error {
|
||||
um.indexKeys = indexes
|
||||
for key, values := range um.table {
|
||||
ud := &UserProfile{Profile: values}
|
||||
ud.SetId(key)
|
||||
for _, index := range indexes {
|
||||
if index == "Tenant" {
|
||||
if ud.Tenant != "" {
|
||||
um.index[utils.ConcatenatedKey(index, ud.Tenant)] = append(um.index[utils.ConcatenatedKey(index, ud.Tenant)], key)
|
||||
}
|
||||
continue
|
||||
}
|
||||
if index == "UserName" {
|
||||
if ud.UserName != "" {
|
||||
um.index[utils.ConcatenatedKey(index, ud.UserName)] = append(um.index[utils.ConcatenatedKey(index, ud.UserName)], key)
|
||||
}
|
||||
continue
|
||||
}
|
||||
|
||||
for k, v := range ud.Profile {
|
||||
if k == index && v != "" {
|
||||
um.index[utils.ConcatenatedKey(k, v)] = append(um.index[utils.ConcatenatedKey(k, v)], key)
|
||||
}
|
||||
}
|
||||
}
|
||||
up := &UserProfile{Profile: values}
|
||||
up.SetId(key)
|
||||
um.addIndex(up)
|
||||
}
|
||||
*reply = utils.OK
|
||||
return nil
|
||||
}
|
||||
|
||||
func (um *UserMap) GetIndexes(in string, reply *[]string) error {
|
||||
var indexes []string
|
||||
for key := range um.index {
|
||||
indexes = append(indexes, key)
|
||||
func (um *UserMap) addIndex(up *UserProfile) {
|
||||
key := up.GetId()
|
||||
for _, index := range um.indexKeys {
|
||||
if index == "Tenant" {
|
||||
if up.Tenant != "" {
|
||||
indexKey := utils.ConcatenatedKey(index, up.Tenant)
|
||||
if um.index[indexKey] == nil {
|
||||
um.index[indexKey] = make(map[string]bool)
|
||||
}
|
||||
um.index[indexKey][key] = true
|
||||
}
|
||||
continue
|
||||
}
|
||||
if index == "UserName" {
|
||||
if up.UserName != "" {
|
||||
indexKey := utils.ConcatenatedKey(index, up.UserName)
|
||||
if um.index[indexKey] == nil {
|
||||
um.index[indexKey] = make(map[string]bool)
|
||||
}
|
||||
um.index[indexKey][key] = true
|
||||
}
|
||||
continue
|
||||
}
|
||||
|
||||
for k, v := range up.Profile {
|
||||
if k == index && v != "" {
|
||||
indexKey := utils.ConcatenatedKey(k, v)
|
||||
if um.index[indexKey] == nil {
|
||||
um.index[indexKey] = make(map[string]bool)
|
||||
}
|
||||
um.index[indexKey][key] = true
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func (um *UserMap) deleteIndex(up *UserProfile) {
|
||||
log.Printf("Delete index: %s: %v", up.GetId(), up.Profile)
|
||||
key := up.GetId()
|
||||
for _, index := range um.indexKeys {
|
||||
if index == "Tenant" {
|
||||
if up.Tenant != "" {
|
||||
indexKey := utils.ConcatenatedKey(index, up.Tenant)
|
||||
delete(um.index[indexKey], key)
|
||||
if len(um.index[indexKey]) == 0 {
|
||||
delete(um.index, indexKey)
|
||||
}
|
||||
}
|
||||
continue
|
||||
}
|
||||
if index == "UserName" {
|
||||
if up.UserName != "" {
|
||||
indexKey := utils.ConcatenatedKey(index, up.UserName)
|
||||
delete(um.index[indexKey], key)
|
||||
if len(um.index[indexKey]) == 0 {
|
||||
delete(um.index, indexKey)
|
||||
}
|
||||
}
|
||||
continue
|
||||
}
|
||||
|
||||
for k, v := range up.Profile {
|
||||
if k == index && v != "" {
|
||||
indexKey := utils.ConcatenatedKey(k, v)
|
||||
delete(um.index[indexKey], key)
|
||||
if len(um.index[indexKey]) == 0 {
|
||||
delete(um.index, indexKey)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func (um *UserMap) GetIndexes(in string, reply *map[string][]string) error {
|
||||
indexes := make(map[string][]string)
|
||||
for key, values := range um.index {
|
||||
var vs []string
|
||||
for val := range values {
|
||||
vs = append(vs, val)
|
||||
}
|
||||
indexes[key] = vs
|
||||
}
|
||||
*reply = indexes
|
||||
return nil
|
||||
@@ -243,6 +318,6 @@ func (ps *ProxyUserService) AddIndex(indexes []string, reply *string) error {
|
||||
return ps.Client.Call("UsersV1.AddIndex", indexes, reply)
|
||||
}
|
||||
|
||||
func (ps *ProxyUserService) GetIndexes(in string, reply *[]string) error {
|
||||
func (ps *ProxyUserService) GetIndexes(in string, reply *map[string][]string) error {
|
||||
return ps.Client.Call("UsersV1.AddIndex", in, reply)
|
||||
}
|
||||
|
||||
@@ -13,7 +13,7 @@ var testMap = UserMap{
|
||||
"test:": map[string]string{"t": "v"},
|
||||
"test1:user1": map[string]string{"t": "v", "x": "y"},
|
||||
},
|
||||
index: make(map[string][]string),
|
||||
index: make(map[string]map[string]bool),
|
||||
}
|
||||
|
||||
func TestUsersAdd(t *testing.T) {
|
||||
@@ -267,7 +267,7 @@ func TestUsersAddIndex(t *testing.T) {
|
||||
|
||||
func TestUsersAddIndexFull(t *testing.T) {
|
||||
var r string
|
||||
testMap.index = make(map[string][]string) // reset index
|
||||
testMap.index = make(map[string]map[string]bool) // reset index
|
||||
testMap.AddIndex([]string{"t", "x", "UserName", "Tenant"}, &r)
|
||||
if r != utils.OK ||
|
||||
len(testMap.index) != 6 ||
|
||||
@@ -278,7 +278,7 @@ func TestUsersAddIndexFull(t *testing.T) {
|
||||
|
||||
func TestUsersAddIndexNone(t *testing.T) {
|
||||
var r string
|
||||
testMap.index = make(map[string][]string) // reset index
|
||||
testMap.index = make(map[string]map[string]bool) // reset index
|
||||
testMap.AddIndex([]string{"test"}, &r)
|
||||
if r != utils.OK ||
|
||||
len(testMap.index) != 0 {
|
||||
@@ -288,7 +288,7 @@ func TestUsersAddIndexNone(t *testing.T) {
|
||||
|
||||
func TestUsersGetFullindex(t *testing.T) {
|
||||
var r string
|
||||
testMap.index = make(map[string][]string) // reset index
|
||||
testMap.index = make(map[string]map[string]bool) // reset index
|
||||
testMap.AddIndex([]string{"t", "x", "UserName", "Tenant"}, &r)
|
||||
up := UserProfile{
|
||||
Tenant: "test",
|
||||
@@ -306,7 +306,7 @@ func TestUsersGetFullindex(t *testing.T) {
|
||||
|
||||
func TestUsersGetTenantindex(t *testing.T) {
|
||||
var r string
|
||||
testMap.index = make(map[string][]string) // reset index
|
||||
testMap.index = make(map[string]map[string]bool) // reset index
|
||||
testMap.AddIndex([]string{"t", "x", "UserName", "Tenant"}, &r)
|
||||
up := UserProfile{
|
||||
Tenant: "testX",
|
||||
@@ -324,7 +324,7 @@ func TestUsersGetTenantindex(t *testing.T) {
|
||||
|
||||
func TestUsersGetUserNameindex(t *testing.T) {
|
||||
var r string
|
||||
testMap.index = make(map[string][]string) // reset index
|
||||
testMap.index = make(map[string]map[string]bool) // reset index
|
||||
testMap.AddIndex([]string{"t", "x", "UserName", "Tenant"}, &r)
|
||||
up := UserProfile{
|
||||
Tenant: "test",
|
||||
@@ -342,7 +342,7 @@ func TestUsersGetUserNameindex(t *testing.T) {
|
||||
|
||||
func TestUsersGetNotFoundProfileindex(t *testing.T) {
|
||||
var r string
|
||||
testMap.index = make(map[string][]string) // reset index
|
||||
testMap.index = make(map[string]map[string]bool) // reset index
|
||||
testMap.AddIndex([]string{"t", "x", "UserName", "Tenant"}, &r)
|
||||
up := UserProfile{
|
||||
Tenant: "test",
|
||||
@@ -360,7 +360,7 @@ func TestUsersGetNotFoundProfileindex(t *testing.T) {
|
||||
|
||||
func TestUsersGetMissingTenantindex(t *testing.T) {
|
||||
var r string
|
||||
testMap.index = make(map[string][]string) // reset index
|
||||
testMap.index = make(map[string]map[string]bool) // reset index
|
||||
testMap.AddIndex([]string{"t", "x", "UserName", "Tenant"}, &r)
|
||||
up := UserProfile{
|
||||
UserName: "user",
|
||||
@@ -377,7 +377,7 @@ func TestUsersGetMissingTenantindex(t *testing.T) {
|
||||
|
||||
func TestUsersGetMissingUserNameindex(t *testing.T) {
|
||||
var r string
|
||||
testMap.index = make(map[string][]string) // reset index
|
||||
testMap.index = make(map[string]map[string]bool) // reset index
|
||||
testMap.AddIndex([]string{"t", "x", "UserName", "Tenant"}, &r)
|
||||
up := UserProfile{
|
||||
Tenant: "test",
|
||||
@@ -394,7 +394,7 @@ func TestUsersGetMissingUserNameindex(t *testing.T) {
|
||||
|
||||
func TestUsersGetMissingIdindex(t *testing.T) {
|
||||
var r string
|
||||
testMap.index = make(map[string][]string) // reset index
|
||||
testMap.index = make(map[string]map[string]bool) // reset index
|
||||
testMap.AddIndex([]string{"t", "x", "UserName", "Tenant"}, &r)
|
||||
up := UserProfile{
|
||||
Profile: map[string]string{
|
||||
@@ -410,7 +410,7 @@ func TestUsersGetMissingIdindex(t *testing.T) {
|
||||
|
||||
func TestUsersGetMissingIdTwoINdex(t *testing.T) {
|
||||
var r string
|
||||
testMap.index = make(map[string][]string) // reset index
|
||||
testMap.index = make(map[string]map[string]bool) // reset index
|
||||
testMap.AddIndex([]string{"t", "x", "UserName", "Tenant"}, &r)
|
||||
up := UserProfile{
|
||||
Profile: map[string]string{
|
||||
|
||||
@@ -32,6 +32,14 @@ func IsSliceMember(ss []string, s string) bool {
|
||||
return false
|
||||
}
|
||||
|
||||
func SliceWithoutMember(ss []string, s string) []string {
|
||||
sort.Strings(ss)
|
||||
if i := sort.SearchStrings(ss, s); i < len(ss) && ss[i] == s {
|
||||
ss[i], ss = ss[len(ss)-1], ss[:len(ss)-1]
|
||||
}
|
||||
return ss
|
||||
}
|
||||
|
||||
//Iterates over slice members and returns true if one starts with prefix
|
||||
func SliceMemberHasPrefix(ss []string, prfx string) bool {
|
||||
for _, mbr := range ss {
|
||||
|
||||
Reference in New Issue
Block a user