Clear balance subject in rates before further monetary debits

This commit is contained in:
DanB
2017-08-30 21:06:33 +02:00
parent 8cbe961282
commit 64db7f6f44
9 changed files with 32 additions and 15 deletions

View File

@@ -378,7 +378,7 @@ func (ub *Account) debitCreditBalance(cd *CallDescriptor, count bool, dryRun boo
//log.Printf("%+v, %+v", usefulMoneyBalances, usefulUnitBalances)
var leftCC *CallCost
cc = cd.CreateCallCost()
var hadBalanceSubj bool
generalBalanceChecker := true
for generalBalanceChecker {
generalBalanceChecker = false
@@ -397,7 +397,9 @@ func (ub *Account) debitCreditBalance(cd *CallDescriptor, count bool, dryRun boo
if debitErr != nil {
return nil, debitErr
}
if balance.RatingSubject != "" && !strings.HasPrefix(balance.RatingSubject, utils.ZERO_RATING_SUBJECT_PREFIX) {
hadBalanceSubj = true
}
//utils.Logger.Info(fmt.Sprintf("CD AFTER UNIT: %+v", cd))
if partCC != nil {
//log.Printf("partCC: %+v", partCC.Timespans[0])
@@ -473,6 +475,9 @@ func (ub *Account) debitCreditBalance(cd *CallDescriptor, count bool, dryRun boo
//log.Print("AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA")
}
//log.Printf("After balances CD: %+v", cd)
if hadBalanceSubj {
cd.RatingInfos = nil
}
leftCC, err = cd.getCost()
if err != nil {
utils.Logger.Err(fmt.Sprintf("Error getting new cost for balance subject: %v", err))

View File

@@ -302,6 +302,8 @@ func (b *Balance) SetDirty() {
b.dirty = true
}
// debitUnits will debit units for call descriptor.
// returns the amount debited within cc
func (b *Balance) debitUnits(cd *CallDescriptor, ub *Account, moneyBalances Balances, count bool, dryRun, debitConnectFee bool) (cc *CallCost, err error) {
if !b.IsActiveAt(cd.TimeStart) || b.GetValue() <= 0 {
return
@@ -405,7 +407,6 @@ func (b *Balance) debitUnits(cd *CallDescriptor, ub *Account, moneyBalances Bala
if ts.Increments == nil {
ts.createIncrementsSlice()
}
if ts.RateInterval == nil {
utils.Logger.Err(fmt.Sprintf("Nil RateInterval ERROR on TS: %+v, CC: %+v, from CD: %+v", ts, cc, cd))
return nil, errors.New("timespan with no rate interval assigned")
@@ -432,7 +433,6 @@ func (b *Balance) debitUnits(cd *CallDescriptor, ub *Account, moneyBalances Bala
maxCost, strategy := ts.RateInterval.GetMaxCost()
for incIndex, inc := range ts.Increments {
if tsIndex == 0 && incIndex == 0 && ts.RateInterval.Rating.ConnectFee > 0 && debitConnectFee && cc.deductConnectFee && ok {
// go to nextincrement
continue
@@ -486,7 +486,7 @@ func (b *Balance) debitUnits(cd *CallDescriptor, ub *Account, moneyBalances Bala
utils.Logger.Warning(fmt.Sprintf("<RALs> Going negative on account %s with AllowNegative: false", cd.GetAccountKey()))
moneyBal = ub.GetDefaultMoneyBalance()
}
if (cost == 0 || moneyBal != nil) && b.GetValue() >= amount {
if b.GetValue() >= amount && (moneyBal != nil || cost == 0) {
b.SubstractValue(amount)
inc.BalanceInfo.Unit = &UnitInfo{
UUID: b.Uuid,

View File

@@ -494,7 +494,6 @@ func (cd *CallDescriptor) GetCost() (*CallCost, error) {
}
func (cd *CallDescriptor) getCost() (*CallCost, error) {
// check for 0 duration
if cd.GetDuration() == 0 {
cc := cd.CreateCallCost()

View File

@@ -1713,7 +1713,6 @@ func TestCDRefundIncrementsZeroValue(t *testing.T) {
}
}
/*
func TestCDDebitBalanceSubjectWithFallback(t *testing.T) {
acnt := &Account{
ID: "TCDDBSWF:account1",
@@ -1815,11 +1814,10 @@ func TestCDDebitBalanceSubjectWithFallback(t *testing.T) {
for _, rpf := range []*RatingProfile{rpfTCDDBSWF, rpfAny} {
dataStorage.SetRatingProfile(rpf, utils.NonTransactional)
}
cd1 := &CallDescriptor{
cd1 := &CallDescriptor{ // test the cost for subject within balance setup
Direction: "*out",
Category: "call",
Tenant: "TCDDBSWF",
Account: "account1",
Subject: "SubjTCDDBSWF",
Destination: "1716",
TimeStart: time.Date(2015, 01, 01, 9, 0, 0, 0, time.UTC),
@@ -1842,9 +1840,20 @@ func TestCDDebitBalanceSubjectWithFallback(t *testing.T) {
if cc, err := cd2.GetCost(); err != nil || cc.Cost != 0.6 {
t.Errorf("Error getting *any dest: %+v %v", cc, err)
}
if cc, err := cd1.Debit(); err != nil {
cd := &CallDescriptor{ // test the cost
Direction: "*out",
Category: "call",
Tenant: "TCDDBSWF",
Account: "account1",
Subject: "account1",
Destination: "1716",
TimeStart: time.Date(2015, 01, 01, 9, 0, 0, 0, time.UTC),
TimeEnd: time.Date(2015, 01, 01, 9, 2, 0, 0, time.UTC),
TOR: utils.VOICE,
}
if cc, err := cd.Debit(); err != nil {
t.Error(err)
} else if cc.Cost != 0 {
} else if cc.Cost != 0.6 {
t.Errorf("CallCost: %v", cc)
}
if resAcnt, err := dataStorage.GetAccount(acnt.ID); err != nil {
@@ -1853,12 +1862,11 @@ func TestCDDebitBalanceSubjectWithFallback(t *testing.T) {
resAcnt.BalanceMap[utils.VOICE][0].Value != 0 {
t.Errorf("Account: %v", resAcnt)
} else if len(resAcnt.BalanceMap[utils.MONETARY]) == 0 ||
resAcnt.BalanceMap[utils.VOICE][0].ID != utils.META_DEFAULT ||
resAcnt.BalanceMap[utils.VOICE][0].Value != -0.60 {
resAcnt.BalanceMap[utils.MONETARY][0].ID != utils.META_DEFAULT ||
resAcnt.BalanceMap[utils.MONETARY][0].Value != -0.600013 { // rounding issue
t.Errorf("Account: %s", utils.ToIJSON(resAcnt))
}
}
*/
/*************** BENCHMARKS ********************/
func BenchmarkStorageGetting(b *testing.B) {

View File

@@ -35,7 +35,9 @@ func TestHistoryRatinPlans(t *testing.T) {
func TestHistoryDestinations(t *testing.T) {
scribe := historyScribe.(*history.MockScribe)
buf := scribe.GetBuffer(history.DESTINATIONS_FN)
expected := `{"Id":"ALL","Prefixes":["49","41","43"]},
expected := `{"Id":"*ddc_test","Prefixes":["333","666"]},
{"Id":"ALL","Prefixes":["49","41","43"]},
{"Id":"DST_TCDDBSWF","Prefixes":["1716"]},
{"Id":"DST_UK_Mobile_BIG5","Prefixes":["447956"]},
{"Id":"EU_LANDLINE","Prefixes":["444"]},
{"Id":"EXOTIC","Prefixes":["999"]},

0
general_tests/acntacts_test.go Executable file → Normal file
View File

0
general_tests/auth_test.go Executable file → Normal file
View File

0
general_tests/smschrg1_test.go Executable file → Normal file
View File

View File

@@ -284,6 +284,9 @@ func MinDuration(d1, d2 time.Duration) time.Duration {
return d2
}
// ParseZeroRatingSubject will parse the subject in the balance
// returns duration if able to extract it from subject
// returns error if not able to parse duration (ie: if ratingSubject is standard one)
func ParseZeroRatingSubject(rateSubj string) (time.Duration, error) {
rateSubj = strings.TrimSpace(rateSubj)
if rateSubj == "" || rateSubj == ANY {