diff --git a/carbonPeriod.go b/carbonPeriod.go new file mode 100644 index 0000000..626d5dd --- /dev/null +++ b/carbonPeriod.go @@ -0,0 +1,35 @@ +package carbon + +import "errors" + +var ( + ErrEndMustBeAfterStart = errors.New("end date must be after start date") + ErrDayAtLeast1 = errors.New("days must be at least 1") +) + +// Period returns an array of Carbon dates by accepting start date, number of +// days, and end date. Useful for generating a recurring dates. +func Period(start *Carbon, days int, end *Carbon) ([]*Carbon, error) { + if end.Before(start.Time) { + return nil, ErrEndMustBeAfterStart + } + if days <= 0 { + return nil, ErrDayAtLeast1 + } + + want := make([]*Carbon, 0) + + want = append(want, start) + + next := start + for { + try := next.AddDays(days) + + if try.Gte(end) { + return want, nil + } + + want = append(want, try) + next = try + } +} diff --git a/carbonPeriod_test.go b/carbonPeriod_test.go new file mode 100644 index 0000000..b3d56f0 --- /dev/null +++ b/carbonPeriod_test.go @@ -0,0 +1,92 @@ +package carbon + +import ( + "testing" + "time" + + "github.com/stretchr/testify/assert" +) + +func TestNewPeriod(t *testing.T) { + start1, _ := Create(2022, time.April, 1, 23, 0, 0, 0, "UTC") + end1, _ := Create(2022, time.April, 30, 23, 0, 0, 0, "UTC") + + days := 7 + + wantTime := make([]*Carbon, 0) + want1a, _ := Create(2022, time.April, 1, 23, 0, 0, 0, "UTC") + want1b, _ := Create(2022, time.April, 8, 23, 0, 0, 0, "UTC") + want1c, _ := Create(2022, time.April, 15, 23, 0, 0, 0, "UTC") + want1d, _ := Create(2022, time.April, 22, 23, 0, 0, 0, "UTC") + want1e, _ := Create(2022, time.April, 29, 23, 0, 0, 0, "UTC") + wantTime = append(wantTime, want1a) + wantTime = append(wantTime, want1b) + wantTime = append(wantTime, want1c) + wantTime = append(wantTime, want1d) + wantTime = append(wantTime, want1e) + + type args struct { + start *Carbon + days int + end *Carbon + } + + type want struct { + wantTime []*Carbon + error + } + + tests := []struct { + name string + args args + //want []*Carbon + want + }{ + { + name: "normal", + args: args{ + start: start1, + days: days, + end: end1, + }, + want: want{ + wantTime: wantTime, + error: nil, + }, + }, + { + name: "date to is before date start", + args: args{ + start: end1, + days: 1, + end: start1, + }, + want: want{ + wantTime: nil, + error: ErrEndMustBeAfterStart, + }, + }, + { + name: "day is zero", + args: args{ + start: start1, + days: 0, + end: end1, + }, + want: want{ + wantTime: nil, + error: ErrDayAtLeast1, + }, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + got, err := Period(tt.args.start, tt.args.days, tt.args.end) + assert.Equal(t, tt.want.error, err) + + for key, val := range got { + assert.Equal(t, tt.want.wantTime[key], val) + } + }) + } +} diff --git a/examples/period.go b/examples/period.go new file mode 100644 index 0000000..185c5e8 --- /dev/null +++ b/examples/period.go @@ -0,0 +1,22 @@ +package examples + +import ( + "fmt" + + "github.com/uniplaces/carbon" +) + +func period() { + t1, _ := carbon.Create(2012, 1, 1, 12, 0, 0, 0, "Lisbon/Rome") + t2, _ := carbon.Create(2012, 1, 31, 12, 0, 0, 0, "Lisbon/Rome") + days := 7 + + periods, err := carbon.Period(t1, days, t2) + if err != nil { + return + } + + for _, val := range periods { + fmt.Println(val) + } +}