• Post Reply Bookmark Topic Watch Topic
  • New Topic
programming forums Java Mobile Certification Databases Caching Books Engineering Micro Controllers OS Languages Paradigms IDEs Build Tools Frameworks Application Servers Open Source This Site Careers Other Pie Elite all forums
this forum made possible by our volunteer staff, including ...
Marshals:
  • Campbell Ritchie
  • Jeanne Boyarsky
  • Ron McLeod
  • Paul Clapham
  • Liutauras Vilda
Sheriffs:
  • paul wheaton
  • Rob Spoor
  • Devaka Cooray
Saloon Keepers:
  • Stephan van Hulst
  • Tim Holloway
  • Carey Brown
  • Frits Walraven
  • Tim Moores
Bartenders:
  • Mikalai Zaikin

Comments on final server design

 
Ranch Hand
Posts: 34
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I've tried a couple of solutions now, and I'm finally comfortable with my latest design (and it works too :
db-package:
-----------
DataInterface -
Defines all public methods of Data.
Data implements DataInterface -
Implements all the generic database functionallity like add, modify, getRecord, etc.
BookingDataInterface extends DataInterface -
Defines all application spesific functionallity.
BookingData extends Data implements BookingDataInterface -
Implements all application spesific functionallity like lock/unlock, criteriaFind and bookSeats. I feel that lock/unlock and criteriaFind should be in a subclass of Data, because different applications might need different implementations of these methods. BookingData holds a private variable of type LockingInterface so different implementations of the locking/unlocking functionality can be applied.
RemoteDataInterface extends Remote -
Contains all the public methods from Data and BookingData, but are contained in a seperate remote interface to separate data and server logic.
LockingInterface -
Defines only the methods lock and unlock.
LockManager -
Implements lock/unlock functionality
Lock -
A simple class representing a lock in the database. Mapped to a record number in LockManager.

server package:
---------------
DataFacade(adapter?) implements RemoteDataInterface -
Contains a private variable of type BookingData and just adapts/forwards remote method calls to the BookingData instance.
Server -
Main server class. Creates a new DataFacade and binds it to rmiregistry.

Any comments on this design? I feel I've both separated remote and local behavior and seperated data and logic, in this design.
[ April 15, 2002: Message edited by: Geir Morten Hagen ]
 
author
Posts: 3252
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Originally posted by Geir Morten Hagen:
BookingDataInterface extends DataInterface -
Defines all application spesific functionallity.

This is like an application-specific session facade or business delegate, isn't it? Do you think that a business delegate interface "IS A" generic database interface? I don't...

BookingData extends Data implements BookingDataInterface - Implements all application spesific functionallity like lock/unlock, criteriaFind and bookSeats.

What is application-specific about lock, unlock and criteriaFind? They strike me as completely generic functionality that should not reside in an application-specific class.

I feel that lock/unlock and criteriaFind should be in a subclass of Data, because different applications might need different implementations of these methods.

Maybe. At the same time, there is nothing application-specific in the semantics you have been given. You may have a case for implementing them in a subclass of Data. You do not, IMHO, have a case for implementing them in the same class as application-specific stuff like bookSeats. This would inhibit the reuse of some pretty generic functionality.
- Peter
 
Geir Morten Hagen
Ranch Hand
Posts: 34
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I get your point, but should I put lock/unlock/criteriaFind in Data then? I find that a bit concerning, because when running in local mode lock and unlock isn't necessary. Another thing is that criteriaFind can possibly take a different criteria-format in another scenario where Data is to be used, and implementing that in Data will then hamper reuse.
Guess I'm not totally comfortable with my design after all
 
Peter den Haan
author
Posts: 3252
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Originally posted by Geir Morten Hagen:
I get your point, but should I put lock/unlock/criteriaFind in Data then? I find that a bit concerning, because when running in local mode lock and unlock isn't necessary.

For criteriaFind, my answer would be an unequivocal "yes". If the totally braindead "find" method has a rightful place in Data, then so does criteriaFind
As to "lock" and "unlock", I couldn't agree more. You don't need them in a local database. Implementing them in a LockManager class is an excellent idea. How the LockManager gets invoked really depends on the rest of your design -- I had a connection object that delegated almost everything to an underlying LockManager and a Data object. Note that this object implemented the Data interface but was not a subclass.

Another thing is that criteriaFind can possibly take a different criteria-format in another scenario where Data is to be used, and implementing that in Data will then hamper reuse.

In that case, you can implement criteriaFind in a Data subclass. Although I would expect that the existing criteriaFind is simply enhanced as new needs come up, e.g. with a pattern matching facility ("Carrier='Speed*',Origin='SF[OA]'") or expression language (("Carrier='SpeedyAir' or Origin='SFO'"). These would be backwards-compatible enhancements of the Data class rather than completely different implementations of the search function.
From this point of view, criteriaFind is like a poor man's SQL. SQL has a fixed expression language too. No problems with that...
- Peter
[ April 15, 2002: Message edited by: Peter den Haan ]
 
Geir Morten Hagen
Ranch Hand
Posts: 34
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Seems not to be the final design afterall Needs some refactoring
But I have a comment on what you said about criteriaFind. The requirements state that 'any' can be used for origin and destination. This applies only to this application. If Data is to be used in a totally different application, you will then need to change the implementation of criteriaFind in Data to adhere to the requirements of the new application. Maybe a solution is to implement only <field>=<value> searches, and leave it to subclasses to extend this functionality with wild-card searches, etc?
An example:
if(criteriaFields[src].equals("Origin airport") && criteriaValues[src].equals("any")) hardcoded into criteriaFind() in Data can't be good?
[ April 15, 2002: Message edited by: Geir Morten Hagen ]
 
Geir Morten Hagen
Ranch Hand
Posts: 34
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Actually, if I can come up with a good reason for implementing criteriaFind in Data, it will leave me with a much simper design. I can move lock and unlock to the DataFacade instead, and drop BookingData and BookingDataInterface
 
Peter den Haan
author
Posts: 3252
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Originally posted by Geir Morten Hagen:
But I have a comment on what you said about criteriaFind. The requirements state that 'any' can be used for origin and destination. This applies only to this application. If Data is to be used in a totally different application, you will then need to change the implementation of criteriaFind in Data to adhere to the requirements of the new application.

I almost agree with you. Yes, that "ANY" thing is application specific, and even locale specific. But there is no need for criteriaFind to understand "ANY"... if you look at the way criteriaFind works, the absence of a field in the search criteria means that no search condition is imposed on that field. In other words, if the user enters/picks "ANY" for a field, the client can just leave it out of the criteriaFind call.

Maybe a solution is to implement only <field>=<value> searches, and leave it to subclasses to extend this functionality with wild-card searches, etc?

As long as the extended search functionality is backwards compatible, it would probably be a straight modification to Data. (But we're getting into hypothetical territory here).

An example:
if(criteriaFields[src].equals("Origin airport") && criteriaValues[src].equals("any")) hardcoded into criteriaFind() in Data can't be good?

Well, no, indeed. But you shouldn't code criteriaFind in that way anyway! Remember that you're coding for reuse. As the functionality offered by criteriaFind() is crucial to just about any application, I think it should be coded in a completely generic way. You know what the fields in the database are called (getFieldInfo()), so you can parse the search expression, find out where each of the fields lives, and check the search condition on a record by record basis. There is no need whatsoever to hardwire a particular field layout or particular field names in there. Done that way, criteriaFind is a completely generic method that will do its job for any database, any application.
- Peter
[ April 15, 2002: Message edited by: Peter den Haan ]
 
Geir Morten Hagen
Ranch Hand
Posts: 34
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Ah, I get it. I should really have figured out that 'any' part myself..
Thanks alot, Peter
 
Geir Morten Hagen
Ranch Hand
Posts: 34
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Ok, now I think I've got my design cleaned up, I had to admit that it was really bloated.
I moved lock/unlock to the DataFacade which holds a private variable of the LockingInterface and forwards lock/unlock request to LockManager. I also moved criteriaFind into Data and bookSeats to the ClientFacade. The client take care of lock->read->modify->unlock. So then I got rid of BookingData and BookingDataInterface
I was thinking of adding lock/unlock to Data again and just leave them empty (perhaps some record validation, as noted in another thread), just to keep the code the way I received it from Sun and to allow the local client code to still call lock/unlock, even though locking is not necessary in local mode.
This looks much cleaner and more consistent to me. And now that both Data and DataFacade (remote implementation) conform to DataInterface, there are no problems with running in both remote and local mode. Any comments?
[ April 16, 2002: Message edited by: Geir Morten Hagen ]
reply
    Bookmark Topic Watch Topic
  • New Topic