Skip to content

Commit 9c9c6d4

Browse files
authored
Update MainTest.java
1 parent ad27883 commit 9c9c6d4

1 file changed

Lines changed: 271 additions & 3 deletions

File tree

Lines changed: 271 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,280 @@
11
package org.example;
22

3+
import com.example.api.ElpriserAPI;
4+
import org.junit.jupiter.api.AfterEach;
5+
import org.junit.jupiter.api.BeforeEach;
36
import org.junit.jupiter.api.Test;
47

8+
import java.io.ByteArrayOutputStream;
9+
import java.io.PrintStream;
10+
import java.time.LocalDate;
11+
import java.util.List;
12+
513
import static org.assertj.core.api.Assertions.assertThat;
14+
import static org.junit.jupiter.api.Assertions.assertNotNull;
15+
import static org.junit.jupiter.api.Assertions.assertTrue;
616

717
class MainTest {
18+
PrintStream originalOut;
19+
ByteArrayOutputStream bos;
20+
21+
@BeforeEach
22+
void setup() {
23+
originalOut = System.out;
24+
bos = new ByteArrayOutputStream();
25+
System.setOut(new PrintStream(bos));
26+
}
27+
28+
@AfterEach
29+
void tearDown() {
30+
System.setOut(originalOut);
31+
ElpriserAPI.clearMockResponse();
32+
}
33+
34+
@Test
35+
void getPriser_shouldReturnParsedPrices_whenMockDataIsProvided() {
36+
// --- ARRANGE ---
37+
// 1. Define your fake JSON data for this specific test
38+
String fakeJson = """
39+
[{"SEK_per_kWh":0.12229,"EUR_per_kWh":0.01112,"EXR":10.997148,"time_start":"2025-09-04T00:00:00+02:00","time_end":"2025-09-04T01:00:00+02:00"},{"SEK_per_kWh":0.09886,"EUR_per_kWh":0.00899,"EXR":10.997148,"time_start":"2025-09-04T01:00:00+02:00","time_end":"2025-09-04T02:00:00+02:00"},{"SEK_per_kWh":0.09095,"EUR_per_kWh":0.00827,"EXR":10.997148,"time_start":"2025-09-04T02:00:00+02:00","time_end":"2025-09-04T03:00:00+02:00"},{"SEK_per_kWh":0.04201,"EUR_per_kWh":0.00382,"EXR":10.997148,"time_start":"2025-09-04T03:00:00+02:00","time_end":"2025-09-04T04:00:00+02:00"},{"SEK_per_kWh":0.04146,"EUR_per_kWh":0.00377,"EXR":10.997148,"time_start":"2025-09-04T04:00:00+02:00","time_end":"2025-09-04T05:00:00+02:00"},{"SEK_per_kWh":0.04465,"EUR_per_kWh":0.00406,"EXR":10.997148,"time_start":"2025-09-04T05:00:00+02:00","time_end":"2025-09-04T06:00:00+02:00"},{"SEK_per_kWh":0.32991,"EUR_per_kWh":0.03,"EXR":10.997148,"time_start":"2025-09-04T06:00:00+02:00","time_end":"2025-09-04T07:00:00+02:00"},{"SEK_per_kWh":0.47123,"EUR_per_kWh":0.04285,"EXR":10.997148,"time_start":"2025-09-04T07:00:00+02:00","time_end":"2025-09-04T08:00:00+02:00"},{"SEK_per_kWh":0.68182,"EUR_per_kWh":0.062,"EXR":10.997148,"time_start":"2025-09-04T08:00:00+02:00","time_end":"2025-09-04T09:00:00+02:00"},{"SEK_per_kWh":0.4125,"EUR_per_kWh":0.03751,"EXR":10.997148,"time_start":"2025-09-04T09:00:00+02:00","time_end":"2025-09-04T10:00:00+02:00"},{"SEK_per_kWh":0.29571,"EUR_per_kWh":0.02689,"EXR":10.997148,"time_start":"2025-09-04T10:00:00+02:00","time_end":"2025-09-04T11:00:00+02:00"},{"SEK_per_kWh":0.06136,"EUR_per_kWh":0.00558,"EXR":10.997148,"time_start":"2025-09-04T11:00:00+02:00","time_end":"2025-09-04T12:00:00+02:00"},{"SEK_per_kWh":0.03662,"EUR_per_kWh":0.00333,"EXR":10.997148,"time_start":"2025-09-04T12:00:00+02:00","time_end":"2025-09-04T13:00:00+02:00"},{"SEK_per_kWh":0.0375,"EUR_per_kWh":0.00341,"EXR":10.997148,"time_start":"2025-09-04T13:00:00+02:00","time_end":"2025-09-04T14:00:00+02:00"},{"SEK_per_kWh":0.26822,"EUR_per_kWh":0.02439,"EXR":10.997148,"time_start":"2025-09-04T14:00:00+02:00","time_end":"2025-09-04T15:00:00+02:00"},{"SEK_per_kWh":0.30429,"EUR_per_kWh":0.02767,"EXR":10.997148,"time_start":"2025-09-04T15:00:00+02:00","time_end":"2025-09-04T16:00:00+02:00"},{"SEK_per_kWh":0.36675,"EUR_per_kWh":0.03335,"EXR":10.997148,"time_start":"2025-09-04T16:00:00+02:00","time_end":"2025-09-04T17:00:00+02:00"},{"SEK_per_kWh":0.58296,"EUR_per_kWh":0.05301,"EXR":10.997148,"time_start":"2025-09-04T17:00:00+02:00","time_end":"2025-09-04T18:00:00+02:00"},{"SEK_per_kWh":0.92145,"EUR_per_kWh":0.08379,"EXR":10.997148,"time_start":"2025-09-04T18:00:00+02:00","time_end":"2025-09-04T19:00:00+02:00"},{"SEK_per_kWh":1.5054,"EUR_per_kWh":0.13689,"EXR":10.997148,"time_start":"2025-09-04T19:00:00+02:00","time_end":"2025-09-04T20:00:00+02:00"},{"SEK_per_kWh":1.00888,"EUR_per_kWh":0.09174,"EXR":10.997148,"time_start":"2025-09-04T20:00:00+02:00","time_end":"2025-09-04T21:00:00+02:00"},{"SEK_per_kWh":0.63179,"EUR_per_kWh":0.05745,"EXR":10.997148,"time_start":"2025-09-04T21:00:00+02:00","time_end":"2025-09-04T22:00:00+02:00"},{"SEK_per_kWh":0.56382,"EUR_per_kWh":0.05127,"EXR":10.997148,"time_start":"2025-09-04T22:00:00+02:00","time_end":"2025-09-04T23:00:00+02:00"},{"SEK_per_kWh":0.52951,"EUR_per_kWh":0.04815,"EXR":10.997148,"time_start":"2025-09-04T23:00:00+02:00","time_end":"2025-09-05T00:00:00+02:00"}]""";
40+
41+
// 2. Set the mock response using the static method.
42+
ElpriserAPI.setMockResponse(fakeJson);
43+
44+
// 3. Create an instance of the class as a student would.
45+
ElpriserAPI api = new ElpriserAPI(false); // Disable caching for predictable tests
46+
47+
// --- ACT ---
48+
// This call will NOT make a network request. It will use `fakeJson`.
49+
List<ElpriserAPI.Elpris> priser = api.getPriser("2025-09-04", ElpriserAPI.Prisklass.SE3);
50+
51+
// --- ASSERT ---
52+
assertThat(priser)
53+
.isNotNull()
54+
.hasSize(24)
55+
.satisfies(list -> {
56+
assertThat(list.get(0).sekPerKWh()).isEqualTo(0.12229);
57+
assertThat(list.get(1).sekPerKWh()).isEqualTo(0.09886);
58+
});
59+
}
60+
61+
@Test
62+
void getPriser_shouldReturnEmptyList_whenMockDataIsNull() {
63+
ElpriserAPI.setMockResponse(null);
64+
ElpriserAPI api = new ElpriserAPI(false);
65+
66+
List<ElpriserAPI.Elpris> priser = api.getPriser(LocalDate.now(), ElpriserAPI.Prisklass.SE1);
67+
68+
assertNotNull(priser);
69+
assertTrue(priser.isEmpty());
70+
}
71+
72+
@Test
73+
void showHelp_whenNoArguments() {
74+
Main.main(new String[]{});
75+
76+
String output = bos.toString();
77+
assertThat(output).containsIgnoringCase("usage");
78+
assertThat(output).containsIgnoringCase("zone");
79+
assertThat(output).containsIgnoringCase("date");
80+
}
81+
82+
@Test
83+
void showHelp_withHelpFlag() {
84+
Main.main(new String[]{"--help"});
85+
86+
String output = bos.toString();
87+
assertThat(output).containsIgnoringCase("electricity price optimizer");
88+
assertThat(output).containsIgnoringCase("--zone");
89+
assertThat(output).containsIgnoringCase("--date");
90+
}
91+
92+
@Test
93+
void displayMeanPrice_withValidData() {
94+
// Mock data with known values for predictable mean calculation
95+
String mockJson = """
96+
[{"SEK_per_kWh":0.10,"EUR_per_kWh":0.01,"EXR":10.0,"time_start":"2025-09-04T00:00:00+02:00","time_end":"2025-09-04T01:00:00+02:00"},
97+
{"SEK_per_kWh":0.20,"EUR_per_kWh":0.02,"EXR":10.0,"time_start":"2025-09-04T01:00:00+02:00","time_end":"2025-09-04T02:00:00+02:00"},
98+
{"SEK_per_kWh":0.30,"EUR_per_kWh":0.03,"EXR":10.0,"time_start":"2025-09-04T02:00:00+02:00","time_end":"2025-09-04T03:00:00+02:00"},
99+
{"SEK_per_kWh":0.40,"EUR_per_kWh":0.04,"EXR":10.0,"time_start":"2025-09-04T03:00:00+02:00","time_end":"2025-09-04T04:00:00+02:00"}]""";
100+
101+
ElpriserAPI.setMockResponse(mockJson);
102+
103+
Main.main(new String[]{"--zone", "SE3", "--date", "2025-09-04"});
104+
105+
String output = bos.toString();
106+
assertThat(output).containsIgnoringCase("medelpris");
107+
// Mean of 0.10, 0.20, 0.30, 0.40 = 0.25 = 25 öre
108+
assertThat(output).contains("25");
109+
}
110+
111+
@Test
112+
void displayMinMaxPrices_withValidData() {
113+
String mockJson = """
114+
[{"SEK_per_kWh":0.50,"EUR_per_kWh":0.05,"EXR":10.0,"time_start":"2025-09-04T00:00:00+02:00","time_end":"2025-09-04T01:00:00+02:00"},
115+
{"SEK_per_kWh":0.10,"EUR_per_kWh":0.01,"EXR":10.0,"time_start":"2025-09-04T01:00:00+02:00","time_end":"2025-09-04T02:00:00+02:00"},
116+
{"SEK_per_kWh":0.80,"EUR_per_kWh":0.08,"EXR":10.0,"time_start":"2025-09-04T02:00:00+02:00","time_end":"2025-09-04T03:00:00+02:00"},
117+
{"SEK_per_kWh":0.30,"EUR_per_kWh":0.03,"EXR":10.0,"time_start":"2025-09-04T03:00:00+02:00","time_end":"2025-09-04T04:00:00+02:00"}]""";
118+
119+
ElpriserAPI.setMockResponse(mockJson);
120+
121+
Main.main(new String[]{"--zone", "SE1", "--date", "2025-09-04"});
122+
123+
String output = bos.toString();
124+
assertThat(output).containsIgnoringCase("lägsta pris");
125+
assertThat(output).containsIgnoringCase("högsta pris");
126+
assertThat(output).contains("01-02"); // Cheapest hour (0.10)
127+
assertThat(output).contains("02-03"); // Most expensive hour (0.80)
128+
assertThat(output).contains("10"); // 10 öre (cheapest)
129+
assertThat(output).contains("80"); // 80 öre (most expensive)
130+
}
131+
132+
@Test
133+
void displaySortedPrices_whenRequested() {
134+
String mockJson = """
135+
[{"SEK_per_kWh":0.30,"EUR_per_kWh":0.03,"EXR":10.0,"time_start":"2025-09-04T00:00:00+02:00","time_end":"2025-09-04T01:00:00+02:00"},
136+
{"SEK_per_kWh":0.10,"EUR_per_kWh":0.01,"EXR":10.0,"time_start":"2025-09-04T01:00:00+02:00","time_end":"2025-09-04T02:00:00+02:00"},
137+
{"SEK_per_kWh":0.20,"EUR_per_kWh":0.02,"EXR":10.0,"time_start":"2025-09-04T02:00:00+02:00","time_end":"2025-09-04T03:00:00+02:00"}]""";
138+
139+
ElpriserAPI.setMockResponse(mockJson);
140+
141+
Main.main(new String[]{"--zone", "SE2", "--date", "2025-09-04", "--sorted"});
142+
143+
String output = bos.toString();
144+
// Should show prices in descending order
145+
assertThat(output).contains("00-01 30 öre");
146+
assertThat(output).contains("02-03 20 öre");
147+
assertThat(output).contains("01-02 10 öre");
148+
}
149+
8150
@Test
9-
void test() {
10-
assertThat(true).isTrue();
151+
void findOptimalCharging2Hours() {
152+
String mockJson = """
153+
[{"SEK_per_kWh":0.50,"EUR_per_kWh":0.05,"EXR":10.0,"time_start":"2025-09-04T00:00:00+02:00","time_end":"2025-09-04T01:00:00+02:00"},
154+
{"SEK_per_kWh":0.10,"EUR_per_kWh":0.01,"EXR":10.0,"time_start":"2025-09-04T01:00:00+02:00","time_end":"2025-09-04T02:00:00+02:00"},
155+
{"SEK_per_kWh":0.05,"EUR_per_kWh":0.005,"EXR":10.0,"time_start":"2025-09-04T02:00:00+02:00","time_end":"2025-09-04T03:00:00+02:00"},
156+
{"SEK_per_kWh":0.15,"EUR_per_kWh":0.015,"EXR":10.0,"time_start":"2025-09-04T03:00:00+02:00","time_end":"2025-09-04T04:00:00+02:00"},
157+
{"SEK_per_kWh":0.30,"EUR_per_kWh":0.03,"EXR":10.0,"time_start":"2025-09-04T04:00:00+02:00","time_end":"2025-09-04T05:00:00+02:00"}]""";
158+
159+
ElpriserAPI.setMockResponse(mockJson);
160+
161+
Main.main(new String[]{"--zone", "SE3", "--date", "2025-09-04", "--charging", "2h"});
162+
163+
String output = bos.toString();
164+
assertThat(output).containsIgnoringCase("påbörja laddning");
165+
assertThat(output).contains("01"); // Should start at 01:00 (cheapest 2h window: 01-02 + 02-03)
166+
assertThat(output).containsIgnoringCase("medelpris");
167+
assertThat(output).contains("7,5"); // Mean of 0.10 and 0.05 = 0.075 = 7.5 öre
168+
}
169+
170+
@Test
171+
void findOptimalCharging4Hours() {
172+
String mockJson = """
173+
[{"SEK_per_kWh":0.40,"EUR_per_kWh":0.04,"EXR":10.0,"time_start":"2025-09-04T00:00:00+02:00","time_end":"2025-09-04T01:00:00+02:00"},
174+
{"SEK_per_kWh":0.10,"EUR_per_kWh":0.01,"EXR":10.0,"time_start":"2025-09-04T01:00:00+02:00","time_end":"2025-09-04T02:00:00+02:00"},
175+
{"SEK_per_kWh":0.05,"EUR_per_kWh":0.005,"EXR":10.0,"time_start":"2025-09-04T02:00:00+02:00","time_end":"2025-09-04T03:00:00+02:00"},
176+
{"SEK_per_kWh":0.15,"EUR_per_kWh":0.015,"EXR":10.0,"time_start":"2025-09-04T03:00:00+02:00","time_end":"2025-09-04T04:00:00+02:00"},
177+
{"SEK_per_kWh":0.20,"EUR_per_kWh":0.02,"EXR":10.0,"time_start":"2025-09-04T04:00:00+02:00","time_end":"2025-09-04T05:00:00+02:00"},
178+
{"SEK_per_kWh":0.30,"EUR_per_kWh":0.03,"EXR":10.0,"time_start":"2025-09-04T05:00:00+02:00","time_end":"2025-09-04T06:00:00+02:00"}]""";
179+
180+
ElpriserAPI.setMockResponse(mockJson);
181+
182+
Main.main(new String[]{"--zone", "SE1", "--date", "2025-09-04", "--charging", "4h"});
183+
184+
String output = bos.toString();
185+
assertThat(output).containsIgnoringCase("påbörja laddning");
186+
assertThat(output).contains("01"); // Should start at 01:00 (cheapest 4h window)
187+
assertThat(output).containsIgnoringCase("medelpris");
188+
// Mean of 0.10, 0.05, 0.15, 0.20 = 0.125 = 12.5 öre
189+
assertThat(output).contains("12,5");
190+
}
191+
192+
@Test
193+
void findOptimalCharging8Hours() {
194+
// Create mock data with 12 hours to allow for 8-hour window
195+
StringBuilder jsonBuilder = new StringBuilder("[");
196+
double[] prices = {0.50, 0.10, 0.05, 0.15, 0.08, 0.12, 0.06, 0.09, 0.25, 0.30, 0.35, 0.40};
197+
198+
for (int i = 0; i < prices.length; i++) {
199+
if (i > 0) jsonBuilder.append(",");
200+
jsonBuilder.append(String.format(
201+
"""
202+
{"SEK_per_kWh":%.2f,"EUR_per_kWh":%.3f,"EXR":10.0,"time_start":"2025-09-04T%02d:00:00+02:00","time_end":"2025-09-04T%02d:00:00+02:00"}""",
203+
prices[i], prices[i] / 10, i, i + 1
204+
));
205+
}
206+
jsonBuilder.append("]");
207+
208+
ElpriserAPI.setMockResponse(jsonBuilder.toString());
209+
210+
Main.main(new String[]{"--zone", "SE4", "--date", "2025-09-04", "--charging", "8h"});
211+
212+
String output = bos.toString();
213+
assertThat(output).containsIgnoringCase("påbörja laddning");
214+
assertThat(output).containsIgnoringCase("medelpris");
215+
}
216+
217+
@Test
218+
void handleInvalidZone() {
219+
Main.main(new String[]{"--zone", "SE5", "--date", "2025-09-04"});
220+
221+
String output = bos.toString();
222+
assertThat(output).containsAnyOf("invalid zone", "ogiltig zon", "fel zon");
223+
}
224+
225+
@Test
226+
void handleInvalidDate() {
227+
Main.main(new String[]{"--zone", "SE3", "--date", "invalid-date"});
228+
229+
String output = bos.toString();
230+
assertThat(output).containsAnyOf("invalid date", "ogiltigt datum", "fel datum");
231+
}
232+
233+
@Test
234+
void handleMissingZoneArgument() {
235+
Main.main(new String[]{"--date", "2025-09-04"});
236+
237+
String output = bos.toString();
238+
assertThat(output).containsAnyOf("zone", "required");
239+
}
240+
241+
@Test
242+
void useCurrentDateWhenNotSpecified() {
243+
ElpriserAPI.setMockResponse("[]"); // Empty response is fine for this test
244+
245+
Main.main(new String[]{"--zone", "SE3"});
246+
247+
String output = bos.toString();
248+
// Should not show error about missing date
249+
assertThat(output).doesNotContainIgnoringCase("invalid date");
250+
assertThat(output).doesNotContainIgnoringCase("missing date");
251+
}
252+
253+
@Test
254+
void handleNoDataAvailable() {
255+
ElpriserAPI.setMockResponse("[]"); // Empty response
256+
257+
Main.main(new String[]{"--zone", "SE3", "--date", "2025-09-04"});
258+
259+
String output = bos.toString();
260+
assertThat(output).containsAnyOf("no data", "ingen data", "inga priser");
261+
}
262+
263+
@Test
264+
void handleMultipleDaysData() {
265+
// Mock response with data for two days
266+
String mockJson = """
267+
[{"SEK_per_kWh":0.30,"EUR_per_kWh":0.03,"EXR":10.0,"time_start":"2025-09-04T22:00:00+02:00","time_end":"2025-09-04T23:00:00+02:00"},
268+
{"SEK_per_kWh":0.25,"EUR_per_kWh":0.025,"EXR":10.0,"time_start":"2025-09-04T23:00:00+02:00","time_end":"2025-09-05T00:00:00+02:00"},
269+
{"SEK_per_kWh":0.10,"EUR_per_kWh":0.01,"EXR":10.0,"time_start":"2025-09-05T00:00:00+02:00","time_end":"2025-09-05T01:00:00+02:00"},
270+
{"SEK_per_kWh":0.15,"EUR_per_kWh":0.015,"EXR":10.0,"time_start":"2025-09-05T01:00:00+02:00","time_end":"2025-09-05T02:00:00+02:00"}]""";
271+
272+
ElpriserAPI.setMockResponse(mockJson);
273+
274+
Main.main(new String[]{"--zone", "SE3", "--date", "2025-09-04", "--charging", "4h"});
275+
276+
String output = bos.toString();
277+
assertThat(output).containsIgnoringCase("påbörja laddning");
278+
// Should be able to find optimal charging window across day boundary
11279
}
12-
}
280+
}

0 commit comments

Comments
 (0)