【问题标题】:Execute SQL command with parameter using Devart EF Drivers for Oracle使用 Devart EF Drivers for Oracle 执行带参数的 SQL 命令
【发布时间】:2017-01-01 10:35:51
【问题描述】:

我正在尝试在使用 sql 命令和参数插入新记录之前从 Oracle 表中删除记录,因为该值来自浏览器。

这是代码:

var tableName = "<myTableName>";
context.Database.ExecuteSqlCommand("DELETE :p0", tableName);

Oracle 抛出“ORA-00903: invalid table name”。

我也试过了:

context.Database.ExecuteSqlCommand("DELETE :p0", new OracleParameter("p0", OracleDbType.VarChar, 200, tableName, ParameterDirection.Input)

我缺少一些简单的东西吗?

【问题讨论】:

  • 参数不能用于指定表名或列名。顺便说一句,SQL 语法是 DELETE FROM tablename
  • 好的,那我该怎么做才能防止SQL注入呢? DELETE 适用于 SqlDeveloper
  • 你不要让你的用户输入表名。您需要提供一个表格列表并让他/她选择表格名称
  • 是的 - 这就是我所做的,但这些表名以字符串格式传回。黑客可以更改这些字符串值。听起来我需要根据有效表名列表添加一些额外的验证。谢谢

标签: .net oracle devart


【解决方案1】:

如果您针对ALL_TABLES 反弹表,您应该能够防止任何 SQL 注入攻击:

private bool TruncateTable(string Schema, string Table)
{
    OracleCommand cmd = new OracleCommand("select count (*) from all_tables " +
        "where owner = :SCHEMANAME and table_name = :TABLENAME", conn);
    cmd.Parameters.Add("SCHEMANAME", Schema.ToUpper());
    cmd.Parameters.Add("TABLENAME", Table.ToUpper());

    if (Convert.ToInt32(cmd.ExecuteScalar()) == 0)
        return false;

    cmd.CommandText = string.Format("delete from {0}.{1}", Schema, Table);
    cmd.Parameters.Clear();
    cmd.ExecuteNonQuery();

    return true;
}

在 DevArt 上,我认为 Add 将改为 AddWithValues,但看起来相同。

在这种情况下,返回值为 false 意味着没有这样的表。这一切都假定用户能够从相关表中删除。

此外,如果可能,truncatedelete from 的一个不错的替代品。它的速度要快得多,并且会重置高水位线。我认为您需要成为所有者或具有“删除任何表”权限才能执行此操作,但还有其他方法可以解决它 - 例如,让 DBA 设置一个存储过程来对某些表进行截断。

【讨论】:

  • 干杯。这是避免注入的好方法。我实际上使用的是 EF,所以我使用反射来确保表存在于 edmx 模型中:)
猜你喜欢
  • 2021-03-26
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-05-06
  • 2020-06-22
  • 2011-10-31
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多