Hanlde trading212 inconsistent date formats
Generate check / check-changes (pull_request) Successful in 2s
Generate check / verify-generate (pull_request) Skipped
Quality / check-changes (pull_request) Successful in 3s
Quality / static-checks (pull_request) Successful in 21s
Quality / run-tests (pull_request) Successful in 52s
Generate check / check-changes (pull_request) Successful in 2s
Generate check / verify-generate (pull_request) Skipped
Quality / check-changes (pull_request) Successful in 3s
Quality / static-checks (pull_request) Successful in 21s
Quality / run-tests (pull_request) Successful in 52s
This commit is contained in:
@@ -104,6 +104,39 @@ func TestRecordReader_ReadRecord(t *testing.T) {
|
||||
r: bytes.NewBufferString(`Market sell,,IE000GA3D489,ABXY,"Aspargus Broccoli",EOF987654321,2.4387014200,7.9999999999,USD,1.17995999,,"EUR",15.25,"EUR",,,0.02,"EUR",,`),
|
||||
wantErr: true,
|
||||
},
|
||||
{
|
||||
name: "well-formed buy with new offset format +00:00",
|
||||
r: bytes.NewBufferString(`Market buy,2025-07-03 10:44:29+00:00,XX1234567890,ABXY,"Aspargus Broccoli",EOF987654321,2.4387014200,7.3690000000,USD,1.17995999,,"EUR",15.25,"EUR",0.25,"EUR",0.02,"EUR",,`),
|
||||
want: Record{
|
||||
symbol: "XX1234567890",
|
||||
kind: internal.KindBuy,
|
||||
quantity: ShouldParseDecimal(t, "2.4387014200"),
|
||||
price: ShouldParseDecimal(t, "7.3690000000"),
|
||||
timestamp: time.Date(2025, 7, 3, 10, 44, 29, 0, time.FixedZone("UTC", 0)),
|
||||
fees: ShouldParseDecimal(t, "0.02"),
|
||||
taxes: ShouldParseDecimal(t, "0.25"),
|
||||
natureGetter: func() internal.Nature { return internal.NatureG01 },
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "well-formed buy with new offset format +01:00",
|
||||
r: bytes.NewBufferString(`Market buy,2025-07-03 10:44:29+01:00,XX1234567890,ABXY,"Aspargus Broccoli",EOF987654321,2.4387014200,7.3690000000,USD,1.17995999,,"EUR",15.25,"EUR",0.25,"EUR",0.02,"EUR",,`),
|
||||
want: Record{
|
||||
symbol: "XX1234567890",
|
||||
kind: internal.KindBuy,
|
||||
quantity: ShouldParseDecimal(t, "2.4387014200"),
|
||||
price: ShouldParseDecimal(t, "7.3690000000"),
|
||||
timestamp: time.Date(2025, 7, 3, 10, 44, 29, 0, time.FixedZone("+01:00", 1*60*60)),
|
||||
fees: ShouldParseDecimal(t, "0.02"),
|
||||
taxes: ShouldParseDecimal(t, "0.25"),
|
||||
natureGetter: func() internal.Nature { return internal.NatureG01 },
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "well-formed buy with garbage timestamp returns error",
|
||||
r: bytes.NewBufferString(`Market buy,not-a-timestamp,IE000GA3D489,ABXY,"Aspargus Broccoli",EOF987654321,2.4387014200,7.3690000000,USD,1.17995999,,"EUR",15.25,"EUR",0.25,"EUR",0.02,"EUR",,`),
|
||||
wantErr: true,
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
@@ -219,6 +252,77 @@ func TestRecordReader_ReadRecord_Split(t *testing.T) {
|
||||
})
|
||||
}
|
||||
|
||||
func TestParseTimestamp(t *testing.T) {
|
||||
utc := time.FixedZone("UTC", 0)
|
||||
plusOne := time.FixedZone("+01:00", 1*60*60)
|
||||
minusFive := time.FixedZone("-05:00", -5*60*60)
|
||||
|
||||
tests := []struct {
|
||||
name string
|
||||
input string
|
||||
want time.Time
|
||||
wantErr bool
|
||||
}{
|
||||
{
|
||||
name: "legacy format without offset parses as UTC",
|
||||
input: "2025-05-22 13:15:52",
|
||||
want: time.Date(2025, 5, 22, 13, 15, 52, 0, time.UTC),
|
||||
},
|
||||
{
|
||||
name: "new format with +00:00 offset",
|
||||
input: "2025-05-22 13:15:52+00:00",
|
||||
want: time.Date(2025, 5, 22, 13, 15, 52, 0, utc),
|
||||
},
|
||||
{
|
||||
name: "new format with +01:00 offset",
|
||||
input: "2025-05-22 13:15:52+01:00",
|
||||
want: time.Date(2025, 5, 22, 13, 15, 52, 0, plusOne),
|
||||
},
|
||||
{
|
||||
name: "new format with -05:00 offset",
|
||||
input: "2025-05-22 13:15:52-05:00",
|
||||
want: time.Date(2025, 5, 22, 13, 15, 52, 0, minusFive),
|
||||
},
|
||||
{
|
||||
name: "explicit Z UTC marker",
|
||||
input: "2025-05-22 13:15:52Z",
|
||||
want: time.Date(2025, 5, 22, 13, 15, 52, 0, time.UTC),
|
||||
},
|
||||
{
|
||||
name: "garbage input returns error",
|
||||
input: "not-a-timestamp",
|
||||
wantErr: true,
|
||||
},
|
||||
{
|
||||
name: "RFC3339 with T separator is rejected",
|
||||
input: "2025-05-22T13:15:52Z",
|
||||
wantErr: true,
|
||||
},
|
||||
{
|
||||
name: "empty string returns error",
|
||||
input: "",
|
||||
wantErr: true,
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
got, err := parseTimestamp(tt.input)
|
||||
if err != nil {
|
||||
if !tt.wantErr {
|
||||
t.Fatalf("parseTimestamp(%q) returned error: %v", tt.input, err)
|
||||
}
|
||||
return
|
||||
}
|
||||
if tt.wantErr {
|
||||
t.Fatalf("parseTimestamp(%q) expected an error", tt.input)
|
||||
}
|
||||
if !got.Equal(tt.want) {
|
||||
t.Fatalf("parseTimestamp(%q) = %v, want %v", tt.input, got, tt.want)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func Test_figiNatureGetter(t *testing.T) {
|
||||
tests := []struct {
|
||||
name string // description of this test case
|
||||
|
||||
Reference in New Issue
Block a user