I am trying to add autofac as my IOC but when i do this GetTransaction fails with the following message: NoScope is in a transaction.
I am using the Our.Umbraco.IoC from Shannon and everything is working except my custom database inserts. I have wrapt my database inserts into a using statement.
using (var transaction = UmbDatabase.Database.GetTransaction())
{
transaction.Complete();
}
UmbDatabase is injected to the controller constructor. When i don't use IOC all works fine.
UPDATE:
After further investigation i found out that the problem is inside of the transaction. I am looking up data inside of the content cache by using the UmbracoContext also injected inside of the constructor.
UPDATE 2:
I have found the problem but need some help to fix it. I am using the TypedMember from the Umbraco helper. This uses MembershipHelper under the covers and the cache layer RequestCache causes for this exception.
System.Exception: NoScope is in a transaction.
bij Umbraco.Core.Cache.HttpRequestCacheProvider.GetCacheItem(String cacheKey, Func`1 getCacheItem)
bij Umbraco.Core.Cache.CacheProviderExtensions.GetCacheItem[T](ICacheProvider provider, String cacheKey, Func`1 getCacheItem)
bij Umbraco.Web.Security.MembershipHelper.GetByProviderKey(Object key)
bij Umbraco.Web.UmbracoHelper.TypedMember(Guid id)
No i have not setup DI myself, i have looked at the source off Our.Umbraco.IoC and I would do the same if i don't use the packaged. I have tried simplefy my code and found te lookup that causes the error.
using (var transaction = UmbDatabase.Database.GetTransaction())
{
UmbDatabase.Database.Insert(new CustomPocoClass{
// this line works
ContentName = UmbHelper.TypedContent(new Guid("bb6467c5-28a2-4aca-9cdc-b82568333150")).Name,
// this line fails
MemberName = UmbHelper.TypedMember(new Guid("765f9ac5-ae5a-430a-b86b-8dc35298ee5b")).Name
});
transaction.Complete();
}
so typedmember causes the error. the strange thing is that when i first lookup the member outside off the transaction and then do a second lookup inside the transaction it works. so like this:
var temp = UmbHelper.TypedMember(new Guid("765f9ac5-ae5a-430a-b86b-8dc35298ee5b")).Name;
using (var transaction = UmbDatabase.Database.GetTransaction())
{
UmbDatabase.Database.Insert(new CustomPocoClass{
// this line works
ContentName = UmbHelper.TypedContent(new Guid("bb6467c5-28a2-4aca-9cdc-b82568333150")).Name,
// this line fails
MemberName = UmbHelper.TypedMember(new Guid("765f9ac5-ae5a-430a-b86b-8dc35298ee5b")).Name
});
transaction.Complete();
}
offcource in my real code the lookup i nested inside of a loop inside off the transaction and i can do it first outside off the transaction.
A it has nothing to do with my ioc container. It is a bug in umbraco the problem appeared after i commented out some logic. so i have never seen it before. But now i am refactoring some code the bug came to the surface.
additional question: you mention that UmbDatabase is injected... but what is it, what CLR type, eg is it a DatabaseContext, and how is it wired into the IOC container?
The problem is i am looking up some Members Data inside off my transaction so when i do this:
using (var transaction = UmbDatabase.Database.GetTransaction())
{
UmbDatabase.Database.Insert(new CustomPocoClass{
// this line fails
MemberName = UmbHelper.TypedMember(new Guid("765f9ac5-ae5a-430a-b86b-8dc35298ee5b")).Name
});
transaction.Complete();
}
i get the NoScope Error. But when i do this it works:
var temp = UmbHelper.TypedMember(new Guid("765f9ac5-ae5a-430a-b86b-8dc35298ee5b")).Name;
using (var transaction = UmbDatabase.Database.GetTransaction())
{
UmbDatabase.Database.Insert(new CustomPocoClass{
// this line no works
MemberName = UmbHelper.TypedMember(new Guid("765f9ac5-ae5a-430a-b86b-8dc35298ee5b")).Name
});
transaction.Complete();
}
So i have tried ScopeProvider and it is internal at the moment so used reflection to get it. and nou this code works:
using (var scope = ScopeProvider.CreateScope(System.Data.IsolationLevel.Unspecified, RepositoryCacheMode.Unspecified, (IEventDispatcher)null, new bool?(), false)) {
UmbDatabase.Database.Insert(new CustomPocoClass{
// this line now works
MemberName = UmbHelper.TypedMember(new Guid("765f9ac5-ae5a-430a-b86b-8dc35298ee5b")).Name
});
scope.Complete();
}
Same problem, i can't figure out how is it possible that problems like this aren't fixed quickly and are still present in V 7.11...
As Marcel van Helmont sais ScopeProvider that should be used as best practice to avoid the NoScope problem when using transactions is defined INTERNAL in ApllicationContext, so is unaccessible!
The issue is tracked from April, the crazy thing is that the Core Team is saying (and apparently updating the documentation too) that the Best Practice is doing this
http://issues.umbraco.org/issue/U4-11207
using (var scope = ApplicationContext.Current.ScopeProvider.CreateScope())
{
var database = scope.Database;
// use database
scope.Complete();
}
but this is not possible! The only way is the one from Marcel!
Don't suggest best practices when we can't use them please!
Database Transaction NoScope
Hello,
I am trying to add autofac as my IOC but when i do this GetTransaction fails with the following message: NoScope is in a transaction.
I am using the Our.Umbraco.IoC from Shannon and everything is working except my custom database inserts. I have wrapt my database inserts into a using statement.
UmbDatabase is injected to the controller constructor. When i don't use IOC all works fine.
UPDATE:
After further investigation i found out that the problem is inside of the transaction. I am looking up data inside of the content cache by using the UmbracoContext also injected inside of the constructor.
UPDATE 2:
I have found the problem but need some help to fix it. I am using the TypedMember from the Umbraco helper. This uses MembershipHelper under the covers and the cache layer RequestCache causes for this exception.
Anybody a idea?
thanks
Hi Marcel,
can you show your autofac setup ?
Maybe something is wrong there ?
dave
Hi Dave,
My autofac setup:
So nothing fancy..
Don't have any idea.
Maybe you can report a issue here : https://github.com/Shazwazza/Our.Umbraco.IoC/issues
Have you tried without the package ? to see if that is the cause ?
Dave
Hi Dave,
No i have not setup DI myself, i have looked at the source off Our.Umbraco.IoC and I would do the same if i don't use the packaged. I have tried simplefy my code and found te lookup that causes the error.
so typedmember causes the error. the strange thing is that when i first lookup the member outside off the transaction and then do a second lookup inside the transaction it works. so like this:
offcource in my real code the lookup i nested inside of a loop inside off the transaction and i can do it first outside off the transaction.
A it has nothing to do with my ioc container. It is a bug in umbraco the problem appeared after i commented out some logic. so i have never seen it before. But now i am refactoring some code the bug came to the surface.
Michael Falk has already created a issue for it: http://issues.umbraco.org/issue/U4-10290
Probably has nothing to do with IOC but with creating your own transaction - see issue http://issues.umbraco.org/issue/U4-10290 - will comment there.
additional question: you mention that
UmbDatabase
is injected... but what is it, what CLR type, eg is it aDatabaseContext
, and how is it wired into the IOC container?Yes the NoScope error has nothing to do with IOC container, i first thought that this causing the problem. But for the IOC i use Shannon packaged and it is using DatabaseContext. see https://github.com/Shazwazza/Our.Umbraco.IoC/blob/master/src/Our.Umbraco.IoC/UmbracoServices.cs
The problem is i am looking up some Members Data inside off my transaction so when i do this:
i get the NoScope Error. But when i do this it works:
So i have tried ScopeProvider and it is internal at the moment so used reflection to get it. and nou this code works:
off course not best practices.
Same problem, i can't figure out how is it possible that problems like this aren't fixed quickly and are still present in V 7.11... As Marcel van Helmont sais ScopeProvider that should be used as best practice to avoid the NoScope problem when using transactions is defined INTERNAL in ApllicationContext, so is unaccessible! The issue is tracked from April, the crazy thing is that the Core Team is saying (and apparently updating the documentation too) that the Best Practice is doing this http://issues.umbraco.org/issue/U4-11207
but this is not possible! The only way is the one from Marcel! Don't suggest best practices when we can't use them please!
Did this ever get fixed?
I have the samme error in 7.15.5 where the connection is null when using the GetTransaction() the first time.
This problem has been present for over 2 years now. It's a huge problem that we are not able to use transactions when operating on custom tables.
Please fix it.
is working on a reply...