Return-Path: Delivered-To: apmail-ibatis-user-java-archive@www.apache.org Received: (qmail 5251 invoked from network); 27 Oct 2006 23:42:59 -0000 Received: from hermes.apache.org (HELO mail.apache.org) (140.211.11.2) by minotaur.apache.org with SMTP; 27 Oct 2006 23:42:59 -0000 Received: (qmail 93327 invoked by uid 500); 27 Oct 2006 23:43:08 -0000 Delivered-To: apmail-ibatis-user-java-archive@ibatis.apache.org Received: (qmail 93316 invoked by uid 500); 27 Oct 2006 23:43:07 -0000 Mailing-List: contact user-java-help@ibatis.apache.org; run by ezmlm Precedence: bulk List-Help: List-Unsubscribe: List-Post: List-Id: Reply-To: user-java@ibatis.apache.org Delivered-To: mailing list user-java@ibatis.apache.org Received: (qmail 93305 invoked by uid 99); 27 Oct 2006 23:43:07 -0000 Received: from herse.apache.org (HELO herse.apache.org) (140.211.11.133) by apache.org (qpsmtpd/0.29) with ESMTP; Fri, 27 Oct 2006 16:43:07 -0700 X-ASF-Spam-Status: No, hits=2.5 required=10.0 tests=DNS_FROM_RFC_ABUSE,HTML_MESSAGE,SPF_PASS X-Spam-Check-By: apache.org Received-SPF: pass (herse.apache.org: domain of jeffgbutler@gmail.com designates 64.233.182.186 as permitted sender) Received: from [64.233.182.186] (HELO nf-out-0910.google.com) (64.233.182.186) by apache.org (qpsmtpd/0.29) with ESMTP; Fri, 27 Oct 2006 16:42:54 -0700 Received: by nf-out-0910.google.com with SMTP id l23so1438475nfc for ; Fri, 27 Oct 2006 16:42:33 -0700 (PDT) DomainKey-Signature: a=rsa-sha1; q=dns; c=nofws; s=beta; d=gmail.com; h=received:message-id:date:from:to:subject:in-reply-to:mime-version:content-type:references; b=YTmnEg2v3s5iiFSH5xDaVlzBlUa2EN50It1GU1KyEvwX7VtaJxGm6Lr4w3q9zgSFCbDwgOv75LdqaXkJUPNbZAo2afZ/F3O7UsO38QOAVV6hMEZxpTN1CFjaCIGP0JGaekwjQsngqECV3/BA+z4UvDUYj7HKePD0fAGS98VcIJs= Received: by 10.78.200.3 with SMTP id x3mr376415huf; Fri, 27 Oct 2006 16:42:32 -0700 (PDT) Received: by 10.78.153.17 with HTTP; Fri, 27 Oct 2006 16:42:32 -0700 (PDT) Message-ID: Date: Fri, 27 Oct 2006 18:42:32 -0500 From: "Jeff Butler" To: user-java@ibatis.apache.org Subject: Re: Statements being closed when they shouldn't be In-Reply-To: MIME-Version: 1.0 Content-Type: multipart/alternative; boundary="----=_Part_43835_19888988.1161992552692" References: X-Virus-Checked: Checked by ClamAV on apache.org ------=_Part_43835_19888988.1161992552692 Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit Content-Disposition: inline Yes - it's new since 2.2.0. I discovered it in some of my own testing, but haven't entered it into JIRA yet. Our JIRA practices are still pretty loose I'm afraid :( Go ahead and enter a JIRA for it so it's not forgotten. Clinton or I will get to it. Or, if you fix it, then you can attach a patch to the JIRA ticket. Jeff Butler On 10/27/06, Christopher.Mathrusse@sybase.com < Christopher.Mathrusse@sybase.com> wrote: > > Yes, if I disable logging all together the error does not occur. I'm > guessing that this is something that you have seen before. > > ------------------------------ > *From:* "Jeff Butler" [mailto:"Jeff Butler" < > jeffgbutler@gmail.com>] > *Sent:* Friday, October 27, 2006 12:40 PM > *To:* user-java@ibatis.apache.org > *Subject:* Re: Statements being closed when they shouldn't be > > > Maybe. > > Chris - can you verify whether the behavior changes if you disable > logging? > > Also, you can disable caching completely by altering the methods in > com.ibatis.sqlmap.engine.scope.SessionScope to always return false. > > Jeff Butler > > > On 10/27/06, Clinton Begin wrote: > > > > Yeah, let's open a JIRA issue.... > > > > JEFF: Could this be the same problem with the prepared statement > > caching when logging is enabled? > > > > Cheers, > > Clinton > > > > On 10/27/06, Christopher.Mathrusse@sybase.com < > > Christopher.Mathrusse@sybase.com> wrote: > > > > > > Hi Clinton, > > > I've run into a bit of a snag in the SqlExecutor class, closeStatement > > > method. (Line 501) It seems that this class caches statements within the > > > session object. In the closeStatement method there is an evaluation: > > > > > > if (!session.hasPreparedStatement(ps)) { > > > if (ps != null) { > > > try { > > > ps.close(); > > > } catch (SQLException e) { > > > // ignore > > > } > > > } > > > } > > > The problem that I'm seeing is that the PreparedStatement is being > > > closed every time. This is due to the fact that the actual PreparedStatement > > > is wrapped within a PreparedStatementLogProxy object. When the > > > evaluation is made above, session.hasPreparedStatement(ps), the > > > session is asking the preparedStatements HashMap if it contains a value, > > > namely the PreparedStatementLogProxy. When the map iterates through the > > > objects it contains the equals() method is invoked on each object. This is > > > where the problem lies. > > > > > > Invoking equals() causes the invoke method of the PreparedStatementLogProxy > > > to intercept the call. Evaluations are made within this method until the > > > following method is invoked, allowing the underlying equals method on the > > > PreparedStatement to be invoked. > > > > > > *return* method.invoke(statement, params); > > > > > > The problem here is that the actual PreparedStatement is being passed > > > in for comparison with an instance of PreparedStatementLogProxy. This always > > > results in evaluating to false. Even if you were to compare an instance of > > > the Proxy with itself, ps.equals(ps), the result will be false. I > > > verified this by setting a breakpoint in the SqlExecutor class and ran this > > > evaluation which resulted in false. > > > > > > I don't have a solution to this unfortunately. I first thought a > > > simple comparison of the parameter object being an instanceof PreparedStatementLogProxy, > > > but that also returns false, as does PreparedStatementLogProxy.*class*.isAssignableFrom(params[0].getClass()). > > > > > > > > > My problem is that the Statements are always being close when they > > > should not be and this is resulting in errors being raised from the JDBC > > > layer because the Statement is being closed more than once. This is because > > > when SqlMapSessionImpl.close() is called the delegate, SqlMapExecutorDelegate > > > pushSession method is called. In here session.reset() is called which > > > closes any PreparedStatements that it contains. Effectively closing the > > > PreparedStatement twice. > > > > > > Should I open an JIRA on this? > > > > > > Chris Mathrusse > > > christopher.mathrusse@sybase.com > > > (925) 236-5553 > > > > > > > > > > > ------=_Part_43835_19888988.1161992552692 Content-Type: text/html; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit Content-Disposition: inline
Yes - it's new since 2.2.0.  I discovered it in some of my own testing, but haven't entered it into JIRA yet.  Our JIRA practices are still pretty loose I'm afraid :(  Go ahead and enter a JIRA for it so it's not forgotten.  Clinton or I will get to it.  Or, if you fix it, then you can attach a patch to the JIRA ticket.
 
Jeff Butler
 


 
On 10/27/06, Christopher.Mathrusse@sybase.com <Christopher.Mathrusse@sybase.com > wrote:
Yes, if I disable logging all together the error does not occur. I'm guessing that this is something that you have seen before.


From: "Jeff Butler" <jeffgbutler@gmail.com> [mailto:"Jeff Butler" < jeffgbutler@gmail.com>]
Sent: Friday, October 27, 2006 12:40 PM
To: user-java@ibatis.apache.org
Subject: Re: Statements being closed when they shouldn't be

 
Maybe.
 
Chris - can you verify whether the behavior changes if you disable logging?
 
Also, you can disable caching completely by altering the methods in com.ibatis.sqlmap.engine.scope.SessionScope to always return false.
 
Jeff Butler

 
On 10/27/06, Clinton Begin <clinton.begin@gmail.com > wrote:
Yeah, let's open a JIRA issue....

JEFF:  Could this be the same problem with the prepared statement caching when logging is enabled?

Cheers,
Clinton


On 10/27/06, Christopher.Mathrusse@sybase.com <Christopher.Mathrusse@sybase.com> wrote:
Hi Clinton,
I've run into a bit of a snag in the SqlExecutor class, closeStatement method. (Line 501) It seems that this class caches statements within the session object. In the closeStatement method there is an evaluation:
 
    if (!session.hasPreparedStatement(ps)) {
      if (ps != null) {
        try {
          ps.close();
        } catch (SQLException e) {
          // ignore
        }
      }
    }
The problem that I'm seeing is that the PreparedStatement is being closed every time. This is due to the fact that the actual PreparedStatement is wrapped within a PreparedStatementLogProxy object. When the evaluation is made above, session.hasPreparedStatement(ps), the session is asking the preparedStatements HashMap if it contains a value, namely the PreparedStatementLogProxy. When the map iterates through the objects it contains the equals() method is invoked on each object. This is where the problem lies.
 
Invoking equals() causes the invoke method of the PreparedStatementLogProxy to intercept the call. Evaluations are made within this method until the following method is invoked, allowing the underlying equals method on the PreparedStatement to be invoked.

return method.invoke(statement, params);

The problem here is that the actual PreparedStatement is being passed in for comparison with an instance of PreparedStatementLogProxy. This always results in evaluating to false. Even if you were to compare an instance of the Proxy with itself, ps.equals(ps), the result will be false. I verified this by setting a breakpoint in the SqlExecutor class and ran this evaluation which resulted in false.

I don't have a solution to this unfortunately. I first thought a simple comparison of the parameter object being an instanceof PreparedStatementLogProxy, but that also returns false, as does PreparedStatementLogProxy.class.isAssignableFrom(params[0].getClass()).

My problem is that the Statements are always being close when they should not be and this is resulting in errors being raised from the JDBC layer because the Statement is being closed more than once. This is because when SqlMapSessionImpl.close() is called the delegate, SqlMapExecutorDelegate pushSession method is called. In here session.reset() is called which closes any PreparedStatements that it contains. Effectively closing the PreparedStatement twice.

Should I open an JIRA on this?

 
Chris Mathrusse
(925) 236-5553
 



------=_Part_43835_19888988.1161992552692--