关于Sql注入的基本概念,相信不需多说,大家都清楚,经典的注入语句是' or 1=1--
单引号而截断字符串,“or 1=1”的永真式的出现使得表的一些信息被暴露出来,如果sql语句是select * from 的话,可能你整个表的信息都会被读取到,更严重的是,如果恶意使用都使用drop命令,那么可能你的整个数据库得全线崩溃。

当然,现在重点不是讲sql注入的害处,而是说说如何最大限度的避免注入问题。

sql注入的存在在最大危害,是sql的执行语句没有和控制语句分开,我们想要select一些东西,但用户可能拼出' or 1=1甚至再加上delete/update/drop,后来是属于控制语句了,所以要避免sql的注入,就必须把查询语句与控制语句分开。

SqlParameter给我们提供了一个很好的类,有了它,我们可以不现拼接字符串,也可以不再担心单引号带来的惨剧,因为,这一切会有人来为我们完成的。

简单的给个示例

传统的查询语句的sql可能为
string sql="select * from users where user_id='"+Request.QueryString["uid"]+"'";
很显然,我们在这里拼接了字符串,这就给sql注入留下了可乘之机。

现在,我们要改写这样的语句,使用SqlParameter来做

SqlCommand SqlCmd = new SqlCommand(sql, SqlConn);
SqlParameter _userid = new SqlParameter("uid", SqlDbType.Int);
_userid.Value = Request.QueryString["u_id"];
SqlCmd.Parameters.Add(_userid);

这样,我们可以保证外接参数能被正确的转换,单引号这些危险的字符也会转义了,不会再对库造成威胁。

当然,这仅是一个示例而已,在真实的情况下,可能你还要对 Request.QueryString["u_id"]进行必要的检测与分析,这样才安全

所以,使用参数化的sql语句,是一种很好的做法

Dim sql As StringBuilder = New StringBuilder()
            sql.Append("")
            sql.Append("SELECT * FROM test")
            sql.Append(" WHERE  a= @p1 ")

Dim command As SqlCommand    =    dac.CreateCommand(sql.ToString())  'dac为自己写的类
            Dim param As SqlParameter = New SqlParameter()
            param .ParameterName = "@p1"
            param .SqlDbType = SqlDbType.NVarChar
            param .Value = b       'b为该函数的参数(ByVal b as String)
            command .Parameters.Add(param)
            Dim reader As SqlDataReader = command.ExecuteReader()

SqlParameter 构造函数

SqlParameter 构造函数 (String, SqlDbType, Int32, ParameterDirection,
Byte, Byte, String, DataRowVersion, Boolean, Object, String, String,
String)
初始化 SqlParameter
类的一个新实例,该类使用参数名、参数的类型、参数的长度、方向、精度、小数位数、源列名称、DataRowVersion
值之一、用于源列映射的布尔值、SqlParameter 的值、此 XML 实例的架构集合所在的数据库的名称、此 XML
实例的架构集合所在的关系架构以及此参数的架构集合的名称。
命名空间: System.Data.SqlClient
程序集: System.Data(在 system.data.dll 中)

C#
public SqlParameter (
    string parameterName,
    SqlDbType dbType,
    int size,
    ParameterDirection direction,
    byte precision,
    byte scale,
    string sourceColumn,
    DataRowVersion sourceVersion,
    bool sourceColumnNullMapping,
    Object value,
    string xmlSchemaCollectionDatabase,
    string xmlSchemaCollectionOwningSchema,
    string xmlSchemaCollectionName
)

参数
parameterName
要映射的参数的名称。

dbType
SqlDbType 值之一。

size
参数的长度。

direction
ParameterDirection 值之一。

precision
要将 Value 解析为的小数点左右两侧的总位数。

scale
要将 Value 解析为的总小数位数。

sourceColumn
源列的名称。

sourceVersion
DataRowVersion 值之一。

sourceColumnNullMapping
如果源列可为空,则为 true;如果不可为空,则为 false。

value
一个 Object,它是 SqlParameter 的值。

xmlSchemaCollectionDatabase
此 XML 实例的架构集合所在的数据库的名称。

xmlSchemaCollectionOwningSchema
包含此 XML 实例的架构集合的关系架构。

xmlSchemaCollectionName
此参数的架构集合的名称。

备注
如果未在 size 和 precision 参数中显式设置 Size 和 Precision,则从 dbType 参数的值推断出它们。

SqlParameter 类
表示 SqlCommand 的参数,也可以是它到 DataSet 列的映射。无法继承此类。

有关此类型所有成员的列表,请参阅 SqlParameter 成员。

System.Object
   System.MarshalByRefObject
      System.Data.SqlClient.SqlParameter

[Visual Basic]
NotInheritable Public Class SqlParameter
   Inherits MarshalByRefObject
   Implements IDbDataParameter, IDataParameter, ICloneable
[C#]
public sealed class SqlParameter : MarshalByRefObject,
   IDbDataParameter, IDataParameter, ICloneable
[C++]
public __gc __sealed class SqlParameter : public
   MarshalByRefObject, IDbDataParameter, IDataParameter, ICloneable
[JScript]
public class SqlParameter extends MarshalByRefObject implements
   IDbDataParameter, IDataParameter, ICloneable
线程安全
此类型的所有公共静态(Visual Basic 中为 Shared)成员是线程安全的。但不保证任何实例成员是线程安全的。

备注
参数名称不区分大小写。

示例
[Visual Basic, C#, C++] 下面的示例通过 SqlDataAdapter 中的
SqlParameterCollection 集合创建 SqlParameter 的多个实例。这些参数用于从数据源中选择数据并将数据放在
DataSet 中。此示例假定已经用适当的架构、命令和连接创建了 DataSet 和 SqlDataAdapter。

[Visual Basic]
Public Sub AddSqlParameters()
    ' ...
    ' create myDataSet and myDataAdapter
    ' ...
    myDataAdapter.SelectCommand.Parameters.Add("@CategoryName", SqlDbType.VarChar, 80).Value = "toasters"
    myDataAdapter.SelectCommand.Parameters.Add("@SerialNum", SqlDbType.Int).Value = 239
   
    myDataAdapter.Fill(myDataSet)
End Sub 'AddSqlParameters

[C#]
public void AddSqlParameters()
{
// ...
// create myDataSet and myDataAdapter
// ...

myDataAdapter.SelectCommand.Parameters.Add("@CategoryName", SqlDbType.VarChar, 80).Value = "toasters";
  myDataAdapter.SelectCommand.Parameters.Add("@SerialNum", SqlDbType.Int).Value = 239;
  myDataAdapter.Fill(myDataSet);

}

[C++]
public:
void AddSqlParameters()
{
// ...
// create myDataSet and myDataAdapter
// ...

myDataAdapter->SelectCommand->Parameters->Add(S"@CategoryName", SqlDbType::VarChar, 80)->Value = S"toasters";
  myDataAdapter->SelectCommand->Parameters->Add(S"@SerialNum", SqlDbType::Int)->Value = __box(239);
  myDataAdapter->Fill(myDataSet);

}

[JScript] 没有可用于 JScript 的示例。若要查看 Visual Basic、C# 或 C++ 示例,请单击页左上角的“语言筛选器”按钮 。

要求
命名空间: System.Data.SqlClient

平台: Windows 98, Windows NT 4.0, Windows ME, Windows 2000, Windows XP
Home Edition, Windows XP Professional, Windows Server 2003 系列, .NET
Framework 精简版

程序集: System.Data (在 System.Data.dll 中)

使用SqlParameter

SqlParameter[] p =
{
SqlHelper.MakeInParam("@EntryID",SqlDbType.Int,4,ev.EntryID),
SqlHelper.MakeInParam("@BlogID",SqlDbType.Int,4,ev.BlogID),
SqlHelper.MakeInParam("@URL",SqlDbType.NVarChar,255,DataHelper.CheckNull(ev.ReferralUrl)),
SqlHelper.MakeInParam("@IsWeb",SqlDbType.Bit,1,ev.PageViewType)
};
SqlHelper.ExecuteNonQuery(conn,CommandType.StoredProcedure,"blog_TrackEntry",p);

答疑:SqlParameter赋值之后怎么添加值
用SqlCommand我知道用add
但我想问的是   SqlParameter
例如
SqlParameter   parm   =   new   SqlParameter(PARM_ORDER_ID,   SqlDbType.Int);
parm.Value   =   orderId;
之后能不能再改parm添加一个值
因为我写了个方法是传递SqlParameter类型的参数
但有时要做些判断
像
SqlParameter   parm   =   new   SqlParameter(PARM_ORDER_ID,   SqlDbType.Int);
parm.Value   =   orderId;
if(...)
{
//添加一个参数
}
ExecuteReader(parm,.....);
请问应该怎么做呢
 
最佳答案        int IArticle.Insert(ArticleInfo article)
        {
            //如果对象存在
            if (article.ID != -1)
                return -1;
            else
                article.ID = TableHelper.GetSequence(SQLHelper.ConnectionString, "Article", "ID");
            //统计执行成功的数量
            int successCount = 0;
            string SQL_THIS = SQL_INSERT_ARTICLE;
            SqlParameter[] paras = GetParas();
            paras[0].Value = article.ID;
            paras[1].Value = article.Title;
            paras[2].Value = article.DateAdded;
            paras[3].Value = article.Text;
            paras[4].Value = article.SourceUrl;
            paras[5].Value = article.PostType;
            paras[6].Value = article.Author;
            paras[7].Value = article.Email;
            paras[8].Value = article.SourceName;
            paras[9].Value = article.BlogID;
            paras[10].Value = article.CategoryID;
            paras[11].Value = article.Summary;
            paras[12].Value = article.IsBySummary;
            paras[13].Value = article.DateUpdated;
            paras[14].Value = article.TitleUrl;
            paras[15].Value = article.FeedBackCount;
            paras[16].Value = article.PostConfig;
            paras[17].Value = article.EntryName;
            paras[18].Value = article.KeyWord;
            SqlConnection conn = new SqlConnection(SQLHelper.ConnectionString);
            successCount = SQLHelper.ExecuteNonQuery(conn, CommandType.Text, SQL_THIS, paras);

return successCount;
        }

SqlParameter的用法的更多相关文章

  1. SqlParameter 基本用法

    因为通过SQL 语句的方式,有时候存在脚本注入的危险,所以在大多数情况下不建议用拼接SQL语句字符串方式,希望通过SqlParameter实现来实现对数据的操 作,针对SqlParameter的方式我 ...

  2. SqlParameter 用法总结

    作用 解决恶意的T-sql语句攻击第一种 //传入参数 string ProductGroupCode, string Ismaintain, int HierarchyID, string BOMN ...

  3. SqlParameter的两种用法【二】

    private void Loadprovince() { string sql = "select * from Tables where ArealdPid=@pid"; /第 ...

  4. SqlParameter用法

    if (id != null) { sql = @"update [User] set Username = @Username, Password = @Password, Type = ...

  5. sql事务(Transaction)用法介绍及回滚实例

    sql事务(Transaction)用法介绍及回滚实例 事务(Transaction)是并发控制的单位,是用户定义的一个操作序列.这些操作要么都做,要么都不做,是一个不可分割的工作单位.通过事务, S ...

  6. Ibatis.net总是报:【ExecuteStoreCommand SqlParameterCollection 中已包含 SqlParameter】(转)

    今天很奇怪调用EF的ExecuteStoreCommand 出现了个这样的错误,怎么也调试不过,痛定思痛 原来 command被连着调用了而没有销毁掉   public static DataTabl ...

  7. 用SqlParameter 给SQL传递参数

    1.数据访问层 using的用法: 01.可以using System;导命名控空间 02.using 的语法结构 using(变量类型  变量名 =new 变量类型()) { } 案例: 03.us ...

  8. Sql server 事务的两种用法

    事务(Transaction)是并发控制的单位,是用户定义的一个操作序列.这些操作要么都做,要么都不做,是一个不可分割的工作单位. 通过事务,SQL Server能将逻辑相关的一组操作绑定在一起,以便 ...

  9. ASP.NET中的ExecuteNonQuery()方法的用法

    下面我将详细讲解在机房收费系统D层中如何对数据库的增加.删除.修改,最后再来总结一下 ExecuteNonQuery(),ExecuteScalar(),ExecuteReader的用法: 一.增.删 ...

随机推荐

  1. AIX 系统补丁升级步骤

    AIX 系统补丁升级步骤   1.升级之前建议备份 rootvg (推荐) # smit mksysb   2.检查系统版本号 # oslevel -r   3.找到补丁光盘或者下载补丁,上传到服务器 ...

  2. Bootstrap Table 的用法

    记录下 Bootstrap Table 的用法,备忘. <!DOCTYPE html> <html> <head> <meta charset="u ...

  3. 2017-2018年红头发新版Cisco认证网络工程师(CCNA-R&S)全新讲解分享

    网名"红头发",多年授课经验,业内资深思科认证讲师,其所写的CISCO认证原创技术文章风靡各大网站与培训机构.精通CISCO各类路由交换产品,熟悉JUNIPER M/T系列路由产品 ...

  4. Mysql第八天 分区与分表

    分区表 主要提供例如以下的特性,或者适合如此场景: 数据量非常大, 或者仅仅有表中最后的部分有热点数据.其它均为历史数据 分区表数据更easy维护,能够对独立的分区删除等操作 分区表的数据能够分布在不 ...

  5. java.lang.IllegalArgumentException: The observer is null.终于解决方式

    java.lang.IllegalArgumentException: The observer is null.终于解决方式 在使用数据适配的时候的问题: java.lang.IllegalArgu ...

  6. Java解析注解

    package com.itbuluoge.anno; import java.lang.reflect.Method; import java.util.ArrayList; import java ...

  7. 淘宝在hbase中的应用和优化

    本文来自于NoSQLFan联合作者@koven2049,他在淘宝从事Hadoop及HBase相关的应用和优化. 对Hadoop.HBase都有深入的了解,本文就是其在工作中对HBase的应用优化小结, ...

  8. vim 基础学习之可视模式

    1. 选择模式这个模式必须通过可视模式进入.在可视模式下,我们通过 <C-g>来把我们的可视选中块作为选择模式下的操作块. 这时候我们输入可见字符,就会把这个块给覆盖掉.例如aaa bbb ...

  9. 漫漫人生路-学点Jakarta基础-Java8新特性 Stream/Lambda

    背景 Stream 是对集合(Collection)对象功能的增强,它专注于对集合对象进行各种非常便利.高效的聚合操作(aggregate operation),或者大批量数据操作 (bulk dat ...

  10. 79.QT解决迷宫问题(面向过程与面向对象)

    面向过程: 创建一个类继承dialog,mydialog,添加两个变量 #ifndef MYDIALOG_H #define MYDIALOG_H #include <QDialog>&g ...