c# - Can you get the DbContext from a DbSet? -
in application necessary save 10,000 or more rows database in 1 operation. i've found iterating , adding each item 1 @ time can take upwards of half hour.
however, if disable autodetectchangesenabled takes ~ 5 seconds (which want)
i'm trying make extension method called "addrange" dbset disable autodetectchangesenabled , re-enable upon completion.
public static void addrange<tentity>(this dbset<tentity> set, dbcontext con, ienumerable<tentity> items) tentity : class { // disable auto detect changes speed var detectchanges = con.configuration.autodetectchangesenabled; try { con.configuration.autodetectchangesenabled = false; foreach (var item in items) { set.add(item); } } { con.configuration.autodetectchangesenabled = detectchanges; } } so, question is: there way dbcontext dbset? don't making parameter - feels should unnecessary.
yes, you can dbcontext dbset<tentity>, solution reflection heavy. have provided example of how below.
i tested following code , able retrieve dbcontext instance dbset generated. please note that, although answer question, there better solution problem.
public static class hackydbsetgetcontexttrick { public static dbcontext getcontext<tentity>(this dbset<tentity> dbset) tentity: class { object internalset = dbset .gettype() .getfield("_internalset",bindingflags.nonpublic|bindingflags.instance) .getvalue(dbset); object internalcontext = internalset .gettype() .basetype .getfield("_internalcontext",bindingflags.nonpublic|bindingflags.instance) .getvalue(internalset); return (dbcontext)internalcontext .gettype() .getproperty("owner",bindingflags.instance|bindingflags.public) .getvalue(internalcontext,null); } } example usage:
using(var originalcontextreference = new mycontext()) { dbset<myobject> set = originalcontextreference.set<myobject>(); dbcontext retrievedcontextreference = set.getcontext(); debug.assert(referenceequals(retrievedcontextreference,originalcontextreference)); } explanation:
according reflector, dbset<tentity> has private field _internalset of type internalset<tentity>. type internal entityframework dll. inherits internalquery<telement> (where tentity : telement). internalquery<telement> internal entityframework dll. has private field _internalcontext of type internalcontext. internalcontext internal entityframework. however, internalcontext exposes public dbcontext property called owner. so, if have dbset<tentity>, can reference dbcontext owner, accessing each of properties reflectively , casting final result dbcontext.
update @loneypixel
in ef7 there private field _context directly in class implements dbset. it's not hard expose field publicly
Comments
Post a Comment