如何从C#Web服务在Access 2007文件中执行SQL查询?

问题描述 投票:1回答:2

我们希望在IIS中有一个托管的C#Web服务,我可以将其传递给它的方法SOL Query,它在存在于包含Web服务和返回数据的同一服务器中的Access 2007 DB文件上执行查询。

我们已经使用以下代码

<%@ WebService Language="C#" 
  CodeBehind="~/App_Code/Service.cs" 
  Class="Service" %>
using System;
using System.Web;
using System.Web.Services;
using System.Web.Services.Protocols;

using System.Data;
using System.Data.OleDb;
using System.IO;

public class Service : System.Web.Services.WebService
{
    [WebMethod]
    public DataSet ExecuteQuery(string sqlQuery) 
    {
        OleDbConnection conn = new OleDbConnection(
             @"Provider=Microsoft.ACE.OLEDB.12.0;Data Source=" + 
             @"C:\Folder\Database2.accdb;Persist Security Info=False;");

        OleDbDataAdapter da = new OleDbDataAdapter(sqlQuery, conn);
        DataSet ds = new DataSet();
        da.Fill(ds);            
        return ds;
    }

}

但是当我们调用此方法时,页面只显示在Load(正在进行中)但没有任何数据返回或Exception。

web-services ms-access-2007
2个回答
6
投票

我可以建议您对设计和代码结构进行一些改进吗?

1.重新评估使其成为Web服务的原因。你可以将它编译成类库程序集(.dll)并从其他项目中引用它吗?进行Web服务调用的开销或时间成本远大于对另一个库的引用。是的,您必须处理Access的配置问题。

2.重新考虑您希望在每次调用时返回DataSet的原因。这是一篇关于ADO.NET DataSet的缺点的优秀文章:www.4guysfromrolla.com/articles/050405-1.aspx

3.如果没有先评估或参数化,请不要执行任何给定的字符串。我理解创建一个能够处理所有数据库查询的层的愿望,你应该为这个想法鼓掌。如上所述,代码会产生更危险的情况,因为它不会检查任何格式错误的语句等。所以建议不要执行传递给您的任何字符串。也许这个网络服务只在你的局域网内部,也许你相信所有的电话都是诚实的,非破坏性的。我们可能会认为所有内部活动都很好,但是一旦员工变坏,你就会开启内部破坏的可能性。

当有人像你这样调用你的web服务时会发生什么:

ExecuteQuery("DELETE FROM Customers")

要么

ExecuteQuery("UPDATE Employee SET Salary = 250000 WHERE ID= 9")

要么

ExecuteQuery("SELECT Salary WHERE EmployeePosition = 'CEO'")

4.为希望图层公开的每个函数创建一个新的web方法。例如,而不是客户端调用

ExecuteQuery("SELECT ID, CustomerName FROM Customers ORDER BY CustomerName")

做这个:

public List<Customer> ListAllCustomers()

考虑创建这样的方法:

public void UpdateEmployee(Employee emp)

要么

public void UpdateEmployeeSalary(string id, double salary) 

5.将Access连接字符串放入app.config文件中。参考System.Configuration并使用ConfigurationManager。每次调用查询时加载它。这有点受到性能影响,但在更改.mdb文件的目录路径或名称时,维护工作量确实为零。

  private string GetConnectionString()
        {
           //do some more checking on whether the value exists as well, instead of just returning it!
            return ConfigurationManager.AppSettings["MyAccessDB"].ToString();
        }

0
投票

也:

using (OleDbConnection conn = new OleDbConnection(
         @"Provider=Microsoft.ACE.OLEDB.12.0;Data Source=" + 
         @"C:\Folder\Database2.accdb;Persist Security Info=False;"))
{
    using (OleDbDataAdapter da = new OleDbDataAdapter(sqlQuery, conn))
    {
        DataSet ds = new DataSet();
        da.Fill(ds);            
        return ds;
    }
}

除非你喜欢资源泄漏,否则这样做。

© www.soinside.com 2019 - 2024. All rights reserved.