Introduction
This CHANGES-file is not like the usual ChangeLog-files. Use CVS instead
to see the detailed changes. This file rather tries to outline the motivation
for various changes and how they were implemented.
If you would like to discuss these ideas then send mail to christ@swl.fh-heilbronn.de.
Dlp vs. Socket
Motivation:
Dlp and Socket are very tightly coupled through an IS-A-relationship. Socket
is also used universally for both a server-socket and a connected socket.
Goal:
Dlp and Socket shall be decoupled. Dlp uses a Socket to perform its communication-tasks.
It is not a Socket itself. This makes their relationship a HAS-A-relationship
rather than an IS-A-relationship.
Socket shall be split into two classes. One to implement server-sockets
and one for connected sockets. The server-socket can only wait for connections
and spawns off connected sockets upon acceptance of clients.
Realization:
Dlp no longer extends Socket, but has a private reference-variable _socket
instead. Socket has been split into two classes. ServerSocket and Socket.
ServerSocket retains all methods which only make sense for a server-socket
(bind, listen, accept, ...), whereas Socket is equipped with all methods
which require a connection (read, write, tickle, version, ...).
Shortcomings:
It would have been nice to use streams instead of socket-descriptors. This
change would be hard to implement as long as I am depending on Kenneth's
native code. Fortunately, it is hardly visible to the application-developer.
I would love to switch to non-native code (CommAPI), but I could
definitely need a few knowledgeable helping hands there.
Status: FINISHED
Constants
Motivation:
All constants are currently bundled together in one huge public constants-class,
regardless of the context in which they are supposed to be used.
Goal:
Make all constants in the constants-class non-public (package-scope). Then
reintroduce them with better names in their corresponding packages.
Realization:
Ditto as goal.
Shortcomings:
Loss of familiarity for those who use the other language bindings as well.
Status: In Progress
DB, Database
Motivation:
The original DB and Database-classes do not sufficiently express their
relationship in their name. Database is also both an implementation of
database-functionality as well as a factory to obtain specializations of
Database. Therefore it inherits all of its factory-functionality to its
specializations.
Goal:
Rename DB and Database to make their relationship more clear. Split the
factory-functionality from Database and tidy it up.
Realization:
DB has been renamed to Database. Database has been renamed to DatabaseImpl.
The factory-functionality has been placed in a class called DatabaseImplFactory.
These naming-conventions are in line with those of the JDK. See java.net.Socket,
java.net.SocketImpl, java.net.SocketImplFactory.
Shortcomings:
Increased danger of Carpal-tunnel-syndrome because of the longer class-names.
Status: FINISHED
Persistance
Motivation:
I find it attractive to save Java objects to a persistant storage. Java
offers the so-called "Serialization"-mechanism to make this possible in
an effortless manner.
Goal:
Identify those objects which would benefit from being persistant. Make
those objects serializable.
Realization:
The Pdapilot.Block-class and all of its specializations have been
made serializable, as well as those classes which they depend upon.
Shortcomings:
This might fan the burning desire to swamp the hard-drive with useless
data.
Status: In Progress
Testability
Motivation:
Untested software can lead to nasty surprises. New additions to software
can also lead to new bugs. Even old bugs might revisit you (regression).
Goal:
Build a suit of automated tests which is suitable to discover a wide range
of problems with the software.
Realization:
The DejaGNU test-framework has been adapted to work with Java and the Pdapilot-packages.
DejaGNU allows for automated POSIX1003.3-compliant testing.
Shortcomings:
The approach contains no automatic coverage-analysis. This could be provided
through other tools. Interactive tests might be hard to implement. A substantial
amount of test-cases will be needed before this testsuite will be able
to give you a good degree of confidence.
Status: In Progress
Defaults only where they make sense
Motivation:
The original design offered default-implementations of many methods in
the Database-area. In many cases these default-implementations did nothing
and were only there to be overwritten. In other cases they returned objects
of a default-class, even though these default-objects were hardly usable,
or didn't make sense in the context of the Pilot's built-in applications.
Goal:
Make unimplemented default-methods abstract. This forces the developer
to override them. It also results in the whole class being abstract, which
makes it clear that it is there to be specialized.
Let factory-methods return null instead of non-sensical
default-objects.
Realization:
Pdapilot.DatabaseImpl has become abstract. Those of its methods which return
objects which almost every application needs in a specialized form have
become abstract. Those of its methods which return objects which are only
used by few applications (SortBlock, Resource, Pref) are now defaulting
to return null. Pdapilot.Block has become abstract. Its fill()-method
is abstract now. This affects every class which is a specialization of
Block. Some of them have become abstract. A new package Pdapilot.generic
has been established to contain the generic versions of those classes.
Shortcomings:
There is a slim chance the old way was more comfortable for you.
Status: In Progress
Support for a variety of Socket-implementations
Motivation:
The original design was tightly coupled with the native socket-implementation
from the pilot-link package. This is clearly a disadvantage, now that alternative
socket-implementations are in the making.
Goal:
Completely decouple the Socket-interface from the underlying implementation.
Do this in a way that looks familiar to seasoned Java developers.
Realization:
Socket and ServerSocket have both been turned into front-ends, which offer
hardly any functionality of their own, but redirect all calls to an instance
of the new SocketImpl-class. Specializations of SocketImpl contain the
actual implementation of the functionality for both Socket and ServerSocket.
The implementation you want to use is specified by setting the appropriate
SocketImplFactory in the Socket-class. This closely mirrors the functionality
from the JDK (in java.net.*). There is currently one specialization of
SocketImpl, called NativeSocketImpl. This uses the native pilot-link sockets.
Communications between the Socket and the higher layers (DLP) is now through
java.io-streams.
Shortcomings:
The native code in Dlp still requires native socket-descriptors. Therefore,
they couldn't be kicked out of the code yet.
Status: Almost FINISHED
Programming by Contract
Motivation:
The package currently has a poorly specified way
to deal with exceptional situations. This should not be the case, for obvious
reasons.
Goal:
Make each method in the package offer a "contract"
to the developer. The contract reads:
-
If you pass me invalid parameters, I shall throw
an unchecked exception at you
-
If you pass me valid parameters, but I cannot satisfy
your request I shall
-
throw an unchecked exception at you, if a failure
of the method can reasonably be expected
-
throw a checked exception at you, if the method can
be expected to succeed
Realization:
Started to add mostly IllegalArgumentExceptions to
some methods. Will continue to do this.
Status: In Progress