Case study · University course, TU Wien
Software Quality Assurance
Coursework in Software Quality Assurance at TU Wien, built around LEIHS, a Spring Boot backend for renting out hardware that the course provided. Over one semester I took it from a review of the specification to a test plan to 99 automated tests, with TDD, stubs and mocks, and static analysis.
- Individual coursework
- Role
- Winter semester 2024/25
- Timeline
- Java 21, Spring Boot 3.2, JUnit 5, Mockito, H2, Checkstyle, SonarLint, GitLab CI
- Stack
- Completed course
- Status
The project
LEIHS rents out hardware: customers, bookings and invoices, a discount and hardware-point system, and repairs through an external HTTP service. The course provided it as a template and followed this one system through the whole semester, from the specification to tested code. The application code comes from the course. The analysis, the test plan, the bug fixes, the tests and the refactoring are mine.
From analysis to automated tests
01, Exercise 1
Analysis
- Reviewed the specification: 4 tickets, each with a question and a proposed solution.
- Classified 6 requirements by ISO 25010 quality factors and checked that each can be verified.
- Measurable quality goals, e.g. at most 3 clicks per core function and critical security issues fixed within 24 hours.
02, Exercise 2
Test planning
- A test plan across 5 test levels: unit, integration, system, acceptance and non-functional.
- Equivalence classes and boundary values for two new requirements.
- 16 black-box test cases, each a normal, special or error case.
03, Exercises 3–4
Test automation
- 99 automated tests, all passing.
- TDD for two new device types.
- A hand-written stub and Mockito mocks for the external repair service.
- Checkstyle and SonarLint, and refactoring of test smells.
One edge case, start to finish
In the review of the specification I flagged an open question: when a student earns a hardware point on a booking, does it already count toward the discount on that same invoice? At 9 of 10 points, the answer decides whether the discount applies right away, so I proposed crediting the point after the booking and pricing on the balance before it. Once there was code, hardware points and discounts were the area with the most bug fixes, and I covered them with their own tests for the invoice preview.
From equivalence classes to a test
In the test plan, the new device types were split into equivalence classes. In the next exercise, the same classes became the tests, written before the feature itself.
| Category | G1 Electronics: no bonusG2 Garden and workshop tools: bonus |
|---|---|
| Rental (G2 only) | V1 1 month: +1 pointV2 longer: +2 points |
| Insurance | S1 noneS2 insured: −5 % on the monthly price |
@ParameterizedTest
@EnumSource(value = DeviceType.class, names = {"GARDEN_TOOL", "MACHINE"})
void testCalculateHardwarePoints_ForNewToolWithOneMonthRental_ShouldEarnOneHardwarePoint(DeviceType deviceType) {
customer.setHardwarePoints(0L);
customer.setIsStudent(false);
hardwareDescription.setType(deviceType);
hardwareDescription.setMonthlyBasePrice(2000.0);
booking.setRentDurationMonths(1);
simpleInvoiceService.generateInvoicePreview(
customer, List.of(booking), List.of(), LocalDateTime.now());
long expectedHardwarePoints = 3 + 1;
assertEquals(expectedHardwarePoints, customer.getHardwarePoints());
}What I did
Bug fixes in the template
Fixed the hardware points, the booking price, the discount at 20 points and the minimum rental durations.
TDD for new device types
Garden tools and machines earn bonus points and get 5 % off with insurance. The tests came first, then the implementation: 13 tests, all green.
Stub and mock for the repair service
A hand-written stub mirrors the rules of the external service: water damage and devices 6 years or older are cancelled. Mockito mocks test the status lifecycle without a network.
Static analysis & refactoring
Checkstyle and SonarLint findings fixed or justified as false positives. Test smells refactored: try/catch to assertThrows, duplicates to parameterised tests. Status strings became an enum.
Architecture
Results
- 99 tests, all passing
- Unit and integration tests, run without the external service.
- Core services covered
- 94 % line coverage on the cost calculation, 100 % on the invoice service.
- Checked in CI
- GitLab CI builds the project and runs the tests, with Checkstyle in the build.