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());
+  }
+}