From ef8d7397d062cbb37f3a0f2a1d0bc9f225eb2b9b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Dominik=20S=C3=A4ume?= Date: Wed, 22 May 2024 11:56:53 +0200 Subject: [PATCH] #27: WIP MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Dominik Säume --- .idea/dataSources.xml | 2 +- db/nursingHome.db | Bin 57344 -> 61440 bytes .../nhplus/fixtures/MedicationFixture.java | 169 ++++++++++-------- .../hitec/nhplus/medication/Medication.java | 22 ++- .../nhplus/medication/MedicationListCell.java | 6 + .../medication/MedicationModalController.java | 17 +- .../medication/database/MedicationDao.java | 128 ++++++++++--- .../database/Medication_Alternative.sql | 7 + 8 files changed, 245 insertions(+), 106 deletions(-) create mode 100644 src/main/resources/de/hitec/nhplus/medication/database/Medication_Alternative.sql diff --git a/.idea/dataSources.xml b/.idea/dataSources.xml index 98f48a2..fed79a7 100644 --- a/.idea/dataSources.xml +++ b/.idea/dataSources.xml @@ -1,7 +1,7 @@ - + sqlite.xerial true org.sqlite.JDBC diff --git a/db/nursingHome.db b/db/nursingHome.db index b89b1465940bb9f8aa1e08321a549d20da8681fd..6337e9c8d13e3b366fa671793242af08d4debf55 100644 GIT binary patch delta 1274 zcmZvcdrVVT9LMkJee~Ya_7n>iC_){9ASeSF1IC;y(rip#!?Fj=L8TWcmRojdVHiUJ z5tX?GIfz-rAQ;fW7}_olnGqu55Hn?eFqz97Apv}BBO8v1kFZs)|{PO$$ z&hO+@4&ap&c)iamau~xfDA;lX{)g6Y3=wD;-zuYD#pFaQChw9zk)3yIm*|-a`gQU9 zw2JZ*tBF=}hCJP1GZ^7I7NsaC@dGixhhd6zNh8>$UR&`xoXT_R|rUAn3xX|XCc7Sw>H zvqh}Ylxwh>EL^t1Y-M>)n3uB8ru3F{omQ{Y=(X`lI?c1sNP;CAp_z{8Q zBOt=yv>?0_BBy)h9*9ut2Z&I333+@iao+F=A)O$NRv`DBKpOr5e}aSXD`78C?#$xe z1E~@<&ZyHYr6!|=^YX!&=w#NKXW@%XTtT^!x8xR>ExgI7^v0PD$%cH6Eiu`OO02Ab zH&~@!IOD&CHJfc_O9|@|gDITuqj%w<;|fP{rrdtAd+|(6M4w4z9pCDQVIyG&dfBdu z5G^0)IC=Qkh03_jZO{33ojvlBz9}PTUw(AcT=tKJrw5huaYuTa>N+*oeowv`!;I|! zcY8ef`}3`1o{^c8yC;6_^&MR^5cz4a8K*Gsq$+8d@J?C2`M1J=2XWzzP1D^8brXe2 z5A5BO6{__!-?bsy5ca3K0}Bj+(Rd85AP;l1{YVFAXA_XC0q z8Tt-$`>p-EcJ1E3U{9{jt3$f0iI(ficFok!<2ywZrV_#x8F-T+rSb7QZ*8{}45kG& zmPHqi%=l+ibowYiFEw4s9*Vj1_~pd}yTO58Oy5K+q+@i6D(ey zrC6sL^=+OF_`a^TZ8%WZc3XTVcXs-cHsmZ@pF42%3$Ff6M_Z-Bah%Xl04`u~;h!3& dk!az%n}8l+@X<07Ljnhk$n|+V%}Ez0{s!)Y#mE2v delta 1490 zcmYk64NMbf7{~8=*Y|pNv~O#{iWN&?@?os@DrKM!1cr)(%0$MZZn4r6I@&91iwI6j ztLPRrLQiyRrr_jbI(4%{oeH|K%o%ZHMo_mn-G^in<~EIP%5=LHZM@5qyw7{T_y0Wi zf0L)~CRTSAYZyOd$%*PN}Qo{dq!<*{M;>|=PD&bcW`+zSSsAfh9LNQ9F z%EdZK`qDG7$Tyq!lKmoIW}t*J2`xnUas&JE2o(3$`f_+Jctpz{qqhl_MuTpQ=8w>- zP_vmRpDJA=E6QCIYbwsqr;@!kUmkx(Iu;cN2Be9o3PDgzrB>itxBa(5V%2aNYUwyI)k1`nPE&}j5GActn938 zt@J4bAsvK_VJL+OLQGB$f{59W4un(~VbTSi6nzNE&eqalm2fGsj!D(02d>PYELOma zh#1xC{rZ9IsC35F4fNq|5!YJteLSzYGkth>CR=d{hnzoa=Q z!y%8rL3kb>fIO@bEGvWK$B6-=icyiFVudSgY#Hk`=+hXZk>@kt4&a4iIWY*Y!d`fs zmn=&VerA#^u!LKR<|%QE)D@V^IM!vYvb)@@*=crD7)GiK9V@LC2Nxm2NKFoFvsKv~ zE_NJ>kuMgo?iCKF-O82MSe%a1a+||xwH&QmEc3+VQ^z6~ENZ>_!cWfk+TF*x=)}7} zFYbJjwyICZT+Fl-oF-TZt2-`XKK@z zOOsMO=GNNfC!lw4(%S3RSyekfi*iKZ@@Zp-2L`Zf6{jyUmy`Qj3zL_8tZ2;G(b)Wf z?^5IZS*AmeOh@?%G_}Qdj=cZPzhGHzSA|HhRVZgSJFVvY^UKd~`u1Ge z!s}Mzjm!gt$8Enr_tyPAO*ywKuW#s+%)U+!P!|5atozu#6RnTh>!XM*Evf$3Dt^2$ zIWAh;X*yF~+`iEN=i%y;PqahP{p&tTFl{T@wZ3^p^^}fnc!0E`08t9nsw@sL<*%)u z$8Aol+rFS{L&Nv@+4}w4x$VQd7HsZCBcsfN(!zC z$;aE|B^hTAcFZ#+wm)Fw?&1HurPy=3S^Ms$8r^?wTa#{8`0v;&i!(g?8sxE5a9qd{ z1dfCTY;edv3#qUs1B%L1kpE#XIYG!Kj9QKfOGU^I5rW_tO5#VG@mLU&c_ { private static final String SCHEMA = "/de/hitec/nhplus/medication/database/Medication.sql"; private static final String INGREDIENT_SCHEMA = "/de/hitec/nhplus/medication/database/Medication_Ingredient.sql"; + private static final String ALTERNATIVE_SCHEMA = "/de/hitec/nhplus/medication/database/Medication_Alternative.sql"; @Override public void dropTable(Connection connection) throws SQLException { connection.createStatement().execute("DROP TABLE IF EXISTS medication"); - connection.createStatement().execute("DROP TABLE IF EXISTS medication_ingredient"); + connection.createStatement().execute("DROP TABLE IF EXISTS medication_ingredient"); + connection.createStatement().execute("DROP TABLE IF EXISTS medication_alternative"); } @Override @@ -32,16 +34,25 @@ public class MedicationFixture implements Fixture { final InputStream schema = Main.class.getResourceAsStream(SCHEMA); final InputStream ingredientSchema = Main.class.getResourceAsStream(INGREDIENT_SCHEMA); + final InputStream alternativeSchema = Main.class.getResourceAsStream(ALTERNATIVE_SCHEMA); + assert schema != null; assert ingredientSchema != null; + assert alternativeSchema != null; + String SQL = new Scanner(schema, StandardCharsets.UTF_8) - .useDelimiter("\\A") - .next(); + .useDelimiter("\\A") + .next(); String ingredientSQL = ";" + new Scanner(ingredientSchema, StandardCharsets.UTF_8) - .useDelimiter("\\A") - .next(); + .useDelimiter("\\A") + .next(); + String alternativeSQL = ";" + new Scanner(alternativeSchema, StandardCharsets.UTF_8) + .useDelimiter("\\A") + .next(); + connection.createStatement().execute(SQL); connection.createStatement().execute(ingredientSQL); + connection.createStatement().execute(alternativeSQL); } @@ -67,81 +78,87 @@ public class MedicationFixture implements Fixture { Ingredient warfarinnatrium = new Ingredient("Warfarinnatrium"); medications.add(new Medication( - "Metformin", - "AstraZeneca", - List.of( - metforminhydrochlorid, - cellulose, - povidon, - magnesiumstearat - ), - "Übelkeit, Durchfall, Laktatazidose (selten)", - "Oral", - 100 + "Metformin", + "AstraZeneca", + List.of( + metforminhydrochlorid, + cellulose, + povidon, + magnesiumstearat + ), + "Übelkeit, Durchfall, Laktatazidose (selten)", + "Oral", + 100, + new ArrayList<>() )); medications.add(new Medication( - "Lisinopril", - "Teva Pharmaceuticals", - List.of( - lisinoprilDihydrat, - mannitol, - calciumphosphat, - magnesiumstearat - ), - "Schwindel, trockener Husten", - "Oral", - 150 + "Lisinopril", + "Teva Pharmaceuticals", + List.of( + lisinoprilDihydrat, + mannitol, + calciumphosphat, + magnesiumstearat + ), + "Schwindel, trockener Husten", + "Oral", + 150, + new ArrayList<>() )); medications.add(new Medication( - "Simvastatin", - "Mylan", - List.of( - simvastatin, - laktose, - cellulose, - magnesiumstearat - ), - "Muskelschmerzen, Leberprobleme(selten)", - "Oral", - 80 + "Simvastatin", + "Mylan", + List.of( + simvastatin, + laktose, + cellulose, + magnesiumstearat + ), + "Muskelschmerzen, Leberprobleme(selten)", + "Oral", + 80, + new ArrayList<>() )); medications.add(new Medication( - "Enoxaparin", - "Sanofi", - List.of( - enoxaparinNatrium, - benzylalkohol, - wasser - ), - "Blutungen, Reaktionen an der Injektionsstelle", - "Unterhautinjektion", - 120 + "Enoxaparin", + "Sanofi", + List.of( + enoxaparinNatrium, + benzylalkohol, + wasser + ), + "Blutungen, Reaktionen an der Injektionsstelle", + "Unterhautinjektion", + 120, + new ArrayList<>() )); medications.add(new Medication( - "Levothyroxin", - "Sandoz", - List.of( - levothyroxinnatrium, - laktose, - staerke, - akaziengummi - ), - "Herzrasen, Gewichtsverlust", - "Oral", - 90 + "Levothyroxin", + "Sandoz", + List.of( + levothyroxinnatrium, + laktose, + staerke, + akaziengummi + ), + "Herzrasen, Gewichtsverlust", + "Oral", + 90, + new ArrayList<>() )); medications.add(new Medication( - "Warfarin", - "Apotex Inc.", - List.of( - warfarinnatrium, - laktose, - staerke, - magnesiumstearat - ), - "Blutungen, Blutergüsse", - "Oral", - 110 + "Warfarin", + "Apotex Inc.", + List.of( + warfarinnatrium, + laktose, + staerke, + magnesiumstearat + ), + "Blutungen, Blutergüsse", + "Oral", + 110, + new ArrayList<>() )); MedicationDao dao = DaoFactory.getInstance().createMedicationDAO(); Map medicationsByName = new HashMap<>(); diff --git a/src/main/java/de/hitec/nhplus/medication/Medication.java b/src/main/java/de/hitec/nhplus/medication/Medication.java index 7fdce57..db4f595 100644 --- a/src/main/java/de/hitec/nhplus/medication/Medication.java +++ b/src/main/java/de/hitec/nhplus/medication/Medication.java @@ -23,6 +23,7 @@ public class Medication { private final SimpleStringProperty possibleSideEffects; private final SimpleStringProperty administrationMethod; private final SimpleIntegerProperty currentStock; + private final SimpleListProperty alternativeMedication; /** * This constructor allows instantiating a {@link Medication} object, @@ -37,7 +38,8 @@ public class Medication { List ingredients, String possibleSideEffects, String administrationMethod, - int currentStock + int currentStock, + List alternativeMedication ) { this.name = new SimpleStringProperty(name); this.manufacturer = new SimpleStringProperty(manufacturer); @@ -45,6 +47,7 @@ public class Medication { this.possibleSideEffects = new SimpleStringProperty(possibleSideEffects); this.administrationMethod = new SimpleStringProperty(administrationMethod); this.currentStock = new SimpleIntegerProperty(currentStock); + this.alternativeMedication = new SimpleListProperty<>(FXCollections.observableArrayList(alternativeMedication)); } /** @@ -57,7 +60,8 @@ public class Medication { List ingredients, String possibleSideEffects, String administrationMethod, - int currentStock + int currentStock, + List alternativeMedication ) { this.id = new SimpleIntegerProperty(id); this.name = new SimpleStringProperty(name); @@ -66,6 +70,7 @@ public class Medication { this.possibleSideEffects = new SimpleStringProperty(possibleSideEffects); this.administrationMethod = new SimpleStringProperty(administrationMethod); this.currentStock = new SimpleIntegerProperty(currentStock); + this.alternativeMedication = new SimpleListProperty<>(FXCollections.observableArrayList(alternativeMedication)); } public int getId() { @@ -124,6 +129,18 @@ public class Medication { this.possibleSideEffects.set(possibleSideEffects); } + public ObservableList getAlternativeMedication() { + return alternativeMedication.get(); + } + + public SimpleListProperty alternativeMedicationProperty() { + return alternativeMedication; + } + + public void setAlternativeMedication(List alternativeMedication) { + this.alternativeMedication.set(FXCollections.observableArrayList(alternativeMedication)); + } + public String getAdministrationMethod() { return administrationMethod.get(); } @@ -162,6 +179,7 @@ public class Medication { .add("Possible Side Effects: " + this.getPossibleSideEffects()) .add("Administration Method: " + this.getAdministrationMethod()) .add("Current Stock: " + this.getCurrentStock()) + .add("Alternative Medication" + this.getAlternativeMedication()) .toString(); } diff --git a/src/main/java/de/hitec/nhplus/medication/MedicationListCell.java b/src/main/java/de/hitec/nhplus/medication/MedicationListCell.java index 608267b..3c8a5f5 100644 --- a/src/main/java/de/hitec/nhplus/medication/MedicationListCell.java +++ b/src/main/java/de/hitec/nhplus/medication/MedicationListCell.java @@ -68,7 +68,13 @@ public class MedicationListCell extends ListCell { Medication oldValue, Medication newValue ) { + Medication selectedMedication = comboBox.getValue(); ListView listView = getListView(); + + listView.getItems().remove(getItem()); + listView.getItems().add(selectedMedication); + setItem(selectedMedication); + double max = listView.lookupAll("*") .stream() .filter(node -> node instanceof MedicationListCell) diff --git a/src/main/java/de/hitec/nhplus/medication/MedicationModalController.java b/src/main/java/de/hitec/nhplus/medication/MedicationModalController.java index fa89b39..737de23 100644 --- a/src/main/java/de/hitec/nhplus/medication/MedicationModalController.java +++ b/src/main/java/de/hitec/nhplus/medication/MedicationModalController.java @@ -70,7 +70,8 @@ public class MedicationModalController { new ArrayList<>(), "", "", - 0 + 0, + new ArrayList<>() ); this.buttonSave.setDisable(true); } @@ -103,6 +104,7 @@ public class MedicationModalController { */ private void showData() { ingredients.setAll(medication.getIngredients()); + alternativeMediaction.setAll(medication.getAlternativeMedication()); try { allOtherMedications = controller.getDao().readAll(); if (!isNewMedication) { @@ -137,6 +139,14 @@ public class MedicationModalController { .toList() ); + List meds = alternativeMediaction + .stream() + .distinct() + .toList(); + this.medication.setAlternativeMedication( + meds + ); + if (isNewMedication) { controller.createMedication(medication); } else { @@ -161,10 +171,11 @@ public class MedicationModalController { alternativeMediaction.add(new Medication( null, null, - List.of(), + new ArrayList<>(), null, null, - -1 + -1, + new ArrayList<>() )); } } diff --git a/src/main/java/de/hitec/nhplus/medication/database/MedicationDao.java b/src/main/java/de/hitec/nhplus/medication/database/MedicationDao.java index e226770..cb16cee 100644 --- a/src/main/java/de/hitec/nhplus/medication/database/MedicationDao.java +++ b/src/main/java/de/hitec/nhplus/medication/database/MedicationDao.java @@ -63,33 +63,41 @@ public class MedicationDao implements Dao { ingredientStatement.setString(2, ingredient.getName()); ingredientStatement.execute(); } + + final String alternativeMedicationSQL = """ + INSERT INTO medication_alternative + (id, alternativeId) + VALUES (?, ?); + """; + for (Medication alternative : medication.getAlternativeMedication()) { + PreparedStatement alternativeStatement = this.connection.prepareStatement(alternativeMedicationSQL); + alternativeStatement.setInt(1, newId); + alternativeStatement.setInt(2, alternative.getId()); + alternativeStatement.execute(); + } } @Override public Medication read(int id) throws SQLException { - final String SQL = """ - SELECT medication.*, medication_ingredient.id - FROM medication - LEFT JOIN medication_ingredient ON medication.id = medication_ingredient.id - WHERE medication.id = ? - """; - PreparedStatement statement = this.connection.prepareStatement(SQL); - statement.setInt(1, id); - ResultSet result = statement.executeQuery(); + ResultSet result = getReadStatement(id).executeQuery(); return getInstanceFromResultSet(result); } @Override public List readAll() throws SQLException { final String SQL = """ - SELECT medication.*, medication_ingredient.name - FROM medication LEFT JOIN + SELECT medication.*, medication_ingredient.name, medication_alternative.alternativeId + FROM medication + LEFT JOIN medication_ingredient ON medication.id = medication_ingredient.id + LEFT JOIN + medication_alternative ON medication.id = medication_alternative.id """; ResultSet result = connection.prepareStatement(SQL).executeQuery(); - List medications = new ArrayList<>(); + Map medications = new HashMap<>(); Map> ingredientMap = new HashMap<>(); + Map> alternativesMap = new HashMap<>(); int currentMedicationId; int lastMedicationId = -1; @@ -103,27 +111,41 @@ public class MedicationDao implements Dao { new ArrayList<>(), result.getString(4), result.getString(5), - result.getInt(6) + result.getInt(6), + new ArrayList<>() ); - medications.add(medication); + medications.put(currentMedicationId, medication); } + List ingredients = ingredientMap.computeIfAbsent(currentMedicationId, k -> new ArrayList<>()); String ingredientName = result.getString(7); - if(ingredientName == null){ - continue; + if (ingredientName != null) { + ingredients.add(new Ingredient(ingredientName)); } - ingredients.add(new Ingredient(ingredientName)); + + List alternatives = alternativesMap.computeIfAbsent(currentMedicationId, k -> new ArrayList<>()); + int alternativeId = result.getInt(8); + if (alternativeId != 0) { + alternatives.add(alternativeId); + } + lastMedicationId = currentMedicationId; } - for (Medication medication : medications) { + for (Medication medication : medications.values()) { List ingredients = ingredientMap.get(medication.getId()); - if(ingredients.isEmpty()){ + if (ingredients.isEmpty()) { continue; } medication.setIngredients(ingredientMap.get(medication.getId())); + List alternativeIds = alternativesMap.get(medication.getId()); + List alternativs = new ArrayList<>(); + for (Integer alternativeId : alternativeIds) { + alternativs.add(medications.get(alternativeId)); + } + medication.setAlternativeMedication(alternativs); } - return medications; + return medications.values().stream().toList(); } @Override @@ -164,6 +186,25 @@ public class MedicationDao implements Dao { statement.setString(2, ingredient.getName()); statement.execute(); } + + final String alternativeDeleteSQL = """ + DELETE FROM medication_alternative WHERE id = ? + """; + PreparedStatement alternativeStatement = this.connection.prepareStatement(alternativeDeleteSQL); + alternativeStatement.setInt(1, medication.getId()); + alternativeStatement.executeUpdate(); + + final String alternativeCreateSQL = """ + INSERT INTO medication_alternative + (id, alternativeId) + VALUES (?, ?); + """; + for (Medication alternative : medication.getAlternativeMedication()) { + PreparedStatement statement = this.connection.prepareStatement(alternativeCreateSQL); + statement.setInt(1, medication.getId()); + statement.setInt(2, alternative.getId()); + statement.execute(); + } } @Override @@ -176,6 +217,23 @@ public class MedicationDao implements Dao { preparedStatement.executeUpdate(); } + /** + * @param id The ID of the database entry to read. + * @return A {@link PreparedStatement} to read a specific entry by its ID. + */ + public PreparedStatement getReadStatement(int id) throws SQLException { + final String SQL = """ + SELECT medication.*, medication_ingredient.name, medication_alternative.alternativeId + FROM medication + LEFT JOIN medication_ingredient ON medication.id = medication_ingredient.id + LEFT JOIN medication_alternative ON medication.id = medication_alternative.id + WHERE medication.id = ? + """; + PreparedStatement statement = this.connection.prepareStatement(SQL); + statement.setInt(1, id); + return statement; + } + /** * Constructs a {@link Medication} object from the {@link ResultSet} obtained after executing a database query. * This method is used internally to map the {@link ResultSet} data to a {@link Medication} object. @@ -188,18 +246,40 @@ public class MedicationDao implements Dao { result.getInt(1), result.getString(2), result.getString(3), - List.of(), + new ArrayList<>(), result.getString(4), result.getString(5), - result.getInt(6) + result.getInt(6), + new ArrayList<>() ); List ingredients = new ArrayList<>(); + List alternatives = new ArrayList<>(); while (result.next()) { - ingredients.add(new Ingredient(result.getString(2))); - + String ingredientName = result.getString(7); + if (ingredientName != null) { + ingredients.add(new Ingredient(ingredientName)); + } + int alternativeId = result.getInt(8); + if (alternativeId != 0) { + ResultSet alternativeResult = getReadStatement(alternativeId).executeQuery(); + Medication alternativeMedication = new Medication( + alternativeResult.getInt(1), + alternativeResult.getString(2), + alternativeResult.getString(3), + new ArrayList<>(), + alternativeResult.getString(4), + alternativeResult.getString(5), + alternativeResult.getInt(6), + new ArrayList<>() + ); + alternatives.add(alternativeMedication); + } } medication.setIngredients(ingredients); + medication.setAlternativeMedication(alternatives); return medication; + + } } diff --git a/src/main/resources/de/hitec/nhplus/medication/database/Medication_Alternative.sql b/src/main/resources/de/hitec/nhplus/medication/database/Medication_Alternative.sql new file mode 100644 index 0000000..76e3364 --- /dev/null +++ b/src/main/resources/de/hitec/nhplus/medication/database/Medication_Alternative.sql @@ -0,0 +1,7 @@ +CREATE TABLE medication_alternative +( + id INTEGER NOT NULL , + alternativeId INTEGER NOT NULL , + FOREIGN KEY (id) REFERENCES medication (id) ON DELETE CASCADE, + FOREIGN KEY (alternativeId) REFERENCES medication (id) ON DELETE CASCADE +) \ No newline at end of file