我有一个crsytal报告报告,该报告具有基于命令的动态参数。当我尝试更改基础数据库连接时,它仅适用于ORACLE,而不适用于IBM DB2。
在调用VerifyDatabase()方法时,它将引发带有“登录失败”且没有更多信息的CrystalDecisions.CrystalReports.Engine.LogOnException。
使用ORACLE或静态参数或基于表(而不是命令)的参数都可以正常工作。
private readonly ConnectionInfo _connectionInfo = new ConnectionInfo();
...
private void ConfigureCrystalReports()
{
_connectionInfo.Type = ConnectionInfoType.CRQE;
_connectionInfo.ServerName = _dbName;
_connectionInfo.UserID = _userId;
_connectionInfo.Password = _password;
PropertyBag connectionAttributes = new PropertyBag();
connectionAttributes.EnsureCapacity(3);
connectionAttributes.Add("Server", _dbName);
connectionAttributes.Add("Trusted_Connection", false);
connectionAttributes.Add("Owner", _userId);
_connectionInfo.Attributes.Collection.Add(new NameValuePair2("Database DLL", "crdb_db2cli.dll"));
_connectionInfo.Attributes.Collection.Add(new NameValuePair2("QE_DatabaseName", ""));
_connectionInfo.Attributes.Collection.Add(new NameValuePair2("QE_LogonProperties", connectionAttributes));
_connectionInfo.Attributes.Collection.Add(new NameValuePair2("QE_ServerDescription", _dbName));
_connectionInfo.Attributes.Collection.Add(new NameValuePair2("QE_SQLDB", true));
_connectionInfo.Attributes.Collection.Add(new NameValuePair2("SSO Enabled", false));
_connectionInfo.Attributes.Collection.Add(new NameValuePair2("Owner", _userId));
}
...
private void SetDBLogonForReport(ReportDocument reportDocument)
{
PropertyBag boMainPropertyBag = new PropertyBag();
PropertyBag boInnerPropertyBag = new PropertyBag();
boInnerPropertyBag.Add("Server", _dbName);
boInnerPropertyBag.Add("Trusted_Connection", "False");
boMainPropertyBag.Add("Database DLL", "crdb_db2cli.dll");
boMainPropertyBag.Add("QE_DatabaseName", "");
boMainPropertyBag.Add("QE_DatabaseType", "");
boMainPropertyBag.Add("QE_LogonProperties", boInnerPropertyBag);
boMainPropertyBag.Add("QE_ServerDescription", _connectionInfo.ServerName);
boMainPropertyBag.Add("QE_SQLDB", "False");
boMainPropertyBag.Add("SSO Enabled", "False");
CrystalDecisions.ReportAppServer.DataDefModel.ConnectionInfo boConnectionInfo = new CrystalDecisions.ReportAppServer.DataDefModel.ConnectionInfo();
boConnectionInfo.Attributes = boMainPropertyBag;
boConnectionInfo.Kind = CrConnectionInfoKindEnum.crConnectionInfoKindCRQE;
boConnectionInfo.UserName = _connectionInfo.UserID;
boConnectionInfo.Password = _connectionInfo.Password;
CrystalDecisions.ReportAppServer.DataDefModel.Tables tables = reportDocument.ReportClientDocument.DatabaseController.Database.Tables;
foreach (InternalConnectionInfo internalConnectionInfo in reportDocument.DataSourceConnections)
{
internalConnectionInfo.SetConnection(_connectionInfo.ServerName, _connectionInfo.DatabaseName,_connectionInfo.UserID, _connectionInfo.Password);
}
foreach (CrystalDecisions.ReportAppServer.DataDefModel.Table table in tables)
{
dynamic d = table;
if (table.ClassName == "CrystalReports.CommandTable")
{
switch (_dbTyp)
{
case "DB2":
// does not work
CommandTable newCommandTable = new CommandTable { ConnectionInfo = boConnectionInfo, Name = table.Name, CommandText = Regex.Replace(d.CommandText, @"RVADMIN\.", _qualifier, RegexOptions.IgnoreCase) };
reportDocument.ReportClientDocument.DatabaseController.SetTableLocation(table, newCommandTable);
// does not work
table.ConnectionInfo.Attributes["QE_DatabaseName"] = _connectionInfo.DatabaseName;
table.ConnectionInfo.Attributes["QE_ServerDescription"] = "XXX";
table.ConnectionInfo.Attributes["QE_LogonProperties"]["Database"] = _connectionInfo.DatabaseName;
table.ConnectionInfo.UserName = boConnectionInfo.UserName;
table.ConnectionInfo.Password = boConnectionInfo.Password;
// does not work
table.ConnectionInfo = boConnectionInfo;
d.CommandText = Regex.Replace(d.CommandText, @"XXX\.", _qualifier, RegexOptions.IgnoreCase);
break;
// EDIT 2019-05-17
// works just fine
reportDocument.SetSQLCommandTable(_connectionInfo, table.Name, Regex.Replace(d.CommandText, @"XXX\.", _qualifier, RegexOptions.IgnoreCase));
case "ORA":
// works just fine
table.ConnectionInfo = boConnectionInfo;
d.CommandText = Regex.Replace(d.CommandText, @"XXX\.", _qualifier, RegexOptions.IgnoreCase);
break;
}
}
else
{
// ...
}
}
reportDocument.VerifyDatabase(); // throws CrystalDecisions.CrystalReports.Engine.LogOnException with "logon failed" and no further information
}
...
crystalReportViewer.ReportSource = ReportDoc
有什么想法吗?
非常感谢您。