问题描述
我的Asp.Net MVC应用程序设置如下.解决方案中有4个项目.
My Asp.Net MVC application is setup as follows.There are 4 projects in solution.
- ge.Web
- ge.BLL
- ge.Core
- ge.Entities
控制器初始化ge.Core中存在的存储库对象
Controller in ge.Web initializes a repository object present in ge.Core
public class MapsController : Controller
{
private AssessmentRepository repAssessments = new AssessmentRepository("name=GEContext", schoolCode);
public ActionResult DisplaySearchResults()
{
.....
}
}
评估资料库
public class AssessmentRepository : Repository<Assessment>, IAssessmentRepository
{
public AssessmentRepository(string connString, string schoolCode)
:base(connString, schoolCode)
{ }
}
存储库
public class Repository<TEntity> : IRepository<TEntity> where TEntity:class
{
protected readonly GEContext context;
public Repository(string connString, string schoolCode) {
context = new GEContext(connString);
}
}
GEContext
public class GEContext : DbContext
{
public GEContext(string connString):base(connString)
{
this.Configuration.LazyLoadingEnabled = false;
Database.SetInitializer(new MySqlInitializer());
}
}
DbContext
public class DbContext : IDisposable, IObjectContextAdapter
{
public DbContext(string nameOrConnectionString);
}
Web.Config
<add name="GEContext" connectionString="server=localhost;port=4040;uid=root;pwd=xxx;database=ge" providerName="MySql.Data.MySqlClient" />
现在我想将web.config中存在的"database = ge"替换为database = ge_ [schoolCode].在运行时如何解决?
now i want to replace "database=ge" present in web.config with database=ge_[schoolCode]. at runtime How can i go about it?
更新我的解决方案不起作用.所以我再次说明问题.
UPDATEMy solution did not work. so i am stating the problem once again.
Web.Config
我已将我的配置文件更改为以下文件(以前GEContext是唯一的连接字符串)
I have changed My config file to the following (previously GEContext was the only connection string)
<connectionStrings>
<add name="GEContext_sc001" connectionString="server=localhost;port=4040;uid=root;pwd=blabla;database=db_sc001" providerName="MySql.Data.MySqlClient" />
<add name="GEContext_sc002" connectionString="server=localhost;port=4040;uid=root;pwd=blabla;database=db" providerName="MySql.Data.MySqlClient" />
<appSettings>
<add key="SchoolCodes" value="sc001,sc002"/>
这些是允许的学校代码
现在,当用户在登录屏幕上输入学校代码时,将根据SchoolCodes密钥中显示的代码进行验证.如果是,则应尝试连接到该特定连接的connectionString.现在,当我的代码进入
Now when the user enters schoolcode at login screen, it is validated against the codes present in SchoolCodes key. and if yes, then it should try to connect to the connectionString for that particular connection. Now when my code comes to
UserManager.FindAsync
在AccountController的登录功能中,尝试查找GEContext时会崩溃.那是在哪儿?以及我该如何更改?
in Login function of AccountController, it crashes trying to find GEContext. Where is that set? and how can i change it?
我已如下更改控制器中调用的存储库
I have changed the repository calling in controller as follows
private static string schoolCode = (string)System.Web.HttpContext.Current.Session["SchoolCode"];
private AssessmentRepository repAssessments = new AssessmentRepository("name=GEContext_" + schoolCode);
UPDATE-2 ge.Web
IdentityConfig.cs
public class ApplicationUserManager : UserManager<ApplicationUser, int>
{
public ApplicationUserManager(IUserStore<ApplicationUser, int> store)
: base(store)
{
}
public static ApplicationUserManager Create(IdentityFactoryOptions<ApplicationUserManager> options, IOwinContext context)
{
var manager = new ApplicationUserManager(new UserStore<ApplicationUser, Role, int, UserLogin, UserRole, UserClaim>(context.Get<ApplicationDbContext>()));
...........
}
ge.Core中存在以下内容
The following is present in ge.Core
ApplicationDbContext
public class ApplicationDbContext : IdentityDbContext<ApplicationUser, Role, int, UserLogin, UserRole, UserClaim>
{
public ApplicationDbContext(string connString)
: base(connString)
{
Database.SetInitializer(new MySqlInitializer());
}
public static ApplicationDbContext Create()
{
return new ApplicationDbContext("name=GEContext_");
}
}
我如何将schoolCode从ge.web传递到ge.Core(答案应该很简单,但目前我无法解决)
How can i pass schoolCode from ge.web to ge.Core (answer should be straight forward but currently i cant get my head around it)
UPDATE-3
正如itikhomi所言,并从这篇文章中寻求帮助,我已经更改了我的代码如下
As told by itikhomi and taking help from this post I have changed my code as follows
-
在ApplicationDbContext类中添加了以下内容
in ApplicationDbContext class added the following
公共静态ApplicationDbContext创建(字符串scCode){ 返回新的ApplicationDbContext("name = GEContext_" + scCode); }
public static ApplicationDbContext Create(string scCode){ return new ApplicationDbContext("name=GEContext_" + scCode); }
在AccountController登录中
in AccountController Login
var appDbContext = ApplicationDbContext.Create(model.SchoolCode);
var appDbContext = ApplicationDbContext.Create(model.SchoolCode);
Request.GetOwinContext().Set<ApplicationDbContext>(appDbContext);
它仍然没有命中正确的数据库
it still does not hit the correct database
推荐答案
您有两种方法
1)
using System.Data.SqlClient;
public class Repository<TEntity> : IRepository<TEntity> where TEntity:class
{
protected readonly GEContext context;
public Repository(string connString, string schoolCode) {
context = new GEContext(connString);
var connection = new SqlConnectionStringBuilder(context.Database.Connection.ConnectionString);
connection.InitialCatalog = "YOUR_PREFIX_FROMSOMEWHERE"+schoolCode;
context.Database.Connection.ConnectionString = connection.ConnectionString;
}
}
2)如果要在使用前打开连接时切换连接 ChangeDatabase :
2) if you wants to switch connection when it opened before use ChangeDatabase:
//open connection if it close
context.Database.Connection.ChangeDatabase("DATABASE-NAME");
注意:如果使用ChangeDatabase连接,应该已经打开
NOTE: if use ChangeDatabase connection should be already opened
对于UPDATE3:
您需要这样做:
public class ApplicationDbContext : IdentityDbContext<ApplicationUser>
{
public ApplicationDbContext()
: base("DefaultConnection", throwIfV1Schema: false)
{
}
public ApplicationDbContext(string schoolCode)
: base(schoolCode)
{
var connection = new SqlConnectionStringBuilder(this.Database.Connection.ConnectionString);
connection.InitialCatalog = "YOUR_PREFIX_FROMSOMEWHERE" + schoolCode;
this.Database.Connection.ConnectionString = connection.ConnectionString;
}
public static ApplicationDbContext Create()
{
return new ApplicationDbContext();
}
}
在帐户控制器中:
public ApplicationSignInManager SignInManager
{
get
{
if (_signInManager == null)
{
var code = HttpContext.Request.Form.Get("SchoolCode");//Get from FORM\QueryString\Session whatever you wants
if (code != null)
{
HttpContext.GetOwinContext().Set<ApplicationSignInManager>(new ApplicationSignInManager(_userManager, HttpContext.GetOwinContext().Authentication));
}
_signInManager = HttpContext.GetOwinContext().Get<ApplicationSignInManager>();
}
return _signInManager;
}
private set
{
_signInManager = value;
}
}
public ApplicationUserManager UserManager
{
get
{
if (_userManager == null)
{
var code = HttpContext.Request.Form.Get("SchoolCode");//Get from FORM\QueryString\Session whatever you wants
if (code != null)
{
var appDbContext = new ApplicationDbContext(code);
HttpContext.GetOwinContext().Set<ApplicationDbContext>(appDbContext);
HttpContext.GetOwinContext().Set<ApplicationUserManager>(new ApplicationUserManager(new UserStore<ApplicationUser>(appDbContext))); //OR USE your specified create Method
}
_userManager = HttpContext.GetOwinContext().GetUserManager<ApplicationUserManager>();
}
return _userManager;
}
private set
{
_userManager = value;
}
}
您的问题是在更改OWIN上下文之前创建了UserManager的存储区,在这种情况下,最好使用像
Your problem is in Store of UserManager is created before you change your OWIN context, in this case better to use DI like here
这篇关于如何在运行时更改dbcontext连接字符串中的数据库名称的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!