diff --git a/engine/activationperiod_test.go b/engine/activationperiod_test.go
index 9b17fc467..9c619c9cb 100644
--- a/engine/activationperiod_test.go
+++ b/engine/activationperiod_test.go
@@ -187,13 +187,6 @@ func BenchmarkActivationPeriodStoreRestoreJson(b *testing.B) {
}
}
-func BenchmarkActivationPeriodRestore(b *testing.B) {
- ap := &ActivationPeriod{}
- for i := 0; i < b.N; i++ {
- ap.Restore("1328106601000000000|;2;1;3,4;14:30:00;15:00:00;0;0;0;0;0")
- }
-}
-
func BenchmarkActivationPeriodStoreRestore(b *testing.B) {
b.StopTimer()
d := time.Date(2012, time.February, 1, 14, 30, 1, 0, time.UTC)
@@ -208,32 +201,41 @@ func BenchmarkActivationPeriodStoreRestore(b *testing.B) {
ap1 := &ActivationPeriod{}
b.StartTimer()
for i := 0; i < b.N; i++ {
- result, _ := ap.Store()
- ap1.Restore(result)
+ result, _ := marsh.Marshal(ap)
+ marsh.Unmarshal(result, ap1)
}
}
-func BenchmarkActivationPeriodMarshallerMyStoreRestore(b *testing.B) {
- b.StopTimer()
- d := time.Date(2012, time.February, 1, 14, 30, 1, 0, time.UTC)
- i := &Interval{Months: []time.Month{time.February},
- MonthDays: []int{1},
- WeekDays: []time.Weekday{time.Wednesday, time.Thursday},
- StartTime: "14:30:00",
- EndTime: "15:00:00"}
- ap := &ActivationPeriod{ActivationTime: d}
- ap.AddInterval(i)
-
- ap1 := &ActivationPeriod{}
- b.StartTimer()
- ms := new(MyMarshaler)
- for i := 0; i < b.N; i++ {
- result, _ := ms.Marshal(ap)
- ms.Unmarshal(result, ap1)
- }
-}
-
-func BenchmarkActivationPeriodMarshallerJSONStoreRestore(b *testing.B) {
+func GetUB() *UserBalance {
+ uc := &UnitsCounter{
+ Direction: OUTBOUND,
+ BalanceId: SMS,
+ Units: 100,
+ MinuteBuckets: []*MinuteBucket{&MinuteBucket{Weight: 20, Price: 1, DestinationId: "NAT"}, &MinuteBucket{Weight: 10, Price: 10, PriceType: ABSOLUTE, DestinationId: "RET"}},
+ }
+ at := &ActionTrigger{
+ Id: "some_uuid",
+ BalanceId: CREDIT,
+ Direction: OUTBOUND,
+ ThresholdValue: 100.0,
+ DestinationId: "NAT",
+ Weight: 10.0,
+ ActionsId: "Commando",
+ }
+ var zeroTime time.Time
+ zeroTime = zeroTime.UTC() // for deep equal to find location
+ ub := &UserBalance{
+ Id: "rif",
+ Type: UB_TYPE_POSTPAID,
+ BalanceMap: map[string]BalanceChain{SMS + OUTBOUND: BalanceChain{&Balance{Value: 14, ExpirationDate: zeroTime}}, TRAFFIC + OUTBOUND: BalanceChain{&Balance{Value: 1024, ExpirationDate: zeroTime}}},
+ MinuteBuckets: []*MinuteBucket{&MinuteBucket{Weight: 20, Price: 1, DestinationId: "NAT"}, &MinuteBucket{Weight: 10, Price: 10, PriceType: ABSOLUTE, DestinationId: "RET"}},
+ UnitCounters: []*UnitsCounter{uc, uc},
+ ActionTriggers: ActionTriggerPriotityList{at, at, at},
+ }
+ return ub
+}
+
+func BenchmarkMarshallerJSONStoreRestore(b *testing.B) {
b.StopTimer()
d := time.Date(2012, time.February, 1, 14, 30, 1, 0, time.UTC)
i := &Interval{Months: []time.Month{time.February},
@@ -243,17 +245,21 @@ func BenchmarkActivationPeriodMarshallerJSONStoreRestore(b *testing.B) {
EndTime: "15:00:00"}
ap := &ActivationPeriod{ActivationTime: d}
ap.AddInterval(i)
+ ub := GetUB()
ap1 := ActivationPeriod{}
+ ub1 := &UserBalance{}
b.StartTimer()
ms := new(JSONMarshaler)
for i := 0; i < b.N; i++ {
result, _ := ms.Marshal(ap)
ms.Unmarshal(result, ap1)
+ result, _ = ms.Marshal(ub)
+ ms.Unmarshal(result, ub1)
}
}
-func BenchmarkActivationPeriodMarshallerBSONStoreRestore(b *testing.B) {
+func BenchmarkMarshallerBSONStoreRestore(b *testing.B) {
b.StopTimer()
d := time.Date(2012, time.February, 1, 14, 30, 1, 0, time.UTC)
i := &Interval{Months: []time.Month{time.February},
@@ -263,17 +269,21 @@ func BenchmarkActivationPeriodMarshallerBSONStoreRestore(b *testing.B) {
EndTime: "15:00:00"}
ap := &ActivationPeriod{ActivationTime: d}
ap.AddInterval(i)
+ ub := GetUB()
ap1 := ActivationPeriod{}
+ ub1 := &UserBalance{}
b.StartTimer()
ms := new(BSONMarshaler)
for i := 0; i < b.N; i++ {
result, _ := ms.Marshal(ap)
ms.Unmarshal(result, ap1)
+ result, _ = ms.Marshal(ub)
+ ms.Unmarshal(result, ub1)
}
}
-func BenchmarkActivationPeriodMarshallerJSONBufStoreRestore(b *testing.B) {
+func BenchmarkMarshallerJSONBufStoreRestore(b *testing.B) {
b.StopTimer()
d := time.Date(2012, time.February, 1, 14, 30, 1, 0, time.UTC)
i := &Interval{Months: []time.Month{time.February},
@@ -283,17 +293,21 @@ func BenchmarkActivationPeriodMarshallerJSONBufStoreRestore(b *testing.B) {
EndTime: "15:00:00"}
ap := &ActivationPeriod{ActivationTime: d}
ap.AddInterval(i)
+ ub := GetUB()
ap1 := ActivationPeriod{}
+ ub1 := &UserBalance{}
b.StartTimer()
ms := new(JSONBufMarshaler)
for i := 0; i < b.N; i++ {
result, _ := ms.Marshal(ap)
ms.Unmarshal(result, ap1)
+ result, _ = ms.Marshal(ub)
+ ms.Unmarshal(result, ub1)
}
}
-func BenchmarkActivationPeriodMarshallerGOBStoreRestore(b *testing.B) {
+func BenchmarkMarshallerGOBStoreRestore(b *testing.B) {
b.StopTimer()
d := time.Date(2012, time.February, 1, 14, 30, 1, 0, time.UTC)
i := &Interval{Months: []time.Month{time.February},
@@ -303,17 +317,21 @@ func BenchmarkActivationPeriodMarshallerGOBStoreRestore(b *testing.B) {
EndTime: "15:00:00"}
ap := &ActivationPeriod{ActivationTime: d}
ap.AddInterval(i)
+ ub := GetUB()
ap1 := ActivationPeriod{}
+ ub1 := &UserBalance{}
b.StartTimer()
ms := new(GOBMarshaler)
for i := 0; i < b.N; i++ {
result, _ := ms.Marshal(ap)
ms.Unmarshal(result, ap1)
+ result, _ = ms.Marshal(ub)
+ ms.Unmarshal(result, ub1)
}
}
-func BenchmarkActivationPeriodMarshallerMsgpackStoreRestore(b *testing.B) {
+func BenchmarkMarshallerMsgpackStoreRestore(b *testing.B) {
b.StopTimer()
d := time.Date(2012, time.February, 1, 14, 30, 1, 0, time.UTC)
i := &Interval{Months: []time.Month{time.February},
@@ -323,17 +341,22 @@ func BenchmarkActivationPeriodMarshallerMsgpackStoreRestore(b *testing.B) {
EndTime: "15:00:00"}
ap := &ActivationPeriod{ActivationTime: d}
ap.AddInterval(i)
+ ub := GetUB()
ap1 := ActivationPeriod{}
+ ub1 := &UserBalance{}
b.StartTimer()
ms := new(MsgpackMarshaler)
for i := 0; i < b.N; i++ {
result, _ := ms.Marshal(ap)
ms.Unmarshal(result, ap1)
+
+ result, _ = ms.Marshal(ub)
+ ms.Unmarshal(result, ub1)
}
}
-func BenchmarkActivationPeriodMarshallerBincStoreRestore(b *testing.B) {
+func BenchmarkMarshallerBincStoreRestore(b *testing.B) {
b.StopTimer()
d := time.Date(2012, time.February, 1, 14, 30, 1, 0, time.UTC)
i := &Interval{Months: []time.Month{time.February},
@@ -343,12 +366,16 @@ func BenchmarkActivationPeriodMarshallerBincStoreRestore(b *testing.B) {
EndTime: "15:00:00"}
ap := &ActivationPeriod{ActivationTime: d}
ap.AddInterval(i)
+ ub := GetUB()
ap1 := ActivationPeriod{}
+ ub1 := &UserBalance{}
b.StartTimer()
ms := NewBincMarshaler()
for i := 0; i < b.N; i++ {
result, _ := ms.Marshal(ap)
ms.Unmarshal(result, ap1)
+ result, _ = ms.Marshal(ub)
+ ms.Unmarshal(result, ub1)
}
}
diff --git a/engine/calldesc_test.go b/engine/calldesc_test.go
index 877e354cd..cffa333d5 100644
--- a/engine/calldesc_test.go
+++ b/engine/calldesc_test.go
@@ -25,6 +25,10 @@ import (
"time"
)
+var (
+ marsh = new(MsgpackMarshaler)
+)
+
func init() {
populateDB()
historyScribe, _ = history.NewMockScribe()
diff --git a/engine/simple_serializer.go b/engine/simple_serializer.go
deleted file mode 100644
index ff11ec3a6..000000000
--- a/engine/simple_serializer.go
+++ /dev/null
@@ -1,669 +0,0 @@
-/*
-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 engine
-
-import (
- "fmt"
- "strconv"
- "strings"
- "time"
-)
-
-type Serializer interface {
- Store() (string, error)
- Restore(string) error
-}
-
-func notEnoughElements(element, line string) error {
- return fmt.Errorf("Too few elements to restore (%v): %v", element, line)
-}
-
-func (ap *ActivationPeriod) Store() (result string, err error) {
- result += ap.ActivationTime.Format(time.RFC3339) + "|"
- for _, i := range ap.Intervals {
- str, err := i.Store()
- if err != nil {
- return "", err
- }
- result += str + "|"
- }
- result = strings.TrimRight(result, "|")
- return
-}
-
-func (ap *ActivationPeriod) Restore(input string) error {
- elements := strings.Split(input, "|")
- var err error
- ap.ActivationTime, err = time.Parse(time.RFC3339, elements[0])
- if err != nil {
- return err
- }
- els := elements[1:]
- if len(els) > 1 {
- els = elements[1 : len(elements)-1]
- }
- for _, is := range els {
- i := &Interval{}
- if err := i.Restore(is); err != nil {
- return err
- }
- ap.Intervals = append(ap.Intervals, i)
- }
- return nil
-}
-
-func (rp *RatingProfile) Store() (result string, err error) {
- result += rp.FallbackKey + ">"
- for k, aps := range rp.DestinationMap {
- result += k + "="
- for _, ap := range aps {
- aps, err := ap.Store()
- if err != nil {
- return result, err
- }
- result += aps + "<"
- }
- result = strings.TrimRight(result, "<")
- result += ">"
- }
- result = strings.TrimRight(result, ">")
- return
-}
-
-func (rp *RatingProfile) Restore(input string) error {
- if rp.DestinationMap == nil {
- rp.DestinationMap = make(map[string][]*ActivationPeriod, 1)
- }
- elements := strings.Split(input, ">")
- rp.FallbackKey = elements[0]
- for _, kv := range elements[1:] {
- pair := strings.SplitN(kv, "=", 2)
- apList := strings.Split(pair[1], "<")
- var newAps []*ActivationPeriod
- for _, aps := range apList {
- ap := new(ActivationPeriod)
- err := ap.Restore(aps)
- if err != nil {
- return err
- }
- newAps = append(newAps, ap)
- }
- rp.DestinationMap[pair[0]] = newAps
- }
- return nil
-}
-
-func (a *Action) Store() (result string, err error) {
- result += a.Id + "|"
- result += a.ActionType + "|"
- result += a.BalanceId + "|"
- result += a.Direction + "|"
- result += a.ExpirationString + "|"
- result += a.ExpirationDate.Format(time.RFC3339) + "|"
- result += strconv.FormatFloat(a.Units, 'f', -1, 64) + "|"
- result += strconv.FormatFloat(a.Weight, 'f', -1, 64)
- if a.MinuteBucket != nil {
- result += "|"
- str, err := a.MinuteBucket.Store()
- if err != nil {
- return "", err
- }
- result += str
- }
- return
-}
-
-func (a *Action) Restore(input string) (err error) {
- elements := strings.Split(input, "|")
- if len(elements) < 8 {
- return notEnoughElements("Action", input)
- }
- a.Id = elements[0]
- a.ActionType = elements[1]
- a.BalanceId = elements[2]
- a.Direction = elements[3]
- a.ExpirationString = elements[4]
- if a.ExpirationDate, err = time.Parse(time.RFC3339, elements[5]); err != nil {
- return err
- }
- a.Units, _ = strconv.ParseFloat(elements[6], 64)
- a.Weight, _ = strconv.ParseFloat(elements[7], 64)
- if len(elements) == 9 {
- a.MinuteBucket = &MinuteBucket{}
- if err := a.MinuteBucket.Restore(elements[8]); err != nil {
- return err
- }
- }
- return nil
-}
-
-func (as Actions) Store() (result string, err error) {
- for _, a := range as {
- str, err := a.Store()
- if err != nil {
- return "", err
- }
- result += str + "~"
- }
- result = strings.TrimRight(result, "~")
- return
-}
-
-func (as *Actions) Restore(input string) error {
- for _, a_string := range strings.Split(input, "~") {
- if len(a_string) > 0 {
- a := &Action{}
- if err := a.Restore(a_string); err != nil {
- return err
- }
- *as = append(*as, a)
- }
- }
- return nil
-}
-
-func (at *ActionTiming) Store() (result string, err error) {
- result += at.Id + "|"
- result += at.Tag + "|"
- for _, ubi := range at.UserBalanceIds {
- result += ubi + ","
- }
- result = strings.TrimRight(result, ",") + "|"
- if at.Timing != nil {
- str, err := at.Timing.Store()
- if err != nil {
- return "", err
- }
- result += str + "|"
- } else {
- result += " |"
- }
- result += strconv.FormatFloat(at.Weight, 'f', -1, 64) + "|"
- result += at.ActionsId
- return
-}
-
-func (at *ActionTiming) Restore(input string) error {
- elements := strings.Split(input, "|")
- at.Id = elements[0]
- at.Tag = elements[1]
- for _, ubi := range strings.Split(elements[2], ",") {
- if strings.TrimSpace(ubi) != "" {
- at.UserBalanceIds = append(at.UserBalanceIds, ubi)
- }
- }
-
- at.Timing = &Interval{}
- if err := at.Timing.Restore(elements[3]); err != nil {
- return err
- }
- at.Weight, _ = strconv.ParseFloat(elements[4], 64)
- at.ActionsId = elements[5]
- return nil
-}
-
-func (ats ActionTimings) Store() (result string, err error) {
- for _, at := range ats {
- str, err := at.Store()
- if err != nil {
- return "", err
- }
- result += str + "~"
- }
- result = strings.TrimRight(result, "~")
- return
-}
-
-func (ats *ActionTimings) Restore(input string) error {
- for _, at_string := range strings.Split(input, "~") {
- if len(at_string) > 0 {
- at := &ActionTiming{}
- if err := at.Restore(at_string); err != nil {
- return err
- }
- *ats = append(*ats, at)
- }
- }
- return nil
-}
-
-func (at *ActionTrigger) Store() (result string, err error) {
- result += at.Id + ";"
- result += at.BalanceId + ";"
- result += at.Direction + ";"
- result += at.DestinationId + ";"
- result += at.ActionsId + ";"
- result += strconv.FormatFloat(at.ThresholdValue, 'f', -1, 64) + ";"
- result += at.ThresholdType + ";"
- result += strconv.FormatFloat(at.Weight, 'f', -1, 64) + ";"
- result += strconv.FormatBool(at.Executed)
- return
-}
-
-func (at *ActionTrigger) Restore(input string) error {
- elements := strings.Split(input, ";")
- if len(elements) != 9 {
- return notEnoughElements("ActionTrigger", input)
- }
- at.Id = elements[0]
- at.BalanceId = elements[1]
- at.Direction = elements[2]
- at.DestinationId = elements[3]
- at.ActionsId = elements[4]
- at.ThresholdValue, _ = strconv.ParseFloat(elements[5], 64)
- at.ThresholdType = elements[6]
- at.Weight, _ = strconv.ParseFloat(elements[7], 64)
- at.Executed, _ = strconv.ParseBool(elements[8])
- return nil
-}
-
-func (b *Balance) Store() (result string, err error) {
- result += b.Id + ")"
- result += strconv.FormatFloat(b.Value, 'f', -1, 64) + ")"
- result += strconv.FormatFloat(b.Weight, 'f', -1, 64) + ")"
- result += b.ExpirationDate.Format(time.RFC3339)
- return result, nil
-}
-
-func (b *Balance) Restore(input string) (err error) {
- elements := strings.Split(input, ")")
- b.Id = elements[0]
- b.Value, _ = strconv.ParseFloat(elements[1], 64)
- b.Weight, _ = strconv.ParseFloat(elements[2], 64)
- b.ExpirationDate, err = time.Parse(time.RFC3339, elements[3])
- return nil
-}
-
-func (bc BalanceChain) Store() (result string, err error) {
- for _, b := range bc {
- str, err := b.Store()
- if err != nil {
- return "", err
- }
- result += str + "^"
- }
- result = strings.TrimRight(result, "^")
- return result, nil
-}
-
-func (bc *BalanceChain) Restore(input string) error {
- elements := strings.Split(input, "^")
- for _, element := range elements {
- b := &Balance{}
- err := b.Restore(element)
- if err != nil {
- return err
- }
- *bc = append(*bc, b)
- }
- return nil
-}
-
-func (ub *UserBalance) Store() (result string, err error) {
- result += ub.Id + "|"
- result += ub.Type + "|"
- for k, v := range ub.BalanceMap {
- bc, err := v.Store()
- if err != nil {
- return "", err
- }
- result += k + "=" + bc + "#"
- }
- result = strings.TrimRight(result, "#") + "|"
- for _, mb := range ub.MinuteBuckets {
- str, err := mb.Store()
- if err != nil {
- return "", err
- }
- result += str + "#"
- }
- result = strings.TrimRight(result, "#") + "|"
- for _, uc := range ub.UnitCounters {
- str, err := uc.Store()
- if err != nil {
- return "", err
- }
- result += str + "#"
- }
- result = strings.TrimRight(result, "#") + "|"
- for _, at := range ub.ActionTriggers {
- res, err := at.Store()
- if err != nil {
- return "", err
- }
- result += res + "#"
- }
- result = strings.TrimRight(result, "#")
- return
-}
-
-func (ub *UserBalance) Restore(input string) error {
- elements := strings.Split(input, "|")
- if len(elements) < 2 {
- return notEnoughElements("UserBalance", input)
- }
- ub.Id = elements[0]
- ub.Type = elements[1]
- if ub.BalanceMap == nil {
- ub.BalanceMap = make(map[string]BalanceChain, 0)
- }
- for _, maps := range strings.Split(elements[2], "#") {
- kv := strings.Split(maps, "=")
- if len(kv) != 2 {
- continue
- }
- bc := BalanceChain{}
- if err := (&bc).Restore(kv[1]); err != nil {
- return err
- }
- ub.BalanceMap[kv[0]] = bc
- }
- for _, mbs := range strings.Split(elements[3], "#") {
- if mbs == "" {
- continue
- }
- mb := &MinuteBucket{}
- if err := mb.Restore(mbs); err != nil {
- return err
- }
- ub.MinuteBuckets = append(ub.MinuteBuckets, mb)
- }
- for _, ucs := range strings.Split(elements[4], "#") {
- if ucs == "" {
- continue
- }
- uc := &UnitsCounter{}
- if err := uc.Restore(ucs); err != nil {
- return err
- }
- ub.UnitCounters = append(ub.UnitCounters, uc)
- }
- for _, ats := range strings.Split(elements[5], "#") {
- if ats == "" {
- continue
- }
- at := &ActionTrigger{}
- if err := at.Restore(ats); err != nil {
- return err
- }
- ub.ActionTriggers = append(ub.ActionTriggers, at)
- }
- return nil
-}
-
-/*
-Serializes the unit counter for the storage. Used for key-value storages.
-*/
-func (uc *UnitsCounter) Store() (result string, err error) {
- result += uc.Direction + "/"
- result += uc.BalanceId + "/"
- result += strconv.FormatFloat(uc.Units, 'f', -1, 64) + "/"
- for _, mb := range uc.MinuteBuckets {
- str, err := mb.Store()
- if err != nil {
- return "", err
- }
- result += str + ","
- }
- result = strings.TrimRight(result, ",")
- return
-}
-
-/*
-De-serializes the unit counter for the storage. Used for key-value storages.
-*/
-func (uc *UnitsCounter) Restore(input string) error {
- elements := strings.Split(input, "/")
- if len(elements) != 4 {
- return notEnoughElements("UnitsCounter", input)
- }
- uc.Direction = elements[0]
- uc.BalanceId = elements[1]
- uc.Units, _ = strconv.ParseFloat(elements[2], 64)
- for _, mbs := range strings.Split(elements[3], ",") {
- mb := &MinuteBucket{}
- if err := mb.Restore(mbs); err != nil {
- return err
- }
- uc.MinuteBuckets = append(uc.MinuteBuckets, mb)
- }
- return nil
-}
-
-func (d *Destination) Store() (result string, err error) {
- for _, p := range d.Prefixes {
- result += p + ","
- }
- result = strings.TrimRight(result, ",")
- return
-}
-
-func (d *Destination) Restore(input string) error {
- d.Prefixes = strings.Split(input, ",")
- return nil
-}
-
-func (pg PriceGroups) Store() (result string, err error) {
- for _, p := range pg {
- result += p.GroupIntervalStart.String() +
- ":" + strconv.FormatFloat(p.Value, 'f', -1, 64) +
- ":" + p.RateIncrement.String() +
- ":" + p.RateUnit.String() +
- ","
- }
- result = strings.TrimRight(result, ",")
- return
-}
-
-func (pg *PriceGroups) Restore(input string) error {
- elements := strings.Split(input, ",")
- for _, element := range elements {
- priceElements := strings.Split(element, ":")
- if len(priceElements) != 4 {
- continue
- }
- ss, err := time.ParseDuration(priceElements[0])
- if err != nil {
- return err
- }
- v, err := strconv.ParseFloat(priceElements[1], 64)
- if err != nil {
- return err
- }
- ri, err := time.ParseDuration(priceElements[2])
- if err != nil {
- return err
- }
- ru, err := time.ParseDuration(priceElements[3])
- if err != nil {
- return err
- }
- price := &Price{
- GroupIntervalStart: ss,
- Value: v,
- RateIncrement: ri,
- RateUnit: ru,
- }
- *pg = append(*pg, price)
- }
- return nil
-}
-
-func (i *Interval) Store() (result string, err error) {
- str, err := i.Years.Store()
- if err != nil {
- return "", err
- }
- result += str + ";"
- str, err = i.Months.Store()
- if err != nil {
- return "", err
- }
- result += str + ";"
- str, err = i.MonthDays.Store()
- if err != nil {
- return "", err
- }
- result += str + ";"
- str, err = i.WeekDays.Store()
- if err != nil {
- return "", err
- }
- result += str + ";"
- result += i.StartTime + ";"
- result += i.EndTime + ";"
- result += strconv.FormatFloat(i.Weight, 'f', -1, 64) + ";"
- result += strconv.FormatFloat(i.ConnectFee, 'f', -1, 64) + ";"
- ps, err := i.Prices.Store()
- if err != nil {
- return "", err
- }
- result += ps + ";"
- result += i.RoundingMethod + ";"
- result += strconv.Itoa(i.RoundingDecimals)
- return
-}
-
-func (i *Interval) Restore(input string) error {
- is := strings.Split(input, ";")
- if len(is) != 11 {
- return notEnoughElements("Interval", input)
- }
- if err := i.Years.Restore(is[0]); err != nil {
- return err
- }
- if err := i.Months.Restore(is[1]); err != nil {
- return err
- }
- if err := i.MonthDays.Restore(is[2]); err != nil {
- return err
- }
- if err := i.WeekDays.Restore(is[3]); err != nil {
- return err
- }
- i.StartTime = is[4]
- i.EndTime = is[5]
- i.Weight, _ = strconv.ParseFloat(is[6], 64)
- i.ConnectFee, _ = strconv.ParseFloat(is[7], 64)
- err := (&i.Prices).Restore(is[8])
- if err != nil {
- return err
- }
- i.RoundingMethod = is[9]
- i.RoundingDecimals, _ = strconv.Atoi(is[10])
- return nil
-}
-
-func (mb *MinuteBucket) Store() (result string, err error) {
- result += strconv.FormatFloat(mb.Seconds, 'f', -1, 64) + ";"
- result += strconv.FormatFloat(mb.Weight, 'f', -1, 64) + ";"
- result += strconv.FormatFloat(mb.Price, 'f', -1, 64) + ";"
- result += mb.PriceType + ";"
- result += mb.DestinationId
- return
-}
-
-func (mb *MinuteBucket) Restore(input string) error {
- input = strings.TrimSpace(input)
- if len(input) == 0 {
- return nil
- }
- elements := strings.Split(input, ";")
- if len(elements) != 5 {
- return notEnoughElements("MinuteBucket", input)
- }
- mb.Seconds, _ = strconv.ParseFloat(elements[0], 64)
- mb.Weight, _ = strconv.ParseFloat(elements[1], 64)
- mb.Price, _ = strconv.ParseFloat(elements[2], 64)
- mb.PriceType = elements[3]
- mb.DestinationId = elements[4]
- return nil
-}
-
-func (wds WeekDays) Store() (result string, err error) {
- for _, wd := range wds {
- result += strconv.Itoa(int(wd)) + ","
- }
- result = strings.TrimRight(result, ",")
- return
-}
-
-func (wds *WeekDays) Restore(input string) error {
- for _, wd := range strings.Split(input, ",") {
- if wd != "" {
- mm, _ := strconv.Atoi(wd)
- *wds = append(*wds, time.Weekday(mm))
- }
- }
- return nil
-}
-
-func (mds MonthDays) Store() (result string, err error) {
- for _, md := range mds {
- result += strconv.Itoa(int(md)) + ","
- }
- result = strings.TrimRight(result, ",")
- return
-}
-
-func (mds *MonthDays) Restore(input string) error {
- for _, md := range strings.Split(input, ",") {
- if md != "" {
- mm, _ := strconv.Atoi(md)
- *mds = append(*mds, mm)
- }
- }
- return nil
-}
-
-func (ms Months) Store() (result string, err error) {
- for _, m := range ms {
- result += strconv.Itoa(int(m)) + ","
- }
- result = strings.TrimRight(result, ",")
- return
-}
-
-func (ms *Months) Restore(input string) error {
- for _, m := range strings.Split(input, ",") {
- if m != "" {
- mm, _ := strconv.Atoi(m)
- *ms = append(*ms, time.Month(mm))
- }
- }
- return nil
-}
-
-func (yss Years) Store() (result string, err error) {
- for _, ys := range yss {
- result += strconv.Itoa(int(ys)) + ","
- }
- result = strings.TrimRight(result, ",")
- return
-}
-
-func (yss *Years) Restore(input string) error {
- for _, ys := range strings.Split(input, ",") {
- if ys != "" {
- mm, _ := strconv.Atoi(ys)
- *yss = append(*yss, mm)
- }
- }
- return nil
-}
diff --git a/engine/simple_serializer_test.go b/engine/simple_serializer_test.go
deleted file mode 100644
index d8179dfbf..000000000
--- a/engine/simple_serializer_test.go
+++ /dev/null
@@ -1,201 +0,0 @@
-/*
-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 engine
-
-import (
- "reflect"
- "testing"
- "time"
-)
-
-func TestSimpleMarshallerApStoreRestore(t *testing.T) {
- d := time.Date(2012, time.February, 1, 14, 30, 1, 0, time.UTC)
- i := &Interval{
- Months: Months{time.February},
- MonthDays: MonthDays{1},
- WeekDays: []time.Weekday{time.Wednesday, time.Thursday},
- StartTime: "14:30:00",
- EndTime: "15:00:00"}
- ap := &ActivationPeriod{ActivationTime: d}
- ap.AddInterval(i)
- result, err := ap.Store()
- ap1 := &ActivationPeriod{}
- err = ap1.Restore(result)
- if err != nil || !reflect.DeepEqual(ap, ap1) {
- t.Errorf("Expected %v was %v: %v", ap, ap1, err)
- }
-}
-
-func TestSimpleMarshallerApRestoreFromString(t *testing.T) {
- s := "2012-02-01T14:30:01Z|;1,2,3,4,5,6,7,8,9,10,11,12;1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31;1,2,3,4,5,6,0;00:00:00;;10;0;0:0.2:1s:60s;1;\n"
- ap := &ActivationPeriod{}
- err := ap.Restore(s)
- if err != nil || len(ap.Intervals) != 1 {
- t.Error("Error restoring activation period from string", ap)
- }
-}
-
-func TestRpStoreRestore(t *testing.T) {
- d := time.Date(2012, time.February, 1, 14, 30, 1, 0, time.UTC)
- i := &Interval{
- Months: Months{time.February},
- MonthDays: MonthDays{1},
- WeekDays: []time.Weekday{time.Wednesday, time.Thursday},
- StartTime: "14:30:00",
- EndTime: "15:00:00"}
- ap := &ActivationPeriod{ActivationTime: d}
- ap.AddInterval(i)
- rp := &RatingProfile{FallbackKey: "test"}
- rp.AddActivationPeriodIfNotPresent("0723", ap)
- result, err := rp.Store()
- rp1 := &RatingProfile{}
- err = rp1.Restore(result)
- if err != nil || !reflect.DeepEqual(rp, rp1) {
- t.Errorf("Expected %v was %v", rp, rp1)
- }
-}
-
-func TestActionTimingStoreRestore(t *testing.T) {
- i := &Interval{
- Months: Months{time.January, time.February, time.March, time.April, time.May, time.June, time.July, time.August, time.September, time.October, time.November, time.December},
- MonthDays: MonthDays{1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31},
- WeekDays: WeekDays{time.Monday, time.Tuesday, time.Wednesday, time.Thursday, time.Friday},
- StartTime: "18:00:00",
- EndTime: "00:00:00",
- Weight: 10.0,
- ConnectFee: 0.0,
- Prices: PriceGroups{&Price{0, 1.0, 1 * time.Second, 60 * time.Second}},
- }
- at := &ActionTiming{
- Id: "some uuid",
- Tag: "test",
- UserBalanceIds: []string{"one", "two", "three"},
- Timing: i,
- Weight: 10.0,
- ActionsId: "Commando",
- }
- r, err := at.Store()
- o := &ActionTiming{}
- err = o.Restore(r)
- if err != nil || !reflect.DeepEqual(o, at) {
- t.Errorf("Expected %v was %v", at, o)
- }
-}
-
-func TestActionTriggerStoreRestore(t *testing.T) {
- at := &ActionTrigger{
- Id: "some_uuid",
- BalanceId: CREDIT,
- Direction: OUTBOUND,
- ThresholdValue: 100.0,
- ThresholdType: "*max_counter",
- DestinationId: "NAT",
- Weight: 10.0,
- ActionsId: "Commando",
- }
- r, err := at.Store()
- if err != nil || r != "some_uuid;*monetary;*out;NAT;Commando;100;*max_counter;10;false" {
- t.Errorf("Error serializing action trigger: %v", string(r))
- }
- o := &ActionTrigger{}
- err = o.Restore(r)
- if err != nil || !reflect.DeepEqual(o, at) {
- t.Errorf("Expected %v was %v", at, o)
- }
-}
-
-func TestIntervalStoreRestore(t *testing.T) {
- i := &Interval{
- Months: Months{time.January, time.February, time.March, time.April, time.May, time.June, time.July, time.August, time.September, time.October, time.November, time.December},
- MonthDays: MonthDays{1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31},
- WeekDays: WeekDays{time.Monday, time.Tuesday, time.Wednesday, time.Thursday, time.Friday},
- StartTime: "18:00:00",
- EndTime: "00:00:00",
- Weight: 10.0,
- ConnectFee: 0.0,
- Prices: PriceGroups{&Price{0, 1777.0, 1 * time.Second, 60 * time.Second}},
- }
- r, err := i.Store()
- o := &Interval{}
- err = o.Restore(r)
- if err != nil || !reflect.DeepEqual(o, i) {
- t.Errorf("Expected %v was %v", i, o)
- }
-}
-
-func TestIntervalRestoreFromString(t *testing.T) {
- s := ";1,2,3,4,5,6,7,8,9,10,11,12;1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31;1,2,3,4,5,6,0;00:00:00;;10;0;0:0.2:1s:60s;0;"
- i := Interval{}
- err := i.Restore(s)
- if err != nil || !i.Prices.Equal(PriceGroups{&Price{0, 0.2, 1 * time.Second, 60 * time.Second}}) {
- t.Errorf("Error restoring inteval period from string %+v", i)
- }
-}
-
-func TestMonthYearStoreRestore(t *testing.T) {
- y := Years{2010, 2011, 2012}
- r, err := y.Store()
- if err != nil || r != "2010,2011,2012" {
- t.Errorf("Error serializing years: %v", string(r))
- }
- o := Years{}
- err = o.Restore(r)
- if err != nil || !reflect.DeepEqual(o, y) {
- t.Errorf("Expected %v was %v", y, o)
- }
-}
-
-func TestMonthStoreRestore(t *testing.T) {
- m := Months{5, 6, 7, 8}
- r, err := m.Store()
- if err != nil || r != "5,6,7,8" {
- t.Errorf("Error serializing months: %v", string(r))
- }
- o := Months{}
- err = o.Restore(r)
- if err != nil || !reflect.DeepEqual(o, m) {
- t.Errorf("Expected %v was %v", m, o)
- }
-}
-
-func TestMonthDayStoreRestore(t *testing.T) {
- md := MonthDays{24, 25, 26}
- r, err := md.Store()
- if err != nil || r != "24,25,26" {
- t.Errorf("Error serializing month days: %v", string(r))
- }
- o := MonthDays{}
- err = o.Restore(r)
- if err != nil || !reflect.DeepEqual(o, md) {
- t.Errorf("Expected %v was %v", md, o)
- }
-}
-
-func TestWeekDayStoreRestore(t *testing.T) {
- wd := WeekDays{time.Saturday, time.Sunday}
- r, err := wd.Store()
- if err != nil || r != "6,0" {
- t.Errorf("Error serializing week days: %v", string(r))
- }
- o := WeekDays{}
- err = o.Restore(r)
- if err != nil || !reflect.DeepEqual(o, wd) {
- t.Errorf("Expected %v was %v", wd, o)
- }
-}
diff --git a/engine/storage_interface.go b/engine/storage_interface.go
index 865aa5be1..cdcdd24da 100644
--- a/engine/storage_interface.go
+++ b/engine/storage_interface.go
@@ -210,16 +210,3 @@ func (gm *GOBMarshaler) Marshal(v interface{}) (data []byte, err error) {
func (gm *GOBMarshaler) Unmarshal(data []byte, v interface{}) error {
return gob.NewDecoder(bytes.NewBuffer(data)).Decode(v)
}
-
-type MyMarshaler struct{}
-
-func (mm *MyMarshaler) Marshal(v interface{}) ([]byte, error) {
- ser := v.(Serializer)
- res, err := ser.Store()
- return []byte(res), err
-}
-
-func (mm *MyMarshaler) Unmarshal(data []byte, v interface{}) error {
- ser := v.(Serializer)
- return ser.Restore(string(data))
-}
diff --git a/engine/storage_map.go b/engine/storage_map.go
index 1f055862f..40192bbc5 100644
--- a/engine/storage_map.go
+++ b/engine/storage_map.go
@@ -33,7 +33,7 @@ type MapStorage struct {
}
func NewMapStorage() (DataStorage, error) {
- return &MapStorage{dict: make(map[string][]byte), ms: new(MyMarshaler)}, nil
+ return &MapStorage{dict: make(map[string][]byte), ms: new(MsgpackMarshaler)}, nil
}
func (ms *MapStorage) Close() {}
diff --git a/engine/storage_redis.go b/engine/storage_redis.go
index db131e70d..9f1d107d7 100644
--- a/engine/storage_redis.go
+++ b/engine/storage_redis.go
@@ -57,7 +57,7 @@ func NewRedisStorage(address string, db int, pass string) (DataStorage, error) {
return nil, err
}
}
- return &RedisStorage{db: ndb, dbNb: db, ms: new(MyMarshaler)}, nil
+ return &RedisStorage{db: ndb, dbNb: db, ms: new(MsgpackMarshaler)}, nil
}
func (rs *RedisStorage) Close() {
diff --git a/engine/units_counter_test.go b/engine/units_counter_test.go
index b118d0bbb..0c942d483 100644
--- a/engine/units_counter_test.go
+++ b/engine/units_counter_test.go
@@ -19,28 +19,9 @@ along with this program. If not, see
package engine
import (
- "reflect"
"testing"
)
-func TestUnitsCounterStoreRestore(t *testing.T) {
- uc := &UnitsCounter{
- Direction: OUTBOUND,
- BalanceId: SMS,
- Units: 100,
- MinuteBuckets: []*MinuteBucket{&MinuteBucket{Weight: 20, Price: 1, DestinationId: "NAT"}, &MinuteBucket{Weight: 10, Price: 10, PriceType: ABSOLUTE, DestinationId: "RET"}},
- }
- r, err := uc.Store()
- if err != nil || r != "*out/*sms/100/0;20;1;;NAT,0;10;10;*absolute;RET" {
- t.Errorf("Error serializing units counter: %v", string(r))
- }
- o := &UnitsCounter{}
- err = o.Restore(r)
- if err != nil || !reflect.DeepEqual(o, uc) {
- t.Errorf("Expected %v was %v", uc, o)
- }
-}
-
func TestUnitsCounterAddMinuteBucket(t *testing.T) {
uc := &UnitsCounter{
Direction: OUTBOUND,
diff --git a/engine/userbalance_test.go b/engine/userbalance_test.go
index 8047df688..80763cee8 100644
--- a/engine/userbalance_test.go
+++ b/engine/userbalance_test.go
@@ -20,7 +20,6 @@ package engine
import (
//"log"
- "reflect"
"testing"
"time"
)
@@ -49,12 +48,13 @@ func populateTestActionsForTriggers() {
func TestBalanceStoreRestore(t *testing.T) {
b := &Balance{Value: 14, Weight: 1, Id: "test", ExpirationDate: time.Date(2013, time.July, 15, 17, 48, 0, 0, time.UTC)}
- output, err := b.Store()
+ marsh := new(MsgpackMarshaler)
+ output, err := marsh.Marshal(b)
if err != nil {
t.Error("Error storing balance: ", err)
}
b1 := &Balance{}
- err = b1.Restore(output)
+ err = marsh.Unmarshal(output, b1)
if err != nil {
t.Error("Error restoring balance: ", err)
}
@@ -65,12 +65,13 @@ func TestBalanceStoreRestore(t *testing.T) {
func TestBalanceStoreRestoreZero(t *testing.T) {
b := &Balance{}
- output, err := b.Store()
+
+ output, err := marsh.Marshal(b)
if err != nil {
t.Error("Error storing balance: ", err)
}
b1 := &Balance{}
- err = b1.Restore(output)
+ err = marsh.Unmarshal(output, b1)
if err != nil {
t.Error("Error restoring balance: ", err)
}
@@ -81,12 +82,12 @@ func TestBalanceStoreRestoreZero(t *testing.T) {
func TestBalanceChainStoreRestore(t *testing.T) {
bc := BalanceChain{&Balance{Value: 14, ExpirationDate: time.Date(2013, time.July, 15, 17, 48, 0, 0, time.UTC)}, &Balance{Value: 1024}}
- output, err := bc.Store()
+ output, err := marsh.Marshal(bc)
if err != nil {
t.Error("Error storing balance chain: ", err)
}
bc1 := BalanceChain{}
- err = (&bc1).Restore(output)
+ err = marsh.Unmarshal(output, &bc1)
if err != nil {
t.Error("Error restoring balance chain: ", err)
}
@@ -95,42 +96,6 @@ func TestBalanceChainStoreRestore(t *testing.T) {
}
}
-func TestUserBalanceStoreRestore(t *testing.T) {
- uc := &UnitsCounter{
- Direction: OUTBOUND,
- BalanceId: SMS,
- Units: 100,
- MinuteBuckets: []*MinuteBucket{&MinuteBucket{Weight: 20, Price: 1, DestinationId: "NAT"}, &MinuteBucket{Weight: 10, Price: 10, PriceType: ABSOLUTE, DestinationId: "RET"}},
- }
- at := &ActionTrigger{
- Id: "some_uuid",
- BalanceId: CREDIT,
- Direction: OUTBOUND,
- ThresholdValue: 100.0,
- DestinationId: "NAT",
- Weight: 10.0,
- ActionsId: "Commando",
- }
- var zeroTime time.Time
- zeroTime = zeroTime.UTC() // for deep equal to find location
- ub := &UserBalance{
- Id: "rif",
- Type: UB_TYPE_POSTPAID,
- BalanceMap: map[string]BalanceChain{SMS + OUTBOUND: BalanceChain{&Balance{Value: 14, ExpirationDate: zeroTime}}, TRAFFIC + OUTBOUND: BalanceChain{&Balance{Value: 1024, ExpirationDate: zeroTime}}},
- MinuteBuckets: []*MinuteBucket{&MinuteBucket{Weight: 20, Price: 1, DestinationId: "NAT"}, &MinuteBucket{Weight: 10, Price: 10, PriceType: ABSOLUTE, DestinationId: "RET"}},
- UnitCounters: []*UnitsCounter{uc, uc},
- ActionTriggers: ActionTriggerPriotityList{at, at, at},
- }
-
- var err error
- r, err := ub.Store()
- o := &UserBalance{}
- err = o.Restore(r)
- if err != nil || !reflect.DeepEqual(ub, o) {
- t.Errorf("Expected [%v] was [%v] , err: %v", ub, o, err)
- }
-}
-
func TestUserBalanceStorageStoreRestore(t *testing.T) {
b1 := &MinuteBucket{Seconds: 10, Weight: 10, Price: 0.01, DestinationId: "NAT"}
b2 := &MinuteBucket{Seconds: 100, Weight: 20, Price: 0.0, DestinationId: "RET"}
diff --git a/sessionmanager/fssessionmanager.go b/sessionmanager/fssessionmanager.go
index 918c98624..1a439e9a2 100644
--- a/sessionmanager/fssessionmanager.go
+++ b/sessionmanager/fssessionmanager.go
@@ -103,11 +103,11 @@ func (sm *FSSessionManager) DisconnectSession(s *Session, notify string) {
engine.Logger.Debug(fmt.Sprintf("Session: %+v", s.uuid))
err := fsock.FS.SendApiCmd(fmt.Sprintf("uuid_setvar %s cgr_notify %s\n\n", s.uuid, notify))
if err != nil {
- engine.Logger.Err("could not send disconect api notification to freeswitch")
+ engine.Logger.Err(fmt.Sprintf("could not send disconect api notification to freeswitch: %v", err))
}
err = fsock.FS.SendMsgCmd(s.uuid, map[string]string{"call-command": "hangup", "hangup-cause": "MANAGER_REQUEST"}) // without + sign
if err != nil {
- engine.Logger.Err("could not send disconect msg to freeswitch")
+ engine.Logger.Err(fmt.Sprintf("could not send disconect msg to freeswitch: %v", err))
}
return
}