Files
butcem/src/shared/card-periods.test.ts
T

83 lines
3.4 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import { describe, expect, it } from "vitest";
import {
cardPeriods,
closingOnOrAfter,
dueDate,
estimateOverdraftInterest,
installmentSchedule,
minimumPayment,
minimumRateBp,
nextPeriod,
periodContaining,
} from "./card-periods";
describe("dönem hesabı", () => {
it("kesim günü dahil hesap kesim dönemine girer; ertesi gün yeni dönem", () => {
expect(periodContaining("2026-10-29", 29)).toEqual({ start: "2026-09-30", end: "2026-10-29" });
expect(periodContaining("2026-10-30", 29)).toEqual({ start: "2026-10-30", end: "2026-11-29" });
});
it("kesim günü ayda yoksa ayın son günü (31 → Şubat 28/29)", () => {
expect(closingOnOrAfter("2026-02-10", 31)).toBe("2026-02-28");
expect(periodContaining("2028-03-05", 31)).toEqual({ start: "2028-03-01", end: "2028-03-31" });
expect(periodContaining("2026-03-01", 30)).toEqual({ start: "2026-03-01", end: "2026-03-30" });
expect(periodContaining("2026-02-28", 30)).toEqual({ start: "2026-01-31", end: "2026-02-28" });
});
it("yıl dönümü ve sonraki dönem", () => {
const p = periodContaining("2026-12-31", 15);
expect(p).toEqual({ start: "2026-12-16", end: "2027-01-15" });
expect(nextPeriod(p, 15)).toEqual({ start: "2027-01-16", end: "2027-02-15" });
});
it("güncel dönem ve son ekstre; kesim günü bugün iken dönem henüz kapanmamış", () => {
expect(cardPeriods("2026-11-05", 29)).toEqual({
current: { start: "2026-10-30", end: "2026-11-29" },
statement: { start: "2026-09-30", end: "2026-10-29" },
});
expect(cardPeriods("2026-11-29", 29).current.end).toBe("2026-11-29");
});
it("son ödeme tarihi", () => {
expect(dueDate("2026-10-29", { kind: "daysAfter", value: 10 })).toBe("2026-11-08");
expect(dueDate("2026-10-29", { kind: "fixedDay", value: 9 })).toBe("2026-11-09");
expect(dueDate("2026-10-05", { kind: "fixedDay", value: 20 })).toBe("2026-10-20");
expect(dueDate("2026-01-29", { kind: "fixedDay", value: 31 })).toBe("2026-01-31");
});
});
describe("asgari ödeme", () => {
it("limite göre %20 / %40; kart bazında oran öncelikli; yukarı yuvarlama", () => {
expect(minimumRateBp(49_999_99, null)).toBe(2000);
expect(minimumRateBp(50_000_00, null)).toBe(4000);
expect(minimumRateBp(60_000_00, 2500)).toBe(2500);
expect(minimumPayment(10_000_01, 2000)).toBe(2_000_01);
expect(minimumPayment(-5, 2000)).toBe(0);
});
});
describe("taksit planı", () => {
it("eşit bölme (kuruş farkı ilk taksitlerde), aylık tarihler, ay sonu", () => {
const s = installmentSchedule("2026-01-31", 10_000_00, 3);
expect(s.map((x) => x.amountMinor)).toEqual([3_333_34, 3_333_33, 3_333_33]);
expect(s.reduce((a, x) => a + x.amountMinor, 0)).toBe(10_000_00);
expect(s.map((x) => x.date)).toEqual(["2026-01-31", "2026-02-28", "2026-03-31"]);
});
});
describe("KMH faiz tahmini", () => {
it("gün sonu eksi bakiyeler üzerinden", () => {
const period = { start: "2026-11-01", end: "2026-11-30" };
// 10 gün boyunca -3.000 TL; sonra sıfır.
const deltas = new Map([
["2026-11-01", -3_000_00],
["2026-11-11", 3_000_00],
]);
const r = estimateOverdraftInterest(period, 0, deltas, 425);
// 10 gün × 3.000 TL × %4,25 / 30 = 42,50 TL
expect(r.interestMinor).toBe(42_50);
expect(r.days).toBe(30);
expect(estimateOverdraftInterest(period, 5_000_00, deltas, 425).interestMinor).toBe(0);
});
});