• 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
  • Tim Cooke
  • paul wheaton
  • Jeanne Boyarsky
  • Ron McLeod
Sheriffs:
  • Paul Clapham
  • Liutauras Vilda
  • Devaka Cooray
Saloon Keepers:
  • Tim Holloway
  • Roland Mueller
Bartenders:

Defence using current thread as client's ID

 
Greenhorn
Posts: 8
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Here is my design:
Define an interface DataAccess that contains all public method in supplied Data class, including lock and unlock.
Modify supplied Data class to implements DataAccess, implement lock and unlock method. The implementation uses a Hashtable, key is Integer object of record number, value is the current thread reference (more on this later).
Define a server side facade call ClientService, which provide functions that are called by client through RMI to get, search and book seat. ClientService implementation calls methods in DataAccess to do its jobs. ClientService is a remote object registries on the server and it has only one instance per server. This facade is the most important point in my design.
Now, let me defence my choice of using current thread reference as client identity. As mentioned in RMI specification, there is no guarantee on how RMI runtime will handle the incoming client request,it may one, create a new thread for each client request, or second, run all client requests to a remote object instance in one single thread, i.e. no concurrency.
In the second case, I don't even need to lock the record before booking a seat, but it does no harm if I do. Lock method will alway succeed without waiting other client as no other client is running. So does unlock, it wouldn't be possible to unlock other client's lock as no that kind of lock exist.
In the first case, things are easy, RMI handles everything for me and each client can be sure identified by its new thread reference.
Do you think this reasoning is fine enough? Any incoming comment will be appreciated.
Lots thanks
[ April 11, 2002: Message edited by: Yuqing Zhu ]
[ April 11, 2002: Message edited by: Yuqing Zhu ]
 
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 Yuqing Zhu:
Modify supplied Data class to implements DataAccess, implement lock and unlock method. The implementation uses a Hashtable, key is Integer object of record number, value is the current thread reference (more on this later).

I would argue that Data should not implement locking... in another thread I said:

For example, do not assume that lock() and unlock() need to be implemented on Data. They are fine as they are. Yes, that means empty methods. Really! If you want to, you can flesh them out a bit by adding validation code for the record number, but the lock() and unlock() methods in Data do not need to implement locking at all.
Why not? Well, think a bit about what Data represents. It represents a local database that can only be used from a single JVM. It is a single-user database object that consequently should not try to implement any of the multi-user features, such as locking. Locking is part of a network-enabled, multi-user layer that is built on top of Data.
With a layered architecture such as this, you achieve clear separation of responsibilities, maximum ease of use (a developer only needs to deal with the multi-user networked stuff when (s)he needs a multi-user networked database) and the highest level of reusability.

But, to be honest, no-one is going to be really worked up about this point, least of all the Sun assessors.

Now, let me defence my choice of using current thread reference as client identity. As mentioned in RMI specification, there is no guarantee on how RMI runtime will handle the incoming client request,it may one, create a new thread for each client request, or second, run all client requests to a remote object instance in one single thread, i.e. no concurrency.
In the second case, I don't even need to lock the record before booking a seat

Oh yes you do! In that hypothetical case, the client requests are serialized in that no more than one method call is handled any given time. But the calls can be interleaved and bookings can still clobber each other:
  • Client #1 locks the record (it thinks).
  • Client #2 locks the same record (it thinks).
  • Client #1 reads the record: 1 seat free.
  • Client #2 reads the record: 1 seat free.
  • Client #1 updates the record: 0 seats free.
  • Client #2 updates the record: 0 seats free.
  • Client #1 unlocks the record.
  • Client #2 unlocks the record.
  • You've just sold your seat twice. Oops.

    In the first case, things are easy, RMI handles everything for me and each client can be sure identified by its new thread reference.

    It certainly can not. RMI gives you no guarantees whatsoever that the same thread will be used for the same client every time! It may maintain a thread pool of 2, 3, maybe 10 threads and a client may get a different thread for every method call it makes.

    Do you think this reasoning is fine enough? Any incoming comment will be appreciated.

    Duck, quickly
    There is no way you can identify the clients by thread. RMI simply does not give you enough guarantees.
    - Peter
    [ April 11, 2002: Message edited by: Peter den Haan ]
     
    Yuqing Zhu
    Greenhorn
    Posts: 8
    • Mark post as helpful
    • send pies
      Number of slices to send:
      Optional 'thank-you' note:
    • Quote
    • Report post to moderator
    Thanks Peter, quick response! Would like to defence my design further.


    I would argue that Data should not implement locking... in another thread I said:
    ......
    Why not? Well, think a bit about what Data represents. It represents a local database that can only be used from a single JVM. It is a single-user database object that consequently should not try to implement any of the multi-user features, such as locking. Locking is part of a network-enabled, multi-user layer that is built on top of Data.


    Quite agree on the ideas behind your desgin, highest level of reusability is always welcomed. But as my focus here is using thread as client's ID, so please allow me to implement lock/unlock in Data class for a while.


    Oh yes you do! In that hypothetical case, the client requests are serialized in that no more than one method call is handled any given time. But the calls can be interleaved and bookings can still clobber each other:


    Yes, that's the point why we can't use thread as client's id when we put the facade in the client side. If the facade is in client side, a bookSeat method actually is a serial of RMI requests which may be interleaved by RMI runtime. Butif we use a server side facade, bookSeat is a single request from the client to our remote object. It will run in a single thread without being interleaved as the other bookSeat(or other methods) requests from the others clients are serialized with this one. So if facade is on server side, which is in my design, we can have a threadsafe booking either with or without locking.


    It certainly can not. RMI gives you no guarantees whatsoever that the same thread will be used for the same client every time! It may maintain a thread pool of 2, 3, maybe 10 threads and a client may get a different thread for every method call it makes.


    Same as above, if we use server side facade, that's bookSeat as one RMI request, every bookSeat will run in one thread from the begining to the end, i.e., from lock to unlock, they all run in a single thread. Thread pool doesn't matter to this, as any thread in a thread pool can only server one request at a time. When the request finishs, lock has been unlocked.
    Two keys to decide whether we can use thread as client's id are one, if the lock and unlock will run in a same thread, if they do, we can tell who locked a record when we try to unlock it, so to prevent a lock from being unlocked by a non-lock-owner. two, if a thread will accommodate 2+ requests to lock 2+ different records at the same time, if it doesn't, we can be sure every records locked by a thread is locked by a same client.
    Thanks
    [ April 11, 2002: Message edited by: Yuqing Zhu ]
     
    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 Yuqing Zhu:
    Yes, that's the point why we can't use thread as client's id when we put the facade in the client side.

    Ah, that wasn't clear to me. If you put a session facade on the server, your scheme makes sense.
    There are two problems with this approach though.
  • It makes nonsense of the requirement (assuming it is still there) to have a client-side object that implements all the Data methods. In your approach, you have no use for such an object, full stop. Or, put differently, this is in fact an implicit requirement that the business logic reside on the client, and not on the server.
  • The database server code that you write is no longer reusable as-is. At best, you have a reusable "server kit" which forces you to put the business logic at the server side. This does not sit entirely comfortably with the reusability aims of the project.
  • Having said that, if you argue for your approach as strongly in your design documentation as you do here, I have little doubt that it will be approved of.
    - Peter
     
    You are HERE! The other map is obviously wrong. Better confirm with this tiny ad:
    Smokeless wood heat with a rocket mass heater
    https://woodheat.net
    reply
      Bookmark Topic Watch Topic
    • New Topic