more loading fixes and more tests

This commit is contained in:
Radu Ioan Fericean
2013-10-09 20:02:13 +03:00
parent c9c4a484eb
commit 54ab6074a6
15 changed files with 100 additions and 49 deletions

View File

@@ -40,7 +40,7 @@ func init() {
//db_server := "192.168.0.17"
m, _ := NewMapStorage()
//m, _ := NewMongoStorage(db_server, "27017", "cgrates_test", "", "")
//m, _ := NewRedisStorage(db_server+":6379", 11, "")
//m, _ := NewRedisStorage(db_server+":6379", 11, "", utils.MSGPACK)
//m, _ := NewRedigoStorage(db_server+":6379", 11, "")
//m, _ := NewRadixStorage(db_server+":6379", 11, "")
storageGetter, _ = m.(DataStorage)
@@ -225,17 +225,24 @@ func (cd *CallDescriptor) splitInTimeSpans(firstSpan *TimeSpan) (timespans []*Ti
Logger.Debug(fmt.Sprintf("After SplitByRatingPlan: %+v", timespans))
// split on price intervals
for i := 0; i < len(timespans); i++ {
//log.Printf("TS: %+v", timespans[i])
rp := timespans[i].ratingPlan
Logger.Debug(fmt.Sprintf("rp: %+v", rp))
//timespans[i].RatingPlan = nil
rp.RateIntervals.Sort()
for _, interval := range rp.RateIntervals {
//log.Printf("\tINTERVAL: %+v %v", interval, len(rp.RateIntervals))
if timespans[i].RateInterval != nil && timespans[i].RateInterval.Weight < interval.Weight {
continue // if the timespan has an interval than it already has a heigher weight
}
newTs := timespans[i].SplitByRateInterval(interval)
if newTs != nil {
newTs.ratingPlan = rp
timespans = append(timespans, newTs)
// insert the new timespan
i++
timespans = append(timespans, nil)
copy(timespans[i+1:], timespans[i:])
timespans[i] = newTs
break
}
}
@@ -307,12 +314,12 @@ func (cd *CallDescriptor) GetCost() (*CallCost, error) {
}
// global rounding
cost = utils.Round(cost, roundingDecimals, roundingMethod)
subject := strings.Split(matchedSubject, ":")
startIndex := len(fmt.Sprintf("%s:%s:%s:", cd.Direction, cd.Tenant, cd.TOR))
cc := &CallCost{
Direction: cd.Direction,
TOR: cd.TOR,
Tenant: cd.Tenant,
Subject: subject[len(subject)-1],
Subject: matchedSubject[startIndex:],
Account: cd.Account,
Destination: destPrefix,
Cost: cost,

View File

@@ -117,6 +117,23 @@ func TestGetCostTimespans(t *testing.T) {
if result.Cost != expected.Cost || result.ConnectFee != expected.ConnectFee || len(result.Timespans) != 2 {
t.Errorf("Expected %+v was %+v", expected, result)
}
}
/*
func TestGetCostRatingPlansAndRatingIntervals(t *testing.T) {
t1 := time.Date(2012, time.February, 27, 23, 50, 0, 0, time.UTC)
t2 := time.Date(2012, time.February, 28, 18, 10, 0, 0, time.UTC)
cd := &CallDescriptor{Direction: "*out", TOR: "0", Tenant: "CUSTOMER_1", Subject: "rif:from:tm", Destination: "49178", TimeStart: t1, TimeEnd: t2, LoopIndex: 0, CallDuration: t2.Sub(t1)}
result, _ := cd.GetCost()
if len(result.Timespans) != 3 ||
!result.Timespans[0].TimeEnd.Equal(result.Timespans[1].TimeStart) ||
!result.Timespans[1].TimeEnd.Equal(result.Timespans[2].TimeStart) {
for _, ts := range result.Timespans {
t.Logf("TS %+v", ts)
}
t.Errorf("Expected %+v was %+v", 3, len(result.Timespans))
}
}
func TestGetCostRateGroups(t *testing.T) {
@@ -132,7 +149,7 @@ func TestGetCostRateGroups(t *testing.T) {
t.Error("Error calculating cost: ", result.Timespans[0])
}
}
*/
func TestGetCostNoConnectFee(t *testing.T) {
t1 := time.Date(2012, time.February, 2, 17, 30, 0, 0, time.UTC)
t2 := time.Date(2012, time.February, 2, 18, 30, 0, 0, time.UTC)
@@ -196,9 +213,8 @@ func TestSpansMultipleRatingPlans(t *testing.T) {
t2 := time.Date(2012, time.February, 8, 0, 30, 0, 0, time.UTC)
cd := &CallDescriptor{Direction: "*out", TOR: "0", Tenant: "vdf", Subject: "rif", Destination: "0257308200", TimeStart: t1, TimeEnd: t2}
result, _ := cd.GetCost()
expected := &CallCost{Tenant: "vdf", Subject: "rif", Destination: "0257", Cost: 1200, ConnectFee: 0}
if result.Cost != expected.Cost || result.ConnectFee != expected.ConnectFee {
t.Errorf("Expected %v was %v", expected, result)
if result.Cost != 300 || result.ConnectFee != 0 {
t.Errorf("Expected %v was %v", 300, result)
}
}

View File

@@ -343,7 +343,11 @@ func (csvr *CSVReader) LoadRatingProfiles() (err error) {
if fallbacksubject != "" {
for _, fbs := range strings.Split(fallbacksubject, ";") {
rp.FallbackKey += fmt.Sprintf("%s:%s:%s:%s", direction, tenant, tor, fbs) + ";"
newKey := fmt.Sprintf("%s:%s:%s:%s", direction, tenant, tor, fbs)
var sslice utils.StringSlice = strings.Split(rp.FallbackKey, ";")
if !sslice.Contains(newKey) {
rp.FallbackKey += newKey + ";"
}
}
rp.FallbackKey = strings.TrimRight(rp.FallbackKey, ";")
}

View File

@@ -79,6 +79,8 @@ T2,GERMANY_PREMIUM,GBP_71
STANDARD,RT_STANDARD,WORKDAYS_00,10
STANDARD,RT_STD_WEEKEND,WORKDAYS_18,10
STANDARD,RT_STD_WEEKEND,WEEKENDS,10
PREMIUM,P1,WORKDAYS_00,10
PREMIUM,T2,WORKDAYS_18,10
PREMIUM,RT_STD_WEEKEND,WEEKENDS,10
DEFAULT,RT_DEFAULT,WORKDAYS_00,10
EVENING,P1,WORKDAYS_00,10
@@ -812,6 +814,10 @@ func TestLoadRatingProfiles(t *testing.T) {
if !reflect.DeepEqual(rp.DestinationMap["GERMANY"], expected.DestinationMap["GERMANY"]) {
t.Errorf("Error loading rating profile: %+v", rp.DestinationMap["GERMANY"][0])
}
if _, ok := csvr.ratingProfiles["*out:CUSTOMER_1:0:rif:from:tm"]; !ok {
t.Error("Failed to load rating profile")
}
}
func TestLoadActions(t *testing.T) {

View File

@@ -197,8 +197,8 @@ func (dbr *DbReader) LoadRatingProfiles() error {
return errors.New(fmt.Sprintf("Could not load destination rate timings for tag: %v", rp.DestinationMap))
}
for _, drt := range drts {
plan := &RatingPlan{ActivationTime: at}
for _, dr := range drt.destinationRates {
plan := &RatingPlan{ActivationTime: at}
plan.AddRateInterval(drt.GetRateInterval(dr))
rp.AddRatingPlanIfNotPresent(dr.DestinationsTag, plan)
}

View File

@@ -163,8 +163,9 @@ func (i *RateInterval) getRightMargin(t time.Time) (rigthtTime time.Time) {
hour, _ = strconv.Atoi(split[0])
min, _ = strconv.Atoi(split[1])
sec, _ = strconv.Atoi(split[2])
return time.Date(year, month, day, hour, min, sec, nsec, loc)
}
return time.Date(year, month, day, hour, min, sec, nsec, loc)
return time.Date(year, month, day, hour, min, sec, nsec, loc).Add(time.Second)
}
/*

View File

@@ -23,6 +23,18 @@ import (
"time"
)
func TestRateIntervalSimpleContains(t *testing.T) {
i := &RateInterval{
WeekDays: WeekDays{time.Monday, time.Tuesday, time.Wednesday, time.Thursday, time.Friday},
StartTime: "18:00:00",
EndTime: "",
}
d := time.Date(2012, time.February, 27, 23, 59, 59, 0, time.UTC)
if !i.Contains(d) {
t.Errorf("Date %+v shoud be in interval %+v", d, i)
}
}
func TestRateIntervalMonth(t *testing.T) {
i := &RateInterval{Months: Months{time.February}}
d := time.Date(2012, time.February, 10, 23, 0, 0, 0, time.UTC)

View File

@@ -34,7 +34,7 @@ func TestApRestoreFromStorage(t *testing.T) {
Destination: "49"}
cd.LoadRatingPlans()
if len(cd.RatingPlans) != 2 {
t.Error("Error restoring activation periods: ", len(cd.RatingPlans))
t.Error("Error restoring activation periods: ", cd.RatingPlans[0])
}
}
@@ -79,8 +79,8 @@ func TestFallbackDirect(t *testing.T) {
func TestFallbackMultiple(t *testing.T) {
cd := &CallDescriptor{TOR: "0", Direction: OUTBOUND, Tenant: "vdf", Subject: "fall", Destination: "0723045"}
cd.LoadRatingPlans()
if len(cd.RatingPlans) != 2 {
t.Errorf("Error restoring rating plans: %#v", cd.RatingPlans)
if len(cd.RatingPlans) != 1 {
t.Errorf("Error restoring rating plans: %+v", cd.RatingPlans)
}
}

View File

@@ -46,6 +46,7 @@ func (ms *MapStorage) Flush() error {
func (ms *MapStorage) GetRatingProfile(key string) (rp *RatingProfile, err error) {
if values, ok := ms.dict[RATING_PROFILE_PREFIX+key]; ok {
rp = new(RatingProfile)
err = ms.ms.Unmarshal(values, rp)
} else {
return nil, errors.New("not found")
@@ -75,8 +76,8 @@ func (ms *MapStorage) DestinationContainsPrefix(key string, prefix string) (prec
if d, err := ms.GetDestination(key); err != nil {
return 0, err
} else {
for _, p := range utils.SplitPrefix(prefix) {
if precision, ok := d.containsPrefix(p); ok {
for _, p := range utils.SplitPrefixInterface(prefix) {
if precision, ok := d.containsPrefix(p.(string)); ok {
return precision, nil
}
}

View File

@@ -23,6 +23,7 @@ import (
"encoding/json"
"fmt"
"github.com/cgrates/cgrates/utils"
"strings"
"time"
)
@@ -1066,7 +1067,14 @@ func (self *SQLStorage) GetTpRatingProfiles(tpid, tag string) (map[string]*Ratin
rp.DestRatesTimingTag = destrates_timing_tag
rp.ActivationTime = activation_time
if fallback_subject != "" {
rp.FallbackKey = fmt.Sprintf("%s:%s:%s:%s", direction, tenant, tor, fallback_subject)
for _, fbs := range strings.Split(fallback_subject, ";") {
newKey := fmt.Sprintf("%s:%s:%s:%s", direction, tenant, tor, fbs)
var sslice utils.StringSlice = strings.Split(rp.FallbackKey, ";")
if !sslice.Contains(newKey) {
rp.FallbackKey += newKey + ";"
}
}
rp.FallbackKey = strings.TrimRight(rp.FallbackKey, ";")
}
}
return rpfs, nil

View File

@@ -154,10 +154,11 @@ func (ts *TimeSpan) SplitByRateInterval(i *RateInterval) (nts *TimeSpan) {
nts.CallDuration = ts.CallDuration
ts.SetNewCallDuration(nts)
Logger.Debug(fmt.Sprintf("Group splitting: %+v %+v", ts, nts))
//log.Printf("Group splitting: %+v %+v", ts, nts)
return
}
}
//log.Printf("%+v %+v", i, ts.TimeEnd)
// if the span is enclosed in the interval try to set as new interval and return nil
if i.Contains(ts.TimeStart) && i.Contains(ts.TimeEnd) {
//Logger.Debug("All in interval")
@@ -168,6 +169,9 @@ func (ts *TimeSpan) SplitByRateInterval(i *RateInterval) (nts *TimeSpan) {
if i.Contains(ts.TimeStart) {
//Logger.Debug("Start in interval")
splitTime := i.getRightMargin(ts.TimeStart)
if ts.TimeEnd.Sub(splitTime) == time.Second {
//return
}
ts.SetRateInterval(i)
if splitTime == ts.TimeStart {
return
@@ -177,6 +181,7 @@ func (ts *TimeSpan) SplitByRateInterval(i *RateInterval) (nts *TimeSpan) {
nts.CallDuration = ts.CallDuration
ts.SetNewCallDuration(nts)
Logger.Debug(fmt.Sprintf("right: %+v %+v", ts, nts))
//log.Printf("right: %+v %+v", ts, nts)
return
}
// if only the end time is in the interval split the interval to the left
@@ -193,6 +198,7 @@ func (ts *TimeSpan) SplitByRateInterval(i *RateInterval) (nts *TimeSpan) {
nts.CallDuration = ts.CallDuration
ts.SetNewCallDuration(nts)
Logger.Debug(fmt.Sprintf("left: %+v %+v", ts, nts))
//log.Printf("left: %+v %+v", ts, nts)
return
}
return

View File

@@ -31,18 +31,18 @@ func TestRightMargin(t *testing.T) {
ts := &TimeSpan{TimeStart: t1, TimeEnd: t2}
oldDuration := ts.GetDuration()
nts := ts.SplitByRateInterval(i)
if ts.TimeStart != t1 || ts.TimeEnd != time.Date(2012, time.February, 3, 23, 59, 59, 0, time.UTC) {
if ts.TimeStart != t1 || ts.TimeEnd != time.Date(2012, time.February, 3, 24, 0, 0, 0, time.UTC) {
t.Error("Incorrect first half", ts)
}
if nts.TimeStart != time.Date(2012, time.February, 3, 23, 59, 59, 0, time.UTC) || nts.TimeEnd != t2 {
if nts.TimeStart != time.Date(2012, time.February, 4, 0, 0, 0, 0, time.UTC) || nts.TimeEnd != t2 {
t.Error("Incorrect second half", nts)
}
if ts.RateInterval != i {
t.Error("RateInterval not attached correctly")
}
if ts.GetDuration().Seconds() != 15*60-1 || nts.GetDuration().Seconds() != 10*60+1 {
t.Error("Wrong durations.for RateIntervals", ts.GetDuration().Seconds(), ts.GetDuration().Seconds())
if ts.GetDuration() != 15*time.Minute || nts.GetDuration() != 10*time.Minute {
t.Error("Wrong durations.for RateIntervals", ts.GetDuration(), ts.GetDuration())
}
if ts.GetDuration().Seconds()+nts.GetDuration().Seconds() != oldDuration.Seconds() {
@@ -57,18 +57,18 @@ func TestRightHourMargin(t *testing.T) {
ts := &TimeSpan{TimeStart: t1, TimeEnd: t2}
oldDuration := ts.GetDuration()
nts := ts.SplitByRateInterval(i)
if ts.TimeStart != t1 || ts.TimeEnd != time.Date(2012, time.February, 3, 17, 59, 00, 0, time.UTC) {
if ts.TimeStart != t1 || ts.TimeEnd != time.Date(2012, time.February, 3, 17, 59, 0, 0, time.UTC) {
t.Error("Incorrect first half", ts)
}
if nts.TimeStart != time.Date(2012, time.February, 3, 17, 59, 00, 0, time.UTC) || nts.TimeEnd != t2 {
if nts.TimeStart != time.Date(2012, time.February, 3, 17, 59, 0, 0, time.UTC) || nts.TimeEnd != t2 {
t.Error("Incorrect second half", nts)
}
if ts.RateInterval != i {
t.Error("RateInterval not attached correctly")
}
if ts.GetDuration().Seconds() != 29*60 || nts.GetDuration().Seconds() != 1*60 {
t.Error("Wrong durations.for RateIntervals", ts.GetDuration().Seconds(), nts.GetDuration().Seconds())
if ts.GetDuration() != 29*time.Minute || nts.GetDuration() != 1*time.Minute {
t.Error("Wrong durations.for RateIntervals", ts.GetDuration(), nts.GetDuration())
}
if ts.GetDuration().Seconds()+nts.GetDuration().Seconds() != oldDuration.Seconds() {
t.Errorf("The duration has changed: %v + %v != %v", ts.GetDuration().Seconds(), nts.GetDuration().Seconds(), oldDuration.Seconds())

View File

@@ -260,6 +260,7 @@ func (ub *UserBalance) debitCreditBalance(cc *CallCost, count bool) error {
}
continue
}
// get the new rate
cd := cc.CreateCallDescriptor()
cd.TimeStart = ts.GetTimeStartForIncrement(incrementIndex)

View File

@@ -684,47 +684,45 @@ func TestDebitNegativeMinuteBalance(t *testing.T) {
}
*/
/*
func TestDebitSMSBalance(t *testing.T) {
b1 := &Balance{Value: 10, Weight: 10, SpecialPrice: 0.0, DestinationId: "NAT"}
b2 := &Balance{Value: 100, Weight: 20, SpecialPrice: 0.0, DestinationId: "RET"}
b1 := &Balance{Value: 10, Weight: 10, DestinationId: "NAT"}
b2 := &Balance{Value: 100, Weight: 20, DestinationId: "RET"}
rifsBalance := &UserBalance{Id: "other", BalanceMap: map[string]BalanceChain{MINUTES + OUTBOUND: BalanceChain{b1, b2}, CREDIT + OUTBOUND: BalanceChain{&Balance{Value: 21}}, SMS + OUTBOUND: BalanceChain{&Balance{Value: 100}}}}
result := rifsBalance.debitBalance(SMS, 12, false)
result := rifsBalance.debitGenericBalance(SMS, 12, false)
if rifsBalance.BalanceMap[SMS+OUTBOUND][0].Value != 88 || result != rifsBalance.BalanceMap[SMS+OUTBOUND][0].Value {
t.Errorf("Expected %v was %v", 88, rifsBalance.BalanceMap[SMS+OUTBOUND])
}
}
func TestDebitAllSMSBalance(t *testing.T) {
b1 := &Balance{Value: 10, Weight: 10, SpecialPrice: 0.0, DestinationId: "NAT"}
b2 := &Balance{Value: 100, Weight: 20, SpecialPrice: 0.0, DestinationId: "RET"}
b1 := &Balance{Value: 10, Weight: 10, DestinationId: "NAT"}
b2 := &Balance{Value: 100, Weight: 20, DestinationId: "RET"}
rifsBalance := &UserBalance{Id: "other", BalanceMap: map[string]BalanceChain{MINUTES + OUTBOUND: BalanceChain{b1, b2}, CREDIT + OUTBOUND: BalanceChain{&Balance{Value: 21}}, SMS + OUTBOUND: BalanceChain{&Balance{Value: 100}}}}
result := rifsBalance.debitBalance(SMS, 100, false)
result := rifsBalance.debitGenericBalance(SMS, 100, false)
if rifsBalance.BalanceMap[SMS+OUTBOUND][0].Value != 0 || result != rifsBalance.BalanceMap[SMS+OUTBOUND][0].Value {
t.Errorf("Expected %v was %v", 0, rifsBalance.BalanceMap[SMS+OUTBOUND])
}
}
func TestDebitMoreSMSBalance(t *testing.T) {
b1 := &Balance{Value: 10, Weight: 10, SpecialPrice: 0.0, DestinationId: "NAT"}
b2 := &Balance{Value: 100, Weight: 20, SpecialPrice: 0.0, DestinationId: "RET"}
b1 := &Balance{Value: 10, Weight: 10, DestinationId: "NAT"}
b2 := &Balance{Value: 100, Weight: 20, DestinationId: "RET"}
rifsBalance := &UserBalance{Id: "other", BalanceMap: map[string]BalanceChain{MINUTES + OUTBOUND: BalanceChain{b1, b2}, CREDIT + OUTBOUND: BalanceChain{&Balance{Value: 21}}, SMS + OUTBOUND: BalanceChain{&Balance{Value: 100}}}}
result := rifsBalance.debitBalance(SMS, 110, false)
result := rifsBalance.debitGenericBalance(SMS, 110, false)
if rifsBalance.BalanceMap[SMS+OUTBOUND][0].Value != -10 || result != rifsBalance.BalanceMap[SMS+OUTBOUND][0].Value {
t.Errorf("Expected %v was %v", -10, rifsBalance.BalanceMap[SMS+OUTBOUND][0].Value)
}
}
func TestDebitNegativeSMSBalance(t *testing.T) {
b1 := &Balance{Value: 10, Weight: 10, SpecialPrice: 0.0, DestinationId: "NAT"}
b2 := &Balance{Value: 100, Weight: 20, SpecialPrice: 0.0, DestinationId: "RET"}
b1 := &Balance{Value: 10, Weight: 10, DestinationId: "NAT"}
b2 := &Balance{Value: 100, Weight: 20, DestinationId: "RET"}
rifsBalance := &UserBalance{Id: "other", BalanceMap: map[string]BalanceChain{MINUTES + OUTBOUND: BalanceChain{b1, b2}, CREDIT + OUTBOUND: BalanceChain{&Balance{Value: 21}}, SMS + OUTBOUND: BalanceChain{&Balance{Value: 100}}}}
result := rifsBalance.debitBalance(SMS, -15, false)
result := rifsBalance.debitGenericBalance(SMS, -15, false)
if rifsBalance.BalanceMap[SMS+OUTBOUND][0].Value != 115 || result != rifsBalance.BalanceMap[SMS+OUTBOUND][0].Value {
t.Errorf("Expected %v was %v", 115, rifsBalance.BalanceMap[SMS+OUTBOUND])
}
}
*/
func TestUserBalancedebitBalance(t *testing.T) {
ub := &UserBalance{

View File

@@ -142,15 +142,6 @@ func (ss StringSlice) Contains(needle string) bool {
return false
}
func SplitPrefix(prefix string) []string {
var subs []string
max := len(prefix)
for i := 0; i < len(prefix)-1; i++ {
subs = append(subs, prefix[:max-i])
}
return subs
}
func SplitPrefixInterface(prefix string) []interface{} {
var subs []interface{}
max := len(prefix)