The specified cast from a materialized 'System.Guid' type to the 'System.Int32' type is not valid.
We have several WCF services that have concurrency mode of Multiple and InstanceContextMode
of Single. Our architecture focuses on a loosely coupled model using constructor-based dependency injection. This in turn is implemented using Unity 2.0 (web.config of each service has mappings between interfaces and types defined in a unity container section). One of our dependencies is a DAL assembly (data access layer) that uses Entity Framework 4 to communicate with MSSql Server. The classes that do the talking to the database are also included in the unity mapping.
Everything is great when we run our integration tests. But when we move to our performance environment to run load tests (2, 3, 4 concurrent users) we start seeing the following error:
System.InvalidOperationException: The 'auth_token' property on 'Session' could not be set to a 'Int32' value. You must set this property to a non-null value of type 'Guid'.
With the following stack:
at System.Data.Common.Internal.Materialization.Shaper.ErrorHandlingValueReader`1.GetValue(DbDataReader reader, Int32 ordinal)
at System.Data.Common.Internal.Materialization.Shaper.GetPropertyValueWithErrorHandling[TProperty](Int32 ordinal, String propertyName, String typeName)
at lambda_method(Closure , Shaper )
at System.Data.Common.Internal.Materialization.Shaper.HandleEntityAppendOnly[TEntity](Func`2 constructEntityDelegate, EntityKey entityKey, EntitySet entitySet)
at lambda_method(Closure , Shaper )
at System.Data.Common.Internal.Materialization.Coordinator`1.ReadNextElement(Shaper shaper)
at System.Data.Common.Internal.Materialization.Shaper`1.SimpleEnumerator.MoveNext()
at System.Linq.Enumerable.First[TSource](IEnumerable`1 source)
at System.Linq.Queryable.First[TSource](IQueryable`1 source)
at MISoa.DataAccessLayer.Authentication.AuthenticationDB.RetrieveSession(Guid authToken)
at MISoa.DataAccessLayer.Authentication.AuthenticationAccess.RetrieveSession(String sessionToken)
Here is the culprit method:
public Session RetrieveSession(Guid authToken)
{
CheckDBContext();
var sessions = (from r in _dbContext.Sessions
where r.auth_token == authToken
select r);
return sessions.Count() > 0 ? sessions.First() : null;
}
CheckDBContext
method simply checks if the db context is null and, if it is, it throws a custom exception.
The emdx Session entity object has these public properties:
Guid auth_token
DateTime time_stamp
String user_id
String app_id
So, it looks like sometimes the above linq returns some other object from the database where the first column is an int
and not a guid
? And if so - why? Do I have a problem with multiple threads overriding each other's db context? BTW - we abstracted the code that instantiates the db context to a separate class (BaseDB) which is also handled by unity. So, because the service is a singleton I have one instance of BaseDB for everyone, right? Is this the problem here?
Oh, one more thing. We were told that we will have MSSql 2005 so in the edmx file we have ProviderManifestToken="2005"
. But I just checked and the server with our performance database is version 2008. Is this a problem?
Thank you for your help.
Do I have a problem with multiple threads overriding each other's db context?
Yes. See here: http://msdn.microsoft.com/en-us/library/system.data.objects.objectcontext.aspx
Quote from the big yellow box in the above link:
The
ObjectContext
class is not thread safe. The integrity of data objects in anObjectContext
cannot be ensured in multithreaded scenarios.
You may want to consider putting [ThreadStaticAttribute]
on your _dbContext
field.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With