65.9K
CodeProject 正在变化。 阅读更多。
Home

使用 C# 枚举 MS SQL Server 2000 中的存储过程

starIconstarIconstarIcon
emptyStarIcon
starIcon
emptyStarIcon

3.15/5 (13投票s)

2006年1月3日

2分钟阅读

viewsIcon

104355

downloadIcon

490

本指南将向您展示如何枚举 MSSQL 2000 中的存储过程,以及检索存储过程的参数信息。

引言

本文将演示如何使用 C#、ASP.NET 和 MS SQL Server 2000 枚举存储过程的参数。

背景

在网上搜索了一段时间,试图找到一种简单的方法来枚举存储过程的参数后,我决定在这里发布我所拥有的解决方案。 为什么它有用? 嗯,如果你想创建一个可以动态地将参数传递给存储过程的解决方案,它非常有用。 我使用该解决方案创建了一个报告应用程序,该应用程序通过在 SQL Server 上执行存储过程将数据返回给用户(通过 Web 应用程序)。 但重要的是,我允许用户提供参数,例如报告开始日期或报告结束日期,并且我需要确保我可以验证输入的数据是否是存储过程参数的正确类型。 我将在本文中向您展示如何操作。

Using the Code

此代码可以在任何 C# 应用程序(Web 或其他)中使用,但该示例将演示在 Web 应用程序中的用法。 如果您下载示例项目,您当然需要 VS.NET 2003、MS SQL Server 2000 的实例和正在运行的 IIS。 您需要更改 Web.config 中的连接字符串以指向您的本地 MS SQL Server 实例。

列出存储过程

由于 MS SQL Server 没有提供用于枚举存储过程的扩展存储过程,我们只需使用 SELECT 命令直接执行

select name from dbo.sysobjects where type ='P' order by name asc

我们的 C#/ASP.NET 函数

//Enumerate and load all stored procedures from the database 
private void loadStoredProcs()
{
    //Clear out the dropdownlist    
    ddlSPs.Items.Clear();
    SqlConnection cn = new SqlConnection(
      System.Configuration.ConfigurationSettings.
      AppSettings["ConnString"]);
    //We'll use a SQL command here. 
    //We use an adapter below. 
    SqlCommand cmd = new SqlCommand();
    cmd.CommandText = "select name from sysobjects" + 
                      " where type='P' order by name asc";
    cmd.CommandType = CommandType.Text;
    cmd.Connection = cn;
     try 
    {
        cn.Open();
        SqlDataReader rdr = cmd.ExecuteReader();
        while (rdr.Read())
        {
             this.ddlSPs.Items.Add(rdr["name"].ToString());
        }
    }
     catch (Exception exc)
    {
         //Send the exception to our exception label 
         this.lblException.Text = exc.ToString();
    }
     finally 
    {
        cn.Close();
    }
}

列出存储过程的参数

现在我们可以列出所有存储过程了,我们将使用以下 SQL 来获取一个表格,列出所选过程的参数的重要列。 我们可以使用 sysobjects 中的 ID 和 syscolumns 中的其余数据来获取我们所选存储过程的每个参数的所有参数和类型信息

 select s.id , s.name, t.name as [type], t.length
 from  syscolumns s
 inner join systypes t
 on s.xtype = t.xtype 
 where id = (select id from sysobjects where name = 
             'sp_TheNameOfYourStoredProcedure')

我们的 C#/ASP.NET 函数

 //Get all parameters for a specified stored procedure 
 private void bindParameters( string strName)
 {
    SqlConnection cn = new SqlConnection(
        System.Configuration.ConfigurationSettings.
        AppSettings["ConnString"]);
    //Use a string builder to hold our SQL command 
    StringBuilder sb = new StringBuilder();
    sb.Append("select s.id, s.name, t.name as [type], t.length ");
    sb.Append("from syscolumns s ");
    sb.Append("inner join systypes t ");
    sb.Append("on s.xtype = t.xtype ");
    sb.Append("where id = (select id from" + 
              " sysobjects where name='" + strName + "')");
    //Use a SqlDataAdapter to fill a datatable, 
    //using the above command 
    SqlDataAdapter adapter = new SqlDataAdapter(sb.ToString(), cn);
    DataTable dt = new DataTable();
    try 
    {
        cn.Open();
        adapter.Fill(dt);
        //Bind the resulting table to the grid 
        this.dgEnum.DataSource=dt;
        this.dgEnum.DataBind();
    }
     catch (Exception exc)
    {
         //Send the exception to our exception label 
         this.lblException.Text = exc.ToString();
    }
    finally 
    {
        //Clean up the connection
        cn.Close();
    }
}

关注点

在过去的几年里,人们对 SQL 注入攻击的担忧很多。 作为一名 Web 程序员,当您使用原始 SQL 和查询字符串时,您会让自己完全暴露于此风险中。 如果您决定使用上述 SQL 或代码,我建议将其编译成参数化存储过程,并以这种方式执行它们。 为了说明的目的,我在这里将它们保留为原始 SQL。

© . All rights reserved.