I posted some parts of my choice.txt for your reference.
Hope this should be helpful.
==================================================
Test: Sun Certified Developer for the
Java 2 Platform (310-027)
Date Taken: 2005-03-04 07:58:47.577
Site: ti8
Grade: P
Score: 359
Comment: This report shows the total number of points awarded for each section. The maximum number of points is 400, to pass you need a score of 320. Section Summary:
Section Max Actual Points Points
General Con: 100 89
Documentation: 70 62
OOD: 30 30
GUI: 40 28
Locking: 80 80
Data Store: 40 30
Network Server: 40 40
Total: 400 359
================================================
GENERAL CONSIDERATIONS
=======================
This is a 3 tier solution and MVC design
pattern is adopted.
OBJECT-ORIENTED DESIGN
======================
Singleton Pattern, Adapter Pattern, Model-View-Controller Pattern,
Factory Pattern, Value Object Pattern
USER INTERFACE
===============
Column width is adjusted automatically to fit screen size.
Numerical columns are right alignment.
Lock Cookie Generation
=================
Unique lock cookie is generated by a sequence number because
this mechanism is easy to code and maintain.
Visibility Of Lock and Unlock
=====================
lockRecord() and unlock() methods are not exposed to DBAdapter.java, which
means lockRecord() and unlock() can be used only within Model tier, because
incorrect using and calling these 2 methods could lead database to crashing or being
in a dead lock trouble.
Thread Queue
==========
In Data.java, the create/read/find functions are executed by the current thread after the
only one Data object is locked by the current thread so that the basic transaction can
be safe. Also, in the multiple-thread environment, the locking implementation of
update/delete function I chose is to maintain a thread queue for each record. Because
a thread must call lockRecord() to lock the thread specified record before calling the
method updateRecord()/deleteRecord() and must call unlock() to unlock the thread
specified record after calling the method updateRecord()/deleteRecord(), the thread
queue mechanism can be done in lockRecord() and unlock(). There are 3 elements to
the thread queue mechanism, long lockCookieCount to generate unique lock cookie,
HashMap lockedRecNos to stroe which record is being locked and to store a thread
waiting list corresponding to this record, and LinkedList threadWaitingList to store all
the waiting threads which wait for the same record. Every time a thread accesses
lockrecord(), lockCookie pluses one to generate a unique number and the thread
name is set with this unique number. When more than one threads want to access the
same record, the very first one thread locks the thread specified record and make an
entry in HashMap lockedRecNos to notify other threads that the very first thread is
being using the record. Then, all other threads have to wait for their turns and are
stored in LinkedList threadWaitingList which is also stored in HashMap
lockedRecNos. After the very first thread finishes its work, the thread queue wakes
up the next thread, removes the very first thread and then allows only the next thread
to access the same record. Due of the thread queue mechanism, threads wanting to
access the same record can be executed one after one in the sequential order (first in
first out with LinkedList objects) and then make basic transaction safe. And no
waiting thread consumes CPU cycles until it is waken up.
Shutdown
=======
The implementation
of shutdown function I chose is when the server is started, Data.java registers a
shutdown hook with JVM to release (close) all open resources. The registered
shutdown hook is responsible for closing the RandomAccessFile Object. Also,
when creating
RandomAccessFile Object, the parameter "rws" is passed to require that every
update to the file's content or metadata be written synchronously to the underlying
storage device.
SwingInfoExceptionHandler
===================
When information of an exception needs to be display, simple and short messages
about this exception are shown in a dialogue to end user with OK and ADVANCED
buttons. The user can click OK button to close the dialogue or can click
ADVANCED button to know more details.
IllegalArgumentException
==================
In Data.java, the checkInputData() method checks all input data to database. It checks
the field length, the field number, data format, data value and data type. If the inputted
data violates constrains, IllegalArgumentException is thrown. There are 2 more
situations to throw IllegalArgumentException. A null value in primary
key also throws IllegalArgumentException in createRecord(). I would throw an
IllegalArgumentException with a message if any attempts to update the primary key
fields are made in the update() method.
AlreadyBookedException
==================
AlreadyBookedException is thrown by interface DBAdapter.java and by 2 concrete
implementation classes, DBAdapterImpl.java and DBAdapterRMIImpl.java. This
exception means that the contractor a user tries to book has bean already booked.
IOException And DataException
=======================
The signature of the methods defined in interface DBAccess.java can not throw an
IOException. But this checked exception could be thrown by methods of
RandomAccessFile.java when the methods of Data.java, implementation of interface
DBAccess.java, need to access database file. Therefore, I decided to add
DataException.java which extends RuntimeException and to make DataException
wrap IOException.
DataNotConsistencyException
=====================
DataNotConsistencyException is thrown when the data of a contractor in the GUI
screen is different from the current data of this contractor in the database.
ControllerException
==============
ControllerException is mainly thrown by Controller.java. When Controller.java
receives any exception from database, it wraps the original exception from database
with ControllerException and rethrows ControllerException to its caller in stead of
throwing the original exception. In this way, a client of Controller.java can deal with
only ControllerException rather than many different kinds of the original exceptions
from the database. This makes programming easy.
Booking Overwriting (Unbook)
=====================
This optional overwriting is
a procedure of unbooking implementation. I decided when a user tries to book an
already booked contractors, he will be warned that the contractor has been already
booked and that he must unbook the specified contractor before booking. When he
tries to unbook, he presses the book bottom with empty owner id field.
Encoding
=======
In the instructions.html, the character encoding is 8 bit US ASCII. However, there is
no 8 bit US ASCII and I think it sould be a typo. Therefore, I used ISO-8859-1
instead of 8 bit US ASCII.
Null Termination
============
All records of data file provided are space-padded but the instructions.html mentions
"all fields...null terminated" and "without altering the data file format" so there is a
conflict. I think the data file should be valid. Therefore, in this project, I chose all
records are space-padded.
Search Function
============
#Server Side: Data.java exposes findByCriteria() method for search function
according to DBAccess.java. This method provides generic serch functions and is
implemented by using String.startsWith. However, the generic search functions can't
fulfill the requirements of the instructions.html and DBAdapter, a wraper class of
Data.java, wraps and extends findByCriteria() to add 3 new search functions,
findByCriteriaStartsWith(), findByCriteriaEquals() and
findByCriteriaIndexOfIgnrCase().
#Client Side: In the user interface, a user can search database by 5 criteria, by name,
by location, by name or location, by name and location, all records. These criteria can
also have 3 different patterns to match records, Start With, Exact Match, Contain so a
user can have at least 13 different search functions with different combinations. Start
With and Exact Match patterns are case-sensitive but Contain pattern is not case-
sensitive.
Primary key
========
I assume that the primary key is the composite key
of Subcontractor Name and City of the contractor because there should not be any
two businesses in the same location with the same name. Besides, from database theory, a
primary key
should not be null. My update() method would not allow the update of primary key
fields.
Lock Cookie Transmission
===================
The instruction doesn't explain lock cookie very much. In order to comply with MVC
design patter, I chose not to send lock cookie to the client but manipulate it only in
server side.