Testing - ModelS2C Home « Testing - Model

In this lesson of the Case Study we do some testing of our Model code. We start by writing a program to test various methods of the StockImpl class which will also test the Manufacturer class in the process. We will write out methods called to a log file and view the logged results, thus also testing that our logging is working as intended. After this we write a test program to validate our locking is functioning correctly.

We start the testing of the model code by writing a program to test various methods of the StockImpl class which will also test the Manufacturer class in the process. We will write out methods invoked to a log file and view the logged results, thus also testing that our logging is working as intended. After this we write a test program to validate our locking functioning is working correctly.

Testing The StockImpl Class Top

Our first test class will test various methods within the StockImpl class including the search, stocking and unstocking functionality requested by the stakeholder Stocking Goods Limited.

Cut and paste the following code into your text editor and save it in the   c:\_Case_Study\src\testing directory.


package testing;

import java.util.logging.FileHandler;
import java.util.logging.Level;
import java.util.logging.Logger;
import java.io.IOException;
import java.util.logging.SimpleFormatter;

import model.StockImpl;
import model.StockingException;

/*
 * In out first test program we create a logger which we will look at after, so we can 
 * see the logger working. We then test various methods of the StockImpl 
 * class that are not tested from the GUI such as creating and deleting Manufacturer 
 * records, as well as a few other tests which will show our methods working as intended.
 * 
 */
public class TestStockImpl {
	
    /*
     * The Logger instance through which all log messages from this class are routed.
     * Logger namespace is s2cCaseStudy.
     */
    private static Logger log = Logger.getLogger("s2cCaseStudy"); // Log output
    static String pathname = "C:\\_Case_Study\\src\\manufacturertestfile.txt";

    public static void main(String[] args) {
        try {
            /*
             * Setup a rotating file in default user directory for machine that will 
             * handle logs for the whole application
             */
            FileHandler manufacturerFileHandler = 
                    new FileHandler("C:\\_Case_Study\\s2cCaseStudy%g.log", 0, 10);
            manufacturerFileHandler.setFormatter(new SimpleFormatter());
            Logger log = Logger.getLogger("s2cCaseStudy");
            log.addHandler(manufacturerFileHandler);
            log.setLevel(Level.FINE);
            // Get StockImpl singleton
            StockImpl getInstance = StockImpl.getStockImplInstance(pathname);
            // Test search
            String[] findArray = {"Fine Fancy Foods", "Chester"};
            long[] retRecNos = new long[1];
            retRecNos = getInstance.findBySearchCriteria(findArray);
            log.fine("Search Criteria 1: record numbers returned: ");
            for (int i = 0; i < retRecNos.length; i++) {
				if (retRecNos[i] == 0) break;
                log.fine("rec Number: " + retRecNos[i]);
            }
            String[] findArray2 = {"Fine Fancy Foods", null};
            long[] retRecNos2 = new long[5];
            retRecNos2 = getInstance.findBySearchCriteria(findArray2);
            log.fine("Search Criteria 2: record numbers returned: ");
            for (int i = 0; i < retRecNos2.length; i++) {
				if (retRecNos2[i] == 0) break;
                log.fine("rec Number: " + retRecNos2[i]);
            }
            String[] findArray3 = {null, "Tooting"};
            long[] retRecNos3 = new long[5];
            retRecNos3 = getInstance.findBySearchCriteria(findArray3);
            log.fine("Search Criteria 3: record numbers returned: ");
            for (int i = 0; i < retRecNos3.length; i++) {
				if (retRecNos3[i] == 0) break;
                log.fine("rec Number: " + retRecNos3[i]);
            }
            // Test manufacturer record creation
            String[] 
                createArray = {" ", "Fine Fancy Foods", "Laindon", "Pyjamas", "12.99", "20", " "};
            getInstance.createRecord(createArray);
            // Test stocking functionality
            getInstance.stocking("Fine Fancy Foods", "Swindon", 10, 10);
            // Test unstocking functionality
            getInstance.unstocking("Fine Fancy Foods", "Birmingham", 12);
            // Test manufacturer record deletion
            //Put record number in the locking map
            Long recNo = 119L;
            Long cookie = getInstance.lockRecord(recNo);
            getInstance.deleteRecord(recNo, cookie);
            getInstance.unlock(recNo, cookie);
        } catch (IOException e) {
            e.printStackTrace();
        } catch (StockingException e) {
            e.printStackTrace();
        }
    }
    public static Logger getLog() {
        return log;
    }
    public static void setLog(Logger log) {
        TestStockImpl.log = log;
    }
}

Compiling Our Source File With the -cp and -d Options

Open your command line editor:

Change to directory  cd c:\_Case_Study\src\testing

Compile TestStockImpl.java using the java compiler with the -cp and -d options
  javac -cp ..\..\classes -d ..\..\classes TestStockImpl.java

Running The Packaged TestStockImpl class

Run the TestStockImpl class from the classes directory using our package as well  java testing.TestStockImpl

run test StockImpl

The screenshot above shows some information messages for record creation, stocking and unstocking. To see the program flow and check the search functionality we will need to check the log file.

Checking The Log FileTop

We should now have our first log file created which we will investigate next to see program flow.

If you go to the text editir you are using and double click on the log file you should be presented with the program flow thats start something like the screenshot below:

Check log file

Take some time and investigate the lock and records numbers created for our cache map and check these against the searches we tested for. The functionality is working as expected and the log file also shows usage of the Manufacturer class.

Testing Record Locking Top

The last thing we are going to test on the model side is record locking and to do this without causing a severe error such as a RecordNotFoundException we are going to run several threads through a lock-update-unlock cycle to ensure that our locking is working correctly. To do this we are going to code a TestThreads class and another class that implements the Runnable interface and pass 10 threads through which is more than enough to ensure our locking code is working correctly.

Cut and paste the following code into your text editor and save it in the   c:\_Case_Study\src\testing directory.


package testing;

import java.util.logging.FileHandler;
import java.util.logging.Level;
import java.util.logging.Logger;
import java.io.IOException;
import java.util.logging.SimpleFormatter;

import model.StockImpl;

class Runner implements Runnable {
    /*
     * The Logger instance through which all log messages from this class are routed.
     * Logger namespace is s2cCaseStudy.
     */
    private static Logger log = Logger.getLogger("s2cCaseStudy"); // Log output
    static String pathname = "C:\\_Case_Study\\src\\manufacturertestfile.txt";

    public void run() {
        log.fine("Entering run method");
        // Get StockImpl singleton
        StockImpl getInstance = StockImpl.getStockImplInstance(pathname);
        // Update locking test
        String[] updateArray = {" ", "Fine Fancy Foods", "Laindon", "Pyjamas", "14.99", "20", " "};
        //Put record number in the locking map
        Long recNo = 1499L;
        Long cookie = getInstance.lockRecord(recNo);
        log.fine("Run by: " + Thread.currentThread().getName());
        getInstance.updateRecord(recNo, updateArray, cookie);
        getInstance.unlock(recNo, cookie);
    }
}

public class TestThreads {
    /*
     * The Logger instance through which all log messages from this class are routed.
     * Logger namespace is s2cCaseStudy.
     */
    private static Logger log = Logger.getLogger("s2cCaseStudy"); // Log output
    static String pathname = "C:\\_Case_Study\\src\\manufacturertestfile.txt";

    public static void main(String[] args) {
        try {
            /*
             * Setup a rotating file in default user directory for machine that will 
             * handle logs for the whole application
             */
            FileHandler manufacturerFileHandler = 
                    new FileHandler("C:\\_Case_Study\\s2cCaseStudy%g.log", 0, 10);
            manufacturerFileHandler.setFormatter(new SimpleFormatter());
            Logger log = Logger.getLogger("s2cCaseStudy");
            log.addHandler(manufacturerFileHandler);
            log.setLevel(Level.FINE);
		} catch (IOException e) {
            e.printStackTrace();
        }
        Runner rnnr = new Runner();
        Thread one = new Thread(rnnr);
        Thread two = new Thread(rnnr);
        Thread three = new Thread(rnnr);
        Thread four = new Thread(rnnr);
        Thread five = new Thread(rnnr);
        Thread six = new Thread(rnnr);
        Thread seven = new Thread(rnnr);
        Thread eight = new Thread(rnnr);
        Thread nine = new Thread(rnnr);
        Thread ten = new Thread(rnnr);
        one.start();
        two.start();
        three.start();
        four.start();
        five.start();
        six.start();
        seven.start();
        eight.start();
        nine.start();
        ten.start();
    }

    public static Logger getLog() {
        return log;
    }

    public static void setLog(Logger log) {
        TestThreads.log = log;
    }
}

Compiling Our Source File With the -cp and -d Options

Open your command line editor:

Change to directory  cd c:\_Case_Study\src\testing

Compile TestThreads.java using the java compiler with the -cp and -d options
  javac -cp ..\..\classes -d ..\..\classes TestThreads.java

Running The Packaged TestThreads class

Run the TestThreads class from the classes directory using our package as well  java testing.TestThreads

run test TestThreads
Check Locking Log FileTop

We should now have another log file created which we will lock at to check our locking. The way the log files are set up the most recent file will always be suffixed with 0 so current file is s2cCaseStudy0.log

If you go to the text editor you are using and double click on the log file and lock through it you can see threads being locked, updated and unlocked as you can partly see in the screenshot below:

Check locking log file

That concludes our testing for the model side of the case study and of course in the real world you would be a lot more thorough and do more tests than those we have shown here.

Lesson 18 Complete

In this lesson we tested the Model elements of the MVC pattern.

Related Java Tutorials

Beginning Java - Primitive Variables
Beginning Java - Conditional Statements
Beginning Java - Loop Statements
Objects & Classes - Arrays
Objects & Classes - Class Structure and Syntax
Objects & Classes - Reference Variables
Objects & Classes - Methods
Objects & Classes - Instance Variables & Scope
Objects & Classes - Constructors
Objects & Classes - Static Members
Objects & Classes - Enumerations
OO Concepts - Encapsulation
OO Concepts - Inheritance Concepts - Using the super keyword
OO Concepts - Interfaces
Exceptions - Handling Exceptions
API Contents - Inheritance - Using the package keyword
API Contents - Inheritance - Using the import keyword
API Contents - Java I/O Overview - The java.io.File Class
Concurrency - Thread Basics
Concurrency - The Runnable Interface
Swing - Swing Containers
Swing - Swing Components
Swing - Layout Managers
Swing - Event Handling
Swing - Dialogs
Swing - RMI

What's Next?

In the next lesson we test the View elements of the MVC pattern.