From 4ecefe4e8aa3c2e540aff9f9063948ac211b7884 Mon Sep 17 00:00:00 2001 From: jxwatson251 <jxwatson251@gmail.com> Date: Sat, 26 Apr 2025 02:25:12 +0000 Subject: [PATCH 1/2] lesson_17 --- .../com/codedifferently/lesson17/bank/SavingAccount.java | 5 +++++ 1 file changed, 5 insertions(+) create mode 100644 lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/SavingAccount.java diff --git a/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/SavingAccount.java b/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/SavingAccount.java new file mode 100644 index 00000000..0c07e02a --- /dev/null +++ b/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/SavingAccount.java @@ -0,0 +1,5 @@ +package com.codedifferently.lesson17.bank; + +public class SavingAccount { + +} From b0099ab29cb27f88025901166a2a62b32b0695b1 Mon Sep 17 00:00:00 2001 From: jxwatson251 <jxwatson251@gmail.com> Date: Sun, 27 Apr 2025 20:40:59 +0000 Subject: [PATCH 2/2] feat: adds savingsaccount and businesscheckingaccount class modified other classes --- .../lesson17/bank/BankAccount.java | 117 ++++++++++++++++++ .../lesson17/bank/BankAtm.java | 16 +-- ...ount.java => BusinessCheckingAccount.java} | 4 +- .../codedifferently/lesson17/bank/Check.java | 6 +- .../lesson17/bank/CheckingAccount.java | 104 +--------------- .../lesson17/bank/Customer.java | 6 +- .../lesson17/bank/SavingsAccount.java | 23 ++++ .../lesson17/bank/BankAtmTest.java | 4 +- .../lesson17/bank/SavingsAccountTest.java | 106 ++++++++++++++++ 9 files changed, 265 insertions(+), 121 deletions(-) create mode 100644 lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/BankAccount.java rename lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/{SavingAccount.java => BusinessCheckingAccount.java} (52%) create mode 100644 lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/SavingsAccount.java create mode 100644 lesson_17/bank/bank_app/src/test/java/com/codedifferently/lesson17/bank/SavingsAccountTest.java diff --git a/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/BankAccount.java b/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/BankAccount.java new file mode 100644 index 00000000..322fa07f --- /dev/null +++ b/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/BankAccount.java @@ -0,0 +1,117 @@ +package com.codedifferently.lesson17.bank; + +import com.codedifferently.lesson17.bank.exceptions.InsufficientFundsException; +import java.util.Set; + +/** + * @author vscode + */ +public class BankAccount { + + protected final Set<Customer> owners; + protected final String accountNumber; + protected double balance; + protected boolean isActive; + + public BankAccount(String accountNumber, Set<Customer> owners, double initialBalance) { + this.accountNumber = accountNumber; + this.owners = owners; + this.balance = initialBalance; + isActive = true; + } + + /** + * Gets the account number. + * + * @return The account number. + */ + public String getAccountNumber() { + return accountNumber; + } + + /** + * Gets the owners of the account. + * + * @return The owners of the account. + */ + public Set<Customer> getOwners() { + return owners; + } + + /** + * Deposits funds into the account. + * + * @param amount The amount to deposit. + */ + public void deposit(double amount) throws IllegalStateException { + if (isClosed()) { + throw new IllegalStateException("Cannot deposit to a closed account"); + } + if (amount <= 0) { + throw new IllegalArgumentException("Deposit amount must be positive"); + } + balance += amount; + } + + /** + * Withdraws funds from the account. + * + * @param amount + * @throws InsufficientFundsException + */ + public void withdraw(double amount) throws InsufficientFundsException { + if (isClosed()) { + throw new IllegalStateException("Cannot withdraw from a closed account"); + } + if (amount <= 0) { + throw new IllegalStateException("Withdrawal amount must be positive"); + } + if (balance < amount) { + throw new InsufficientFundsException("Account does not have enough funds for withdrawal"); + } + balance -= amount; + } + + /** + * Gets the balance of the account. + * + * @return The balance of the account. + */ + public double getBalance() { + return balance; + } + + /** Closes the account. */ + public void closeAccount() throws IllegalStateException { + if (balance > 0) { + throw new IllegalStateException("Cannot close account with a positive balance"); + } + isActive = false; + } + + /** + * Checks if the account is closed. + * + * @return True if the account is closed, otherwise false. + */ + public boolean isClosed() { + return !isActive; + } + + @Override + public int hashCode() { + return accountNumber.hashCode(); + } + + @Override + public boolean equals(Object obj) { + if (obj instanceof BankAccount other) { + return accountNumber.equals(other.accountNumber); + } + return false; + } + + public String toString() { + return null; + } +} diff --git a/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/BankAtm.java b/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/BankAtm.java index 8cbcd3cc..f7df8ca6 100644 --- a/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/BankAtm.java +++ b/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/BankAtm.java @@ -10,14 +10,14 @@ public class BankAtm { private final Map<UUID, Customer> customerById = new HashMap<>(); - private final Map<String, CheckingAccount> accountByNumber = new HashMap<>(); + private final Map<String, BankAccount> accountByNumber = new HashMap<>(); /** * Adds a checking account to the bank. * * @param account The account to add. */ - public void addAccount(CheckingAccount account) { + public void addAccount(BankAccount account) { accountByNumber.put(account.getAccountNumber(), account); account .getOwners() @@ -33,7 +33,7 @@ public void addAccount(CheckingAccount account) { * @param customerId The ID of the customer. * @return The unique set of accounts owned by the customer. */ - public Set<CheckingAccount> findAccountsByCustomerId(UUID customerId) { + public Set<BankAccount> findAccountsByCustomerId(UUID customerId) { return customerById.containsKey(customerId) ? customerById.get(customerId).getAccounts() : Set.of(); @@ -46,7 +46,7 @@ public Set<CheckingAccount> findAccountsByCustomerId(UUID customerId) { * @param amount The amount to deposit. */ public void depositFunds(String accountNumber, double amount) { - CheckingAccount account = getAccountOrThrow(accountNumber); + BankAccount account = getAccountOrThrow(accountNumber); account.deposit(amount); } @@ -57,7 +57,7 @@ public void depositFunds(String accountNumber, double amount) { * @param check The check to deposit. */ public void depositFunds(String accountNumber, Check check) { - CheckingAccount account = getAccountOrThrow(accountNumber); + BankAccount account = getAccountOrThrow(accountNumber); check.depositFunds(account); } @@ -68,7 +68,7 @@ public void depositFunds(String accountNumber, Check check) { * @param amount */ public void withdrawFunds(String accountNumber, double amount) { - CheckingAccount account = getAccountOrThrow(accountNumber); + BankAccount account = getAccountOrThrow(accountNumber); account.withdraw(amount); } @@ -78,8 +78,8 @@ public void withdrawFunds(String accountNumber, double amount) { * @param accountNumber The account number. * @return The account. */ - private CheckingAccount getAccountOrThrow(String accountNumber) { - CheckingAccount account = accountByNumber.get(accountNumber); + private BankAccount getAccountOrThrow(String accountNumber) { + BankAccount account = accountByNumber.get(accountNumber); if (account == null || account.isClosed()) { throw new AccountNotFoundException("Account not found"); } diff --git a/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/SavingAccount.java b/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/BusinessCheckingAccount.java similarity index 52% rename from lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/SavingAccount.java rename to lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/BusinessCheckingAccount.java index 0c07e02a..a1485670 100644 --- a/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/SavingAccount.java +++ b/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/BusinessCheckingAccount.java @@ -1,5 +1,3 @@ package com.codedifferently.lesson17.bank; -public class SavingAccount { - -} +public class BusinessCheckingAccount {} diff --git a/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/Check.java b/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/Check.java index 061fa4a5..d30c8ea0 100644 --- a/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/Check.java +++ b/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/Check.java @@ -43,14 +43,14 @@ public void voidCheck() { /** * Deposits the check into an account. * - * @param toAccount The account to deposit the check into. + * @param account2 The account to deposit the check into. */ - public void depositFunds(CheckingAccount toAccount) { + public void depositFunds(BankAccount account2) { if (isVoided) { throw new CheckVoidedException("Check is voided"); } account.withdraw(amount); - toAccount.deposit(amount); + account2.deposit(amount); voidCheck(); } diff --git a/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/CheckingAccount.java b/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/CheckingAccount.java index 5d8aeb74..57d09ffc 100644 --- a/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/CheckingAccount.java +++ b/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/CheckingAccount.java @@ -1,15 +1,9 @@ package com.codedifferently.lesson17.bank; -import com.codedifferently.lesson17.bank.exceptions.InsufficientFundsException; import java.util.Set; /** Represents a checking account. */ -public class CheckingAccount { - - private final Set<Customer> owners; - private final String accountNumber; - private double balance; - private boolean isActive; +public class CheckingAccount extends BankAccount { /** * Creates a new checking account. @@ -19,101 +13,7 @@ public class CheckingAccount { * @param initialBalance The initial balance of the account. */ public CheckingAccount(String accountNumber, Set<Customer> owners, double initialBalance) { - this.accountNumber = accountNumber; - this.owners = owners; - this.balance = initialBalance; - isActive = true; - } - - /** - * Gets the account number. - * - * @return The account number. - */ - public String getAccountNumber() { - return accountNumber; - } - - /** - * Gets the owners of the account. - * - * @return The owners of the account. - */ - public Set<Customer> getOwners() { - return owners; - } - - /** - * Deposits funds into the account. - * - * @param amount The amount to deposit. - */ - public void deposit(double amount) throws IllegalStateException { - if (isClosed()) { - throw new IllegalStateException("Cannot deposit to a closed account"); - } - if (amount <= 0) { - throw new IllegalArgumentException("Deposit amount must be positive"); - } - balance += amount; - } - - /** - * Withdraws funds from the account. - * - * @param amount - * @throws InsufficientFundsException - */ - public void withdraw(double amount) throws InsufficientFundsException { - if (isClosed()) { - throw new IllegalStateException("Cannot withdraw from a closed account"); - } - if (amount <= 0) { - throw new IllegalStateException("Withdrawal amount must be positive"); - } - if (balance < amount) { - throw new InsufficientFundsException("Account does not have enough funds for withdrawal"); - } - balance -= amount; - } - - /** - * Gets the balance of the account. - * - * @return The balance of the account. - */ - public double getBalance() { - return balance; - } - - /** Closes the account. */ - public void closeAccount() throws IllegalStateException { - if (balance > 0) { - throw new IllegalStateException("Cannot close account with a positive balance"); - } - isActive = false; - } - - /** - * Checks if the account is closed. - * - * @return True if the account is closed, otherwise false. - */ - public boolean isClosed() { - return !isActive; - } - - @Override - public int hashCode() { - return accountNumber.hashCode(); - } - - @Override - public boolean equals(Object obj) { - if (obj instanceof CheckingAccount other) { - return accountNumber.equals(other.accountNumber); - } - return false; + super(accountNumber, owners, initialBalance); } @Override diff --git a/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/Customer.java b/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/Customer.java index af084713..3057f681 100644 --- a/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/Customer.java +++ b/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/Customer.java @@ -9,7 +9,7 @@ public class Customer { private final UUID id; private final String name; - private final Set<CheckingAccount> accounts = new HashSet<>(); + private final Set<BankAccount> accounts = new HashSet<>(); /** * Creates a new customer. @@ -45,7 +45,7 @@ public String getName() { * * @param account The account to add. */ - public void addAccount(CheckingAccount account) { + public void addAccount(BankAccount account) { accounts.add(account); } @@ -54,7 +54,7 @@ public void addAccount(CheckingAccount account) { * * @return The unique set of accounts owned by the customer. */ - public Set<CheckingAccount> getAccounts() { + public Set<BankAccount> getAccounts() { return accounts; } diff --git a/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/SavingsAccount.java b/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/SavingsAccount.java new file mode 100644 index 00000000..775bdd81 --- /dev/null +++ b/lesson_17/bank/bank_app/src/main/java/com/codedifferently/lesson17/bank/SavingsAccount.java @@ -0,0 +1,23 @@ +package com.codedifferently.lesson17.bank; + +import java.util.Set; + +public class SavingsAccount extends BankAccount { + + public SavingsAccount(String accountNumber, Set<Customer> owners, double initialBalance) { + super(accountNumber, owners, initialBalance); + } + + @Override + public String toString() { + return "SavingsAccount{" + + "accountNumber='" + + accountNumber + + '\'' + + ", balance=" + + balance + + ", isActive=" + + isActive + + '}'; + } +} diff --git a/lesson_17/bank/bank_app/src/test/java/com/codedifferently/lesson17/bank/BankAtmTest.java b/lesson_17/bank/bank_app/src/test/java/com/codedifferently/lesson17/bank/BankAtmTest.java index fa4a913a..325f2345 100644 --- a/lesson_17/bank/bank_app/src/test/java/com/codedifferently/lesson17/bank/BankAtmTest.java +++ b/lesson_17/bank/bank_app/src/test/java/com/codedifferently/lesson17/bank/BankAtmTest.java @@ -43,14 +43,14 @@ void testAddAccount() { classUnderTest.addAccount(account3); // Assert - Set<CheckingAccount> accounts = classUnderTest.findAccountsByCustomerId(customer3.getId()); + Set<BankAccount> accounts = classUnderTest.findAccountsByCustomerId(customer3.getId()); assertThat(accounts).containsOnly(account3); } @Test void testFindAccountsByCustomerId() { // Act - Set<CheckingAccount> accounts = classUnderTest.findAccountsByCustomerId(customer1.getId()); + Set<BankAccount> accounts = classUnderTest.findAccountsByCustomerId(customer1.getId()); // Assert assertThat(accounts).containsOnly(account1, account2); diff --git a/lesson_17/bank/bank_app/src/test/java/com/codedifferently/lesson17/bank/SavingsAccountTest.java b/lesson_17/bank/bank_app/src/test/java/com/codedifferently/lesson17/bank/SavingsAccountTest.java new file mode 100644 index 00000000..934ea6b7 --- /dev/null +++ b/lesson_17/bank/bank_app/src/test/java/com/codedifferently/lesson17/bank/SavingsAccountTest.java @@ -0,0 +1,106 @@ +package com.codedifferently.lesson17.bank; + +import static org.assertj.core.api.Assertions.assertThatExceptionOfType; +import static org.junit.jupiter.api.Assertions.assertEquals; +import static org.junit.jupiter.api.Assertions.assertFalse; +import static org.junit.jupiter.api.Assertions.assertTrue; + +import com.codedifferently.lesson17.bank.exceptions.InsufficientFundsException; +import java.util.HashSet; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class SavingsAccountTest { + + private SavingsAccount classUnderTest; + private Set<Customer> owners; + + @BeforeEach + void setUp() { + owners = new HashSet<>(); + owners.add(new Customer(UUID.randomUUID(), "John Doe")); + owners.add(new Customer(UUID.randomUUID(), "Jane Smith")); + classUnderTest = new SavingsAccount("123456789", owners, 100.0); + } + + @Test + void getAccountNumber() { + assertEquals("123456789", classUnderTest.getAccountNumber()); + } + + @Test + void getOwners() { + assertEquals(owners, classUnderTest.getOwners()); + } + + @Test + void deposit() { + classUnderTest.deposit(50.0); + assertEquals(150.0, classUnderTest.getBalance()); + } + + @Test + void deposit_withNegativeAmount() { + assertThatExceptionOfType(IllegalArgumentException.class) + .isThrownBy(() -> classUnderTest.deposit(-50.0)); + } + + @Test + void withdraw() { + classUnderTest.withdraw(50.0); + assertEquals(50.0, classUnderTest.getBalance()); + } + + @Test + void withdraw_withNegativeAmount() { + assertThatExceptionOfType(IllegalStateException.class) + .isThrownBy(() -> classUnderTest.withdraw(-50.0)) + .withMessage("Withdrawal amount must be positive"); + } + + @Test + void withdraw_withInsufficientBalance() { + assertThatExceptionOfType(InsufficientFundsException.class) + .isThrownBy(() -> classUnderTest.withdraw(150.0)) + .withMessage("Account does not have enough funds for withdrawal"); + } + + @Test + void getBalance() { + assertEquals(100.0, classUnderTest.getBalance()); + } + + @Test + void closeAccount_withPositiveBalance() { + assertThatExceptionOfType(IllegalStateException.class) + .isThrownBy(() -> classUnderTest.closeAccount()); + } + + @Test + void isClosed() { + assertFalse(classUnderTest.isClosed()); + classUnderTest.withdraw(100); + classUnderTest.closeAccount(); + assertTrue(classUnderTest.isClosed()); + } + + @Test + void equals() { + SavingsAccount otherAccount = new SavingsAccount("123456789", owners, 200.0); + assertEquals(classUnderTest, otherAccount); + } + + @Test + void hashCodeTest() { + SavingsAccount otherAccount = new SavingsAccount("123456789", owners, 200.0); + assertEquals(classUnderTest.hashCode(), otherAccount.hashCode()); + } + + @Test + void toStringTest() { + String expected = "SavingsAccount{accountNumber='123456789', balance=100.0, isActive=true}"; + assertEquals(expected, classUnderTest.toString()); + } +}