Hi Satheesh,
if (foundInCache) {
if (preparedStmt.referencesSessionSchema()) {
// cannot use this state since it is private to a connection.
// switch to a new statement.
foundInCache = false;
preparedStmt = new GenericPreparedStatement(this);
break;
}
}
GenericPreparedStatement or GenericStatement at the time of the check above donot have the query tree object and hence we can't simply call qt.referencesSessionSchema. For this reason, I had to add
public boolean referencesSessionSchema(QueryTreeNode qt) to GenericPreparedStatement(which gets called by the compile phase after the qt object is constructed) and the method saves the qt object's referencesSessionSchema() status in it's own local variable referencesSessionSchema. This local information is what will be used by the other referencesSessionSchema method to determine if statement found in cache should be discarded and compile phase should be re-executed.
throws StandardException {
//If the query references a SESSION schema table (temporary or permanent), then mark so in this statement
referencesSessionSchema = qt.referencesSessionSchema();
return(referencesSessionSchema);
}
{
return referencesSessionSchema;
}
3)At the end of the bind phase for select * from session.st1; GenericStatement's qt (QueryTreeNode object which in this case is CursorNode) object has it's resultSet object as a SelectNode which has a fromList object with referencesSessionSchema field set to true because it was referencing an object from SESSION schema.
Mamta
Thanks Mamta for the patch. I just have some comments and questions... Thanks for commenting the changes well!
1) Why there is a new method in GenericPreparedStatement? This doesn't return any info about the PreparedStatement itself, so, does this belong here? Why not just have the check qt.referencesSessionSchema() in GenericStatement.java ?
+ public boolean referencesSessionSchema(QueryTreeNode qt)2) Thanks for changing completeCompile() to NOT return referencesSessionSchema flag... Seems like an ugly way to do it.
+ throws StandardException {
+ //If the query references a SESSION schema table (temporary or permanent), then mark so in this statement
+ referencesSessionSchema = qt.referencesSessionSchema();
+ return(referencesSessionSchema);
+ }
3) You also mentioned:
This information is again lost during the optimization and generate phase and hence I moved the check for
SESSION schema reference to right after the bind phase in GenericStatement.Do you know why this info is lost?Thanks for the good patch.
Satheesh
Mamta Satoor wrote:Hi,I have attached a review package for this bug to JIRA, hopefully, in time for 10.1.2 release.The files affected by this change are
M java\engine\org\apache\derby\impl\sql\GenericStatement.java
M java\engine\org\apache\derby\impl\sql\compile\FromList.java
M java\engine\org\apache\derby\impl\sql\GenericPreparedStatement.java
M java\testing\org\apache\derbyTesting\functionTests\tests\lang\declareGlobalTempTableJava.java
M java\testing\org\apache\derbyTesting\functionTests\master\declareGlobalTempTableJava.outThe changes for this fix are very localized, affecting only 3 files in Derby engine. Basically, the problem is that, during the compile phase of views, the reference to the view gets replaced by the view definition, which causes us to loose the information that the view might have belonged in SESSION schema. In order to fix this, during the bind phase in FromList, before the view gets replaced by its definition, I find out if the view is from SESSION schema, If yes, then I save this information in FromList and this gets used by FromList when it is asked if it has any items referencing SESSION schema objects. This information is again lost during the optimization and generate phase and hence I moved the check for SESSION schema reference to right after the bind phase in GenericStatement. If there is a reference to SESSION schema object, GenericStatement will remove the statement from the cache.
I have put in quite a big of comments in the code which hopefully will make the patch easier to understand. I have added a new test for this and have run all the tests with no failures using Sun's jdk142 on Windows XP machine.thanks,Mamta
