Compare commits

...

10 Commits

@ -1,24 +1,3 @@
---
kind: pipeline
type: docker
name: gradle
steps:
- name: test
image: gradle:8.3.0-jdk17-graal
commands:
- gradle assemble
- gradle check
services:
- name: postgres
image: postgres:15-alpine
environment:
POSTGRES_DB: testdb
POSTGRES_USER: user
POSTGRES_PASSWORD: testpassword
---
kind: pipeline kind: pipeline
type: docker type: docker
name: maven name: maven

@ -30,9 +30,8 @@ Type: build
Type: preparation Type: preparation
- create a folder, for example, `project`. - create a folder, for example, `project`.
- copy config/db to the folder. - copy `jpa_hospital_example-2.0.1.jar` from a release to the folder.
- copy `jpa_hospital_example-1.0.2.jar` from a release to the folder. - if you build the application from source, find the file (`jpa_hospital_example-2.0.1-all.jar`) in `build/libs/`.
- if you build the application from source, find the file (`jpa_hospital_example-1.0.2-all.jar`) in `build/libs/`.
- copy docker/docker-compose.yml to the folder. - copy docker/docker-compose.yml to the folder.
- turn up the database in the `project/docker`: - turn up the database in the `project/docker`:
``` ```
@ -45,7 +44,7 @@ Type: run
After the preparation, run the application in the folder, for example, `project`: After the preparation, run the application in the folder, for example, `project`:
```shell ```shell
java -jar jpa_hospital_example-1.0.2.jar java -jar jpa_hospital_example-2.0.1.jar
``` ```
## Building with Maven ## Building with Maven
@ -67,7 +66,6 @@ Type: build
Type: preparation Type: preparation
- create a folder, for example, `project`. - create a folder, for example, `project`.
- copy config/db to the folder.
- copy `jpa_hospital_example-version.jar` from a release to the folder. - copy `jpa_hospital_example-version.jar` from a release to the folder.
- if you build the application from source, find the file in `target/`. - if you build the application from source, find the file in `target/`.
- copy docker/docker-compose.yml to the folder. - copy docker/docker-compose.yml to the folder.
@ -82,7 +80,7 @@ Type: run
After the preparation, run the application in the folder, for example, `project`: After the preparation, run the application in the folder, for example, `project`:
```shell ```shell
java -jar jpa_hospital_example-1.0.2.jar java -jar jpa_hospital_example-2.0.1.jar
``` ```
## Author ## Author

@ -1,70 +0,0 @@
plugins {
id('groovy')
id('application')
id 'com.github.johnrengelman.shadow' version '7.1.2'
}
version = "1.0.2"
description = "Example of using jpa for a hostpital."
application {
mainClassName = 'space.kklochko.jpa_hospital_example.Main'
}
shadowJar {
mergeServiceFiles()
minimize()
}
java {
toolchain {
languageVersion.set(JavaLanguageVersion.of(17))
}
}
compileJava {
options.encoding = 'UTF-8'
sourceCompatibility = '1.8'
targetCompatibility = '1.8'
}
repositories {
// Spock releases are available from Maven Central
mavenCentral()
// Spock snapshots are available from the Sonatype OSS snapshot repository
maven { url "https://oss.sonatype.org/content/repositories/snapshots/" }
}
dependencies {
implementation 'org.hibernate.orm:hibernate-core:6.3.0.Final'
compileOnly 'org.projectlombok:lombok:1.18.30'
annotationProcessor 'org.projectlombok:lombok:1.18.30'
testCompileOnly 'org.projectlombok:lombok:1.18.30'
testAnnotationProcessor 'org.projectlombok:lombok:1.18.30'
implementation 'org.postgresql:postgresql:42.6.0'
implementation 'io.github.cdimascio:dotenv-java:3.0.0'
// mandatory dependencies for using Spock
implementation platform('org.apache.groovy:groovy-bom:4.0.15')
implementation 'org.apache.groovy:groovy'
testImplementation platform("org.spockframework:spock-bom:2.3-groovy-4.0")
testImplementation "org.spockframework:spock-core"
testImplementation "org.spockframework:spock-junit4" // you can remove this if your code does not rely on old JUnit 4 rules
// optional dependencies for using Spock
testImplementation "org.hamcrest:hamcrest-core:2.2" // only necessary if Hamcrest matchers are used
testRuntimeOnly 'net.bytebuddy:byte-buddy:1.14.8' // allows mocking of classes (in addition to interfaces)
testRuntimeOnly "org.objenesis:objenesis:3.3" // allows mocking of classes without default constructor (together with ByteBuddy or CGLIB)
// testing dependencies for sql
implementation "org.apache.groovy:groovy-sql"
}
test {
useJUnitPlatform()
testLogging {
events "passed", "skipped", "failed"
}
}

Binary file not shown.

@ -1,8 +0,0 @@
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
distributionSha256Sum=591855b517fc635b9e04de1d05d5e76ada3f89f5fc76f87978d1b245b4f69225
distributionUrl=https\://services.gradle.org/distributions/gradle-8.3-bin.zip
networkTimeout=10000
validateDistributionUrl=true
zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists

249
gradlew vendored

@ -1,249 +0,0 @@
#!/bin/sh
#
# Copyright © 2015-2021 the original authors.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# https://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
##############################################################################
#
# Gradle start up script for POSIX generated by Gradle.
#
# Important for running:
#
# (1) You need a POSIX-compliant shell to run this script. If your /bin/sh is
# noncompliant, but you have some other compliant shell such as ksh or
# bash, then to run this script, type that shell name before the whole
# command line, like:
#
# ksh Gradle
#
# Busybox and similar reduced shells will NOT work, because this script
# requires all of these POSIX shell features:
# * functions;
# * expansions «$var», «${var}», «${var:-default}», «${var+SET}»,
# «${var#prefix}», «${var%suffix}», and «$( cmd )»;
# * compound commands having a testable exit status, especially «case»;
# * various built-in commands including «command», «set», and «ulimit».
#
# Important for patching:
#
# (2) This script targets any POSIX shell, so it avoids extensions provided
# by Bash, Ksh, etc; in particular arrays are avoided.
#
# The "traditional" practice of packing multiple parameters into a
# space-separated string is a well documented source of bugs and security
# problems, so this is (mostly) avoided, by progressively accumulating
# options in "$@", and eventually passing that to Java.
#
# Where the inherited environment variables (DEFAULT_JVM_OPTS, JAVA_OPTS,
# and GRADLE_OPTS) rely on word-splitting, this is performed explicitly;
# see the in-line comments for details.
#
# There are tweaks for specific operating systems such as AIX, CygWin,
# Darwin, MinGW, and NonStop.
#
# (3) This script is generated from the Groovy template
# https://github.com/gradle/gradle/blob/HEAD/subprojects/plugins/src/main/resources/org/gradle/api/internal/plugins/unixStartScript.txt
# within the Gradle project.
#
# You can find Gradle at https://github.com/gradle/gradle/.
#
##############################################################################
# Attempt to set APP_HOME
# Resolve links: $0 may be a link
app_path=$0
# Need this for daisy-chained symlinks.
while
APP_HOME=${app_path%"${app_path##*/}"} # leaves a trailing /; empty if no leading path
[ -h "$app_path" ]
do
ls=$( ls -ld "$app_path" )
link=${ls#*' -> '}
case $link in #(
/*) app_path=$link ;; #(
*) app_path=$APP_HOME$link ;;
esac
done
# This is normally unused
# shellcheck disable=SC2034
APP_BASE_NAME=${0##*/}
# Discard cd standard output in case $CDPATH is set (https://github.com/gradle/gradle/issues/25036)
APP_HOME=$( cd "${APP_HOME:-./}" > /dev/null && pwd -P ) || exit
# Use the maximum available, or set MAX_FD != -1 to use that value.
MAX_FD=maximum
warn () {
echo "$*"
} >&2
die () {
echo
echo "$*"
echo
exit 1
} >&2
# OS specific support (must be 'true' or 'false').
cygwin=false
msys=false
darwin=false
nonstop=false
case "$( uname )" in #(
CYGWIN* ) cygwin=true ;; #(
Darwin* ) darwin=true ;; #(
MSYS* | MINGW* ) msys=true ;; #(
NONSTOP* ) nonstop=true ;;
esac
CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar
# Determine the Java command to use to start the JVM.
if [ -n "$JAVA_HOME" ] ; then
if [ -x "$JAVA_HOME/jre/sh/java" ] ; then
# IBM's JDK on AIX uses strange locations for the executables
JAVACMD=$JAVA_HOME/jre/sh/java
else
JAVACMD=$JAVA_HOME/bin/java
fi
if [ ! -x "$JAVACMD" ] ; then
die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME
Please set the JAVA_HOME variable in your environment to match the
location of your Java installation."
fi
else
JAVACMD=java
if ! command -v java >/dev/null 2>&1
then
die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
Please set the JAVA_HOME variable in your environment to match the
location of your Java installation."
fi
fi
# Increase the maximum file descriptors if we can.
if ! "$cygwin" && ! "$darwin" && ! "$nonstop" ; then
case $MAX_FD in #(
max*)
# In POSIX sh, ulimit -H is undefined. That's why the result is checked to see if it worked.
# shellcheck disable=SC3045
MAX_FD=$( ulimit -H -n ) ||
warn "Could not query maximum file descriptor limit"
esac
case $MAX_FD in #(
'' | soft) :;; #(
*)
# In POSIX sh, ulimit -n is undefined. That's why the result is checked to see if it worked.
# shellcheck disable=SC3045
ulimit -n "$MAX_FD" ||
warn "Could not set maximum file descriptor limit to $MAX_FD"
esac
fi
# Collect all arguments for the java command, stacking in reverse order:
# * args from the command line
# * the main class name
# * -classpath
# * -D...appname settings
# * --module-path (only if needed)
# * DEFAULT_JVM_OPTS, JAVA_OPTS, and GRADLE_OPTS environment variables.
# For Cygwin or MSYS, switch paths to Windows format before running java
if "$cygwin" || "$msys" ; then
APP_HOME=$( cygpath --path --mixed "$APP_HOME" )
CLASSPATH=$( cygpath --path --mixed "$CLASSPATH" )
JAVACMD=$( cygpath --unix "$JAVACMD" )
# Now convert the arguments - kludge to limit ourselves to /bin/sh
for arg do
if
case $arg in #(
-*) false ;; # don't mess with options #(
/?*) t=${arg#/} t=/${t%%/*} # looks like a POSIX filepath
[ -e "$t" ] ;; #(
*) false ;;
esac
then
arg=$( cygpath --path --ignore --mixed "$arg" )
fi
# Roll the args list around exactly as many times as the number of
# args, so each arg winds up back in the position where it started, but
# possibly modified.
#
# NB: a `for` loop captures its iteration list before it begins, so
# changing the positional parameters here affects neither the number of
# iterations, nor the values presented in `arg`.
shift # remove old arg
set -- "$@" "$arg" # push replacement arg
done
fi
# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"'
# Collect all arguments for the java command;
# * $DEFAULT_JVM_OPTS, $JAVA_OPTS, and $GRADLE_OPTS can contain fragments of
# shell script including quotes and variable substitutions, so put them in
# double quotes to make sure that they get re-expanded; and
# * put everything else in single quotes, so that it's not re-expanded.
set -- \
"-Dorg.gradle.appname=$APP_BASE_NAME" \
-classpath "$CLASSPATH" \
org.gradle.wrapper.GradleWrapperMain \
"$@"
# Stop when "xargs" is not available.
if ! command -v xargs >/dev/null 2>&1
then
die "xargs is not available"
fi
# Use "xargs" to parse quoted args.
#
# With -n1 it outputs one arg per line, with the quotes and backslashes removed.
#
# In Bash we could simply go:
#
# readarray ARGS < <( xargs -n1 <<<"$var" ) &&
# set -- "${ARGS[@]}" "$@"
#
# but POSIX shell has neither arrays nor command substitution, so instead we
# post-process each arg (as a line of input to sed) to backslash-escape any
# character that might be a shell metacharacter, then use eval to reverse
# that process (while maintaining the separation between arguments), and wrap
# the whole thing up as a single "set" statement.
#
# This will of course break if any of these variables contains a newline or
# an unmatched quote.
#
eval "set -- $(
printf '%s\n' "$DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS" |
xargs -n1 |
sed ' s~[^-[:alnum:]+,./:=@_]~\\&~g; ' |
tr '\n' ' '
)" '"$@"'
exec "$JAVACMD" "$@"

92
gradlew.bat vendored

@ -1,92 +0,0 @@
@rem
@rem Copyright 2015 the original author or authors.
@rem
@rem Licensed under the Apache License, Version 2.0 (the "License");
@rem you may not use this file except in compliance with the License.
@rem You may obtain a copy of the License at
@rem
@rem https://www.apache.org/licenses/LICENSE-2.0
@rem
@rem Unless required by applicable law or agreed to in writing, software
@rem distributed under the License is distributed on an "AS IS" BASIS,
@rem WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
@rem See the License for the specific language governing permissions and
@rem limitations under the License.
@rem
@if "%DEBUG%"=="" @echo off
@rem ##########################################################################
@rem
@rem Gradle startup script for Windows
@rem
@rem ##########################################################################
@rem Set local scope for the variables with windows NT shell
if "%OS%"=="Windows_NT" setlocal
set DIRNAME=%~dp0
if "%DIRNAME%"=="" set DIRNAME=.
@rem This is normally unused
set APP_BASE_NAME=%~n0
set APP_HOME=%DIRNAME%
@rem Resolve any "." and ".." in APP_HOME to make it shorter.
for %%i in ("%APP_HOME%") do set APP_HOME=%%~fi
@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
set DEFAULT_JVM_OPTS="-Xmx64m" "-Xms64m"
@rem Find java.exe
if defined JAVA_HOME goto findJavaFromJavaHome
set JAVA_EXE=java.exe
%JAVA_EXE% -version >NUL 2>&1
if %ERRORLEVEL% equ 0 goto execute
echo.
echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
echo.
echo Please set the JAVA_HOME variable in your environment to match the
echo location of your Java installation.
goto fail
:findJavaFromJavaHome
set JAVA_HOME=%JAVA_HOME:"=%
set JAVA_EXE=%JAVA_HOME%/bin/java.exe
if exist "%JAVA_EXE%" goto execute
echo.
echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%
echo.
echo Please set the JAVA_HOME variable in your environment to match the
echo location of your Java installation.
goto fail
:execute
@rem Setup the command line
set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
@rem Execute Gradle
"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %*
:end
@rem End local scope for the variables with windows NT shell
if %ERRORLEVEL% equ 0 goto mainEnd
:fail
rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
rem the _cmd.exe /c_ return code!
set EXIT_CODE=%ERRORLEVEL%
if %EXIT_CODE% equ 0 set EXIT_CODE=1
if not ""=="%GRADLE_EXIT_CONSOLE%" exit %EXIT_CODE%
exit /b %EXIT_CODE%
:mainEnd
if "%OS%"=="Windows_NT" endlocal
:omega

@ -4,7 +4,7 @@
<modelVersion>4.0.0</modelVersion> <modelVersion>4.0.0</modelVersion>
<groupId>space.kklochko</groupId> <groupId>space.kklochko</groupId>
<artifactId>jpa_hospital_example</artifactId> <artifactId>jpa_hospital_example</artifactId>
<version>1.0.2</version> <version>2.0.1</version>
<packaging>jar</packaging> <packaging>jar</packaging>
<name>Example of using jpa for a hostpital.</name> <name>Example of using jpa for a hostpital.</name>
@ -147,7 +147,6 @@
<groupId>net.bytebuddy</groupId> <groupId>net.bytebuddy</groupId>
<artifactId>byte-buddy</artifactId> <artifactId>byte-buddy</artifactId>
<version>1.14.8</version> <version>1.14.8</version>
<scope>test</scope>
</dependency> </dependency>
<dependency> <!-- enables mocking of classes without default constructor (together with ByteBuddy or CGLIB) --> <dependency> <!-- enables mocking of classes without default constructor (together with ByteBuddy or CGLIB) -->
<groupId>org.objenesis</groupId> <groupId>org.objenesis</groupId>

@ -1 +0,0 @@
rootProject.name = "jpa_hospital_example"

@ -6,7 +6,7 @@ import space.kklochko.jpa_hospital_example.db.factories.EntityManagerConnection;
public class Main { public class Main {
public static void main(String[] args) { public static void main(String[] args) {
EntityManager manager = (new EntityManagerConnection()).connect(); EntityManager manager = (new EntityManagerConnection("jpa_hospital_example")).connect();
CLI cli = new CLI(manager); CLI cli = new CLI(manager);
cli.run(); cli.run();

@ -1,136 +0,0 @@
package space.kklochko.jpa_hospital_example.cli;
import jakarta.persistence.EntityManager;
import lombok.Getter;
import lombok.NonNull;
import lombok.Setter;
import space.kklochko.jpa_hospital_example.cli.commands.CommandData;
import space.kklochko.jpa_hospital_example.cli.commands.CommandEntities;
import space.kklochko.jpa_hospital_example.cli.commands.CommandEntity;
import space.kklochko.jpa_hospital_example.cli.commands.factories.CommandFactory;
import space.kklochko.jpa_hospital_example.cli.commands.factories.ReadAllFactory;
import space.kklochko.jpa_hospital_example.cli.parsers.CommandParser;
import space.kklochko.jpa_hospital_example.cli.validators.CommandValidator;
import space.kklochko.jpa_hospital_example.cli.validators.InputStringFormatValidator;
import space.kklochko.jpa_hospital_example.cli.validators.Validator;
import space.kklochko.jpa_hospital_example.db.factories.DataBaseConnection;
import space.kklochko.jpa_hospital_example.db.repositories.AbstractRepository;
import space.kklochko.jpa_hospital_example.db.repositories.DepartmentRepository;
import space.kklochko.jpa_hospital_example.db.repositories.IndicatorRepository;
import space.kklochko.jpa_hospital_example.db.repositories.PatientRepository;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.Scanner;
@Setter
@Getter
public class CLI {
private final String prompt = "> ";
private String state = "prompt";
private final String help = "Help (help or h)\n" +
"Command format: `command {item}(arg1=value1, ...`\n\n" +
"Commands: \n" +
"insert {item}({args}): \n" +
"update {item}({args}): \n" +
"readAll {item}: \n" +
"delete {item}(uuid='07c6e39e-727a-11ee-8e7b-c0e4349366ab'}).\n" +
"Examples:\n" +
"\nDepartment:\n" +
"\tinsert department(id='bcbbcdb4-702c-11ee-9113-c0e4349366cb', name='First department', location='Stepan Bandera Street', phone='380123451244')\n" +
"\tinsert department(name='First department', location='Stepan Bandera Street', phone='380123451244')\n" +
"\tupdate department(id='bcbbcdb4-702c-11ee-9113-c0e4349366cb', name='First department', location='Stepan Bandera Street', phone='380123451244')\n" +
"\treadAll department()\n" +
"\tremove department(id='bcbbcdb4-702c-11ee-9113-c0e4349366cb')\n" +
"\nPatient:\n" +
"\tinsert patient(id='bcbbcdb4-702c-11ee-9113-c0e4349366bb', name='Oleh', age='21', phone='380123451234')\n" +
"\tinsert patient(name='Oleh', age='21', phone='380123451234')\n" +
"\tupdate patient(id='bcbbcdb4-702c-11ee-9113-c0e4349366bb', name='Oleh', age='21', phone='380123451234')\n" +
"\treadAll patient()\n" +
"\tremove patient(id='bcbbcdb4-702c-11ee-9113-c0e4349366bb')\n" +
"\nIndicators:\n" +
"\tinsert indicator(id='07c6e39e-727a-11ee-8e7b-c0e4349366ab', type='blood245', values='well maybe', timestamp='2023-10-17 14:30:00')\n" +
"\tinsert indicator(type='blood246', values='well maybe', timestamp='2023-10-17 14:30:00')\n" +
"\tupdate indicator(id='07c6e39e-727a-11ee-8e7b-c0e4349366ab', type='blood247', values='well maybe', timestamp='2023-10-17 14:30:00')\n" +
"\treadAll indicator()\n" +
"\tremove indicator(id='07c6e39e-727a-11ee-8e7b-c0e4349366ab')\n";
EntityManager manager;
public CLI(EntityManager manager) {
this.manager = manager;
}
public void run() {
Scanner reader = new Scanner(System.in);
String line = "";
CommandData commandData;
while(true) {
if(getState() == "prompt") {
System.out.print(prompt);
setState("waitInput");
}else if(getState() == "waitInput") {
line = reader.nextLine();
setState("isHelp?");
}else if(getState() == "isHelp?") {
if(line.equals("h") || line.equals("help")) {
System.out.println(help);
setState("prompt");
}else {
setState("validate");
}
} else if(getState() == "validate") {
ArrayList<Validator> validators = new ArrayList<>();
validators.add(new CommandValidator(line));
validators.add(new InputStringFormatValidator(line));
setState("run");
for (Validator validator : validators) {
if(!validator.isValid()) {
System.err.println(validator.getMessage());
System.out.println();
setState("prompt");
}
}
} else if(getState() == "run") {
CommandParser commandParser = new CommandParser();
commandData = commandParser.parse(line);
runCommand(commandData);
setState("prompt");
}
}
}
public void runCommand(CommandData commandData) {
if(commandData.getName().equals("readAll")) {
ReadAllFactory factory = new ReadAllFactory();
CommandEntities command = factory.create(commandData, getRepository(commandData));
ArrayList items = command.run();
for(Iterator iter = command.run().iterator(); iter.hasNext(); ) {
System.out.println(iter.next());
}
} else {
CommandFactory factory = new CommandFactory();
CommandEntity command = factory.create(commandData, getRepository(commandData));
command.run();
}
}
public AbstractRepository getRepository(@NonNull CommandData commandData) {
if(commandData.getDatatype().equals("indicator")) {
return new IndicatorRepository(manager);
}else if(commandData.getDatatype().equals("patient")) {
return new PatientRepository(manager);
}else {
return new DepartmentRepository(manager);
}
}
}

@ -1,14 +0,0 @@
package space.kklochko.jpa_hospital_example.cli.commands;
import lombok.AllArgsConstructor;
import lombok.Data;
import java.util.Map;
@AllArgsConstructor
@Data
public class CommandData {
public String name;
public String datatype;
public Map<String, String> arguments;
}

@ -1,28 +0,0 @@
package space.kklochko.jpa_hospital_example.cli.commands;
import lombok.AllArgsConstructor;
import lombok.Data;
import space.kklochko.jpa_hospital_example.db.repositories.AbstractRepository;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.ArrayList;
@AllArgsConstructor
@Data
public class CommandEntities<T> {
private AbstractRepository<T> repository;
private Method method;
public ArrayList<T> run() {
try {
return (ArrayList<T>) method.invoke(getRepository());
} catch (InvocationTargetException e) {
System.err.println(e.getMessage());
throw new RuntimeException(e);
} catch (IllegalAccessException e) {
System.err.println(e.getMessage());
throw new RuntimeException(e);
}
};
}

@ -1,32 +0,0 @@
package space.kklochko.jpa_hospital_example.cli.commands;
import lombok.Data;
import space.kklochko.jpa_hospital_example.db.repositories.AbstractRepository;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
@Data
public class CommandEntity <A, T> {
private AbstractRepository<T> repository;
private Method method;
private A argument;
public CommandEntity(AbstractRepository<T> repository, Method method, A argument) {
this.repository = repository;
this.method = method;
this.argument = argument;
}
public boolean run() {
try {
return (Boolean) method.invoke(getRepository(), getArgument());
} catch (InvocationTargetException e) {
System.err.println(e.getMessage());
throw new RuntimeException(e);
} catch (IllegalAccessException e) {
System.err.println(e.getMessage());
throw new RuntimeException(e);
}
};
}

@ -1,58 +0,0 @@
package space.kklochko.jpa_hospital_example.cli.commands.factories;
import lombok.NonNull;
import space.kklochko.jpa_hospital_example.cli.commands.CommandData;
import space.kklochko.jpa_hospital_example.cli.commands.CommandEntity;
import space.kklochko.jpa_hospital_example.db.repositories.AbstractRepository;
import space.kklochko.jpa_hospital_example.models.Department;
import space.kklochko.jpa_hospital_example.models.Indicator;
import space.kklochko.jpa_hospital_example.models.Patient;
import java.lang.reflect.Method;
import java.util.UUID;
public class CommandFactory {
public <T> CommandEntity create(@NonNull CommandData commandData, @NonNull AbstractRepository<T> repository) {
try {
EntityFactory entityFactory = new EntityFactory();
if(commandData.getName().equals("insert")) {
if(commandData.getDatatype().equals("indicator")) {
Method method = repository.getClass().getMethod("create", Indicator.class);
Indicator indicator = (Indicator) entityFactory.create(commandData);
return new CommandEntity<Indicator, T>(repository, method, indicator);
}else if(commandData.getDatatype().equals("patient")) {
Method method = repository.getClass().getMethod("create", Patient.class);
Patient patient = (Patient) entityFactory.create(commandData);
return new CommandEntity<Patient, T>(repository, method, patient);
}else {
Method method = repository.getClass().getMethod("create", Department.class);
Department department = (Department) entityFactory.create(commandData);
return new CommandEntity<Department, T>(repository, method, department);
}
}else if(commandData.getName().equals("update")) {
if(commandData.getDatatype().equals("indicator")) {
Method method = repository.getClass().getMethod("update", Indicator.class);
Indicator indicator = (Indicator) entityFactory.create(commandData);
return new CommandEntity<Indicator, T>(repository, method, indicator);
}else if(commandData.getDatatype().equals("patient")) {
Method method = repository.getClass().getMethod("update", Patient.class);
Patient patient = (Patient) entityFactory.create(commandData);
return new CommandEntity<Patient, T>(repository, method, patient);
}else {
Method method = repository.getClass().getMethod("update", Department.class);
Department department = (Department) entityFactory.create(commandData);
return new CommandEntity<Department, T>(repository, method, department);
}
}else {
String uuidString = commandData.arguments.get("id");
UUID uuid = UUID.fromString(uuidString);
Method method = repository.getClass().getMethod("delete", UUID.class);
return new CommandEntity<UUID, T>(repository, method, uuid);
}
} catch (NoSuchMethodException e) {
throw new RuntimeException(e);
}
}
}

@ -1,52 +0,0 @@
package space.kklochko.jpa_hospital_example.cli.commands.factories;
import lombok.NonNull;
import space.kklochko.jpa_hospital_example.cli.commands.CommandData;
import space.kklochko.jpa_hospital_example.models.Department;
import space.kklochko.jpa_hospital_example.models.Indicator;
import space.kklochko.jpa_hospital_example.models.Patient;
import java.sql.Timestamp;
import java.util.Map;
import java.util.UUID;
public class EntityFactory {
public Object create(@NonNull CommandData commandData) {
if(commandData.getDatatype().equals("indicator")) {
Map<String, String> values = commandData.getArguments();
Timestamp timestamp = Timestamp.valueOf(values.get("timestamp"));
Indicator indicator = new Indicator(values.get("type"), values.get("values"), timestamp);
String uuidString = values.getOrDefault("id", null);
if(uuidString != null) {
UUID uuid = UUID.fromString(uuidString);
indicator.setId(uuid);
}
return (Object) indicator;
}else if(commandData.getDatatype().equals("patient")) {
Map<String, String> values = commandData.getArguments();
short age = Short.parseShort(values.get("age"));
Patient patient = new Patient(values.get("name"), age, values.get("phone"));
String uuidString = values.getOrDefault("id", null);
if(uuidString != null) {
UUID uuid = UUID.fromString(uuidString);
patient.setId(uuid);
}
return (Object) patient;
}else {
Map<String, String> values = commandData.getArguments();
Department department = new Department(values.get("name"), values.get("location"), values.get("phone"));
String uuidString = values.getOrDefault("id", null);
if(uuidString != null) {
UUID uuid = UUID.fromString(uuidString);
department.setId(uuid);
}
return (Object) department;
}
}
}

@ -1,19 +0,0 @@
package space.kklochko.jpa_hospital_example.cli.commands.factories;
import lombok.NonNull;
import space.kklochko.jpa_hospital_example.cli.commands.CommandData;
import space.kklochko.jpa_hospital_example.cli.commands.CommandEntities;
import space.kklochko.jpa_hospital_example.db.repositories.AbstractRepository;
import java.lang.reflect.Method;
public class ReadAllFactory {
public <T> CommandEntities<T> create(@NonNull CommandData commandData, @NonNull AbstractRepository<T> repository) {
try {
Method method = repository.getClass().getMethod("readAll");
return new CommandEntities<T>(repository, method);
} catch (NoSuchMethodException e) {
throw new RuntimeException(e);
}
}
}

@ -1,30 +0,0 @@
package space.kklochko.jpa_hospital_example.cli.parsers;
import lombok.NonNull;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.Map;
import java.util.TreeMap;
public class ArgumentParser {
public Map<String, String> parse(@NonNull String args) {
Map<String, String> parsed = new LinkedHashMap<String, String>();
if(args == "") return parsed;
// remove last '
args = args.substring(0, args.length() - 1);
for(String arg : args.split("',")) {
String[] parts = arg.split("=");
parsed.put(parts[0].trim(), removeQuotes(parts[1]));
}
return parsed;
}
public String removeQuotes(@NonNull String withQuotes) {
return withQuotes.substring(1, withQuotes.length());
}
}

@ -1,20 +0,0 @@
package space.kklochko.jpa_hospital_example.cli.parsers;
import lombok.NonNull;
import lombok.ToString;
import space.kklochko.jpa_hospital_example.cli.commands.CommandData;
@ToString
public class CommandParser {
public CommandData parse(@NonNull String command) {
ArgumentParser parser = new ArgumentParser();
String[] command_args = command.split("[()]");
String[] command_parts = command_args[0].split(" ");
String args="";
if(command_args.length > 1)
args = command_args[1];
return new CommandData(command_parts[0], command_parts[1], parser.parse(args));
}
}

@ -1,22 +0,0 @@
package space.kklochko.jpa_hospital_example.cli.validators;
import java.util.regex.Pattern;
public class CommandValidator extends Validator {
String command;
String formatRegEx = "(readAll|insert|update|remove)\\s(indicator|patient|department)\\(.*\\)";
public CommandValidator(String command) {
this.command = command;
}
public boolean isValid() {
Pattern pattern = Pattern.compile(formatRegEx);
return pattern.matcher(command).matches();
}
public String getMessage() {
return "Please, check the format: `command item(arg1=value1, ...)`. Or check the `help`";
}
}

@ -1,21 +0,0 @@
package space.kklochko.jpa_hospital_example.cli.validators;
import java.util.regex.Pattern;
public class InputStringFormatValidator extends Validator {
String command;
String formatRegEx = "\\w+\\s\\w+\\([^)]*\\)";
public InputStringFormatValidator(String command) {
this.command = command;
}
public boolean isValid() {
Pattern pattern = Pattern.compile(formatRegEx);
return pattern.matcher(command).matches();
}
public String getMessage() {
return "Please, check the format: `command item(arg1=value1, ...)`. Or check the `help`";
}
}

@ -1,9 +0,0 @@
package space.kklochko.jpa_hospital_example.cli.validators;
import java.util.regex.Pattern;
abstract public class Validator {
abstract public boolean isValid();
abstract public String getMessage();
}

@ -1,47 +0,0 @@
package space.kklochko.jpa_hospital_example.db.repositories;
import jakarta.persistence.EntityManager;
import jakarta.persistence.TypedQuery;
import space.kklochko.jpa_hospital_example.db.repositories.blocks.TransactionalInsert;
import space.kklochko.jpa_hospital_example.db.repositories.blocks.TransactionalRemove;
import space.kklochko.jpa_hospital_example.db.repositories.blocks.TransactionalUpdate;
import space.kklochko.jpa_hospital_example.models.Department;
import java.util.ArrayList;
import java.util.UUID;
public class DepartmentRepository extends AbstractRepository<Department> {
public DepartmentRepository(EntityManager manager){
super(manager);
}
public boolean create(Department object) {
TransactionalInsert insert = new TransactionalInsert();
return insert.run(manager, object);
}
public Department read(UUID id) {
return manager.find(Department.class, id);
}
public ArrayList<Department> readAll() {
TypedQuery<Department> query = manager.createQuery("SELECT d FROM Department d", Department.class);
return (ArrayList<Department>) query.getResultList();
}
public boolean update(Department object) {
TransactionalUpdate update = new TransactionalUpdate();
return update.run(manager, object);
}
public boolean delete(UUID id) {
Department object = read(id);
TransactionalRemove remove = new TransactionalRemove();
return remove.run(manager, object);
}
}

@ -1,4 +1,4 @@
package space.kklochko.jpa_hospital_example.config.env; package space.kklochko.spring_rest_example.config.env;
import io.github.cdimascio.dotenv.Dotenv; import io.github.cdimascio.dotenv.Dotenv;
import lombok.Getter; import lombok.Getter;

@ -1,8 +1,8 @@
package space.kklochko.jpa_hospital_example.config.factories; package space.kklochko.spring_rest_example.config.factories;
import lombok.NonNull; import lombok.NonNull;
import space.kklochko.jpa_hospital_example.config.env.DataBaseEnvConfig; import space.kklochko.spring_rest_example.config.env.DataBaseEnvConfig;
import space.kklochko.jpa_hospital_example.config.models.DataBaseConfig; import space.kklochko.spring_rest_example.config.models.DataBaseConfig;
public class LoadDataBaseConfigFromEnvFile { public class LoadDataBaseConfigFromEnvFile {
public DataBaseConfig load(@NonNull String filename) { public DataBaseConfig load(@NonNull String filename) {

@ -1,4 +1,4 @@
package space.kklochko.jpa_hospital_example.config.models; package space.kklochko.spring_rest_example.config.models;
import lombok.Data; import lombok.Data;
import java.util.Properties; import java.util.Properties;

@ -1,7 +1,7 @@
package space.kklochko.jpa_hospital_example.db.factories; package space.kklochko.spring_rest_example.db.factories;
import lombok.Setter; import lombok.Setter;
import space.kklochko.jpa_hospital_example.config.models.DataBaseConfig; import space.kklochko.spring_rest_example.config.models.DataBaseConfig;
import java.sql.Connection; import java.sql.Connection;
import java.sql.DriverManager; import java.sql.DriverManager;

@ -1,4 +1,4 @@
package space.kklochko.jpa_hospital_example.db.factories; package space.kklochko.spring_rest_example.db.factories;
import java.sql.Connection; import java.sql.Connection;
import java.sql.SQLException; import java.sql.SQLException;

@ -1,4 +1,4 @@
package space.kklochko.jpa_hospital_example.db.factories; package space.kklochko.spring_rest_example.db.factories;
import jakarta.persistence.EntityManager; import jakarta.persistence.EntityManager;
import jakarta.persistence.EntityManagerFactory; import jakarta.persistence.EntityManagerFactory;
@ -14,7 +14,7 @@ public class EntityManagerConnection {
} }
public EntityManagerConnection() { public EntityManagerConnection() {
setUnitName("jpa_hospital_example"); setUnitName("spring_rest_example");
} }
public EntityManager connect() { public EntityManager connect() {

@ -1,9 +1,9 @@
package space.kklochko.jpa_hospital_example.db.repositories; package space.kklochko.spring_rest_example.db.repositories;
import jakarta.persistence.EntityManager; import jakarta.persistence.EntityManager;
import lombok.Setter; import lombok.Setter;
import java.util.ArrayList; import java.util.List;
import java.util.UUID; import java.util.UUID;
@Setter @Setter
@ -18,7 +18,7 @@ public abstract class AbstractRepository<T> {
public abstract T read(UUID id); public abstract T read(UUID id);
public abstract ArrayList<T> readAll(); public abstract List<T> readAll();
public abstract boolean update(T object); public abstract boolean update(T object);

@ -0,0 +1,67 @@
package space.kklochko.spring_rest_example.db.repositories;
import jakarta.persistence.EntityGraph;
import jakarta.persistence.EntityManager;
import jakarta.persistence.TypedQuery;
import space.kklochko.spring_rest_example.db.repositories.blocks.TransactionalInsert;
import space.kklochko.spring_rest_example.db.repositories.blocks.TransactionalRemove;
import space.kklochko.spring_rest_example.db.repositories.blocks.TransactionalUpdate;
import space.kklochko.spring_rest_example.models.Department;
import space.kklochko.spring_rest_example.models.Patient;
import java.util.List;
import java.util.UUID;
public class DepartmentRepository extends AbstractRepository<Department> {
public DepartmentRepository(EntityManager manager){
super(manager);
}
public boolean create(Department object) {
TransactionalInsert insert = new TransactionalInsert();
return insert.run(manager, object);
}
public Department read(UUID id) {
return manager.find(Department.class, id);
}
public List<Department> readAll() {
EntityGraph<Department> entityGraph = manager.createEntityGraph(Department.class);
entityGraph.addAttributeNodes("patients");
//entityGraph.addSubgraph("patients")
//.addAttributeNodes("indicators");
TypedQuery<Department> query = manager.createQuery("SELECT d FROM Department d", Department.class);
query.setHint( "javax.persistence.fetchgraph", entityGraph);
List<Department> departments = query.getResultList();
for(Department department : departments) {
EntityGraph<Patient> patientEntityGraph = manager.createEntityGraph(Patient.class);
patientEntityGraph.addAttributeNodes("indicators");
TypedQuery<Patient> patientQuery = manager.createQuery("SELECT p FROM Patient p", Patient.class);
patientQuery.setHint( "javax.persistence.fetchgraph", patientEntityGraph);
department.setPatients(patientQuery.getResultList());
}
return departments;
}
public boolean update(Department object) {
TransactionalUpdate update = new TransactionalUpdate();
return update.run(manager, object);
}
public boolean delete(UUID id) {
Department object = read(id);
TransactionalRemove remove = new TransactionalRemove();
return remove.run(manager, object);
}
}

@ -1,13 +1,13 @@
package space.kklochko.jpa_hospital_example.db.repositories; package space.kklochko.spring_rest_example.db.repositories;
import jakarta.persistence.EntityManager; import jakarta.persistence.EntityManager;
import jakarta.persistence.TypedQuery; import jakarta.persistence.TypedQuery;
import space.kklochko.jpa_hospital_example.db.repositories.blocks.TransactionalInsert; import space.kklochko.spring_rest_example.db.repositories.blocks.TransactionalInsert;
import space.kklochko.jpa_hospital_example.db.repositories.blocks.TransactionalRemove; import space.kklochko.spring_rest_example.db.repositories.blocks.TransactionalRemove;
import space.kklochko.jpa_hospital_example.db.repositories.blocks.TransactionalUpdate; import space.kklochko.spring_rest_example.db.repositories.blocks.TransactionalUpdate;
import space.kklochko.jpa_hospital_example.models.Indicator; import space.kklochko.spring_rest_example.models.Indicator;
import java.util.ArrayList; import java.util.List;
import java.util.UUID; import java.util.UUID;
public class IndicatorRepository extends AbstractRepository<Indicator> { public class IndicatorRepository extends AbstractRepository<Indicator> {
@ -25,10 +25,10 @@ public class IndicatorRepository extends AbstractRepository<Indicator> {
return manager.find(Indicator.class, id); return manager.find(Indicator.class, id);
} }
public ArrayList<Indicator> readAll() { public List<Indicator> readAll() {
TypedQuery<Indicator> query = manager.createQuery("SELECT i FROM Indicator i", Indicator.class); TypedQuery<Indicator> query = manager.createQuery("SELECT i FROM Indicator i", Indicator.class);
return (ArrayList<Indicator>) query.getResultList(); return query.getResultList();
} }
public boolean update(Indicator object) { public boolean update(Indicator object) {

@ -1,13 +1,14 @@
package space.kklochko.jpa_hospital_example.db.repositories; package space.kklochko.spring_rest_example.db.repositories;
import jakarta.persistence.EntityGraph;
import jakarta.persistence.EntityManager; import jakarta.persistence.EntityManager;
import jakarta.persistence.TypedQuery; import jakarta.persistence.TypedQuery;
import space.kklochko.jpa_hospital_example.db.repositories.blocks.TransactionalInsert; import space.kklochko.spring_rest_example.db.repositories.blocks.TransactionalInsert;
import space.kklochko.jpa_hospital_example.db.repositories.blocks.TransactionalRemove; import space.kklochko.spring_rest_example.db.repositories.blocks.TransactionalRemove;
import space.kklochko.jpa_hospital_example.db.repositories.blocks.TransactionalUpdate; import space.kklochko.spring_rest_example.db.repositories.blocks.TransactionalUpdate;
import space.kklochko.jpa_hospital_example.models.Patient; import space.kklochko.spring_rest_example.models.Patient;
import java.util.ArrayList; import java.util.List;
import java.util.UUID; import java.util.UUID;
public class PatientRepository extends AbstractRepository<Patient> { public class PatientRepository extends AbstractRepository<Patient> {
@ -25,10 +26,14 @@ public class PatientRepository extends AbstractRepository<Patient> {
return manager.find(Patient.class, id); return manager.find(Patient.class, id);
} }
public ArrayList<Patient> readAll() { public List<Patient> readAll() {
EntityGraph<Patient> entityGraph = manager.createEntityGraph(Patient.class);
entityGraph.addAttributeNodes("indicators");
TypedQuery<Patient> query = manager.createQuery("SELECT p FROM Patient p", Patient.class); TypedQuery<Patient> query = manager.createQuery("SELECT p FROM Patient p", Patient.class);
query.setHint( "javax.persistence.fetchgraph", entityGraph);
return (ArrayList<Patient>) query.getResultList(); return query.getResultList();
} }
public boolean update(Patient object) { public boolean update(Patient object) {

@ -1,11 +1,11 @@
package space.kklochko.jpa_hospital_example.db.repositories.blocks; package space.kklochko.spring_rest_example.db.repositories.blocks;
import jakarta.persistence.EntityManager; import jakarta.persistence.EntityManager;
import jakarta.persistence.PersistenceException; import jakarta.persistence.PersistenceException;
import jakarta.persistence.RollbackException; import jakarta.persistence.RollbackException;
import space.kklochko.jpa_hospital_example.models.Department; import space.kklochko.spring_rest_example.models.Department;
import space.kklochko.jpa_hospital_example.models.Indicator; import space.kklochko.spring_rest_example.models.Indicator;
import space.kklochko.jpa_hospital_example.models.Patient; import space.kklochko.spring_rest_example.models.Patient;
import java.util.UUID; import java.util.UUID;

@ -1,4 +1,4 @@
package space.kklochko.jpa_hospital_example.db.repositories.blocks; package space.kklochko.spring_rest_example.db.repositories.blocks;
import jakarta.persistence.EntityManager; import jakarta.persistence.EntityManager;
import jakarta.persistence.RollbackException; import jakarta.persistence.RollbackException;

@ -1,4 +1,4 @@
package space.kklochko.jpa_hospital_example.db.repositories.blocks; package space.kklochko.spring_rest_example.db.repositories.blocks;
import jakarta.persistence.EntityManager; import jakarta.persistence.EntityManager;
import jakarta.persistence.RollbackException; import jakarta.persistence.RollbackException;

@ -1,9 +1,10 @@
package space.kklochko.jpa_hospital_example.models; package space.kklochko.spring_rest_example.models;
import jakarta.persistence.*; import jakarta.persistence.*;
import lombok.AllArgsConstructor; import lombok.AllArgsConstructor;
import lombok.Data; import lombok.Data;
import java.util.List;
import java.util.UUID; import java.util.UUID;
@Table(name="departments") @Table(name="departments")
@ -18,6 +19,9 @@ public class Department {
String location; String location;
String phone; String phone;
@OneToMany(cascade = CascadeType.ALL, mappedBy="department")
private List<Patient> patients;
public Department(){ public Department(){
setId(UUID.randomUUID()); setId(UUID.randomUUID());
setName(""); setName("");
@ -31,5 +35,12 @@ public class Department {
setLocation(location); setLocation(location);
setPhone(phone); setPhone(phone);
} }
public Department(UUID id, String name, String location, String phone){
setId(id);
setName(name);
setLocation(location);
setPhone(phone);
}
} }

@ -1,8 +1,9 @@
package space.kklochko.jpa_hospital_example.models; package space.kklochko.spring_rest_example.models;
import jakarta.persistence.*; import jakarta.persistence.*;
import lombok.AllArgsConstructor; import lombok.AllArgsConstructor;
import lombok.Data; import lombok.Data;
import org.springframework.stereotype.Component;
import java.sql.Timestamp; import java.sql.Timestamp;
import java.util.UUID; import java.util.UUID;
@ -11,13 +12,17 @@ import java.util.UUID;
@Entity @Entity
@AllArgsConstructor @AllArgsConstructor
@Data @Data
@Component
public class Indicator { public class Indicator {
@Id @Id
@Column(nullable = true) @Column(nullable = true)
UUID id; private UUID id;
String type; private String type;
String values; private String values;
Timestamp timestamp; private Timestamp timestamp;
@ManyToOne
private Patient patient;
public Indicator(){ public Indicator(){
setId(UUID.randomUUID()); setId(UUID.randomUUID());
@ -32,5 +37,12 @@ public class Indicator {
setValues(values); setValues(values);
setTimestamp(timestamp); setTimestamp(timestamp);
} }
public Indicator(UUID id, String type, String values, Timestamp timestamp){
setId(id);
setType(type);
setValues(values);
setTimestamp(timestamp);
}
} }

@ -1,22 +1,29 @@
package space.kklochko.jpa_hospital_example.models; package space.kklochko.spring_rest_example.models;
import jakarta.persistence.*; import jakarta.persistence.*;
import lombok.AllArgsConstructor; import lombok.AllArgsConstructor;
import lombok.Data; import lombok.Data;
import java.util.ArrayList; import java.util.List;
import java.util.UUID; import java.util.UUID;
@Table(name="patients") @Table(name="patients")
@Entity @Entity
@AllArgsConstructor
@Data @Data
public class Patient { public class Patient {
@Id @Id
@Column(nullable = true) @Column(nullable = true)
UUID id; private UUID id;
String name; private String name;
short age; private short age;
String phone; private String phone;
@OneToMany(cascade = CascadeType.ALL, mappedBy="patient")
private List<Indicator> indicators;
@ManyToOne
private Department department;
public Patient() { public Patient() {
setId(UUID.randomUUID()); setId(UUID.randomUUID());

@ -21,7 +21,9 @@
<property name="hibernate.dialect" value="org.hibernate.dialect.PostgreSQLDialect" /> <property name="hibernate.dialect" value="org.hibernate.dialect.PostgreSQLDialect" />
<!-- Auto create the tables of the entities if they are not exist --> <!-- Auto create the tables of the entities if they are not exist -->
<property name="hibernate.hbm2ddl.auto" value="create" /> <property name="hibernate.hbm2ddl.auto" value="update" />
<!-- <property name="hibernate.show_sql" value="true"/>-->
</properties> </properties>
</persistence-unit> </persistence-unit>
@ -42,7 +44,9 @@
<property name="jakarta.persistence.jdbc.password" value="testpassword" /> <property name="jakarta.persistence.jdbc.password" value="testpassword" />
<property name="hibernate.dialect" value="org.hibernate.dialect.PostgreSQLDialect" /> <property name="hibernate.dialect" value="org.hibernate.dialect.PostgreSQLDialect" />
<!-- Auto create the tables of the entities if they are not exist --> <!-- Auto create the tables of the entities if they are not exist -->
<property name="hibernate.hbm2ddl.auto" value="create" /> <property name="hibernate.hbm2ddl.auto" value="update" />
<property name="hibernate.show_sql" value="true"/>
</properties> </properties>
</persistence-unit> </persistence-unit>
</persistence> </persistence>

@ -1,163 +0,0 @@
package space.kklochko.jpa_hospital_example.cli.commands
import groovy.sql.Sql
import jakarta.persistence.EntityManager
import space.kklochko.jpa_hospital_example.cli.commands.factories.CommandFactory
import space.kklochko.jpa_hospital_example.config.factories.LoadDataBaseConfigFromEnvFile
import space.kklochko.jpa_hospital_example.config.models.DataBaseConfig
import space.kklochko.jpa_hospital_example.db.factories.DataBaseConnection
import space.kklochko.jpa_hospital_example.db.factories.EntityManagerConnection
import space.kklochko.jpa_hospital_example.db.repositories.DepartmentRepository
import space.kklochko.jpa_hospital_example.db.repositories.IndicatorRepository
import space.kklochko.jpa_hospital_example.db.repositories.PatientRepository
import spock.lang.Shared
import spock.lang.Specification
import spock.lang.Stepwise
import spock.lang.Subject
@Stepwise
class CommandEntitySpec extends Specification {
@Shared
Sql sql
@Shared
EntityManager manager
@Shared
DataBaseConfig db
@Shared
DataBaseConnection dbc
def setupSpec() {
db = (new LoadDataBaseConfigFromEnvFile()).load("db.testing")
dbc = new DataBaseConnection(db)
manager = (new EntityManagerConnection("testing")).connect()
sql = Sql.newInstance(db.getUrl(), db.getProperties().get("user"), db.getProperties().get("password"))
}
def "Test insert commands"() {
given: "I have a command data"
CommandData data = new CommandData("insert", datatype, values)
UUID id = UUID.fromString(data.arguments.get("id"))
and: "I have factory for the command"
CommandFactory factory = new CommandFactory()
@Subject
CommandEntity command = factory.create(data, repository)
when: "The command is executed"
def result = command.run()
then: "checking that the insert was successful"
result
id
and: "checking that the entry is added"
def isExist = sql.firstRow(verifyStatement, id)
isExist
cleanup: "remove the data"
sql.execute("delete from " + datatype + "s")
where:
datatype | values | repository || verifyStatement
"indicator" | ["id": "3b3f62f4-75b4-11ee-99cb-c0e4349366ad",
"type": "blood, blood",
"values": "Good samples.",
"timestamp": "2023-10-17 14:30:00"] | new IndicatorRepository(manager) || "SELECT type FROM indicators WHERE id = ?"
"patient" | ["id": "bcbbcdb4-702c-11ee-9113-c0e4349366bd",
"name": "Oleh",
"age": "21",
"phone": "380123451234"] | new PatientRepository(manager) || "SELECT name FROM patients WHERE id = ?"
"department" | ["id": "bcbbcdb4-702c-11ee-9113-c0e4349366cd",
"name": "First department",
"location": "Stepan Bandera Street",
"phone": "380123451244"] | new DepartmentRepository(manager) || "SELECT name FROM departments WHERE id = ?"
}
def "Test update commands"() {
given: "I have a command data"
CommandData data = new CommandData("update", datatype, values)
UUID id = UUID.fromString(data.arguments.get("id"))
and: "I have a fixture"
sql.execute(fixture)
and: "I have factory for the command"
CommandFactory factory = new CommandFactory()
@Subject
CommandEntity command = factory.create(data, repository)
when: "The command is executed"
def result = command.run()
then: "checking that the insert was successful"
result
id
and: "checking that the entry is added"
def isExist = sql.firstRow(verifyStatement, id)
isExist
cleanup: "remove the data"
sql.execute("delete from " + datatype + "s")
where:
datatype | values | fixture | repository || verifyStatement
"indicator" | ["id": "bcbbcdb4-702c-11ee-9113-c0e4349366ab",
"type": "blood, blood",
"values": "Good samples.",
"timestamp": "2023-10-17 14:30:00"] | "insert into indicators (id, type, values, timestamp) values ('bcbbcdb4-702c-11ee-9113-c0e4349366ab', 'Samples', 'fine', '2023-10-17 16:30:00')"
| new IndicatorRepository(manager) || "SELECT type FROM indicators WHERE id = ? AND type='blood, blood'"
"patient" | ["id": "bcbbcdb4-702c-11ee-9113-c0e4349366bb",
"name": "Oleh",
"age": "21",
"phone": "380123451234"] | "insert into patients (id, name, age, phone) values ('bcbbcdb4-702c-11ee-9113-c0e4349366bb', 'Maybe Oleh', 22, '380123451234')"
| new PatientRepository(manager) || "SELECT name FROM patients WHERE id = ? AND name='Oleh'"
"department" | ["id": "bcbbcdb4-702c-11ee-9113-c0e4349366cb",
"name": "First department",
"location": "Stepan Bandera Street",
"phone": "380123451244"] | "insert into departments (id, name, location, phone) values ('bcbbcdb4-702c-11ee-9113-c0e4349366cb', 'Second department', 'Stepan Bandera Street', '380123451244')"
| new DepartmentRepository(manager) || "SELECT name FROM departments WHERE id = ? AND name='First department'"
}
def "Test delete commands"() {
given: "I have a command data"
CommandData data = new CommandData("remove", datatype, values)
UUID id = UUID.fromString(data.arguments.get("id"))
and: "I have a fixture"
sql.execute(fixture)
and: "I have factory for the command"
CommandFactory factory = new CommandFactory()
@Subject
CommandEntity command = factory.create(data, repository)
when: "The command is executed"
def result = command.run()
then: "checking that the insert was successful"
result
id
and: "checking that the entry is added"
def isExist = sql.firstRow(verifyStatement, id)
!isExist
cleanup: "remove the data"
sql.execute("delete from " + datatype + "s")
where:
datatype | values | fixture | repository || verifyStatement
"indicator" | ["id": "bcbbcdb4-702c-11ee-9113-c0e4349366ab"] | "insert into indicators (id, type, values, timestamp) values ('bcbbcdb4-702c-11ee-9113-c0e4349366ab', 'Samples', 'fine', '2023-10-17 16:30:00')"
| new IndicatorRepository(manager) || "SELECT type FROM indicators WHERE id = ?"
"patient" | ["id": "bcbbcdb4-702c-11ee-9113-c0e4349366bb"] | "insert into patients (id, name, age, phone) values ('bcbbcdb4-702c-11ee-9113-c0e4349366bb', 'Maybe Oleh', 22, '380123451234')"
| new PatientRepository(manager) || "SELECT name FROM patients WHERE id = ?"
"department" | ["id": "bcbbcdb4-702c-11ee-9113-c0e4349366cb"] | "insert into departments (id, name, location, phone) values ('bcbbcdb4-702c-11ee-9113-c0e4349366cb', 'Second department', 'Stepan Bandera Street', '380123451244')"
| new DepartmentRepository(manager) || "SELECT name FROM departments WHERE id = ?"
}
}

@ -1,27 +0,0 @@
package space.kklochko.jpa_hospital_example.cli.validators
import spock.lang.Specification
import spock.lang.Subject
class CommandValidatorSpec extends Specification {
def "Parser parse the commands"() {
given: "I have the validator"
@Subject
def validator = new CommandValidator(command)
when: "check if valid"
boolean status = validator.isValid()
then: "the result must be as expected"
status == expectedStatus
where:
command || expectedStatus
"insert indicator(id='1', type='blood', values='Good samples.', timestamp='2023-10-17 14:30:00')" || true
"insert indicator(id='1', type='blood, blood', values='Good samples.', timestamp='2023-10-17 14:30:00')" || true
"update indicator(id='1', type='blood, blood', values='Good samples.', timestamp='2023-10-17 14:30:00')" || true
"remove indicator(id='1', type='blood, blood', values='Good samples.', timestamp='2023-10-17 14:30:00')" || true
"readAll indicator()" || true
}
}

@ -1,28 +0,0 @@
package space.kklochko.jpa_hospital_example.cli.validators
import space.kklochko.jpa_hospital_example.cli.commands.CommandData
import space.kklochko.jpa_hospital_example.cli.parsers.CommandParser
import spock.lang.Specification
import spock.lang.Subject
class InputStringFormatValidatorSpec extends Specification {
def "Parser parse the commands"() {
given: "I have the validator"
@Subject
def validator = new InputStringFormatValidator(command)
when: "check if valid"
boolean status = validator.isValid()
then: "the result must be as expected"
status == expectedStatus
where:
command || expectedStatus
"insert indicator(id='1', type='blood', values='Good samples.', timestamp='2023-10-17 14:30:00')" || true
" insert indicator(id='1', type='blood, blood', values='Good samples.', timestamp='2023-10-17 14:30:00') " || false
"insert indicator(id='1', type='blood, blood', values='Good samples.', timestamp='2023-10-17 14:30:00')" || true
"readAll indicator()" || true
" readAll indicator() " || false
}
}
Loading…
Cancel
Save