• 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

Create/Update Method Synchronization

 
Greenhorn
Posts: 9
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Hi,

I would like to know different opinions on Synchronization of Create/Update method:

1. Synchronize Entire method?
2. ReadWriteLock on recordNumbers -
a. If the option is create add the recordNumber and location(append at the end) to the collection and release the lock.
b. Synchronize on raf and write to file?

My concern with option 2 is - what if there is a read/write between 2a and 2b.

Please let me know your thoughts on this.

Thank You,
Vijay
 
Sheriff
Posts: 11604
178
Hibernate jQuery Eclipse IDE Spring MySQL Database AngularJS Tomcat Server Chrome Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Hi Vijay,

I went for the first option: synchronize all methods (so not only create and update). of course your data class should certainly be a singleton, otherwise it will not have any effect.
The drawback of this approach is that your program is not that concurrent/performant as it could be. But your code is very simple, clear and can easily be understood by a junior programmer.

The second option is similar to how it is described in the Andrew Monkhouse book. And i think the main concern there is what if 2 client will create a new record.
client1: determine offset, offset = database.length
client2: determine offset, offset = database.length
client2: write record at end of file
client1: write record at end of file (and so overwrite the record written by client2)

a read or an update or a delete in between (offset determination and the actual write) would have no effect in my opinion, because the records are fixed size, so updating or deleting a record will result in same size.

I don't have any idea about how to solve this item and i looked to sources of Andrew's book and there can just happen the same i guess.

Kind regards,
Roel
 
Vijay Sai
Greenhorn
Posts: 9
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Thanks Roel for your detailed explanation. I think Synchronizing entire method may impact some performance but that seem to be the simpler approach.

I wonder how many people used the 2nd option!? and how they implemented it? hope someone answers it, I'm curious to know.

Thank you,
Vijay
 
Ranch Hand
Posts: 232
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I'm going with little different approach:

1. Data-class has one ReentrantLock, which controls access to lock-hashmap containing locked record numbers
-> Methods are NOT synchronized (you should do this in any case - no matter what's your approach)
2. Every client should instantiate Data-class
3. Every client get's own access to file - that is, RandomAccessFile is opened every time
4. I'm using WRITE_LOCK = -1, to inform, that writing is forbidden while using find method

-> Gives real concurrent access to file
-> Already tried with Cache-implementation - too compilcated -> changed whole back end.
-> UB 1.3.3 does not define lock cookie -> RMI Factory Design pattern is a must, since RMI does not guarantee single thread access to server from client.
 
Roel De Nijs
Sheriff
Posts: 11604
178
Hibernate jQuery Eclipse IDE Spring MySQL Database AngularJS Tomcat Server Chrome Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Jari Timonen wrote:
UB 1.3.3 does not define lock cookie -> RMI Factory Design pattern is a must, since RMI does not guarantee single thread access to server from client.



UB 1.3.1 also defines no lockCookie, but i didn't use the RMI factory design pattern. so it is not a must
 
Jari Timonen
Ranch Hand
Posts: 232
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Roel De Nijs wrote:

Jari Timonen wrote:
UB 1.3.3 does not define lock cookie -> RMI Factory Design pattern is a must, since RMI does not guarantee single thread access to server from client.



UB 1.3.1 also defines no lockCookie, but i didn't use the RMI factory design pattern. so it is not a must



Ok. Maybe i'm just too accurate ;) But... there is then possibility, that thread that locks record and after that reads it, is different.
 
Greenhorn
Posts: 13
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Vijay Sai wrote:Thanks Roel for your detailed explanation. I think Synchronizing entire method may impact some performance but that seem to be the simpler approach.

I wonder how many people used the 2nd option!? and how they implemented it? hope someone answers it, I'm curious to know.

Thank you,
Vijay


Hi,

I like your idea about locking whole methods, did you used it in your assignment and did you passed?

Regards,
Adam.
 
Vijay Sai
Greenhorn
Posts: 9
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Hi Adam,

I thought of exploring the 2nd option to learn more but didn't get a chance to implement it. I'll be restarting it soon. For the first option, you can implement it as Roel mentioned above.

Thanks,
Vijay
 
author and jackaroo
Posts: 12200
280
Mac IntelliJ IDE Firefox Browser Oracle C++ Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Jari Timonen wrote:

Roel De Nijs wrote:

Jari Timonen wrote:
UB 1.3.3 does not define lock cookie -> RMI Factory Design pattern is a must, since RMI does not guarantee single thread access to server from client.



UB 1.3.1 also defines no lockCookie, but i didn't use the RMI factory design pattern. so it is not a must



Ok. Maybe i'm just too accurate ;) But... there is then possibility, that thread that locks record and after that reads it, is different.


There are several ways that you can ensure that the client who locked the record is the client who is modifying the record without using a factory, although I personally think the factory method is the most elegant.

The lock method you expose via RMI does not use the same signature as the lock method defined in the Sun interface. Given that, you could easily justify modifying your RMI methods even further - say by creating your own lock cookie or some other "id" field. When the client calls the remote method with that ID field set, you could use it to set the name of the thread that is currently running for that particular client which can then be used within the Data class' methods.

Or there is the option that I believe is against the intent of the assignment (but you will not be marked down for doing this) - only expose business methods to the client. If you only expose a book() method, and that book method internally calls lock(), update(), unlock() then you will be assured that the same thread is calling all three methods. Makes a mockery of having cookies (for those who have cookies).

Note that although I have said that I prefer the factory solution, and although I believe that only exposing business methods is going against the intent of the assignment, I am also explicitly stating that this is pure hubris on my part: the reality is that this assignment (as with most assignments you will get in real life) was written by someone else, and any attempt to state that "this is what they intended" based on just a reading of the provided document is bad mind reading at best. In a real life situation you would be better off going to the author of the document and saying "here are 'x' number of possible ways of handling this problem - which do you prefer. You might then find that they never considered the problem you've found, and/or that they think that solution 'y' is better than anything that they had previously thought of. Meh.
 
Jari Timonen
Ranch Hand
Posts: 232
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Thanks Andrew. I already hide my lock/unlock methods from RMI. Exposed only business methods. I'm using thread id as locking cookie inside Data-class
 
Roel De Nijs
Sheriff
Posts: 11604
178
Hibernate jQuery Eclipse IDE Spring MySQL Database AngularJS Tomcat Server Chrome Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Jari Timonen wrote:Thanks Andrew. I already hide my lock/unlock methods from RMI. Exposed only business methods. I'm using thread id as locking cookie inside Data-class



Sounds too simple to me, but maybe I am worried for nothing so to be sure you don't make mistake in the rmi part.

If you have an interface with a lockCookie you should use that one to make sure the right client locks/updates/unlocks the record. If you don't have a lockCookie in your interface, you should be aware that RMI doesnot guarantee that consecutive requests from 1 client are handled by the same thread.

Kind regards,
Roel
 
Jari Timonen
Ranch Hand
Posts: 232
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Roel De Nijs wrote:

Jari Timonen wrote:Thanks Andrew. I already hide my lock/unlock methods from RMI. Exposed only business methods. I'm using thread id as locking cookie inside Data-class



Sounds too simple to me, but maybe I am worried for nothing so to be sure you don't make mistake in the rmi part.

If you have an interface with a lockCookie you should use that one to make sure the right client locks/updates/unlocks the record. If you don't have a lockCookie in your interface, you should be aware that RMI doesnot guarantee that consecutive requests from 1 client are handled by the same thread.

Kind regards,
Roel




I'm aware of those. There's no locking cookie in my interface. As I said before, factory design + thin client is a must OR andews "set thread name" strategy.

-jari
 
Vijay Sai
Greenhorn
Posts: 9
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Hi Roel and Jari,

Please let me know your thughts on this:

1.get writelock
2. In the try /catch block - synchronize(RAF) and write to the db.
3. unlock in the finally block


Thanks,
Vijay
 
Roel De Nijs
Sheriff
Posts: 11604
178
Hibernate jQuery Eclipse IDE Spring MySQL Database AngularJS Tomcat Server Chrome Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Hi Vijay,

Vijay Sai wrote:
1.get writelock
2. In the try /catch block - synchronize(RAF) and write to the db.
3. unlock in the finally block


don't know what you mean with "3. unlock"? If you mean a call to the unlock-method from within the update/delete method, I don't think that's a good idea. These methods should just do what they are supposed to do, and that's updating/deleting, not locking/unlocking the record. This should be seperate calls.

Without the use of a lockCookie to update a record it would look like this


in the update-method you would have something like:

So the seek and the write should always be 1 atomic operation, otherwise you could corrupt your data file.

Kind regards,
Roel
 
Ranch Hand
Posts: 42
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Hi Ranchers,

I have a threading question that arose while I was implementing lockRecord and unlock() for B&S 2.2.1...

According to page 35 of Core Java 2, Vol. II (7th ed.) by Horstmann, Cornell, the following are equivalent...

public synchronized void method() { //method body... }

public void method() {
implicitLock.lock();
try
{ //method body } finally {implicitLock.unlock();}

In this spirit, I thought I'd try to code simply in my locking methods as follows (somewhat in pseudocode)...

class LockManager {

private static Map<Long, Long> cookieMap =
new HashMap<Long, Long>();

public synchronize void lock(long recNo, long cookie) {

while(cookieMap.containsKey(recNo))
wait();

long cookie = randomCookieGenerator.nextLong();
cookieMap.put(recNo, cookie);
return cookie;

} // end lock


public synchronized void unlock(long recNo, long cookie) throws SecurityException {

if(!cookieAndRecordMatch(recNo, cookie)) {
throw new SecurityException();
}

cookieMap.remove(recNo);
notifyAll();

} // end unlock

} // end class

Puzzlingly to me, this seems to deadlock, i.e., some threads stay blocked waiting in lockRecord forever. Why?

Thanks,

Grary

 
Roel De Nijs
Sheriff
Posts: 11604
178
Hibernate jQuery Eclipse IDE Spring MySQL Database AngularJS Tomcat Server Chrome Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Hi Grary,

Could you edit your previous post and put your code blocks in code-tags, it keeps the identation intact and so makes your code snippets a lot more readible

Regards,
Roel
 
Vijay Sai
Greenhorn
Posts: 9
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Hi Roel,

The sequence should be same as you mentioned- lock, cretae/update/delete, unlock. I was talking about WriteLock.unlock() in the update/create method.

Thanks,
Vijay
 
Without deviation from the norm, progress is not possible - Zappa. Tiny ad:
a bit of art, as a gift, the permaculture playing cards
https://gardener-gift.com
reply
    Bookmark Topic Watch Topic
  • New Topic