diff --git a/apier/tpcdrstats.go b/apier/tpcdrstats.go
new file mode 100644
index 000000000..e4990eae4
--- /dev/null
+++ b/apier/tpcdrstats.go
@@ -0,0 +1,99 @@
+/*
+Rating system designed to be used in VoIP Carriers World
+Copyright (C) 2013 ITsysCOM
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see
+*/
+
+package apier
+
+import (
+ "errors"
+ "fmt"
+
+ "github.com/cgrates/cgrates/utils"
+)
+
+// Creates a new CdrStats profile within a tariff plan
+func (self *ApierV1) SetTPCdrStats(attrs utils.TPCdrStats, reply *string) error {
+ if missing := utils.MissingStructFields(&attrs, []string{"TPid", "CdrStatsId", "CdrStats"}); len(missing) != 0 {
+ return fmt.Errorf("%s:%v", utils.ERR_MANDATORY_IE_MISSING, missing)
+ }
+ /*for _, action := range attrs.CdrStats {
+ requiredFields := []string{"Identifier", "Weight"}
+ if action.BalanceType != "" { // Add some inter-dependent parameters - if balanceType then we are not talking about simply calling actions
+ requiredFields = append(requiredFields, "Direction", "Units")
+ }
+ if missing := utils.MissingStructFields(action, requiredFields); len(missing) != 0 {
+ return fmt.Errorf("%s:CdrStat:%s:%v", utils.ERR_MANDATORY_IE_MISSING, action.Identifier, missing)
+ }
+ }*/
+ if err := self.StorDb.SetTPCdrStats(attrs.TPid, map[string][]*utils.TPCdrStat{attrs.CdrStatsId: attrs.CdrStats}); err != nil {
+ return fmt.Errorf("%s:%s", utils.ERR_SERVER_ERROR, err.Error())
+ }
+ *reply = "OK"
+ return nil
+}
+
+type AttrGetTPCdrStats struct {
+ TPid string // Tariff plan id
+ CdrStatsId string // CdrStat id
+}
+
+// Queries specific CdrStat on tariff plan
+func (self *ApierV1) GetTPCdrStats(attrs AttrGetTPCdrStats, reply *utils.TPCdrStats) error {
+ if missing := utils.MissingStructFields(&attrs, []string{"TPid", "CdrStatsId"}); len(missing) != 0 { //Params missing
+ return fmt.Errorf("%s:%v", utils.ERR_MANDATORY_IE_MISSING, missing)
+ }
+ if sgs, err := self.StorDb.GetTpCdrStats(attrs.TPid, attrs.CdrStatsId); err != nil {
+ return fmt.Errorf("%s:%s", utils.ERR_SERVER_ERROR, err.Error())
+ } else if len(sgs) == 0 {
+ return errors.New(utils.ERR_NOT_FOUND)
+ } else {
+ *reply = utils.TPCdrStats{TPid: attrs.TPid, CdrStatsId: attrs.CdrStatsId, CdrStats: sgs[attrs.CdrStatsId]}
+ }
+ return nil
+}
+
+type AttrGetTPCdrStatIds struct {
+ TPid string // Tariff plan id
+}
+
+// Queries CdrStats identities on specific tariff plan.
+func (self *ApierV1) GetTPCdrStatsIds(attrs AttrGetTPCdrStatIds, reply *[]string) error {
+ if missing := utils.MissingStructFields(&attrs, []string{"TPid"}); len(missing) != 0 { //Params missing
+ return fmt.Errorf("%s:%v", utils.ERR_MANDATORY_IE_MISSING, missing)
+ }
+ if ids, err := self.StorDb.GetTPTableIds(attrs.TPid, utils.TBL_TP_CDR_STATS, "id", nil); err != nil {
+ return fmt.Errorf("%s:%s", utils.ERR_SERVER_ERROR, err.Error())
+ } else if ids == nil {
+ return errors.New(utils.ERR_NOT_FOUND)
+ } else {
+ *reply = ids
+ }
+ return nil
+}
+
+// Removes specific CdrStats on Tariff plan
+func (self *ApierV1) RemTPCdrStats(attrs AttrGetTPCdrStats, reply *string) error {
+ if missing := utils.MissingStructFields(&attrs, []string{"TPid", "CdrStatsId"}); len(missing) != 0 { //Params missing
+ return fmt.Errorf("%s:%v", utils.ERR_MANDATORY_IE_MISSING, missing)
+ }
+ if err := self.StorDb.RemTPData(utils.TBL_TP_SHARED_GROUPS, attrs.TPid, attrs.CdrStatsId); err != nil {
+ return fmt.Errorf("%s:%s", utils.ERR_SERVER_ERROR, err.Error())
+ } else {
+ *reply = "OK"
+ }
+ return nil
+}
diff --git a/apier/tpderivedcharges.go b/apier/tpderivedcharges.go
new file mode 100644
index 000000000..57b40a09f
--- /dev/null
+++ b/apier/tpderivedcharges.go
@@ -0,0 +1,94 @@
+/*
+Rating system designed to be used in VoIP Carriers World
+Copyright (C) 2013 ITsysCOM
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see
+*/
+
+package apier
+
+/*
+// Creates a new DerivedCharges profile within a tariff plan
+func (self *ApierV1) SetTPDerivedCharges(attrs utils.TPDerivedCharges, reply *string) error {
+ if missing := utils.MissingStructFields(&attrs, []string{"TPid", "DerivedChargesId", "DerivedCharges"}); len(missing) != 0 {
+ return fmt.Errorf("%s:%v", utils.ERR_MANDATORY_IE_MISSING, missing)
+ }
+ for _, action := range attrs.DerivedCharges {
+ requiredFields := []string{"Identifier", "Weight"}
+ if action.BalanceType != "" { // Add some inter-dependent parameters - if balanceType then we are not talking about simply calling actions
+ requiredFields = append(requiredFields, "Direction", "Units")
+ }
+ if missing := utils.MissingStructFields(action, requiredFields); len(missing) != 0 {
+ return fmt.Errorf("%s:DerivedCharge:%s:%v", utils.ERR_MANDATORY_IE_MISSING, action.Identifier, missing)
+ }
+ }
+ if err := self.StorDb.SetTPDerivedCharges(attrs.TPid, map[string][]*utils.TPDerivedCharge{attrs.DerivedChargesId: attrs.DerivedCharges}); err != nil {
+ return fmt.Errorf("%s:%s", utils.ERR_SERVER_ERROR, err.Error())
+ }
+ *reply = "OK"
+ return nil
+}
+
+type AttrGetTPDerivedCharges struct {
+ TPid string // Tariff plan id
+ DerivedChargesId string // DerivedCharge id
+}
+
+// Queries specific DerivedCharge on tariff plan
+func (self *ApierV1) GetTPDerivedCharges(attrs AttrGetTPDerivedCharges, reply *utils.TPDerivedCharges) error {
+ if missing := utils.MissingStructFields(&attrs, []string{"TPid", "DerivedChargesId"}); len(missing) != 0 { //Params missing
+ return fmt.Errorf("%s:%v", utils.ERR_MANDATORY_IE_MISSING, missing)
+ }
+ if sgs, err := self.StorDb.GetTpDerivedCharges(attrs.TPid, attrs.DerivedChargesId); err != nil {
+ return fmt.Errorf("%s:%s", utils.ERR_SERVER_ERROR, err.Error())
+ } else if len(sgs) == 0 {
+ return errors.New(utils.ERR_NOT_FOUND)
+ } else {
+ *reply = utils.TPDerivedCharges{TPid: attrs.TPid, DerivedChargesId: attrs.DerivedChargesId, DerivedCharges: sgs[attrs.DerivedChargesId]}
+ }
+ return nil
+}
+
+type AttrGetTPDerivedChargeIds struct {
+ TPid string // Tariff plan id
+}
+
+// Queries DerivedCharges identities on specific tariff plan.
+func (self *ApierV1) GetTPDerivedChargeIds(attrs AttrGetTPDerivedChargeIds, reply *[]string) error {
+ if missing := utils.MissingStructFields(&attrs, []string{"TPid"}); len(missing) != 0 { //Params missing
+ return fmt.Errorf("%s:%v", utils.ERR_MANDATORY_IE_MISSING, missing)
+ }
+ if ids, err := self.StorDb.GetTPTableIds(attrs.TPid, utils.TBL_TP_DERIVED_CHARGES, "id", nil); err != nil {
+ return fmt.Errorf("%s:%s", utils.ERR_SERVER_ERROR, err.Error())
+ } else if ids == nil {
+ return errors.New(utils.ERR_NOT_FOUND)
+ } else {
+ *reply = ids
+ }
+ return nil
+}
+
+// Removes specific DerivedCharges on Tariff plan
+func (self *ApierV1) RemTPDerivedCharges(attrs AttrGetTPDerivedCharges, reply *string) error {
+ if missing := utils.MissingStructFields(&attrs, []string{"TPid", "DerivedChargesId"}); len(missing) != 0 { //Params missing
+ return fmt.Errorf("%s:%v", utils.ERR_MANDATORY_IE_MISSING, missing)
+ }
+ if err := self.StorDb.RemTPData(utils.TBL_TP_DERIVED_CHARGES, attrs.TPid, attrs.DerivedChargesId); err != nil {
+ return fmt.Errorf("%s:%s", utils.ERR_SERVER_ERROR, err.Error())
+ } else {
+ *reply = "OK"
+ }
+ return nil
+}
+*/
diff --git a/data/storage/mysql/create_tariffplan_tables.sql b/data/storage/mysql/create_tariffplan_tables.sql
index 6ff71521b..36a4920dd 100644
--- a/data/storage/mysql/create_tariffplan_tables.sql
+++ b/data/storage/mysql/create_tariffplan_tables.sql
@@ -269,3 +269,35 @@ CREATE TABLE tp_derived_chargers (
);
+--
+-- Table structure for table `tp_cdr_stats`
+--
+
+DROP TABLE IF EXISTS tp_cdr_stats;
+CREATE TABLE tp_cdr_stats (
+ `tbid` int(11) NOT NULL AUTO_INCREMENT,
+ `tpid` varchar(64) NOT NULL,
+ `id` varchar(64) NOT NULL,
+ `queue_length` int(11) NOT NULL,
+ `time_window` int(11) NOT NULL,
+ `metrics` varchar(64) NOT NULL,
+ `setup_interval` varchar(64) NOT NULL,
+ `tor` varchar(64) NOT NULL,
+ `cdr_host` varchar(64) NOT NULL,
+ `cdr_source` varchar(64) NOT NULL,
+ `req_type` varchar(64) NOT NULL,
+ `direction` varchar(8) NOT NULL,
+ `tenant` varchar(64) NOT NULL,
+ `category` varchar(16) NOT NULL,
+ `account` varchar(24) NOT NULL,
+ `subject` varchar(64) NOT NULL,
+ `destination_prefix` varchar(64) NOT NULL,
+ `usage_interval` varchar(64) NOT NULL,
+ `mediation_run_ids` varchar(64) NOT NULL,
+ `rated_account` varchar(64) NOT NULL,
+ `rated_subject` varchar(64) NOT NULL,
+ `cost_interval` varchar(24) NOT NULL,
+ `action_triggers` varchar(64) NOT NULL,
+ PRIMARY KEY (`tbid`),
+ KEY `tpid` (`tpid`)
+);
diff --git a/engine/models.go b/engine/models.go
index a76abb5af..8b23111a1 100644
--- a/engine/models.go
+++ b/engine/models.go
@@ -137,3 +137,52 @@ type TpSharedGroup struct {
Strategy string
RatingSubject string
}
+
+type TpDerivedCharges struct {
+ Tbid int64 `gorm:"primary_key:yes"`
+ Tpid string
+ Loadid string
+ Direction string
+ Tenant string
+ Category string
+ Account string
+ Subject string
+ RunId string
+ RunFilter string
+ ReqtypeField string
+ DirectionField string
+ TenantField string
+ CategoryField string
+ AccountField string
+ SubjectField string
+ DestinationField string
+ SetupTimeField string
+ AnswerTimeField string
+ DurationField string
+}
+
+type TpCdrStat struct {
+ Tbid int64 `gorm:"primary_key:yes"`
+ Tpid string
+ Id string
+ QueueLength int
+ TimeWindow int64
+ Metrics string
+ SetupInterval string
+ Tor string
+ CdrHost string
+ CdrSource string
+ ReqType string
+ Direction string
+ Tenant string
+ Category string
+ Account string
+ Subject string
+ DestinationPrefix string
+ UsageInterval string
+ MediationRunIds string
+ RatedAccount string
+ RatedSubject string
+ CostInterval string
+ ActionTriggers string
+}
diff --git a/engine/storage_interface.go b/engine/storage_interface.go
index 9284b25a9..62373e53f 100644
--- a/engine/storage_interface.go
+++ b/engine/storage_interface.go
@@ -159,6 +159,9 @@ type LoadStorage interface {
SetTPSharedGroups(string, map[string][]*utils.TPSharedGroup) error
GetTpSharedGroups(string, string) (map[string][]*utils.TPSharedGroup, error)
+ SetTPCdrStats(string, map[string][]*utils.TPCdrStat) error
+ GetTpCdrStats(string, string) (map[string][]*utils.TPCdrStat, error)
+
SetTPLCRs(string, map[string]*LCR) error
GetTpLCRs(string, string) (map[string]*LCR, error)
diff --git a/engine/storage_sql.go b/engine/storage_sql.go
index a0a210a50..fcc390109 100644
--- a/engine/storage_sql.go
+++ b/engine/storage_sql.go
@@ -314,6 +314,44 @@ func (self *SQLStorage) SetTPSharedGroups(tpid string, sgs map[string][]*utils.T
return nil
}
+func (self *SQLStorage) SetTPCdrStats(tpid string, css map[string][]*utils.TPCdrStat) error {
+ if len(css) == 0 {
+ return nil //Nothing to set
+ }
+ tx := self.db.Begin()
+ for csId, cStats := range css {
+ tx.Where("tpid = ?", tpid).Where("id = ?", csId).Delete(TpCdrStat{})
+ for _, cs := range cStats {
+ tx.Save(TpCdrStat{
+ Tpid: tpid,
+ Id: csId,
+ QueueLength: cs.QueueLength,
+ TimeWindow: cs.TimeWindow,
+ Metrics: cs.Metrics,
+ SetupInterval: cs.SetupInterval,
+ Tor: cs.TOR,
+ CdrHost: cs.CdrHost,
+ CdrSource: cs.CdrSource,
+ ReqType: cs.ReqType,
+ Direction: cs.Direction,
+ Tenant: cs.Tenant,
+ Category: cs.Category,
+ Account: cs.Account,
+ Subject: cs.Subject,
+ DestinationPrefix: cs.DestinationPrefix,
+ UsageInterval: cs.UsageInterval,
+ MediationRunIds: cs.MediationRunIds,
+ RatedAccount: cs.RatedAccount,
+ RatedSubject: cs.RatedSubject,
+ CostInterval: cs.CostInterval,
+ ActionTriggers: cs.ActionTriggers,
+ })
+ }
+ }
+ tx.Commit()
+ return nil
+}
+
func (self *SQLStorage) SetTPLCRs(tpid string, lcrs map[string]*LCR) error {
if len(lcrs) == 0 {
return nil //Nothing to set
@@ -1192,16 +1230,16 @@ func (self *SQLStorage) GetTpRatingProfiles(qryRpf *utils.TPRatingProfile) (map[
func (self *SQLStorage) GetTpSharedGroups(tpid, tag string) (map[string][]*utils.TPSharedGroup, error) {
sgs := make(map[string][]*utils.TPSharedGroup)
- var tpSharedGroups []TpSharedGroup
+ var tpCdrStats []TpSharedGroup
q := self.db.Where("tpid = ?", tpid)
if len(tag) != 0 {
q = q.Where("id = ?", tag)
}
- if err := q.Find(&tpSharedGroups).Error; err != nil {
+ if err := q.Find(&tpCdrStats).Error; err != nil {
return nil, err
}
- for _, tpSg := range tpSharedGroups {
+ for _, tpSg := range tpCdrStats {
sgs[tag] = append(sgs[tag], &utils.TPSharedGroup{
Account: tpSg.Account,
Strategy: tpSg.Strategy,
@@ -1211,6 +1249,45 @@ func (self *SQLStorage) GetTpSharedGroups(tpid, tag string) (map[string][]*utils
return sgs, nil
}
+func (self *SQLStorage) GetTpCdrStats(tpid, tag string) (map[string][]*utils.TPCdrStat, error) {
+ css := make(map[string][]*utils.TPCdrStat)
+
+ var tpCdrStats []TpCdrStat
+ q := self.db.Where("tpid = ?", tpid)
+ if len(tag) != 0 {
+ q = q.Where("id = ?", tag)
+ }
+ if err := q.Find(&tpCdrStats).Error; err != nil {
+ return nil, err
+ }
+
+ for _, tpCs := range tpCdrStats {
+ css[tag] = append(css[tag], &utils.TPCdrStat{
+ QueueLength: tpCs.QueueLength,
+ TimeWindow: tpCs.TimeWindow,
+ Metrics: tpCs.Metrics,
+ SetupInterval: tpCs.SetupInterval,
+ TOR: tpCs.Tor,
+ CdrHost: tpCs.CdrHost,
+ CdrSource: tpCs.CdrSource,
+ ReqType: tpCs.ReqType,
+ Direction: tpCs.Direction,
+ Tenant: tpCs.Tenant,
+ Category: tpCs.Category,
+ Account: tpCs.Account,
+ Subject: tpCs.Subject,
+ DestinationPrefix: tpCs.DestinationPrefix,
+ UsageInterval: tpCs.UsageInterval,
+ MediationRunIds: tpCs.MediationRunIds,
+ RatedAccount: tpCs.RatedAccount,
+ RatedSubject: tpCs.RatedSubject,
+ CostInterval: tpCs.CostInterval,
+ ActionTriggers: tpCs.ActionTriggers,
+ })
+ }
+ return css, nil
+}
+
func (self *SQLStorage) GetTpLCRs(tpid, tag string) (map[string]*LCR, error) {
lcrs := make(map[string]*LCR)
q := fmt.Sprintf("SELECT * FROM %s WHERE tpid='%s'", utils.TBL_TP_LCRS, tpid)
diff --git a/utils/apitpdata.go b/utils/apitpdata.go
index 37553ad47..f42e02d5c 100644
--- a/utils/apitpdata.go
+++ b/utils/apitpdata.go
@@ -251,6 +251,35 @@ type TPLcrRule struct {
Weight float64
}
+type TPCdrStats struct {
+ TPid string
+ CdrStatsId string
+ CdrStats []*TPCdrStat
+}
+
+type TPCdrStat struct {
+ QueueLength int
+ TimeWindow int64
+ Metrics string
+ SetupInterval string
+ TOR string
+ CdrHost string
+ CdrSource string
+ ReqType string
+ Direction string
+ Tenant string
+ Category string
+ Account string
+ Subject string
+ DestinationPrefix string
+ UsageInterval string
+ MediationRunIds string
+ RatedAccount string
+ RatedSubject string
+ CostInterval string
+ ActionTriggers string
+}
+
type TPActionPlan struct {
TPid string // Tariff plan id
Id string // ActionPlan id
diff --git a/utils/consts.go b/utils/consts.go
index d1546be2f..20f4b76be 100644
--- a/utils/consts.go
+++ b/utils/consts.go
@@ -28,11 +28,13 @@ const (
TBL_TP_RATING_PLANS = "tp_rating_plans"
TBL_TP_RATE_PROFILES = "tp_rating_profiles"
TBL_TP_SHARED_GROUPS = "tp_shared_groups"
+ TBL_TP_CDR_STATS = "tp_cdr_stats"
TBL_TP_LCRS = "tp_lcr_rules"
TBL_TP_ACTIONS = "tp_actions"
TBL_TP_ACTION_PLANS = "tp_action_plans"
TBL_TP_ACTION_TRIGGERS = "tp_action_triggers"
TBL_TP_ACCOUNT_ACTIONS = "tp_account_actions"
+ TBL_TP_DERIVED_CHARGES = "tp_derived_charges"
TBL_CDRS_PRIMARY = "cdrs_primary"
TBL_CDRS_EXTRA = "cdrs_extra"
TBL_COST_DETAILS = "cost_details"