从列表中调用数据

时间:2016-03-09 09:43:34

标签: c# sql visual-foxpro

我一直在编写一个从SQL Server数据库中提取数据的程序,并推送到Visual Foxpro数据库,但我遇到了麻烦。

我已经定义了与两台服务器的连接:

var exportConnection = new SqlConnection(connectionString:
    "Data Source=Localhost;"
    + "Trusted_Connection=yes;"
    + @"connection timeout=30;"
    + @"database=001-CARL_V4");

var importConnection = new OleDbConnection(connectionString:
    "Data Source=Localhost;"
    + @"connection timeout=30;"
    + @"Provider=vfpoledb.1;"
    + @"data source=C:\Users\Joshua.cameron\Desktop\PCHomesImportTestBlank\PCHomesServer\DATABASE\pchomes.dbc");

我已经测试了这两个,没有问题。

我已使用访问者从SQL服务器中提取数据:

 public string OwTitle { get; set; }
 public string OwForenames { get; set; }
 public string OwSurname { get; set; }

并将这些值分配到列表中:

ImportArray[] exportArray = null;

SqlCommand exportCommand = new SqlCommand(@"select * from dbo.CARL_Owners", exportConnection);
{
    exportConnection.Open();
    using (var exportReader = exportCommand.ExecuteReader())
    {
        Console.WriteLine("Populating Array...");
        try
        {

            var list = new List<ImportArray>();
            //while(exportReader.Read())
            var read = exportReader.Read();
            list.Add(item: new ImportArray
            {
                OwTitle = exportReader.GetValue(0).ToString(),
                OwForenames = exportReader.GetValue(1).ToString(),
                OwSurname = exportReader.GetValue(2).ToString(),                          
            });

            exportArray = list.ToArray();
            Console.WriteLine("Array populated");
           // Console.Write(list);
            Console.ReadKey();

然后我尝试从列表中提取数据并将其推送到FoxPro表

try
{
    importConnection.Open();
    Console.WriteLine("Foxpro connection open");
    OleDbCommand deleteOleDbCommand = new OleDbCommand(@"TRUNCATE TABLE CLIENT",
        importConnection);

    Console.WriteLine("writing to table");
    Console.ReadKey();
    using (
        var importCommand =
            new OleDbCommand(
                string.Format(@"INSERT INTO CLIENT (Title,Fname,Sname) VALUES ({0},{1},{2}",
                    exportReader.GetValue(0), exportReader.GetValue(1), exportReader.GetValue(2)),
                importConnection))
    {
        importCommand.ExecuteNonQuery();
        Console.ReadKey();
    }

}
catch (Exception exception)
{
    Console.Write("Foxpro Database unreachable");
    Console.WriteLine(exception.ToString());
}
finally
{
    importConnection.Close();
    Console.WriteLine("Connection closed");
    Console.ReadKey();
}

这是问题发生的地方。它几乎似乎正在跳过本节的一部分。

documentation

从输出中可以看出,它甚至不显示Console.writeline(&#34;写入表格#34;)部分。

谁能看到我出错的地方?

3 个答案:

答案 0 :(得分:1)

此问题与您的其他问题有关。 VFP没有“Truncate table”命令,您需要引用值,更好的是您需要使用参数。以下是连接两个问题的修订代码:

void Main()
{
  using (var exportConnection = new SqlConnection(connectionString:
      "Data Source=Localhost;"
      + "Trusted_Connection=yes;"
      + @"connection timeout=30;"
      + @"database=001-CARL_V4"))
  using (var importConnection = new OleDbConnection(connectionString:
      @"Provider=vfpoledb.1;" +
      @"data source=C:\Users\Joshua.cameron\Desktop\PCHomesImportTestBlank\PCHomesServer\DATABASE\pchomes.dbc"))
  using (OleDbCommand importCommand = new OleDbCommand(
      @"INSERT INTO CLIENT (Title,Fname,Sname) VALUES (?,?,?)",
      importConnection))
  using (SqlCommand exportCommand = new SqlCommand(@"select 
      title as [title], firstName as [fname], lastName as [sname] 
      from dbo.CARL_Owners", exportConnection))
  {
    importCommand.Parameters.AddWithValue("title", "");
    importCommand.Parameters.AddWithValue("fname", "");
    importCommand.Parameters.AddWithValue("sname", "");

    {
      importConnection.Open();
      Console.WriteLine("Foxpro connection open");
      new OleDbCommand(@"Delete from CLIENT", importConnection).ExecuteNonQuery();

      Console.WriteLine("writing to table");
      exportConnection.Open();

      var exportReader = exportCommand.ExecuteReader();
      while (exportReader.Read())
      {
        importCommand.Parameters["title"].Value = (string)exportReader["title"];
        importCommand.Parameters["fname"].Value = (string)exportReader["fname"];
        importCommand.Parameters["sname"].Value = (string)exportReader["sname"];
        importCommand.ExecuteNonQuery();
      }
      importConnection.Close();
      exportConnection.Close();
    }
  }
}

您还可以创建从VFP代码到SQL服务器的连接,从而使用“ExecScript”一次性完成更好的优化插入。即:

void Main()
{
  var vfpCode = @"
  local lnHandle
  lnHandle = SQLStringConnect('driver={SQL Server Native Client 11.0};'+;
      'server=.;Trusted_Connection=yes;database=001-CARL_V4')
  SQLExec( m.lnHandle, ;
   'select  title as [title], firstName as [fname], lastName as [sname] from CARL_Owners', ;
   'crsOwners')
  SQLDisconnect(0)


  * if you can use exclusive locks then:
  * zap    
  * assuming you cant

  delete from Client
  insert into Client (Title,Fname,Sname) ;
      select Title,Fname,Sname from crsOwners";


  using (var importConnection = new OleDbConnection(connectionString:
      @"Provider=vfpoledb.1;" +
      @"data source=C:\Users\Joshua.cameron\Desktop\PCHomesImportTestBlank\PCHomesServer\DATABASE\pchomes.dbc"))
  {
    OleDbCommand cmd = new OleDbCommand("ExecScript", importConnection);
    cmd.CommandType = CommandType.StoredProcedure;
    cmd.Parameters.AddWithValue("code", vfpCode);

    importConnection.Open();
    cmd.ExecuteNonQuery();
    importConnection.Close();
  }
}

PS:请注意,我假设您在MS SQL上有字段名称作为title,firstName和lastName。

答案 1 :(得分:0)

您的代码可能存在两个问题。

  1. 我认为您没有执行deleteOleDbCommand。你初始化它但你没有在任何地方执行该命令。

  2. @&#34; INSERT INTO CLIENT(Title,Fname,Sname)VALUES({0},{1},{2}&#34;。您的查询中缺少结束括号。它应该像 @&#34; INSERT INTO CLIENT(Title,Fname,Sname)VALUES({0},{1},{2})&#34;

  3. 这两个可能是您的代码可能出现的问题。

答案 2 :(得分:0)

我在这里添加另一个答案,因为你的另一个问题(不幸的是)已经关闭(我不知道他们为什么这样做)。我把解释放在两者之间作为评论。请先关闭您现有的问题。

void Main()
{
  using (var exportConnection = new SqlConnection(connectionString: "Data Source=Localhost;"
                                                                   + "Trusted_Connection=yes;"
                                                                   + @"connection timeout=30;"
                                                                   + @"database=001-CARL_V4"))

  // your importConnection was wrong
  using (var importConnection = new OleDbConnection(connectionString: @"Provider=vfpoledb.1;"
                                                               + @"data source=C:\Users\Joshua.cameron\Desktop\PCHomesImportTestBlank\PCHomesServer\DATABASE\pchomes.dbc"))

  using (SqlCommand exportCommand = new SqlCommand(@"select * from dbo.CARL_Owners", exportConnection))

  using (OleDbCommand importCommand = new OleDbCommand(@"INSERT INTO CLIENT (itle,Fname,Sname) VALUES (?,?,?)",
        importConnection))
  {
    // you shouldn't use an array in between
    // because if the data is large you would be unnecessarily
    // wasting memory. Instead fill the rows in VFP database 
    // as you read data from SQL with the reader.
    // IOW do the process streaming. Read -> insert 
    // You are doing: Read into an array -> insert from array 
    // (but erroneously attempting to read from the reader again)


    importCommand.Parameters.AddWithValue("Title", "");
    importCommand.Parameters.AddWithValue("Fname", "");
    importCommand.Parameters.AddWithValue("Sname", "");

    // Open connections to both
    exportConnection.Open();
    importConnection.Open();

    Console.WriteLine("Visual Foxpro connection open");
    new OleDbCommand(@"DELETE FROM CLIENT", importConnection).ExecuteNonQuery();

    Console.WriteLine("Writing to table");
    Console.ReadKey();


    // Initiate the reader to SQL
    var exportReader = exportCommand.ExecuteReader();

    // Start reading
    while (exportReader.Read())
    {
      // as you read rows from SQL, set the parameter values
      // I would suggest using (string)row["sourceColumn"]
      // style but reader.GetValue, reader.GetString(index)
      // would work as well - although not safe (what happens
      // if someone modifies the structure of the SQL table a bit?)

      // anyway set the values
      importCommand.Parameters["Title"].Value = exportReader.GetString(0);
      importCommand.Parameters["Fname"].Value = exportReader.GetString(1);
      importCommand.Parameters["Sname"].Value = exportReader.GetString(2);

      // insert into VFP
      importCommand.ExecuteNonQuery();
    }

    // done
    exportConnection.Close();
    importConnection.Close();
  }
}