我正在尝试更新我在DataSet(XSD文件)中创建的QueriesTableAdapter中每个查询的连接字符串。我已经尝试通过反射尝试这样做的方法(我有一个类似的方法使用表适配器)但是它似乎无法访问查询。这是我的方法:
/// <summary>
/// Changes the database all the queries in a queries table adapter connect to
/// </summary>
/// <typeparam name="IQA">The type of the queries table adapter</typeparam>
/// <param name="InstanceQueriesAdapter">The instance of the queries table adapter</param>
/// <param name="sqlDatabaseName">The name of the database the queries table adapter queries should connect to</param>
public static void GetInstanceQueriesAdapter<IQA>(ref IQA InstanceQueriesAdapter, string sqlDatabaseName)
{
try
{
PropertyInfo qAdapterCommandCollection = InstanceQueriesAdapter.GetType().GetProperty("CommandCollection");
if (qAdapterCommandCollection != null)
{
SqlCommand[] qaCC = (SqlCommand[])qAdapterCommandCollection.GetValue(InstanceQueriesAdapter, null);
foreach (SqlCommand singleCommand in qaCC)
{
SqlConnection newSQLConnection = singleCommand.Connection;
SqlConnectionStringBuilder csBulider = new SqlConnectionStringBuilder(newSQLConnection.ConnectionString);
csBulider.InitialCatalog = sqlDatabaseName;
newSQLConnection.ConnectionString = csBulider.ConnectionString;
singleCommand.Connection = newSQLConnection;
}
qAdapterCommandCollection.SetValue(InstanceQueriesAdapter, qaCC, null);
}
else
{
throw new Exception("Could not find command collection.");
}
}
catch (Exception _exception)
{
throw new Exception(_exception.ToString());
}
}
由于GetProperty方法返回null,因此失败。但是你可以在这里看到该物业确实存在:
以下是立即窗口的输出:
? InstanceQueriesAdapter.GetType().GetProperties()
{System.Reflection.PropertyInfo[2]}
[0]: {System.ComponentModel.ISite Site}
[1]: {System.ComponentModel.IContainer Container}
? InstanceQueriesAdapter.GetType().GetMethods()
{System.Reflection.MethodInfo[14]}
[0]: {System.Object ImportProcess(System.Object, System.Object, System.Object, System.Object, System.Object, System.Object, System.Nullable`1[System.Guid], System.String ByRef)}
[1]: {Void add_Disposed(System.EventHandler)}
[2]: {Void remove_Disposed(System.EventHandler)}
[3]: {System.ComponentModel.ISite get_Site()}
[4]: {Void set_Site(System.ComponentModel.ISite)}
[5]: {Void Dispose()}
[6]: {System.ComponentModel.IContainer get_Container()}
[7]: {System.String ToString()}
[8]: {System.Object GetLifetimeService()}
[9]: {System.Object InitializeLifetimeService()}
[10]: {System.Runtime.Remoting.ObjRef CreateObjRef(System.Type)}
[11]: {Boolean Equals(System.Object)}
[12]: {Int32 GetHashCode()}
[13]: {System.Type GetType()}
有没有人知道如何获得这个“CommandCollection”,以便我可以动态更改连接?
答案 0 :(得分:0)
从我所看到的,CommandCollection属性受到保护;试试这个:
GetProperty( "CommandCollection", BindingFlags.GetProperty | BindingFlags.Instance | BindingFlags.NonPublic )
答案 1 :(得分:0)
更改数据库的工作代码。还值得注意的是,连接的所有部分都可以在这里更改,例如超时等。
/// <summary>
/// Changes the database all the queries in a queries table adapter connect to
/// </summary>
/// <typeparam name="IQA">The type of the queries table adapter</typeparam>
/// <param name="InstanceQueriesAdapter">The instance of the queries table adapter</param>
/// <param name="sqlDatabaseName">The name of the database the queries table adapter queries should connect to</param>
public static void GetInstanceQueriesAdapter<IQA>(ref IQA InstanceQueriesAdapter, string sqlDatabaseName)
{
try
{
FieldInfo qAdapterCommandCollection = InstanceQueriesAdapter.GetType().GetField("_commandCollection", BindingFlags.GetProperty | BindingFlags.Instance | BindingFlags.NonPublic);
MethodInfo initCC = InstanceQueriesAdapter.GetType().GetMethod("InitCommandCollection", BindingFlags.GetProperty | BindingFlags.Instance | BindingFlags.NonPublic);
if (qAdapterCommandCollection != null && initCC != null)
{
initCC.Invoke(InstanceQueriesAdapter, null);
IDbCommand[] qaCC = (IDbCommand[])qAdapterCommandCollection.GetValue(InstanceQueriesAdapter);
foreach (SqlCommand singleCommand in qaCC)
{
SqlConnection newSQLConnection = singleCommand.Connection;
SqlConnectionStringBuilder csBulider = new SqlConnectionStringBuilder(newSQLConnection.ConnectionString);
csBulider.InitialCatalog = sqlDatabaseName;
newSQLConnection.ConnectionString = csBulider.ConnectionString;
singleCommand.Connection = newSQLConnection;
}
qAdapterCommandCollection.SetValue(InstanceQueriesAdapter, qaCC);
}
else
{
throw new Exception("Could not find command collection.");
}
}
catch (Exception _exception)
{
throw new Exception(_exception.ToString());
}
}