Skip to content

Discriminate query plan caches by the assembly depending return type #1913

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 12 additions & 3 deletions src/NHibernate/Engine/Query/QueryPlanCache.cs
Original file line number Diff line number Diff line change
Expand Up @@ -196,20 +196,23 @@ private class HQLQueryPlanKey : IEquatable<HQLQueryPlanKey>, IDeserializationCal
// hashcode may vary among processes, they cannot be stored and have to be re-computed after deserialization
[NonSerialized]
private int? _hashCode;

private readonly System.Type queryType;
private readonly System.Type queryTypeDiscriminator;

public HQLQueryPlanKey(string query, bool shallow, IDictionary<string, IFilter> enabledFilters)
: this(typeof(object), query, shallow, enabledFilters)
: this(typeof(object), typeof(object), query, shallow, enabledFilters)
{
}

public HQLQueryPlanKey(IQueryExpression queryExpression, bool shallow, IDictionary<string, IFilter> enabledFilters)
: this(queryExpression.GetType(), queryExpression.Key, shallow, enabledFilters)
: this(queryExpression.Type, queryExpression.GetType(), queryExpression.Key, shallow, enabledFilters)
{
}

protected HQLQueryPlanKey(System.Type queryTypeDiscriminator, string query, bool shallow, IDictionary<string, IFilter> enabledFilters)
protected HQLQueryPlanKey(System.Type queryType, System.Type queryTypeDiscriminator, string query, bool shallow, IDictionary<string, IFilter> enabledFilters)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have attempted to reproduce the issue, to no avail. The query parameter was always enough to distinguish the cases, without the need of this additional queryType parameter.
I have mapped two entities having the same type name and build in different dynamic assemblies, and I have build LINQ queries on them: no troubles. The query parameter contains the entity name instead of the type name, and so they are distinguished. I had to map them with different entity names, otherwise the mapping would not compile.

I have put this test case in a PR on your branch: Ablu#1

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have done some checks in the history, entity names were not in the query parameter before NH-2218. Was this issue reproduced with a version earlier than NH v4.1?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The reproduction should not even require any special mappings. We hit the issues with an anonymous type (so doing from collection select new { x }), which was generated by the Roslyn scripting API. The API generates new assemblies for each evaluation. I did not test it with the very latest NH, but the bug should still occur given the code. I unfortunately have no time left this week, but I will try to take a look at it next week!

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Then your issue looks heavily like a duplicate of #1526, fixed by #1532 in v5.1.

{
this.queryType = queryType;
this.queryTypeDiscriminator = queryTypeDiscriminator;
this.query = query;
this.shallow = shallow;
Expand Down Expand Up @@ -255,6 +258,11 @@ public bool Equals(HQLQueryPlanKey that)
return false;
}

if (queryType != that.queryType)
{
return false;
}

if (queryTypeDiscriminator != that.queryTypeDiscriminator)
{
return false;
Expand Down Expand Up @@ -285,6 +293,7 @@ private int GenerateHashCode()
var hash = query.GetHashCode();
hash = 29 * hash + (shallow ? 1 : 0);
hash = 29 * hash + CollectionHelper.GetHashCode(_filterNames);
hash = 29 * hash + queryType.GetHashCode();
hash = 29 * hash + queryTypeDiscriminator.GetHashCode();
return hash;
}
Expand Down