ibatis-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From "Christian Poitras (JIRA)" <ibatis-...@incubator.apache.org>
Subject [jira] Commented: (IBATIS-281) Nested iterate tags does not work
Date Fri, 05 May 2006 14:59:28 GMT
    [ http://issues.apache.org/jira/browse/IBATIS-281?page=comments#action_12378050 ] 

Christian Poitras commented on IBATIS-281:

The best way to correct this issue is to change the IterateContext class to add a "public
IterateContext getParent()" method.
Or the SqlTagContext class could be changed to add a "public IterateContext getIterateContext(int
i)" or a "public IterateContext getParentIterateContext(IterateContext ic)".

Another way to fix this in a convenient way would be to allow access to any parent tag we
want based on the JSP model of java. The method "public static final Tag findAncestorWithClass(Tag
from, Class klass)" from class javax.servlet.jsp.tagext.TagSupport gives a good way to search
for any parent class we want to look at and will simplify my patch and make it readable for
most people.
This part of code from IterateTagHandler could be simplified since it only searches for the
parent IterateContext.

For example, the patch.
                  // Add iteration number to property.
                  Object parentContext = ctx.getAttribute(parentTag);
                  while (!(parentContext instanceof IterateContext)) {
                      parentTag = parentTag.getParent();
                      parentContext = ctx.getAttribute(parentTag);
                  IterateContext parentIterateContext = (IterateContext) parentContext;

could be changed to:
                  // Add iteration number to property.
                  IterateContext parentIterate = ctx.getAttribute(parentIterate);

Also a utility class could handle the problem of adding the value of many IterateContext to
any property value of any tags or any replacement value contained in a sql request (like #list[].id#)
by executing the code in the patch in only one place.

Considering this, it would make correcting this bug in any very easy since we could also handle
the current problem of my patch which is having the following tag <isEqual property="list[].list[3].list[].id"
value="someValue"/>. It throws an exception when processing the "list[3]" part. By putting
this logic in one place, we could check if a number is already between the "[]" and skip the
corresponding IterateContext (if it is linked to an iterateContext).
But we must be carreful that the following example will not cause a problem, so we can't automatically
skip an IterateContext without first checking if the "[]" is linked to an iterate tag.
  <iterate property="list">
    <iterate property="list[].list[3].list">

> Nested iterate tags does not work
> ---------------------------------
>          Key: IBATIS-281
>          URL: http://issues.apache.org/jira/browse/IBATIS-281
>      Project: iBatis for Java
>         Type: Bug

>   Components: SQL Maps
>     Versions: 2.1.7
>     Reporter: Christian Poitras
>  Attachments: ConditionalTagHandler.java, DynamicSql.java, IterateTagHandler.java
> No nested iterate tags work. The second iterate tag is not supported and produces the
following error.
> java.lang.NumberFormatException: For input string: ""
> at java.lang.NumberFormatException.forInputString(NumberFormatException.java:48)
> at java.lang.Integer.parseInt(Integer.java:489)
> at java.lang.Integer.parseInt(Integer.java:518)
> at com.ibatis.common.beans.BaseProbe.getIndexedProperty(BaseProbe.java:51)
> at com.ibatis.common.beans.ComplexBeanProbe.getProperty(ComplexBeanProbe.java:297)
> at com.ibatis.common.beans.ComplexBeanProbe.getObject(ComplexBeanProbe.java:188)
> at com.ibatis.common.beans.GenericProbe.getObject(GenericProbe.java:76)
> at com.ibatis.sqlmap.engine.mapping.sql.dynamic.elements.IterateTagHandler.doStartFragment(IterateTagHandler.java:34)
> at com.ibatis.sqlmap.engine.mapping.sql.dynamic.DynamicSql.processBodyChildren(DynamicSql.java:157)
> at com.ibatis.sqlmap.engine.mapping.sql.dynamic.DynamicSql.processBodyChildren(DynamicSql.java:160)
> at com.ibatis.sqlmap.engine.mapping.sql.dynamic.DynamicSql.processBodyChildren(DynamicSql.java:99)
> at com.ibatis.sqlmap.engine.mapping.sql.dynamic.DynamicSql.process(DynamicSql.java:79)
> at com.ibatis.sqlmap.engine.mapping.sql.dynamic.DynamicSql.getParameterMap(DynamicSql.java:61)
> at com.ibatis.sqlmap.engine.mapping.statement.GeneralStatement.executeQueryWithCallback(GeneralStatement.java:156)
> at com.ibatis.sqlmap.engine.mapping.statement.GeneralStatement.executeQueryForList(GeneralStatement.java:123)
> at com.ibatis.sqlmap.engine.impl.SqlMapExecutorDelegate.queryForList(SqlMapExecutorDelegate.java:610)
> at com.ibatis.sqlmap.engine.impl.SqlMapExecutorDelegate.queryForList(SqlMapExecutorDelegate.java:584)
> at com.ibatis.sqlmap.engine.impl.SqlMapSessionImpl.queryForList(SqlMapSessionImpl.java:101)
> at com.ibatis.sqlmap.engine.impl.SqlMapClientImpl.queryForList(SqlMapClientImpl.java:78)
> at com.ibatis.dao.client.template.SqlMapDaoTemplate.queryForList(SqlMapDaoTemplate.java:203)
> at ca.qc.ircm.lana.persistence.sqlmapdao.SpotSqlMapDao.getSpotsInter(SpotSqlMapDao.java:159)
> at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
> at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
> at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
> at java.lang.reflect.Method.invoke(Method.java:324)
> at com.ibatis.dao.engine.impl.DaoProxy.invoke(DaoProxy.java:72)
> at $Proxy14.getSpotsInter(Unknown Source)
> at ca.qc.ircm.lana.service.InterpretationService.getSpotsInter(InterpretationService.java:82)
> at TEST.testInterpretation.main(testInterpretation.java:111)
> It seems the second iterate tag cannot have a property of this type.
> <iterate property="list" >
>   <iterate property="list[].list">
>   <iterate>
> </iterate>
> On the nested iterate, SQL Maps does not add the number in attribute property "list[].list"
and tries to call a getter for parameterClass.getList[]() and this is not allowed and produces
the error.
> This could be prevented in the IterateTagHandler class (doStartFragment method) by adding
code that replaces "[]" in the property attribute by values of IterateContext that are parents
of the current tag (for multiple nested iterate).
> Other code would need to be updated since using a property in the second list also causes
SQL Map to crash even it IterateTagHandler is patched.
> <iterate property="list" >
>   <iterate property="list[].list">
>     #list[].list[].someProperty#
>   <iterate>
> </iterate>
> I produced a patch that can correct the problem. I will include it in a future message.

This message is automatically generated by JIRA.
If you think it was sent incorrectly contact one of the administrators:
For more information on JIRA, see:

View raw message