diff --git a/src/main/java/PasswordManager.java b/src/main/java/PasswordManager.java index 29960fd..f17f6f1 100644 --- a/src/main/java/PasswordManager.java +++ b/src/main/java/PasswordManager.java @@ -1,6 +1,7 @@ import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; +import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; import java.lang.reflect.Modifier; import java.nio.charset.StandardCharsets; @@ -12,6 +13,9 @@ public class PasswordManager implements PasswordManagerInterface { boolean running = true; InputStream inputStream = System.in; OutputStream outputStream = System.out; + ArrayList vaults = new ArrayList<>(); + int selectedVaultId = -1; + ArrayList vaultOperationOptions = new ArrayList<>(); public static void main(String[] args) { PasswordManager pm = new PasswordManager(); @@ -26,11 +30,6 @@ public class PasswordManager implements PasswordManagerInterface { println("Hello World"); } - @Override - public void listVaults() { - println("Vaults:"); - } - private void println(String output) { try { outputStream.write((output + "\n").getBytes(StandardCharsets.UTF_8)); @@ -39,6 +38,18 @@ public class PasswordManager implements PasswordManagerInterface { } } + @Override + public void listVaults() { + println("Vaults:"); + for (int i = 0; i < vaults.size(); i++) { + println("- vault id: " + i); + } + } + + public void createNewVault() { + vaults.add(new Vault()); + } + @Override public void openVault() { @@ -53,8 +64,10 @@ public class PasswordManager implements PasswordManagerInterface { sb.append("\nciip Gruppe 8 - Password Manager\n\n"); sb.append("Menu:\n"); - sb.append("- list vaults: l:\n"); - sb.append("- select vault: v x (replace x with vault id)\n"); + sb.append("- list vaults: l\n"); + sb.append("- create new vault: v\n"); + sb.append("- select vault and show operations: v x (replace x with vault id)\n"); + sb.append("- select vault operation: o x (replace o with a operation id for the selected vault)\n"); sb.append("- exit: e\n"); println(sb.toString()); @@ -65,7 +78,9 @@ public class PasswordManager implements PasswordManagerInterface { running = false; } else if (input.equals("l")) { listVaults(); - } else if (input.startsWith("v")) { + } else if (input.equals("v")) { + createNewVault(); + } else if (input.startsWith("v")) { String vaultAction = (input.replace('v', ' ')).trim(); int vaultId = -1; @@ -76,14 +91,16 @@ public class PasswordManager implements PasswordManagerInterface { } if (vaultId >= 0) { + selectedVaultId = vaultId; + println("\nVault " + vaultId + " selected."); try { int internalOptionCounter = 0; - ArrayList options = new ArrayList<>(); + println("\nAvailable vault operations:"); for (Method m : Class.forName("Vault").getDeclaredMethods()) { // returns all declared methods including private or protected try { - if (Modifier.isPublic(this.getClass().getDeclaredMethod(m.getName()).getModifiers())) { // filter out methods that are not public (using Modifier) or have arguments (using getDeclaredMethod) - options.add(m.getName()); + if (Modifier.isPublic(Class.forName("Vault").getDeclaredMethod(m.getName()).getModifiers())) { // filter out methods that are not public (using Modifier) or have arguments (using getDeclaredMethod) + vaultOperationOptions.add(m.getName()); println(internalOptionCounter + " - " + m.getName()); internalOptionCounter++; } @@ -95,6 +112,30 @@ public class PasswordManager implements PasswordManagerInterface { println("-- vaults not implemented yet"); } } + } else if (input.startsWith("o")) { + String operation = (input.replace('o', ' ')).trim(); + int operationId = -1; + + try { + operationId = Integer.parseInt(operation); + } catch (NumberFormatException e) { + println("-- please enter a valid operation id"); + } + + if (selectedVaultId < 0) { + println("-- a vault needs to be selected"); + } else if (operationId >= 0 && operationId < vaultOperationOptions.size()) { + Vault vault = vaults.get(selectedVaultId); + try { + println("Run selected operation '" + vaultOperationOptions.get(operationId) + "':"); + vault.getClass().getDeclaredMethod(vaultOperationOptions.get(operationId)).invoke(vault); + } catch (IllegalAccessException | NoSuchMethodException | InvocationTargetException e) { + e.printStackTrace(); + println("-- selected operation failed"); + } + } else { + println("-- please enter a valid operation id"); + } } } } diff --git a/src/test/java/PasswordManagerTest.java b/src/test/java/PasswordManagerTest.java index c96f747..76bff98 100644 --- a/src/test/java/PasswordManagerTest.java +++ b/src/test/java/PasswordManagerTest.java @@ -46,7 +46,18 @@ class PasswordManagerTest { pm.inputStream = new ByteArrayInputStream("l\n".getBytes(StandardCharsets.UTF_8)); pm.outputStream = outputStream; pm.showMenu(); - assertTrue(outputStream.toString().endsWith("Vaults:\n")); + pm.createNewVault(); + assertTrue(outputStream.toString().contains("Vaults:\n- vault id: 0\n")); + } + + @Test + void menuNavigationCreateNewVault() { + ByteArrayOutputStream outputStream = new ByteArrayOutputStream(); + pm.inputStream = new ByteArrayInputStream("v\n".getBytes(StandardCharsets.UTF_8)); + pm.outputStream = outputStream; + int vaultCount = pm.vaults.size(); + pm.showMenu(); + assertEquals(vaultCount + 1, pm.vaults.size()); } @Test @@ -58,6 +69,39 @@ class PasswordManagerTest { assertFalse(outputStream.toString().endsWith("-- vaults not implemented yet\n")); } + @Test + void menuNavigationSelectVaultOperation() { + ByteArrayOutputStream outputStream = new ByteArrayOutputStream(); + + pm.inputStream = new ByteArrayInputStream("v\n".getBytes(StandardCharsets.UTF_8)); + pm.outputStream = new ByteArrayOutputStream(); + pm.showMenu(); + + pm.inputStream = new ByteArrayInputStream("v 0\n".getBytes(StandardCharsets.UTF_8)); + pm.outputStream = new ByteArrayOutputStream(); + pm.showMenu(); + + pm.inputStream = new ByteArrayInputStream("o 0\n".getBytes(StandardCharsets.UTF_8)); + pm.outputStream = outputStream; + pm.showMenu(); + assertTrue(outputStream.toString().contains("Run selected operation")); + + outputStream = new ByteArrayOutputStream(); + + pm.inputStream = new ByteArrayInputStream("o foobert\n".getBytes(StandardCharsets.UTF_8)); + pm.outputStream = outputStream; + pm.showMenu(); + assertTrue(outputStream.toString().endsWith("-- please enter a valid operation id\n")); + + outputStream = new ByteArrayOutputStream(); + + pm.inputStream = new ByteArrayInputStream("o 1000\n".getBytes(StandardCharsets.UTF_8)); + pm.outputStream = outputStream; + pm.showMenu(); + System.out.println(outputStream); + assertTrue(outputStream.toString().endsWith("-- please enter a valid operation id\n")); + } + @Test void showMenu() { ByteArrayOutputStream outputStream = new ByteArrayOutputStream(); @@ -88,6 +132,13 @@ class PasswordManagerTest { assertTrue(outputStream.toString().startsWith("\nciip Gruppe 8")); } + @Test + void createNewVault() { + int vaultCount = pm.vaults.size(); + pm.createNewVault(); + assertEquals(vaultCount + 1, pm.vaults.size()); + } + private ByteArrayInputStream getEmptyStringInputStream() { return new ByteArrayInputStream("".getBytes(StandardCharsets.UTF_8)); }