Thank you very much. You are right - the problem was in the DAO !!

Valli
IIC SSS
INDIA



-----Original Message-----
From: Paul Hodgetts [mailto:[EMAIL PROTECTED]]
Sent: Monday, January 27, 2003 1:19 AM
To: Struts Users Mailing List
Subject: RE: Newbie: Action class - how to make it thread safe?


Sowbhagya Valli Suryadevara wrote:

 > We are using the struts(1.0.2) framework in our application.
 > When multiple users are clicking on the same SAVE button
 > simultaneously the data is getting interchanged for the users.
 >
 > Am I supposed to synchronize any of the blocks? The sample
 > code provided by struts does not have any synchronized
 > blocks. If required then should it be for accessing the
 > session and the dao ??
[original sample code below...]

mech responded:

 > So you could either try for example to synchronize only the block after
 > checking for "saveUser". Could already solve your problem. Or try to
 > make your DAOs thread-safe.

It's a really bad idea to introduce synchronized blocks into
methods in the request processing chain.  This can have serious
negative repercussions for scalability.  If some protection is
needed for concurrent access to data, such as might occur if
multiple clients are updating the same record, that should be
handled at the database level with transactions and strategies
for preventing updates with stale data (e.g., time stamps).

A few observations:

* The data seems to be coming from the session.  Assuming there
is no sharing of session IDs across clients, the data should be
unique per client request.

* The action seems to be using only local variables.  The data
in these variables should be unique to the thread, and thus the
client request.

* You are doing a database insert, which presumably is creating
a new record for each client request.  I'm assuming there are
either constraints at the database level for unique keys, or you
don't care about unique keys and every insert creates a new
record, even with duplicate data, so the database insert should
be unique per client request.

In short, unless I've missed something in the small block of
sample code in the original post, there is nothing that
indicates there should any conflict between clients as described.
There must be more to this story.  It doesn't seem like it has
anything to do with Struts.

It's possible the DAO, or maybe the form object depending on how
you wrote it, have some static variables that might be shared.
The DAO looks like it might be a singleton, so it's possible it
is sharing some instance data.  But that's not visible from the
example.

FWIW, you really shouldn't be using your form as a domain object
and passing it all the way to the persistence tier, thus coupling
the tiers.  It's a better design pattern to have the action
transfer the needed values out of the form into a domain object,
or into a data transfer/value object, and then pass that around
instead.

Also, as a matter of naming style calling something a "Session
Bean" is very confusing when J2EE has something called a Session
Bean that is widely used and means something entirely different.

Regards,
Paul
-----
Paul Hodgetts -- President, Principal Consultant
Agile Logic  -- www.agilelogic.com
Consulting, Coaching, Training -- On-Site & Out-Sourced Development
Java, J2EE, C++, OOA/D -- Agile Methods/XP/Scrum, Use Cases, UI/IA


-----Original Sample Code-----

public class UserActions extends Action {
   public ActionForward perform(ActionMapping mapping,
       ActionForm form, HttpServletRequest request,
       HttpServletResponse response)
       throws IOException, ServletException {
   String actionType = request.getParameter("actionType");
   HttpSession session = request.getSession();
   MessageResources messageResources = getResources();
   // getting user-specific values from the session
   MSSessionBean sessionBean =
(MSSessionBean)session.getAttribute(MSSessionBean.SESSION_PARAM);
   // for saving the user
   if (actionType.equals("saveUser")) {
     int companyId = sessionBean.getCompanyId();
     String strUserId = sessionBean.getUserId();
     Locale userLocale = sessionBean.getUserLocale();
     PersonForm person = (PersonForm) form;
     // calling the data access object to insert into the data base
     PersonDAO personDAO = PersonDAO.getInstance();
     personDAO.insert(person);
     }
   }


--
To unsubscribe, e-mail:
<mailto:[EMAIL PROTECTED]>
For additional commands, e-mail:
<mailto:[EMAIL PROTECTED]>


---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]

Reply via email to