60 Commits

Author SHA1 Message Date
677336e534 Changed Tests so they don't permanently insert workers and tasks into the database 2026-01-06 23:51:24 +01:00
342338f6e5 Merge pull request 'Hotfix to address the IOException in the SimpleDatabaseManager class, modified modifier and deleted useless test.' (#6) from database into main
Reviewed-on: #6

Jup, gecheckt
2026-01-06 23:39:24 +01:00
Riley Schneider
3050405792 Hotfix to address the IOException in the SimpleDatabaseManager class, modified modifier and deleted useless test. 2026-01-06 23:36:29 +01:00
e667389694 Changed the build.gradle to have an automatic build script, added the README 2026-01-06 23:08:43 +01:00
6ac08e2db1 Merge branch 'main' of https://home.luithardt.cloud:5400/KevinSchoenmayer/GseTDDUebungKCLR
Problems with merging into main, new version
2026-01-06 21:56:07 +01:00
20afbbf461 Problems with the merge to main 2026-01-06 21:52:34 +01:00
0b74bf5eea Merge pull request 'ScannerImplementation' (#5) from ScannerImplementation into main
Reviewed-on: #5

Reviewed this together in a call
2026-01-06 21:24:36 +01:00
6ccb68285f Added syncing with database when starting the Manager, adding, removing or editing anything 2026-01-06 21:14:09 +01:00
0c83baec46 Merging 2026-01-06 20:23:49 +01:00
654305f2cd Small fix for listing tasks 2026-01-06 20:05:43 +01:00
a390509f87 Fixed CLI to allow for full testing by using State Machines for everything, test for editing passes now 2026-01-06 19:35:52 +01:00
85446bc230 Quick change to the access Modifiers for fields in Worker,Task and Assignmentmanager, refactored tests to use getWorkerMap 2026-01-04 16:33:12 +01:00
f0da7b0f9a Mid-Work of changing the CLI to use State Machines so all input can be tested with the Tests using handleInput() 2026-01-04 16:27:53 +01:00
c85d55ce7d Almost full implementation of Scanner UI. Two tests not passing, but safety commit 2026-01-04 16:09:48 +01:00
a875f24e83 Commit for the rebase on ScannerImplementation from main 2026-01-04 15:23:53 +01:00
760009b4d6 Merge pull request 'Implemented database functionality' (#4) from database into main
Reviewed-on: #4

Tried with a few extra steps. Needs a ReadME, but works otherwise.
2025-12-18 21:13:10 +01:00
bb71c7e329 Fixed assignment manager to pass some tests, scanner is not yet implemented fully 2025-12-18 19:58:03 +01:00
Riley Schneider
35e22bba99 Added MySQL functionality 2025-12-18 10:01:58 +01:00
Riley Schneider
3344ba67cc Updated files and created compose.yml for internal database usage 2025-12-14 17:53:04 +01:00
Riley Schneider
97990a3e76 Deleted unnecessary files. 2025-12-08 21:15:46 +01:00
4eb0f6c3bd Merge pull request 'database' (#3) from database into main
Reviewed-on: #3
2025-12-08 18:10:07 +01:00
Riley Schneider
0dd7fd4687 Provide mock-like DB manager for integration testing 2025-12-08 18:06:43 +01:00
Riley Schneider
e9b2ad0a57 Heavily refactored DatabaseManager.java and SimpleDatabaseManager.java. Fully refactored DatabaseGoodCasesTest.java and DatabaseBadCasesTest.java. 2025-12-08 17:50:21 +01:00
Riley Schneider
292d6c74c3 Implemented Update method 2025-12-03 23:17:31 +01:00
Riley Schneider
f2cc964d39 Added new tests that needs to be implemented. 2025-12-03 23:04:21 +01:00
Riley Schneider
995fba6fce Added a placeholder method to delete objects from the database. 2025-12-03 22:29:52 +01:00
Riley Schneider
daafd7d09e Fixed a typo in the query 2025-12-03 22:24:04 +01:00
Riley Schneider
41e711ab74 Added resultSet.next() 2025-12-03 22:22:30 +01:00
Riley Schneider
625e089a36 Prepared new tests 2025-12-03 22:10:24 +01:00
Riley Schneider
d9da291d45 Added first sql-queries into the SimpleDatabaseManager.java (Still failing / Red Errors) 2025-12-03 21:45:26 +01:00
2af4f4b7a4 Wrote all the Tests for the Scanner UI 2025-12-03 21:13:59 +01:00
Riley Schneider
b801ea7d21 Added NotImplementedException, edited some DatabaseGoodCasesTest tests. 2025-12-03 20:52:47 +01:00
Riley Schneider
8150fdbf13 Updated from origin/main 2025-12-03 20:42:23 +01:00
79df3d300e Just a small commit so i can pull 2025-12-03 20:40:15 +01:00
7201f66214 Small commit while writing tests 2025-12-03 20:40:15 +01:00
0db43fe51a Fixed Merge Conflicts, uploaded local main 2025-12-03 20:37:10 +01:00
90fbacadaa Merge pull request 'database' (#2) from database into main
Reviewed-on: #2
2025-12-03 20:16:49 +01:00
Riley Schneider
57144fa772 Updated MySQL Methods, Tests and Information accordingly. (High security risk btw) 2025-12-03 20:15:28 +01:00
c10de39091 Just a commit to push the build files so I can push 2025-12-03 19:36:50 +01:00
98bbddb31a Added Tests for removing, finishing and unfinishing tasks and so on for test coverage. 2025-12-03 19:32:59 +01:00
7640b1ef35 Added Tests for TaskState Changes. Actually added functionality to pass that test. 2025-12-03 19:20:24 +01:00
20daf315ca Added Task Adding, Removing, Editing and corrected some relatex tests. Coverage still not 100% 2025-12-03 19:08:16 +01:00
Riley Schneider
d3488f1f1c Update connect method in SimpleDatabaseManager.java 2025-12-03 18:26:13 +01:00
Riley Schneider
382aad70f7 Updated gitignore 2025-12-03 18:24:42 +01:00
Riley Schneider
dbebcad97d First runnable tests for Database / Commented out Good/BadCasesTests (not relevant to this branch) 2025-12-03 18:23:07 +01:00
4fa55c8607 Added Full Skeleton Methods for AssignmentManager and Task 2025-12-03 18:21:53 +01:00
Riley Schneider
ec0abd85b9 Merge remote-tracking branch 'origin/database' into database
# Conflicts:
#	.gradle/8.14/executionHistory/executionHistory.lock
#	.gradle/8.14/fileHashes/fileHashes.bin
#	.gradle/8.14/fileHashes/fileHashes.lock
#	.gradle/buildOutputCleanup/buildOutputCleanup.lock
#	.gradle/buildOutputCleanup/cache.properties
#	build/classes/java/main/hhn/temp/project/provider/DatabaseManager.class
#	build/tmp/compileJava/previous-compilation-data.bin
#	src/main/java/hhn/temp/project/provider/SimpleDatabaseManager.java
#	test/hhn/temp/project/BadCasesTest.java
#	test/hhn/temp/project/DatabaseBadCasesTest.java
#	test/hhn/temp/project/DatabaseGoodCasesTest.java
#	test/hhn/temp/project/GoodCasesTest.java
2025-12-03 18:20:36 +01:00
Riley Schneider
04f2087456 First runnable tests for Database / Commented out Good/BadCasesTests (not relevant to this branch) 2025-12-03 18:19:48 +01:00
fb0e05fd4d Added a basic test for the worker get methods 2025-12-03 18:06:09 +01:00
4bb1e13f21 Added basic worker so tests can create them 2025-12-03 17:59:30 +01:00
Riley Schneider
0c4f092312 Backup 2025-12-03 17:49:06 +01:00
8c4849fdf0 Just adding the report so I can rebase 2025-12-03 17:43:40 +01:00
a5378868ea Changed a small setting so test results are actually displayed 2025-12-03 17:39:42 +01:00
9641825200 Wrote the first BadCasesTests 2025-12-03 17:36:12 +01:00
Riley Schneider
bc0e30860c First database tests 2025-12-03 17:30:33 +01:00
d5a9825ec1 Wrote the first GoodCasesTests 2025-12-03 17:29:56 +01:00
26f7ecbee6 Merge pull request 'Skeleton' (#1) from Skeleton into main
Reviewed-on: #1
2025-12-03 16:44:45 +01:00
Riley Schneider
eed1390c65 Remove database folder 2025-12-03 16:42:41 +01:00
Riley Schneider
b732d8d4b5 Initial Commit 2025-12-03 16:38:10 +01:00
c5e26bf594 Rough Skeleton for Tests and Classes 2025-12-03 16:28:17 +01:00
49 changed files with 1810 additions and 63 deletions

2
.gitignore vendored
View File

@@ -0,0 +1,2 @@
build/
.gradle/

View File

@@ -1,2 +0,0 @@
#Tue Dec 02 10:03:29 CET 2025
gradle.version=8.14

9
.idea/GSEUebung.iml generated
View File

@@ -1,9 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<module type="JAVA_MODULE" version="4">
<component name="NewModuleRootManager" inherit-compiler-output="true">
<exclude-output />
<content url="file://$MODULE_DIR$" />
<orderEntry type="inheritedJdk" />
<orderEntry type="sourceFolder" forTests="false" />
</component>
</module>

2
.idea/gradle.xml generated
View File

@@ -5,6 +5,8 @@
<option name="linkedExternalProjectsSettings">
<GradleProjectSettings>
<option name="externalProjectPath" value="$PROJECT_DIR$" />
<option name="gradleHome" value="C:\Gradle\gradle-9.0.0" />
<option name="gradleJvm" value="17" />
<option name="modules">
<set>
<option value="$PROJECT_DIR$" />

2
.idea/misc.xml generated
View File

@@ -4,7 +4,7 @@
<component name="FrameworkDetectionExcludesConfiguration">
<file type="web" url="file://$PROJECT_DIR$" />
</component>
<component name="ProjectRootManager" version="2" languageLevel="JDK_17" default="true" project-jdk-name="homebrew-17" project-jdk-type="JavaSDK">
<component name="ProjectRootManager" version="2" languageLevel="JDK_17" default="true" project-jdk-name="17" project-jdk-type="JavaSDK">
<output url="file://$PROJECT_DIR$/out" />
</component>
</project>

3
.idea/modules.xml generated
View File

@@ -2,7 +2,8 @@
<project version="4">
<component name="ProjectModuleManager">
<modules>
<module fileurl="file://$PROJECT_DIR$/.idea/GSEUebung.iml" filepath="$PROJECT_DIR$/.idea/GSEUebung.iml" />
<module fileurl="file://$PROJECT_DIR$/.idea/modules/Template.iml" filepath="$PROJECT_DIR$/.idea/modules/Template.iml" />
<module fileurl="file://$PROJECT_DIR$/.idea/modules/Template.test.iml" filepath="$PROJECT_DIR$/.idea/modules/Template.test.iml" />
</modules>
</component>
</project>

8
.idea/modules/Template.test.iml generated Normal file
View File

@@ -0,0 +1,8 @@
<?xml version="1.0" encoding="UTF-8"?>
<module version="4">
<component name="AdditionalModuleElements">
<content url="file://$MODULE_DIR$/../../src/test" dumb="true">
<sourceFolder url="file://$MODULE_DIR$/../../src/test/resources" type="java-test-resource" />
</content>
</component>
</module>

View File

@@ -1,2 +1,40 @@
# Temp-Java-Gradle
@Author Kevin Schoenmayer, Riley Schneider, Can Oezdemir, Lasse Grosshans
Volle Dokumentation mit Bildern, Vorbereitungen und Klassendiagramm unter
https://docs.google.com/document/d/1iPl3XoZdvn1zqYCNlzHklEf_bRBGnQm41bAEaWz_s0w/edit?usp=sharing
Voraussetzungen:
Docker (inkl. Docker Compose)
Java 17
Git
Projekt bauen, testen und starten:
1. Projekt klonen:
git clone https://home.luithardt.cloud:5400/KevinSchoenmayer/GseTDDUebungKCLR
2. Zu ...\GseTDDUebungKCLR\docker in cmd navigieren
Docker starten:
docker compose up -d
3. Tabellenerstellung fuer die Testumgebung:
Verbinden Sie sich mit dem Programm Ihrer Wahl mit der Datenbank (z.B. HeidiSQL). Die Anmeldeinformationen finden Sie in der compose.yml-Datei.
Fuehren Sie nun auf der Datenbank folgende SQL-Befehle aus dieser Dateien aus:
resources\sql\createTaskTable.sql
resources\sql\createWorkerTable.sql
Sie sollten in Ihrer Datenbank nun zwei neue Tabellen sehen: Task und Worker. Wenn dem so sei, koennen Sie mit Punkt (6) fortfahren.
4. Projekt starten:
gradle cleanRun --console=plain --quiet
Jetzt werden die Tests durchgefuehrt und in
...\GseTDDUebungKCLR\build\reports\tests\index.html
gespeichert (genaue Adresse fuer .html wird automatisch angegeben),
die Jacoco Test Coverage erzeugt und in
...\GseTDDUebungKCLR\build\reports\jacoco\html\index.html
gespeichert (genaue Adresse fuer .html wird automatisch angegeben),
und das Programm in der Command Line gestartet.
Nutze ?, um dir die Befehle anzeigen zu lassen.

View File

@@ -1,6 +1,7 @@
plugins {
id 'java'
id 'jacoco'
id 'application'
}
group = 'hhn.temp.project'
@@ -14,11 +15,7 @@ dependencies {
testImplementation platform('org.junit:junit-bom:5.10.0')
testImplementation 'org.junit.jupiter:junit-jupiter'
testRuntimeOnly 'org.junit.platform:junit-platform-launcher'
}
jacoco {
toolVersion = '0.8.13'
reportsDirectory.set(layout.buildDirectory.dir('customJacocoReportDir'))
implementation 'com.mysql:mysql-connector-j:9.5.0'
}
sourceSets {
@@ -34,15 +31,113 @@ sourceSets {
}
}
// Test configuration
test {
useJUnitPlatform()
testLogging {
events "passed", "skipped", "failed"
exceptionFormat "full"
showStandardStreams = true
}
// Generate test reports in a specific location
reports {
html.outputLocation.set(layout.buildDirectory.dir("reports/tests"))
junitXml.outputLocation.set(layout.buildDirectory.dir("reports/tests"))
}
finalizedBy jacocoTestReport
}
// Jacoco configuration
jacoco {
toolVersion = '0.8.13'
reportsDirectory.set(layout.buildDirectory.dir('reports/jacoco'))
}
jacocoTestReport {
dependsOn test
reports {
xml.required = false
xml.required = true
csv.required = false
html.outputLocation.set(layout.buildDirectory.dir('jacocoHtml'))
html.required = true
html.outputLocation.set(layout.buildDirectory.dir("reports/jacoco/html"))
}
}
// Application configuration
application {
mainClass = "hhn.temp.project.Main"
}
// Custom task to print information after build
task printInfo {
dependsOn test, jacocoTestReport
doLast {
println("\n" + "="*50)
println("BUILD AND TESTS COMPLETED SUCCESSFULLY!")
println("="*50)
println("\nTest Results Location:")
println(" HTML: ${layout.buildDirectory.get()}/reports/tests/index.html")
println(" XML: ${layout.buildDirectory.get()}/reports/tests/TEST-*.xml")
println("\nJacoco Coverage Reports:")
println(" HTML: ${layout.buildDirectory.get()}/reports/jacoco/html/index.html")
println(" XML: ${layout.buildDirectory.get()}/reports/jacoco/test/jacocoTestReport.xml")
println("\nTo run the application:")
println(" gradle run --console=plain")
println("\nTo run tests and generate coverage reports:")
println(" gradle test jacocoTestReport")
println("="*50)
}
}
// Custom task that combines clean, test, jacocoTestReport
task cleanTestReport {
dependsOn clean, test, jacocoTestReport
description = 'Clean build and run tests with coverage reports'
group = 'verification'
}
// Configure the standard run task
run {
dependsOn test, jacocoTestReport
standardInput = System.in
doFirst {
println("\n" + "="*50)
println("TESTS COMPLETED - STARTING APPLICATION...")
println("="*50)
}
}
// Create an alias task
task cleanRun {
dependsOn clean, run
description = 'Clean build, run tests with coverage, then run the application'
group = 'application'
}
// Alternative: Create a separate task that doesn't chain dependencies
task startApp(type: JavaExec) {
description = 'Start the application (without running tests first)'
group = 'application'
classpath = sourceSets.main.runtimeClasspath
mainClass = application.mainClass
standardInput = System.in
standardOutput = System.out
// Configure to run in foreground
systemProperties System.getProperties()
doFirst {
println("\n" + "="*50)
println("STARTING APPLICATION...")
println("="*50)
}
}
// Make test and jacocoTestReport trigger the info print
test.finalizedBy printInfo

19
docker/compose.yml Normal file
View File

@@ -0,0 +1,19 @@
version: "3.9"
services:
mysql:
image: mysql:8.0
container_name: mysql-db
restart: unless-stopped
environment:
MYSQL_ROOT_PASSWORD: root
MYSQL_DATABASE: sql7810540
MYSQL_USER: sql7810540
MYSQL_PASSWORD: mXdJCFtDZz
ports:
- "3306:3306"
volumes:
- mysql_data:/var/lib/mysql
volumes:
mysql_data:

View File

@@ -0,0 +1 @@
SELECT COUNT(*) AS total FROM Task

View File

@@ -0,0 +1 @@
SELECT COUNT(*) AS total FROM Worker

View File

@@ -0,0 +1 @@
DELETE FROM Task WHERE taskid = ?

View File

@@ -0,0 +1 @@
INSERT INTO Task (taskid, name, description, workerid, taskstate) VALUES (?, ?, ?, ?, ?)

View File

@@ -0,0 +1 @@
INSERT INTO Worker (workerid, name) VALUES (?, ?)

View File

@@ -0,0 +1 @@
SELECT * FROM Task

View File

@@ -0,0 +1 @@
SELECT * FROM Worker

View File

@@ -0,0 +1 @@
SELECT * FROM Task WHERE taskid = ? LIMIT 1

View File

@@ -0,0 +1 @@
SELECT * FROM Task WHERE workerid = ?

View File

@@ -0,0 +1 @@
SELECT * FROM Worker WHERE workerid = ? LIMIT 1

View File

@@ -0,0 +1 @@
UPDATE Task SET name = ?, description = ?, taskstate = ? WHERE taskid = ?

View File

@@ -0,0 +1 @@
UPDATE Worker SET workerid = ?, name = ? WHERE workerid = ?

View File

@@ -0,0 +1,8 @@
CREATE TABLE Task (
id INT AUTO_INCREMENT PRIMARY KEY,
taskid INT,
name VARCHAR(255) NOT NULL,
description TEXT,
workerid INT,
taskstate BIT
);

View File

@@ -0,0 +1,5 @@
CREATE TABLE Worker (
id INT AUTO_INCREMENT PRIMARY KEY,
workerid INT,
name VARCHAR(255) NOT NULL
);

View File

@@ -0,0 +1,172 @@
package hhn.temp.project;
import hhn.temp.project.provider.SimpleDatabaseManager;
import java.sql.SQLException;
import java.util.*;
public class AssignmentManager {
private Map<Integer, Worker> workerMap;
private Map<Integer, Task> taskMap;
private int workerIdCounter;
private int taskIdCounter;
private UserCommands userInterface;
private SimpleDatabaseManager database;
public AssignmentManager() {
database = new SimpleDatabaseManager();
connect();
workerMap = new HashMap<>();
taskMap = new HashMap<>();
workerIdCounter = 1000;
taskIdCounter = 0;
sync();
userInterface = new UserCommands(this);
}
private void connect() {
try {
database.connect();
} catch (SQLException e) {
System.err.println("Failed to connect to database");
}
}
private void sync() {
workerMap.clear();
taskMap.clear();
try {
Collection<Worker> workers = database.getWorkers();
if (workers != null) {
for (Worker worker : workers) {
workerMap.put(worker.getId(),worker);
if (worker.getId() > workerIdCounter) {
workerIdCounter = worker.getId();
}
}
}
Collection<Task> tasks = database.getTasks();
if (tasks != null) {
for (Task task : tasks) {
taskMap.put(task.getTaskId(),task);
if (task.getTaskId() > taskIdCounter) {
taskIdCounter = task.getTaskId();
}
}
}
} catch (SQLException e) {
System.err.println("Failed to sync");
}
}
public Map<Integer, Task> getTaskMap() {
return taskMap;
}
public Map<Integer, Worker> getWorkerMap() {return workerMap;}
public int createWorker(String name) {
sync();
Worker worker = new Worker(name, ++workerIdCounter);
workerMap.put(workerIdCounter, worker);
try {
database.saveWorker(worker);
} catch (SQLException e) {
System.err.println("Failed to save worker");
}
return workerIdCounter;
}
public void removeWorker(int workerId) {
if (!workerMap.containsKey(workerId)) {
throw new IllegalArgumentException("WorkerId must exist in order to remove it");
}
workerMap.remove(workerId);
try {
database.deleteWorker(workerId);
} catch (SQLException e) {
System.err.println("Failed to delete worker");
}
}
public int addTask(int workerId, String name, String description) {
if (!workerMap.containsKey(workerId) || name == null || description == null) {
throw new IllegalArgumentException("WorkerId must exist and name or description can't be null");
}
Task task = new Task(++taskIdCounter, workerId, name, description);
taskMap.put(taskIdCounter, task);
try {
database.saveTask(task);
} catch (SQLException e) {
System.err.println("Failed to save task");
}
return taskIdCounter;
}
public Task getTask(int taskId) {
if (!taskMap.containsKey(taskId)) {
throw new IllegalArgumentException("Task Id does not exist");
}
return taskMap.get(taskId);
}
public Worker getWorker(int workerId) {
if (!workerMap.containsKey(workerId)) {
throw new IllegalArgumentException("Worker Id does not exist");
}
return workerMap.get(workerId);
}
public void editTask(int workerId, int taskId, String name, String description) {
if (!workerMap.containsKey(workerId) || !taskMap.containsKey(taskId)) {
throw new IllegalArgumentException("Task Id or Worker Id does not exist");
}
Task task = taskMap.get(taskId);
task.setName(name);
task.setDescription(description);
try {
database.updateTask(task.getTaskId(),task);
} catch (SQLException e) {
System.err.println("Failed to update Task");
}
}
public void removeTask(int taskId) {
if (!taskMap.containsKey(taskId)) {
throw new IllegalArgumentException("Task Id does not exist");
}
taskMap.remove(taskId);
try {
database.deleteTask(taskId);
} catch (SQLException e) {
System.err.println("Failed to remove task");
}
}
public void finishTask(int workerId, int taskId) {
if (!workerMap.containsKey(workerId) || !taskMap.containsKey(taskId)) {
throw new IllegalArgumentException("Task Id or Worker Id does not exist");
}
Task task = taskMap.get(taskId);
task.setTaskState(TaskState.FINISHED);
try {
database.updateTask(taskId,task);
} catch (SQLException e) {
System.err.println("Failed to finish task");
}
}
public void unfinishTask(int workerId, int taskId) {
if (!workerMap.containsKey(workerId) || !taskMap.containsKey(taskId)) {
throw new IllegalArgumentException("Task Id or Worker Id does not exist");
}
Task task = taskMap.get(taskId);
task.setTaskState(TaskState.IN_PROGRESS);
try {
database.updateTask(taskId,task);
} catch (SQLException e) {
System.err.println("Failed to finish task");
}
}
public UserCommands getUserCommands() {
return userInterface;
}
public void startCLI() {
userInterface.start();
}
public void stopCLI() {
userInterface.stop();
}
}

View File

@@ -1,17 +1,10 @@
package hhn.temp.project;
//TIP To <b>Run</b> code, press <shortcut actionId="Run"/> or
// click the <icon src="AllIcons.Actions.Execute"/> icon in the gutter.
public class Main {
public static void main(String[] args) {
//TIP Press <shortcut actionId="ShowIntentionActions"/> with your caret at the highlighted text
// to see how IntelliJ IDEA suggests fixing it.
System.out.printf("Hello and welcome!");
import java.util.Scanner;
for (int i = 1; i <= 5; i++) {
//TIP Press <shortcut actionId="Debug"/> to start debugging your code. We have set one <icon src="AllIcons.Debugger.Db_set_breakpoint"/> breakpoint
// for you, but you can always add more by pressing <shortcut actionId="ToggleLineBreakpoint"/>.
System.out.println("i = " + i);
public class Main {
public static void main(String[] args) {
AssignmentManager manager = new AssignmentManager();
manager.startCLI();
}
}
}

View File

@@ -0,0 +1,42 @@
package hhn.temp.project;
public class Task {
private String name;
private String description;
private int taskId;
private int workerId;
private TaskState state;
public Task(int taskId, int workerId, String name, String description) {
this.name = name;
this.description = description;
this.taskId = taskId;
this.workerId = workerId;
this.state = TaskState.IN_PROGRESS;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getDescription() {
return description;
}
public void setDescription(String description) {
this.description = description;
}
public int getTaskId() {
return taskId;
}
public int getWorkerId() {
return workerId;
}
public void setTaskState(TaskState state) {
this.state = state;
}
public TaskState getTaskState() {
return state;
}
}

View File

@@ -0,0 +1,6 @@
package hhn.temp.project;
public enum TaskState {
IN_PROGRESS,
FINISHED;
}

View File

@@ -0,0 +1,444 @@
package hhn.temp.project;
import java.util.Scanner;
import java.util.concurrent.atomic.AtomicBoolean;
public class UserCommands implements Runnable {
private Scanner scanner;
private AssignmentManager manager;
private Integer selectedTaskId = null;
private Integer selectedWorkerId = null;
private AtomicBoolean running = new AtomicBoolean(false);
private Thread cliThread;
private enum InputState {
MAIN_MENU,
TASK_SELECTED,
WORKER_SELECTED,
AWAITING_EDIT_INPUT,
AWAITING_CREATE_TASK_WORKER,
AWAITING_CREATE_TASK_NAME,
AWAITING_CREATE_TASK_DESC,
AWAITING_CREATE_WORKER_NAME,
AWAITING_TASK_SELECTION
}
private InputState currentState = InputState.MAIN_MENU;
private Integer tempWorkerId = null;
private String tempTaskName = null;
public UserCommands(AssignmentManager manager) {
this.manager = manager;
}
@Override
public void run() {
scanner = new Scanner(System.in);
running.set(true);
while (running.get()) {
printPrompt();
String input = scanner.nextLine().trim();
if ("exit".equalsIgnoreCase(input)) {
stop();
continue;
}
handleInput(input);
}
scanner.close();
}
public void start() {
if (cliThread == null || !cliThread.isAlive()) {
cliThread = new Thread(this, "CLI-Thread");
cliThread.start();
}
}
public void stop() {
running.set(false);
if (cliThread != null) {
cliThread.interrupt();
}
}
private void printPrompt() {
if (!running.get()) return;
switch (currentState) {
case MAIN_MENU:
System.out.println("Type '?' or 'help' for a list of commands");
break;
case TASK_SELECTED:
System.out.println("Task " + selectedTaskId + " selected. Commands: finish, unfinish, remove, edit, back");
break;
case WORKER_SELECTED:
if (selectedWorkerId != null) {
System.out.println("Worker " + selectedWorkerId + " selected. Commands: remove, back");
} else {
System.out.println("Enter worker ID to select (or 'back'):");
}
break;
case AWAITING_EDIT_INPUT:
System.out.println("Enter new name;description:");
break;
case AWAITING_CREATE_WORKER_NAME:
System.out.println("Enter worker name:");
break;
case AWAITING_CREATE_TASK_WORKER:
System.out.println("Enter worker ID:");
break;
case AWAITING_CREATE_TASK_NAME:
System.out.println("Enter task name:");
break;
case AWAITING_CREATE_TASK_DESC:
System.out.println("Enter task description:");
break;
}
System.out.print("> ");
}
public void handleInput(String input) {
if (input == null || input.isEmpty()) {
return;
}
if ("?".equals(input) || "help".equalsIgnoreCase(input)) {
showHelp();
return;
}
try {
switch (currentState) {
case MAIN_MENU:
handleMainMenuInput(input);
break;
case TASK_SELECTED:
handleTaskSelectionInput(input);
break;
case WORKER_SELECTED:
handleWorkerSelectionInput(input);
break;
case AWAITING_EDIT_INPUT:
handleEditInput(input);
break;
case AWAITING_CREATE_TASK_WORKER:
handleCreateTaskWorkerInput(input);
break;
case AWAITING_CREATE_TASK_NAME:
handleCreateTaskNameInput(input);
break;
case AWAITING_CREATE_TASK_DESC:
handleCreateTaskDescInput(input);
break;
case AWAITING_CREATE_WORKER_NAME:
handleCreateWorkerNameInput(input);
break;
case AWAITING_TASK_SELECTION:
handleTaskIdInput(input);
break;
}
} catch (Exception e) {
System.out.println("Error: " + e.getMessage());
resetToMainMenu();
}
}
private void showHelp() {
System.out.println("=== Available Commands ===");
System.out.println("General:");
System.out.println(" help, ? - Show this help");
System.out.println(" exit - Exit the program");
System.out.println(" createworker - Create a new worker");
System.out.println(" createtask - Create a new task");
System.out.println(" selecttask - Select a task to work with");
System.out.println(" listworkers - List all workers");
System.out.println(" listtasks - List all tasks with status");
System.out.println(" listfinished - List only finished tasks");
System.out.println(" listunfinished - List only unfinished tasks");
System.out.println("\nWhen a task is selected:");
System.out.println(" finish - Mark task as finished");
System.out.println(" unfinish - Mark task as unfinished");
System.out.println(" remove - Remove the task");
System.out.println(" edit - Edit task name and description");
System.out.println(" back - Return to main menu");
System.out.println("\nWhen a worker is selected:");
System.out.println(" remove - Remove the worker");
System.out.println(" back - Return to main menu");
}
private void handleMainMenuInput(String input) {
switch (input.toLowerCase()) {
case "createworker":
System.out.println("Enter worker name:");
currentState = InputState.AWAITING_CREATE_WORKER_NAME;
break;
case "createtask":
System.out.println("Enter worker ID:");
currentState = InputState.AWAITING_CREATE_TASK_WORKER;
break;
case "selecttask":
System.out.println("Enter task ID:");
currentState = InputState.AWAITING_TASK_SELECTION;
break;
case "listworkers":
listWorkers();
break;
case "listtasks":
listAllTasks();
break;
case "listfinished":
listTasksByStatus(TaskState.FINISHED);
break;
case "listunfinished":
listTasksByStatus(TaskState.IN_PROGRESS);
break;
default:
System.out.println("Unknown command. Type 'help' for available commands.");
}
}
private void listWorkers() {
System.out.println("\nAvailable workers:");
if (manager.getWorkerMap().isEmpty()) {
System.out.println(" No workers found.");
} else {
for (Worker w : manager.getWorkerMap().values()) {
System.out.println(" " + w.getId() + ": " + w.getName());
}
}
System.out.println();
}
private void listAllTasks() {
System.out.println("\nAll tasks:");
if (manager.getTaskMap().isEmpty()) {
System.out.println(" No tasks found.");
} else {
for (Task task : manager.getTaskMap().values()) {
Worker worker = manager.getWorker(task.getWorkerId());
String status = task.getTaskState() == TaskState.FINISHED ? "[FINISHED]" : "[IN PROGRESS]";
System.out.println(String.format(" %d: %s - %s (Worker: %d - %s)",
task.getTaskId(), status, task.getName(),
worker.getId(), worker.getName()));
}
}
System.out.println();
}
private void listTasksByStatus(TaskState status) {
System.out.println("\nTasks with status: " + status);
boolean found = false;
for (Task task : manager.getTaskMap().values()) {
if (task.getTaskState() == status) {
Worker worker = manager.getWorker(task.getWorkerId());
System.out.println(String.format(" %d: %s (Worker: %d - %s)",
task.getTaskId(), task.getName(),
worker.getId(), worker.getName()));
found = true;
}
}
if (!found) {
System.out.println(" No tasks found with this status.");
}
System.out.println();
}
private void handleWorkerSelectionInput(String input) {
if ("back".equalsIgnoreCase(input)) {
resetToMainMenu();
return;
}
try {
int workerId = Integer.parseInt(input.trim());
Worker worker = manager.getWorker(workerId);
if (worker != null) {
selectedWorkerId = workerId;
System.out.println("Worker " + workerId + " (" + worker.getName() + ") selected");
System.out.println("Commands: remove, back");
} else {
System.out.println("Worker not found. Please enter a valid worker ID:");
}
} catch (NumberFormatException e) {
if (selectedWorkerId != null) {
handleWorkerCommand(input);
} else {
System.out.println("Invalid input. Please enter a worker ID or 'back':");
}
}
}
private void handleWorkerCommand(String input) {
switch (input.toLowerCase()) {
case "remove":
manager.removeWorker(selectedWorkerId);
System.out.println("Worker removed");
resetToMainMenu();
break;
case "back":
resetToMainMenu();
break;
default:
System.out.println("Unknown command. Available commands: remove, back");
}
}
private void handleCreateWorkerNameInput(String input) {
int workerId = manager.createWorker(input.trim());
System.out.println("Created worker with ID: " + workerId);
resetToMainMenu();
}
private void handleTaskIdInput(String input) {
if ("back".equalsIgnoreCase(input)) {
resetToMainMenu();
return;
}
try {
int taskId = Integer.parseInt(input.trim());
Task task = manager.getTask(taskId);
if (task != null) {
selectedTaskId = taskId;
currentState = InputState.TASK_SELECTED;
System.out.println("Task " + taskId + " (" + task.getName() + ") selected");
System.out.println("Commands: finish, unfinish, remove, edit, back");
} else {
System.out.println("Task not found. Please enter a valid task ID:");
}
} catch (NumberFormatException e) {
System.out.println("Invalid input. Please enter a task ID or 'back':");
}
}
private void handleCreateTaskWorkerInput(String input) {
try {
tempWorkerId = Integer.parseInt(input.trim());
System.out.println("Enter task name:");
currentState = InputState.AWAITING_CREATE_TASK_NAME;
} catch (NumberFormatException e) {
System.out.println("Invalid worker ID. Please enter a number:");
}
}
private void handleCreateTaskNameInput(String input) {
tempTaskName = input.trim();
System.out.println("Enter task description:");
currentState = InputState.AWAITING_CREATE_TASK_DESC;
}
private void handleCreateTaskDescInput(String input) {
int taskId = manager.addTask(tempWorkerId, tempTaskName, input.trim());
System.out.println("Created task with ID: " + taskId);
resetToMainMenu();
}
private void resetToMainMenu() {
currentState = InputState.MAIN_MENU;
selectedTaskId = null;
selectedWorkerId = null;
tempWorkerId = null;
tempTaskName = null;
}
private void handleTaskSelectionInput(String input) {
if ("back".equalsIgnoreCase(input)) {
resetToMainMenu();
return;
}
try {
int taskId = Integer.parseInt(input.trim());
Task task = manager.getTask(taskId);
if (task != null) {
selectedTaskId = taskId;
currentState = InputState.TASK_SELECTED;
System.out.println("Task " + taskId + " (" + task.getName() + ") selected");
System.out.println("Commands: finish, unfinish, remove, edit, back");
} else {
System.out.println("Task not found. Please enter a valid task ID:");
}
} catch (NumberFormatException e) {
if (selectedTaskId != null) {
handleTaskCommand(input);
} else {
System.out.println("Invalid input. Please enter a task ID or 'back':");
}
}
}
private void handleTaskCommand(String input) {
switch (input.toLowerCase()) {
case "finish":
manager.finishTask(manager.getTask(selectedTaskId).getWorkerId(),selectedTaskId);
System.out.println("Task marked as finished");
break;
case "unfinish":
manager.unfinishTask(manager.getTask(selectedTaskId).getWorkerId(),selectedTaskId);
System.out.println("Task marked as unfinished");
break;
case "remove":
manager.removeTask(selectedTaskId);
System.out.println("Task removed");
resetToMainMenu();
break;
case "edit":
System.out.println("Enter new name;description:");
currentState = InputState.AWAITING_EDIT_INPUT;
break;
case "back":
resetToMainMenu();
break;
default:
System.out.println("Unknown command. Type 'help' for available commands.");
}
}
private void handleEditInput(String input) {
String[] parts = input.split(";", 2);
if (parts.length == 2) {
manager.editTask(manager.getTask(selectedTaskId).getWorkerId(), selectedTaskId, parts[0], parts[1]);
System.out.println("Task edited");
} else {
System.out.println("Invalid format. Use: name;description");
System.out.println("Please try again:");
return;
}
currentState = InputState.TASK_SELECTED;
}
public Scanner getScanner() {
return scanner;
}
//only for testing
public void setScanner(Scanner scanner) {
this.scanner = scanner;
}
//only for testing
public boolean isRunning() {
return running.get();
}
}

View File

@@ -0,0 +1,17 @@
package hhn.temp.project;
public class Worker {
private String name;
private int workerId;
public Worker(String name, int workerId) {
this.name = name;
this.workerId = workerId;
}
public String getName() {
return name;
}
public int getId() {
return workerId;
}
}

View File

@@ -0,0 +1,29 @@
package hhn.temp.project.provider;
import java.io.IOException;
import java.nio.file.Path;
import java.sql.SQLException;
/**
* A database interface with basic database connectivity
* @author Riley Schneider
*/
public interface Database {
/**
* Creates a connection to the database
* @throws SQLException Thrown if database error occurs
*/
void connect() throws SQLException;
/**
* Closes a connection to the database
* @throws SQLException Thrown if database error occurs
*/
void close() throws SQLException;
/**
* Clears the entire tables in the database and reset primary key counter to each table
* @throws SQLException Thrown if database error occurs
*/
void clearDatabase() throws SQLException;
}

View File

@@ -0,0 +1,115 @@
package hhn.temp.project.provider;
import hhn.temp.project.Task;
import hhn.temp.project.Worker;
import java.sql.SQLException;
import java.util.Collection;
/**
* Simple Database Manager to handle simple command such as insertion, deletion, updating of Task and Worker objects.
* @author Riley Schneider
*/
public interface DatabaseManager extends Database {
/**
* Saves a Task object into the database
* @param task Task to be saved into the database
* @throws SQLException Thrown if database error occurs
*/
void saveTask(Task task) throws SQLException;
/**
* Saves a collection of Task objects into the database
* @param tasks Tasks to be saved into the database
* @throws SQLException Thrown if database error occurs
*/
void saveTasks(Collection<Task> tasks) throws SQLException;
/**
* Saves a Worker object into the database
* @param worker Worker to be saved into the database
* @throws SQLException Thrown if database error occurs
*/
void saveWorker(Worker worker) throws SQLException;
/**
* Saves a collection Worker objects into the database
* @param workers Workers to be saved into the database
* @throws SQLException Thrown if database error occurs
*/
void saveWorkers(Collection<Worker> workers) throws SQLException;
/**
* Updates a Task object that already exists in the database
* @param taskId The ID of the given task
* @param newTaskObject The new Task object that will overwrite the existent task on database
* @throws SQLException Thrown if database error occurs
*/
void updateTask(int taskId, Task newTaskObject) throws SQLException;
/**
* Updates a Worker object that already exists in the database
* @param workerId The ID of the given worker
* @param newWorkerObject The new Worker object that will overwrite the existent task on database
* @throws SQLException Thrown if database error occurs
*/
void updateWorker(int workerId, Worker newWorkerObject) throws SQLException;
/**
* Deletes a task from the database
* @param taskId The ID of the given task that needs to be deleted
* @throws SQLException Thrown if database error occurs
*/
void deleteTask(int taskId) throws SQLException;
/**
* Deletes a worker from the database
* @param workerId The ID of the given worker that needs to be deleted
* @throws SQLException Thrown if database error occurs
*/
void deleteWorker(int workerId) throws SQLException;
/**
* Gets a collection of all tasks available in the database
* @return A collection of tasks (empty if no task available)
* @throws SQLException Thrown if database error occurs
*/
Collection<Task> getTasks() throws SQLException;
/**
* Gets a collection of all workers available in the database
* @return A collection of workers (empty if no task available)
* @throws SQLException Thrown if database error occurs
*/
Collection<Worker> getWorkers() throws SQLException;
/**
* Gets a task given by its ID from the database
* @param taskId The task ID
* @return A task from the database (NULL if no task found)
* @throws SQLException Thrown if database error occurs
*/
Task getTaskByTaskId(int taskId) throws SQLException;
/**
* Gets a worker given by its ID from the database
* @param workerId The worker ID
* @return A worker from the database (NULL if no worker found)
* @throws SQLException Thrown if database error occurs
*/
Worker getWorkerByWorkerId(int workerId) throws SQLException;
/**
* Gets the total number of available tasks in the database.
* @return The total number of tasks (0 = zero entries; -1 = error)
* @throws SQLException Thrown if database error occurs
*/
int getTotalNumberOfTasks() throws SQLException;
/**
* Gets the total number of available workers in the database.
* @return The total number of workers (0 = zero entries; -1 = error)
* @throws SQLException Thrown if database error occurs
*/
int getTotalNumberOfWorkers() throws SQLException;
}

View File

@@ -0,0 +1,403 @@
package hhn.temp.project.provider;
import hhn.temp.project.Task;
import hhn.temp.project.TaskState;
import hhn.temp.project.Worker;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.sql.*;
import java.util.*;
public class SimpleDatabaseManager implements DatabaseManager {
private Connection connection;
private final static Path INSERT_TASK = Path.of("resources/sql/InsertTaskTable.sql");
private final static Path DELETE_TASK = Path.of("resources/sql/DeleteTaskTable.sql");
private final static Path SELECT_TASK = Path.of("resources/sql/SelectTaskTable.sql");
private final static Path UPDATE_TASK = Path.of("resources/sql/UpdateTaskTable.sql");
private final static Path COUNT_ALL_TASK = Path.of("resources/sql/CountAllFieldsTask.sql");
private final static Path SELECT_ALL_TASK = Path.of("resources/sql/SelectAllTask.sql");
private final static Path SELECT_TASK_BY_ID = Path.of("resources/sql/SelectTaskById.sql");
private final static Path INSERT_WORKER = Path.of("resources/sql/InsertWorkerTable.sql");
private final static Path DELETE_WORKER = Path.of("resources/sql/DeleteWorkerTable.sql");
private final static Path SELECT_WORKER = Path.of("resources/sql/SelectWorkerTable.sql");
private final static Path UPDATE_WORKER = Path.of("resources/sql/UpdateWorkerTable.sql");
private final static Path COUNT_ALL_WORKER = Path.of("resources/sql/CountAllFieldsWorker.sql");
private final static Path SELECT_ALL_WORKER = Path.of("resources/sql/SelectAllWorker.sql");
private final static Path SELECT_WORKER_BY_ID = Path.of("resources/sql/SelectWorkerById.sql");
public enum QueryMode {
INSERT_TASK,
SELECT_TASK,
UPDATE_TASK,
DELETE_TASK,
SELECT_ALL_TASK,
SELECT_TASK_BY_ID,
COUNT_ALL_TASK,
INSERT_WORKER,
SELECT_WORKER,
UPDATE_WORKER,
DELETE_WORKER,
COUNT_ALL_WORKER,
SELECT_ALL_WORKER,
SELECT_WORKER_BY_ID,
}
private String loadFile(QueryMode queryMode) throws IOException {
switch (queryMode) {
case INSERT_TASK -> {
return Files.readString(INSERT_TASK);
}
case SELECT_TASK -> {
return Files.readString(SELECT_TASK);
}
case DELETE_TASK -> {
return Files.readString(DELETE_TASK);
}
case UPDATE_TASK -> {
return Files.readString(UPDATE_TASK);
}
case COUNT_ALL_TASK -> {
return Files.readString(COUNT_ALL_TASK);
}
case SELECT_ALL_TASK -> {
return Files.readString(SELECT_ALL_TASK);
}
case SELECT_TASK_BY_ID -> {
return Files.readString(SELECT_TASK_BY_ID);
}
case INSERT_WORKER -> {
return Files.readString(INSERT_WORKER);
}
case SELECT_WORKER -> {
return Files.readString(SELECT_WORKER);
}
case DELETE_WORKER -> {
return Files.readString(DELETE_WORKER);
}
case UPDATE_WORKER -> {
return Files.readString(UPDATE_WORKER);
}
case COUNT_ALL_WORKER -> {
return Files.readString(COUNT_ALL_WORKER);
}
case SELECT_ALL_WORKER -> {
return Files.readString(SELECT_ALL_WORKER);
}
case SELECT_WORKER_BY_ID -> {
return Files.readString(SELECT_WORKER_BY_ID);
}
default -> {
return "";
}
}
}
private TaskState integerToTaskState(final int in) {
return in == 1 ? TaskState.FINISHED : TaskState.IN_PROGRESS;
}
private int taskStateToInteger(final TaskState taskState) {
return taskState == TaskState.FINISHED ? 1 : 0;
}
@Override
public void saveTask(final Task task) throws SQLException {
String query;
try {
query = loadFile(QueryMode.INSERT_TASK);
} catch (IOException e) {
e.printStackTrace();
return;
}
try (PreparedStatement preparedStatement = connection.prepareStatement(query);) {
preparedStatement.setInt(1, task.getTaskId());
preparedStatement.setString(2, task.getName());
preparedStatement.setString(3, task.getDescription());
preparedStatement.setInt(4, task.getWorkerId());
preparedStatement.setInt(5, taskStateToInteger(task.getTaskState()));
preparedStatement.execute();
}
}
@Override
public void saveTasks(final Collection<Task> tasks) throws SQLException {
for (Task task : tasks) {
saveTask(task);
}
}
@Override
public void saveWorker(final Worker worker) throws SQLException {
String query;
try {
query = loadFile(QueryMode.INSERT_WORKER);
} catch (IOException e) {
e.printStackTrace();
return;
}
try (PreparedStatement preparedStatement = connection.prepareStatement(query);) {
preparedStatement.setInt(1, worker.getId());
preparedStatement.setString(2, worker.getName());
preparedStatement.execute();
}
}
@Override
public void saveWorkers(final Collection<Worker> workers) throws SQLException {
for (Worker worker : workers) {
saveWorker(worker);
}
}
@Override
public void updateTask(final int taskId, final Task newTaskObject) throws SQLException {
String query;
try {
query = loadFile(QueryMode.UPDATE_TASK);
} catch (IOException e) {
e.printStackTrace();
return;
}
try (PreparedStatement preparedStatement = connection.prepareStatement(query);) {
preparedStatement.setString(1, newTaskObject.getName());
preparedStatement.setString(2, newTaskObject.getDescription());
preparedStatement.setInt(3, taskStateToInteger(newTaskObject.getTaskState()));
preparedStatement.setInt(4, taskId);
preparedStatement.execute();
}
}
@Override
public void updateWorker(final int workerId, final Worker newWorkerObject) throws SQLException {
String query;
try {
query = loadFile(QueryMode.UPDATE_WORKER);
} catch (IOException e) {
e.printStackTrace();
return;
}
try (PreparedStatement preparedStatement = connection.prepareStatement(query);) {
preparedStatement.setInt(1, newWorkerObject.getId());
preparedStatement.setString(2, newWorkerObject.getName());
preparedStatement.setInt(3, workerId);
preparedStatement.execute();
}
}
@Override
public void deleteTask(final int taskId) throws SQLException {
String query;
try {
query = loadFile(QueryMode.DELETE_TASK);
} catch (IOException e) {
e.printStackTrace();
return;
}
try (PreparedStatement preparedStatement = connection.prepareStatement(query);) {
preparedStatement.setInt(1, taskId);
preparedStatement.execute();
}
}
@Override
public void deleteWorker(final int workerId) throws SQLException {
String query;
try {
query = loadFile(QueryMode.DELETE_WORKER);
} catch (IOException e) {
e.printStackTrace();
return;
}
try (PreparedStatement preparedStatement = connection.prepareStatement(query);) {
preparedStatement.setInt(1, workerId);
preparedStatement.execute();
}
}
@Override
public Collection<Task> getTasks() throws SQLException {
String query;
try {
query = loadFile(QueryMode.SELECT_ALL_TASK);
} catch (IOException e) {
e.printStackTrace();
return null;
}
Collection<Task> tasks = new ArrayList<>();
try (Statement statement = connection.createStatement();
ResultSet rs = statement.executeQuery(query);) {
while (rs.next()) {
int taskId = rs.getInt("taskid");
String name = rs.getString("name");
String description = rs.getString("description");
int workerId = rs.getInt("workerid");
TaskState taskState = integerToTaskState(rs.getInt("taskstate"));
Task task = new Task(taskId, workerId, name, description);
task.setTaskState(taskState);
tasks.add(task);
}
}
return tasks;
}
@Override
public Collection<Worker> getWorkers() throws SQLException {
String query;
try {
query = loadFile(QueryMode.SELECT_ALL_WORKER);
} catch (IOException e) {
e.printStackTrace();
return null;
}
Collection<Worker> workers = new ArrayList<>();
try (Statement statement = connection.createStatement();
ResultSet rs = statement.executeQuery(query);) {
while (rs.next()) {
int workerId = rs.getInt("workerid");
String name = rs.getString("name");
Worker worker = new Worker(name, workerId);
workers.add(worker);
}
}
return workers;
}
@Override
public Task getTaskByTaskId(final int taskId) throws SQLException {
String query;
try {
query = loadFile(QueryMode.SELECT_TASK_BY_ID);
} catch (IOException e) {
e.printStackTrace();
return null;
}
try (PreparedStatement statement = connection.prepareStatement(query);) {
statement.setInt(1, taskId);
ResultSet rs = statement.executeQuery();
while (rs.next()) {
int taskId1 = rs.getInt("taskid");
String name = rs.getString("name");
String description = rs.getString("description");
int workerId = rs.getInt("workerid");
TaskState taskState = integerToTaskState(rs.getInt("taskstate"));
Task task = new Task(taskId1, workerId, name, description);
task.setTaskState(taskState);
return task;
}
}
return null;
}
@Override
public Worker getWorkerByWorkerId(final int workerId) throws SQLException {
String query;
try {
query = loadFile(QueryMode.SELECT_WORKER_BY_ID);
} catch (IOException e) {
e.printStackTrace();
return null;
}
try (PreparedStatement statement = connection.prepareStatement(query);) {
statement.setInt(1, workerId);
ResultSet rs = statement.executeQuery();
while (rs.next()) {
int workerId1 = rs.getInt("workerid");
String name = rs.getString("name");
Worker worker = new Worker(name, workerId1);
return worker;
}
}
return null;
}
@Override
public int getTotalNumberOfTasks() throws SQLException {
String query = "";
try {
query = loadFile(QueryMode.COUNT_ALL_TASK);
} catch (IOException e) {
e.printStackTrace();
return -1;
}
try (Statement statement = connection.createStatement();
ResultSet rs = statement.executeQuery(query);) {
if (rs.next()) {
return rs.getInt("total");
}
}
return 0;
}
@Override
public int getTotalNumberOfWorkers() throws SQLException {
String query = "";
try {
query = loadFile(QueryMode.COUNT_ALL_WORKER);
} catch (IOException e) {
e.printStackTrace();
return -1;
}
try (Statement statement = connection.createStatement();
ResultSet rs = statement.executeQuery(query);) {
if (rs.next()) {
return rs.getInt("total");
}
}
return 0;
}
public void clearDatabase() throws SQLException {
try (Statement statement = connection.createStatement()) {
statement.execute("TRUNCATE TABLE Task");
statement.execute("TRUNCATE TABLE Worker");
}
}
@Override
public void connect() throws SQLException {
connection = DriverManager.getConnection("jdbc:mysql://localhost:3306/sql7810540?user=sql7810540&password=mXdJCFtDZz");
}
@Override
public void close() throws SQLException {
connection.close();
}
}

View File

@@ -0,0 +1,78 @@
package hhn.temp.project;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.DisplayName;
import org.junit.jupiter.api.Test;
import static org.junit.jupiter.api.Assertions.*;
public class BadCasesTest {
AssignmentManager manager;
@BeforeEach
public void setup() {
manager = new AssignmentManager();
}
@Test
@DisplayName("Assert that added tasks can't be Null")
public void assertNewTasksAreNotNull() {
int workerId = manager.createWorker("Alfred");
assertThrows(IllegalArgumentException.class, () -> manager.addTask(workerId, null, null));
manager.removeWorker(workerId);
}
@Test
@DisplayName("Assert List isn't empty after adding a task")
public void assertListNowEmptyAfterAdd() {
int workerId = manager.createWorker("Alfred");
int taskId = manager.addTask(workerId, "Run", "Jog 10 Miles");
assertFalse(manager.getTaskMap().isEmpty());
manager.removeWorker(workerId);
manager.removeTask(taskId);
}
@Test
@DisplayName("Assert only existing tasks can be edited")
public void assertEditOnlyExistingTasks() {
int workerId = manager.createWorker("Alfred");
assertThrows(IllegalArgumentException.class, () -> manager.editTask(workerId, 99969, "I", "am Illegal"));
assertThrows(IllegalArgumentException.class, () -> manager.editTask(22200, 99969, "I", "am Illegal"));
manager.removeWorker(workerId);
}
@Test
@DisplayName("Assert Add Task is programmed defensively")
public void assertAddTaskOnlyAcceptsValidParameters() {
int workerId = manager.createWorker("Alfred");
assertThrows(IllegalArgumentException.class, () -> manager.addTask( 20203,"I", "am Illegal"));
assertThrows(IllegalArgumentException.class, () -> manager.addTask( workerId,null, null));
manager.removeWorker(workerId);
}
@Test
@DisplayName("Assert that Remove Task is programmed defensively")
public void assertRemoveTaskOnlyAcceptsValidParameters() {
assertThrows(IllegalArgumentException.class, () -> manager.removeTask(20320));
}
@Test
@DisplayName("Assert that un-/finishing a Task only works with valid parameters")
public void assertTaskStateChangesOnlyAcceptsValidParameters() {
assertThrows(IllegalArgumentException.class, () -> manager.finishTask(20405, 21034));
assertThrows(IllegalArgumentException.class, () -> manager.unfinishTask(20405, 21034));
}
@Test
@DisplayName("Assert that removing a non-existent worker throws an Exception")
public void assertRemovingNonExistentWorkerFails() {
assertThrows(IllegalArgumentException.class, () -> manager.removeWorker(34054));
}
@Test
@DisplayName("Assert non-existent commands are recognized as such")
public void assertInvalidCommandsDontCrash() {
int workerId = manager.createWorker("Alfred");
int taskId = manager.addTask(workerId, "Run", "Jog 10 Miles");
try {
manager.getUserCommands().handleInput("baum");
} catch (Exception e) {
fail("Should not crash just because a command is invalid");
}
manager.removeWorker(workerId);
manager.removeTask(taskId);
}
}

View File

@@ -0,0 +1,42 @@
package hhn.temp.project;
import hhn.temp.project.provider.DatabaseManager;
import hhn.temp.project.provider.SimpleDatabaseManager;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.DisplayName;
import org.junit.jupiter.api.Test;
import java.sql.SQLException;
public class DatabaseBadCasesTest {
private DatabaseManager databaseManager;
@BeforeEach
public void setup() throws SQLException {
databaseManager = new SimpleDatabaseManager();
databaseManager.connect();
databaseManager.clearDatabase();
}
@Test
@DisplayName("Inserting Tasks with the same ID")
public void insertTasksWithTheSameId() throws SQLException {
Task task = new Task(10, 10, "ABC", "XYZ");
Task taskFaker = new Task(10, 5, "ABC!", "XYZ!");
databaseManager.saveTask(task);
databaseManager.saveTask(taskFaker);
}
@Test
@DisplayName("Inserting Workers with the same ID")
public void insertWorkersWithTheSameId() throws SQLException {
Worker worker = new Worker("Worker-1", 1);
Worker workerFaker = new Worker("Worker-100", 1);
databaseManager.saveWorker(worker);
databaseManager.saveWorker(workerFaker);
}
}

View File

@@ -0,0 +1,83 @@
package hhn.temp.project;
import hhn.temp.project.provider.SimpleDatabaseManager;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.DisplayName;
import org.junit.jupiter.api.Test;
import static org.junit.jupiter.api.Assertions.*;
import java.sql.SQLException;
import java.util.Collection;
import java.util.List;
public class DatabaseGoodCasesTest {
private SimpleDatabaseManager databaseManager;
@BeforeEach
public void setup() throws SQLException {
databaseManager = new SimpleDatabaseManager();
databaseManager.connect();
databaseManager.clearDatabase();
}
@Test
@DisplayName("Inserting test task into the database and receiving back the same test task")
public void insertTaskAndReceiveItBackTest() throws SQLException {
Task task = new Task(123, 10, "Hello World", "Doing Something, hell yeah!");
databaseManager.saveTask(task);
Task reTask = databaseManager.getTaskByTaskId(task.getTaskId());
assertNotNull(reTask);
assertEquals(task.getTaskId(), reTask.getTaskId());
assertEquals(task.getDescription(), reTask.getDescription());
assertEquals(task.getName(), reTask.getName());
assertEquals(task.getWorkerId(), reTask.getWorkerId());
assertEquals(1, databaseManager.getTotalNumberOfTasks());
}
@Test
@DisplayName("Inserting test worker into the database and receiving back the same test worker")
public void insertWorkerAndReceivedItBackTest() throws SQLException {
Worker worker = new Worker("Worker-01", 12345678);
databaseManager.saveWorker(worker);
Worker reWorker = databaseManager.getWorkerByWorkerId(worker.getId());
assertNotNull(reWorker);
assertEquals(worker.getId(), reWorker.getId());
assertEquals(worker.getName(), reWorker.getName());
}
@Test
@DisplayName("Clearing the database (Task and Worker) test")
public void clearDatabaseTest() throws SQLException, InterruptedException {
Task task1 = new Task(10, 5, "Hello", "World");
Task task2 = new Task(9, 4, "Hochschule", "Heilbronn");
Task task3 = new Task(8, 9, "Gangnam", "Style");
Collection<Task> tasks = List.of(task1, task2, task3);
Worker worker1 = new Worker("ABC", 2);
Worker worker2 = new Worker("XYZ", 9);
Collection<Worker> workers = List.of(worker1, worker2);
databaseManager.saveTasks(tasks);
databaseManager.saveWorkers(workers);
Thread.sleep(500);
assertEquals(tasks.size(), databaseManager.getTotalNumberOfTasks());
assertEquals(workers.size(), databaseManager.getTotalNumberOfWorkers());
databaseManager.clearDatabase();
assertEquals(0, databaseManager.getTotalNumberOfTasks());
assertEquals(0, databaseManager.getTotalNumberOfWorkers());
}
}

View File

@@ -0,0 +1,172 @@
package hhn.temp.project;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.DisplayName;
import org.junit.jupiter.api.Test;
import java.util.Scanner;
import static org.junit.jupiter.api.Assertions.*;
public class GoodCasesTest {
AssignmentManager manager;
@BeforeEach
public void setup() {
manager = new AssignmentManager();
}
@Test
@DisplayName("Assert that a Worker can add a Task")
public void assertWorkerCanAddTask() {
int workerId = manager.createWorker("Alfred");
int taskId = manager.addTask(workerId, "Run", "Jog 10 Miles");
assertNotNull(manager.getTask(taskId));
assertEquals("Run", manager.getTask(taskId).getName());
manager.removeWorker(workerId);
manager.removeTask(taskId);
}
@Test
@DisplayName("Assert that added Tasks are added to the List")
public void assertTasksShowInList() {
int sizeCount = manager.getTaskMap().size();
int workerId = manager.createWorker("Alfred");
int taskId = manager.addTask(workerId, "Run", "Jog 10 Miles");
assertEquals(sizeCount + 1, manager.getTaskMap().size());
manager.removeWorker(workerId);
manager.removeTask(taskId);
}
@Test
@DisplayName("Assert existing Tasks can be edited")
public void assertExistingTasksCanBeEdited() {
int workerId = manager.createWorker("Alfred");
int taskId = manager.addTask(workerId, "Run", "Jog 10 Miles");
manager.editTask(workerId, taskId, "Walk", "Walk 3 Miles");
assertEquals("Walk", manager.getTask(taskId).getName());
assertEquals("Walk 3 Miles", manager.getTask(taskId).getDescription());
manager.removeWorker(workerId);
manager.removeTask(taskId);
}
@Test
@DisplayName("Assert that Worker can remove Task")
public void assertWorkerCanRemoveOwnTask() {
int sizeCount = manager.getTaskMap().size();
int workerId = manager.createWorker("Alfred");
int taskId = manager.addTask(workerId, "Run", "Jog 10 Miles");
assertEquals(sizeCount + 1, manager.getTaskMap().size());
manager.removeTask(taskId);
assertEquals(sizeCount, manager.getTaskMap().size());
manager.removeWorker(workerId);
}
@Test
@DisplayName("Assert deleted Tasks no longer show up in the List")
public void assertDeletedTasksDisappear() {
int workerId = manager.createWorker("Alfred");
int taskId = manager.addTask(workerId, "Run", "Jog 10 Miles");
manager.removeTask(taskId);
assertThrows(IllegalArgumentException.class, () -> manager.getTask(taskId));
manager.removeWorker(workerId);
}
@Test
@DisplayName("Check Getters")
public void assertGettersWorkCorrectly() {
int workerId = manager.createWorker("Alfred");
int taskId = manager.addTask(workerId, "Run", "Jog 10 Miles");
assertEquals("Alfred", manager.getWorkerMap().get(workerId).getName());
//This one may be somewhat nonsensical, but it ensures the getId works so one may iterate over the workerMap
assertEquals(manager.getWorkerMap().get(workerId).getId(), workerId);
assertEquals(manager.getTask(taskId).getTaskId(), taskId);
assertEquals(manager.getTask(taskId).getWorkerId(), workerId);
manager.removeWorker(workerId);
manager.removeTask(taskId);
}
@Test
@DisplayName("Assert that Task State is actually changed when submitted as finished")
public void assertTaskStateChanges() {
int workerId = manager.createWorker("Alfred");
int taskId = manager.addTask(workerId, "Run", "Jog 10 Miles");
manager.finishTask(workerId, taskId);
assertSame(TaskState.FINISHED, manager.getTask(taskId).getTaskState());
manager.unfinishTask(workerId, taskId);
assertSame(TaskState.IN_PROGRESS, manager.getTask(taskId).getTaskState());
manager.removeWorker(workerId);
manager.removeTask(taskId);
}
@Test
@DisplayName("Assert that the Scanner is actually started when AM calls start")
public void assertScannerExists() {
try {
Scanner scanner = manager.getUserCommands().getScanner();
} catch (Exception e) {
fail("Scanner does not exists or can't be gotten by getScanner()");
}
}
@Test
@DisplayName("Check that every required surface command actually works")
public void assertCommandsAreRecognized() {
assertDoesNotThrow(() -> manager.getUserCommands().handleInput("?"));
assertDoesNotThrow(() -> manager.getUserCommands().handleInput("help"));
assertDoesNotThrow(() -> manager.getUserCommands().handleInput("createWorker"));
assertDoesNotThrow(() -> manager.getUserCommands().handleInput("createTask"));
assertDoesNotThrow(() -> manager.getUserCommands().handleInput("selectTask"));
assertDoesNotThrow(() -> manager.getUserCommands().handleInput("listWorkers"));
assertDoesNotThrow(() -> manager.getUserCommands().handleInput("exit"));
}
@Test
@DisplayName("Check that every task command works")
public void assertFinishingTasksIsPossibleThroughUi() {
int workerId = manager.createWorker("Alfred");
int taskId = manager.addTask(workerId, "Run", "Jog 10 Miles");
manager.getUserCommands().handleInput("selectTask");
assertDoesNotThrow(() -> manager.getUserCommands().handleInput(taskId + ""));
assertDoesNotThrow(() -> manager.getUserCommands().handleInput("finish"));
assertDoesNotThrow(() -> manager.getUserCommands().handleInput("unfinish"));
assertDoesNotThrow(() -> manager.getUserCommands().handleInput("remove"));
assertDoesNotThrow(() -> manager.getUserCommands().handleInput("back"));
assertDoesNotThrow(() -> manager.getUserCommands().handleInput("edit"));
manager.removeWorker(workerId);
}
@Test
@DisplayName("Check that editing is possible through UI")
public void assertEditingTasksIsPossibleThroughUi() {
int workerId = manager.createWorker("Alfred");
int taskId = manager.addTask(workerId, "Run", "Jog 10 Miles");
manager.getUserCommands().handleInput("selectTask");
manager.getUserCommands().handleInput(taskId + "");
manager.getUserCommands().handleInput("edit");
manager.getUserCommands().handleInput("Walk;Walk 3 Miles");
assertEquals("Walk", manager.getTask(taskId).getName());
assertEquals("Walk 3 Miles", manager.getTask(taskId).getDescription());
manager.getUserCommands().handleInput("back");
manager.removeWorker(workerId);
manager.removeTask(taskId);
}
@Test
@DisplayName("Assert that removing Workers is possible through the UI")
public void assertRemovingWorkersIsPossibleThroughUI() {
int workerId = manager.createWorker("Alfred");
int workerId2 = manager.createWorker("Balfred");
manager.getUserCommands().handleInput("listWorkers");
manager.getUserCommands().handleInput(workerId + "");
assertDoesNotThrow(() -> manager.getUserCommands().handleInput("remove"));
manager.getUserCommands().handleInput(workerId2 + "");
assertDoesNotThrow(() -> manager.getUserCommands().handleInput("back"));
manager.removeWorker(workerId);
manager.removeWorker(workerId2);
}
@Test
@DisplayName("Assert that removing a worker removes the worker from the worker list")
public void assertRemoveWorkerActuallyRemoves() {
int workerId = manager.createWorker("Alfred");
manager.removeWorker(workerId);
assertThrows(IllegalArgumentException.class, () -> manager.getWorker(workerId)); // Use getWorker
}
}

View File

@@ -1,14 +0,0 @@
package java;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Assertions.*;
public class BadCasesTest {
@BeforeEach
public void setup() {
}
}

View File

@@ -1,14 +0,0 @@
package java;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Assertions.*;
public class GoodCasesTest {
@BeforeEach
public void setup() {
}
}