Updated ArgRSv1ResourceUsage to use CGREvent

This commit is contained in:
edwardro22
2017-12-15 08:31:46 +02:00
committed by Dan Christian Bogos
parent d105646eb3
commit cec463f658
7 changed files with 91 additions and 125 deletions

View File

@@ -132,9 +132,9 @@ func testV1RsFromFolder(t *testing.T) {
func testV1RsGetResourcesForEvent(t *testing.T) {
var reply *[]*engine.ResourceProfile
args := &utils.ArgRSv1ResourceUsage{
Tenant: "cgrates.org",
Event: map[string]interface{}{"Unknown": "unknown"}}
args := &utils.ArgRSv1ResourceUsage{}
args.CGREvent.Tenant="cgrates.org"
args.CGREvent.Event=map[string]interface{}{"Unknown": "unknown" }
if err := rlsV1Rpc.Call(utils.ResourceSv1GetResourcesForEvent, args, &reply); err == nil || err.Error() != utils.ErrNotFound.Error() {
t.Error(err)
}
@@ -179,49 +179,41 @@ func testV1RsGetResourcesForEvent(t *testing.T) {
func testV1RsTTL0(t *testing.T) {
// only matching Resource3
argsRU := utils.ArgRSv1ResourceUsage{
Tenant: "cgrates.org",
UsageID: "651a8db2-4f67-4cf8-b622-169e8a482e21",
Event: map[string]interface{}{
"Account": "3001",
"Destination": "3002"},
Units: 1,
}
argsRU.CGREvent.Tenant="cgrates.org"
argsRU.CGREvent.Event=map[string]interface{}{"Account": "3001","Destination": "3002"}
var reply string
if err := rlsV1Rpc.Call(utils.ResourceSv1AllocateResource, argsRU, &reply); err != nil {
t.Error(err)
}
// second allocation should be also allowed
argsRU = utils.ArgRSv1ResourceUsage{
Tenant: "cgrates.org",
UsageID: "651a8db2-4f67-4cf8-b622-169e8a482e21",
Event: map[string]interface{}{
"Account": "3001",
"Destination": "3002"},
Units: 1,
}
argsRU.CGREvent.Tenant="cgrates.org"
argsRU.CGREvent.Event=map[string]interface{}{"Account": "3001","Destination": "3002"}
if err := rlsV1Rpc.Call(utils.ResourceSv1AllocateResource, argsRU, &reply); err != nil {
t.Error(err)
}
// too many units should be rejected
argsRU = utils.ArgRSv1ResourceUsage{
Tenant: "cgrates.org",
UsageID: "651a8db2-4f67-4cf8-b622-169e8a482e22",
Event: map[string]interface{}{
"Account": "3001",
"Destination": "3002"},
Units: 2,
}
argsRU.CGREvent.Tenant="cgrates.org"
argsRU.CGREvent.Event=map[string]interface{}{"Account": "3001","Destination": "3002"}
if err := rlsV1Rpc.Call(utils.ResourceSv1AllocateResource, argsRU, &reply); err == nil ||
err.Error() != utils.ErrResourceUnavailable.Error() {
t.Error(err)
}
// make sure no usage was recorded
var rs *engine.Resources
args := &utils.ArgRSv1ResourceUsage{
Tenant: "cgrates.org",
Event: map[string]interface{}{
"Account": "3001",
"Destination": "3002"}}
args := &utils.ArgRSv1ResourceUsage{}
args.CGREvent.Tenant="cgrates.org"
args.CGREvent.Event=map[string]interface{}{"Account": "3001","Destination": "3002"}
if err := rlsV1Rpc.Call(utils.ResourceSv1GetResourcesForEvent, args, &rs); err != nil {
t.Error(err)
} else if len(*rs) != 1 {
@@ -235,12 +227,10 @@ func testV1RsTTL0(t *testing.T) {
// release should not give out errors
var releaseReply string
argsRU = utils.ArgRSv1ResourceUsage{
Tenant: "cgrates.org",
UsageID: "651a8db2-4f67-4cf8-b622-169e8a482e25", // same ID should be accepted by first group since the previous resource should be expired
Event: map[string]interface{}{
"Account": "3001",
"Destination": "3002"},
}
argsRU.CGREvent.Tenant="cgrates.org"
argsRU.CGREvent.Event=map[string]interface{}{"Account": "3001","Destination": "3002"}
if err := rlsV1Rpc.Call(utils.ResourceSv1ReleaseResource, argsRU, &releaseReply); err != nil {
t.Error(err)
}
@@ -250,14 +240,11 @@ func testV1RsAllocateResource(t *testing.T) {
// first event matching Resource1
var reply string
argsRU := utils.ArgRSv1ResourceUsage{
Tenant: "cgrates.org",
UsageID: "651a8db2-4f67-4cf8-b622-169e8a482e51",
Event: map[string]interface{}{
"Account": "1002",
"Subject": "1001",
"Destination": "1002"},
Units: 3,
}
argsRU.CGREvent.Tenant="cgrates.org"
argsRU.CGREvent.Event=map[string]interface{}{"Account":"1002","Subject":"1001","Destination":"1002"}
if err := rlsV1Rpc.Call(utils.ResourceSv1AllocateResource, argsRU, &reply); err != nil {
t.Error(err)
}
@@ -267,14 +254,11 @@ func testV1RsAllocateResource(t *testing.T) {
}
// Second event to test matching of exact limit of first resource
argsRU = utils.ArgRSv1ResourceUsage{
Tenant: "cgrates.org",
UsageID: "651a8db2-4f67-4cf8-b622-169e8a482e52",
Event: map[string]interface{}{
"Account": "1002",
"Subject": "1001",
"Destination": "1002"},
Units: 4,
}
argsRU.CGREvent.Tenant="cgrates.org"
argsRU.CGREvent.Event=map[string]interface{}{"Account":"1002","Subject":"1001","Destination":"1002"}
if err := rlsV1Rpc.Call(utils.ResourceSv1AllocateResource, argsRU, &reply); err != nil {
t.Error(err)
}
@@ -284,14 +268,11 @@ func testV1RsAllocateResource(t *testing.T) {
}
// Third event testing overflow to second resource which still has one resource available
argsRU = utils.ArgRSv1ResourceUsage{
Tenant: "cgrates.org",
UsageID: "651a8db2-4f67-4cf8-b622-169e8a482e53",
Event: map[string]interface{}{
"Account": "dan",
"Subject": "dan",
"Destination": "1002"},
Units: 1,
}
argsRU.CGREvent.Tenant="cgrates.org"
argsRU.CGREvent.Event=map[string]interface{}{"Account":"dan","Subject":"dan","Destination":"1002"}
if err := rlsV1Rpc.Call(utils.ResourceSv1AllocateResource, argsRU, &reply); err != nil {
t.Error(err)
}
@@ -301,14 +282,11 @@ func testV1RsAllocateResource(t *testing.T) {
}
// Test resource unavailable
argsRU = utils.ArgRSv1ResourceUsage{
Tenant: "cgrates.org",
UsageID: "651a8db2-4f67-4cf8-b622-169e8a482e54", // same ID should be accepted by first group since the previous resource should be expired
Event: map[string]interface{}{
"Account": "1002",
"Subject": "1001",
"Destination": "1002"},
Units: 1,
}
argsRU.CGREvent.Tenant="cgrates.org"
argsRU.CGREvent.Event=map[string]interface{}{"Account":"1002","Subject":"1001","Destination":"1002"}
if err := rlsV1Rpc.Call(utils.ResourceSv1AllocateResource, argsRU, &reply); err == nil || err.Error() != utils.ErrResourceUnavailable.Error() {
t.Error(err)
}
@@ -316,14 +294,11 @@ func testV1RsAllocateResource(t *testing.T) {
time.Sleep(time.Duration(1000) * time.Millisecond) // Give time for allocations on first resource to expire
argsRU = utils.ArgRSv1ResourceUsage{
Tenant: "cgrates.org",
UsageID: "651a8db2-4f67-4cf8-b622-169e8a482e55", // same ID should be accepted by first group since the previous resource should be expired
Event: map[string]interface{}{
"Account": "1002",
"Subject": "1001",
"Destination": "1002"},
Units: 1,
}
argsRU.CGREvent.Tenant="cgrates.org"
argsRU.CGREvent.Event=map[string]interface{}{"Account":"1002","Subject":"1001","Destination":"1002"}
if err := rlsV1Rpc.Call(utils.ResourceSv1AllocateResource, argsRU, &reply); err != nil {
t.Error(err)
}
@@ -336,28 +311,23 @@ func testV1RsAllocateResource(t *testing.T) {
func testV1RsAllowUsage(t *testing.T) {
var allowed bool
argsRU := utils.ArgRSv1ResourceUsage{
Tenant: "cgrates.org",
UsageID: "651a8db2-4f67-4cf8-b622-169e8a482e61",
Event: map[string]interface{}{
"Account": "1002",
"Subject": "1001",
"Destination": "1002"},
Units: 6,
}
argsRU.CGREvent.Tenant="cgrates.org"
argsRU.CGREvent.Event=map[string]interface{}{"Account":"1002","Subject":"1001","Destination":"1002"}
if err := rlsV1Rpc.Call(utils.ResourceSv1AllowUsage, argsRU, &allowed); err != nil {
t.Error(err)
} else if !allowed { // already 3 usages active before allow call, we should have now more than allowed
t.Error("resource is not allowed")
}
argsRU = utils.ArgRSv1ResourceUsage{
Tenant: "cgrates.org",
UsageID: "651a8db2-4f67-4cf8-b622-169e8a482e61",
Event: map[string]interface{}{
"Account": "1002",
"Subject": "1001",
"Destination": "1002"},
Units: 7,
}
argsRU.CGREvent.Tenant="cgrates.org"
argsRU.CGREvent.Event=map[string]interface{}{"Account":"1002","Subject":"1001","Destination":"1002"}
if err := rlsV1Rpc.Call(utils.ResourceSv1AllowUsage, argsRU, &allowed); err != nil {
t.Error(err)
} else if allowed { // already 3 usages active before allow call, we should have now more than allowed
@@ -369,27 +339,21 @@ func testV1RsReleaseResource(t *testing.T) {
// relase the only resource active for Resource1
var reply string
argsRU := utils.ArgRSv1ResourceUsage{
Tenant: "cgrates.org",
UsageID: "651a8db2-4f67-4cf8-b622-169e8a482e55", // same ID should be accepted by first group since the previous resource should be expired
Event: map[string]interface{}{
"Account": "1002",
"Subject": "1001",
"Destination": "1002"},
}
argsRU.CGREvent.Tenant="cgrates.org"
argsRU.CGREvent.Event=map[string]interface{}{"Account":"1002","Subject":"1001","Destination":"1002"}
if err := rlsV1Rpc.Call(utils.ResourceSv1ReleaseResource, argsRU, &reply); err != nil {
t.Error(err)
}
// try reserving with full units for Resource1, case which did not work in previous test
// only match Resource1 since we don't want for storing of the resource2 bellow
argsRU = utils.ArgRSv1ResourceUsage{
Tenant: "cgrates.org",
UsageID: "651a8db2-4f67-4cf8-b622-169e8a482e61",
Event: map[string]interface{}{
"Account": "1002",
"Subject": "1001",
"Destination": "2002"},
Units: 7,
}
argsRU.CGREvent.Tenant="cgrates.org"
argsRU.CGREvent.Event=map[string]interface{}{"Account":"1002","Subject":"1001","Destination":"1002"}
var allowed bool
if err := rlsV1Rpc.Call(utils.ResourceSv1AllowUsage, argsRU, &allowed); err != nil {
t.Error(err)
@@ -397,12 +361,9 @@ func testV1RsReleaseResource(t *testing.T) {
t.Error("resource should be allowed")
}
var rs *engine.Resources
args := &utils.ArgRSv1ResourceUsage{
Tenant: "cgrates.org",
Event: map[string]interface{}{
"Account": "1002",
"Subject": "1001",
"Destination": "1002"}}
args := &utils.ArgRSv1ResourceUsage{}
args.CGREvent.Tenant="cgrates.org"
args.CGREvent.Event=map[string]interface{}{"Account":"1002","Subject":"1001","Destination":"1002"}
if err := rlsV1Rpc.Call(utils.ResourceSv1GetResourcesForEvent, args, &rs); err != nil {
t.Error(err)
} else if len(*rs) != 2 {
@@ -419,14 +380,11 @@ func testV1RsReleaseResource(t *testing.T) {
func testV1RsDBStore(t *testing.T) {
argsRU := utils.ArgRSv1ResourceUsage{
Tenant: "cgrates.org",
UsageID: "651a8db2-4f67-4cf8-b622-169e8a482e71",
Event: map[string]interface{}{
"Account": "1002",
"Subject": "1001",
"Destination": "1002"},
Units: 1,
}
argsRU.CGREvent.Tenant="cgrates.org"
argsRU.CGREvent.Event=map[string]interface{}{"Account":"1002","Subject":"1001","Destination":"1002"}
var reply string
eAllocationMsg := "ResGroup1"
if err := rlsV1Rpc.Call(utils.ResourceSv1AllocateResource, argsRU, &reply); err != nil {
@@ -435,12 +393,9 @@ func testV1RsDBStore(t *testing.T) {
t.Errorf("Expecting: %+v, received: %+v", eAllocationMsg, reply)
}
var rs *engine.Resources
args := &utils.ArgRSv1ResourceUsage{
Tenant: "cgrates.org",
Event: map[string]interface{}{
"Account": "1002",
"Subject": "1001",
"Destination": "1002"}}
args := &utils.ArgRSv1ResourceUsage{}
args.CGREvent.Tenant="cgrates.org"
args.CGREvent.Event=map[string]interface{}{"Account":"1002","Subject":"1001","Destination":"1002"}
if err := rlsV1Rpc.Call(utils.ResourceSv1GetResourcesForEvent, args, &rs); err != nil {
t.Error(err)
} else if len(*rs) != 2 {
@@ -468,12 +423,10 @@ func testV1RsDBStore(t *testing.T) {
t.Fatal("Could not connect to rater: ", err.Error())
}
rs = new(engine.Resources)
args = &utils.ArgRSv1ResourceUsage{
Tenant: "cgrates.org",
Event: map[string]interface{}{
"Account": "1002",
"Subject": "1001",
"Destination": "1002"}}
args = &utils.ArgRSv1ResourceUsage{}
args.CGREvent.Tenant="cgrates.org"
args.CGREvent.Event=map[string]interface{}{"Account":"1002","Subject":"1001","Destination":"1002"}
if err := rlsV1Rpc.Call(utils.ResourceSv1GetResourcesForEvent, args, &rs); err != nil {
t.Error(err)
} else if len(*rs) != 2 {

View File

@@ -63,8 +63,8 @@ func (self *CmdThresholdProcessEvent) PostprocessRpcParams() error { //utils.CGR
ID: utils.UUIDSha1Prefix(),
Event: *param,
}
if (*param)[utils.TENANT] != nil && (*param)[utils.TENANT].(string) != "" {
cgrev.Tenant = (*param)[utils.TENANT].(string)
if (*param)[utils.Tenant] != nil && (*param)[utils.Tenant].(string) != "" {
cgrev.Tenant = (*param)[utils.Tenant].(string)
}
self.rpcParams = cgrev
return nil

View File

@@ -45,7 +45,6 @@ func (sqp *StatQueueProfile) TenantID() string {
return utils.ConcatenatedKey(sqp.Tenant, sqp.ID)
}
// NewStoredStatQueue initiates a StoredStatQueue out of StatQueue
func NewStoredStatQueue(sq *StatQueue, ms Marshaler) (sSQ *StoredStatQueue, err error) {
sSQ = &StoredStatQueue{

View File

@@ -510,18 +510,20 @@ func (rS *ResourceService) processThresholds(r *Resource) (err error) {
// V1ResourcesForEvent returns active resource configs matching the event
func (rS *ResourceService) V1ResourcesForEvent(args utils.ArgRSv1ResourceUsage, reply *Resources) (err error) {
if args.Tenant == "" {
if args.CGREvent.Tenant == "" {
return utils.NewErrMandatoryIeMissing("Tenant")
} else if args.UsageID == "" {
return utils.NewErrMandatoryIeMissing("UsageID")
}
var mtcRLs Resources
if args.UsageID != "" { // only cached if UsageID is present
mtcRLs = rS.cachedResourcesForEvent(args.TenantID())
mtcRLs = rS.cachedResourcesForEvent(args.CGREvent.TenantID())
}
if mtcRLs == nil {
if mtcRLs, err = rS.matchingResourcesForEvent(args.Tenant, args.Event); err != nil {
if mtcRLs, err = rS.matchingResourcesForEvent(args.CGREvent.Tenant, args.CGREvent.Event); err != nil {
return err
}
cache.Set(utils.EventResourcesPrefix+args.TenantID(), mtcRLs.tenantIDs(), true, "")
cache.Set(utils.EventResourcesPrefix+args.CGREvent.TenantID(), mtcRLs.tenantIDs(), true, "")
}
if len(mtcRLs) == 0 {
return utils.ErrNotFound
@@ -530,10 +532,14 @@ func (rS *ResourceService) V1ResourcesForEvent(args utils.ArgRSv1ResourceUsage,
return
}
//cgrevent tenant +id si la args USAGEID
// V1AllowUsage queries service to find if an Usage is allowed
func (rS *ResourceService) V1AllowUsage(args utils.ArgRSv1ResourceUsage, allow *bool) (err error) {
if missing := utils.MissingStructFields(&args, []string{"Tenant", "UsageID"}); len(missing) != 0 { //Params missing
return utils.NewErrMandatoryIeMissing(missing...)
if args.CGREvent.Tenant == "" {
return utils.NewErrMandatoryIeMissing("Tenant")
} else if args.UsageID == "" {
return utils.NewErrMandatoryIeMissing("UsageID")
}
mtcRLs := rS.cachedResourcesForEvent(args.TenantID())
if mtcRLs == nil {
@@ -560,8 +566,10 @@ func (rS *ResourceService) V1AllowUsage(args utils.ArgRSv1ResourceUsage, allow *
// V1AllocateResource is called when a resource requires allocation
func (rS *ResourceService) V1AllocateResource(args utils.ArgRSv1ResourceUsage, reply *string) (err error) {
if missing := utils.MissingStructFields(&args, []string{"Tenant", "UsageID"}); len(missing) != 0 { //Params missing
return utils.NewErrMandatoryIeMissing(missing...)
if args.CGREvent.Tenant == "" {
return utils.NewErrMandatoryIeMissing("Tenant")
} else if args.UsageID == "" {
return utils.NewErrMandatoryIeMissing("UsageID")
}
var wasCached bool
mtcRLs := rS.cachedResourcesForEvent(args.UsageID)
@@ -613,8 +621,10 @@ func (rS *ResourceService) V1AllocateResource(args utils.ArgRSv1ResourceUsage, r
// V1ReleaseResource is called when we need to clear an allocation
func (rS *ResourceService) V1ReleaseResource(args utils.ArgRSv1ResourceUsage, reply *string) (err error) {
if missing := utils.MissingStructFields(&args, []string{"Tenant", "UsageID"}); len(missing) != 0 { //Params missing
return utils.NewErrMandatoryIeMissing(missing...)
if args.CGREvent.Tenant == "" {
return utils.NewErrMandatoryIeMissing("Tenant")
} else if args.UsageID == "" {
return utils.NewErrMandatoryIeMissing("UsageID")
}
mtcRLs := rS.cachedResourcesForEvent(args.UsageID)
if mtcRLs == nil {

View File

@@ -214,11 +214,12 @@ func (sm *FSSessionManager) onChannelPark(ev engine.Event, connId string) {
if sm.rls != nil {
var reply string
attrRU := utils.ArgRSv1ResourceUsage{
Tenant: ev.(FSEvent).GetTenant(utils.META_DEFAULT),
UsageID: ev.GetUUID(),
Event: ev.(FSEvent).AsMapStringInterface(sm.timezone),
Units: 1,
}
attrRU.CGREvent.ID=utils.UUIDSha1Prefix()
attrRU.CGREvent.Tenant=ev.(FSEvent).GetTenant(utils.META_DEFAULT)
attrRU.CGREvent.Event=ev.(FSEvent).AsMapStringInterface(sm.timezone)
if err := sm.rls.Call(utils.ResourceSv1AllocateResource, attrRU, &reply); err != nil {
if err.Error() == utils.ErrResourceUnavailable.Error() {
sm.unparkCall(ev.GetUUID(), connId, ev.GetCallDestNr(utils.META_DEFAULT), "-"+utils.ErrResourceUnavailable.Error())
@@ -280,11 +281,12 @@ func (sm *FSSessionManager) onChannelHangupComplete(ev engine.Event) {
}
var reply string
attrRU := utils.ArgRSv1ResourceUsage{
Tenant: ev.(FSEvent).GetTenant(utils.META_DEFAULT),
UsageID: ev.GetUUID(),
Event: ev.(FSEvent).AsMapStringInterface(sm.timezone),
Units: 1,
}
UsageID: ev.GetUUID(),
Units: 1,
}
attrRU.CGREvent.ID=utils.UUIDSha1Prefix()
attrRU.CGREvent.Tenant=ev.(FSEvent).GetTenant(utils.META_DEFAULT)
attrRU.CGREvent.Event=ev.(FSEvent).AsMapStringInterface(sm.timezone)
if sm.rls != nil {
if err := sm.rls.Call(utils.ResourceSv1ReleaseResource, attrRU, &reply); err != nil {
utils.Logger.Err(fmt.Sprintf("<SM-FreeSWITCH> RLs API error: %s", err.Error()))

View File

@@ -81,11 +81,12 @@ func (self *KamailioSessionManager) allocateResources(kev KamEvent) (err error)
return
}
attrRU := utils.ArgRSv1ResourceUsage{
Tenant: kev.GetTenant(utils.META_DEFAULT),
UsageID: kev.GetUUID(),
Event: ev,
Units: 1, // One channel reserved
}
UsageID: kev.GetUUID(),
Units: 1,
}
attrRU.CGREvent.ID=utils.UUIDSha1Prefix()
attrRU.CGREvent.Tenant=kev.GetTenant(utils.META_DEFAULT)
attrRU.CGREvent.Event=ev
var reply string
return self.rlS.Call(utils.ResourceSv1AllocateResource, attrRU, &reply)
}
@@ -214,12 +215,13 @@ func (self *KamailioSessionManager) onCallEnd(evData []byte, connId string) {
return
}
var reply string
attrRU := utils.ArgRSv1ResourceUsage{
Tenant: kev.GetTenant(utils.META_DEFAULT),
UsageID: kev.GetUUID(),
Event: ev,
Units: 1,
}
attrRU := utils.ArgRSv1ResourceUsage{
UsageID: kev.GetUUID(),
Units: 1,
}
attrRU.CGREvent.ID=utils.UUIDSha1Prefix()
attrRU.CGREvent.Tenant=kev.GetTenant(utils.META_DEFAULT)
attrRU.CGREvent.Event=ev
if err := self.rlS.Call(utils.ResourceSv1ReleaseResource, attrRU, &reply); err != nil {
utils.Logger.Err(fmt.Sprintf("<SM-Kamailio> RLs API error: %s", err.Error()))
}

View File

@@ -23,6 +23,7 @@ import (
"sort"
"strings"
"time"
)
// Used to extract ids from stordb
@@ -1276,10 +1277,9 @@ type AttrRLsCache struct {
}
type ArgRSv1ResourceUsage struct {
Tenant string
CGREvent
UsageID string // ResourceUsage Identifier
Units float64
Event map[string]interface{}
}
func (args *ArgRSv1ResourceUsage) TenantID() string {