社区首页 >问答首页 >将数据从sqlite复制到SQL Server

将数据从sqlite复制到SQL Server
EN

Stack Overflow用户
提问于 2012-10-25 20:43:15
回答 2查看 5.9K关注 0票数 3

在C#中,有没有一种不用读取数据表就能将sqlite表复制到SQL Server的方法?

sqlite数据库在内存中,包含数百万行,所以除非绝对必要,否则我不想将其复制到datatable中。

谢谢KevCri

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2015-11-23 14:47:59

尽管这个问题很老,但我还是想用一些源代码来回答,以供将来参考。我也遇到了同样的问题,找到了这篇文章。我创建了这个控制台应用程序,它将完成此任务。它只适用于表,不适用于视图,而且我只在有限的数据集上进行了测试。但从理论上讲,它应该将任何SQLite数据库转换/复制到Microsoft SQL Server,并且只使用很少的内存。

代码语言:javascript
代码运行次数:0
复制
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Data.SQLite;
using System.Data.SqlClient;
using System.Data;

namespace SQLite2MSSQL
{
  class Program
  {
    private static SQLiteConnection m_sqlitecon;
    private static SqlConnection m_sqlcon;

    private static List<KeyValuePair<string, string>> getSQLiteSchema(string tablename)
    {
        using (var cmd = new SQLiteCommand("PRAGMA table_info(" + tablename + ");", m_sqlitecon))
        {
          var table = new DataTable();

          SQLiteDataAdapter adp = null;
          try
          {
            adp = new SQLiteDataAdapter(cmd);
            adp.Fill(table);
            List<KeyValuePair<string, string>> res = new List<KeyValuePair<string, string>>();
            for (int i = 0; i < table.Rows.Count; i++)
            {
              string key = table.Rows[i]["name"].ToString();
              string value = table.Rows[i]["type"].ToString();
              KeyValuePair<string, string> kvp = new KeyValuePair<string, string>(key, value);

              res.Add(kvp);
            }
            return res;
          }
          catch (Exception ex) { Console.WriteLine(ex.Message); }
        }
      return null;
    }

    private static void transfer(string tablename, List<KeyValuePair<string, string>> schema)
    {
      using (SQLiteCommand cmd = new SQLiteCommand("select * from " + tablename, m_sqlitecon))
      {
        using (SQLiteDataReader reader = cmd.ExecuteReader())
        {
          while (reader.Read())
          {
            StringBuilder sql = new StringBuilder();
            sql.Append("insert into " + tablename + " (");
            bool first = true;
            foreach (KeyValuePair<string, string> column in schema)
            {
              if (first)
                first=false;
              else
                sql.Append(",");
              sql.Append("["+column.Key+"]");
            }
            sql.Append(") Values(");
            first = true;
            foreach (KeyValuePair<string, string> column in schema)
            {
              if (first)
                first = false;
              else
                sql.Append(",");
              sql.Append("@");
              sql.Append(column.Key);
            }
            sql.Append(");");
            try
            {
              using (SqlCommand sqlcmd = new SqlCommand(sql.ToString(), m_sqlcon))
              {
                foreach (KeyValuePair<string, string> column in schema)
                {
                  sqlcmd.Parameters.AddWithValue("@" + column.Key, reader[column.Key]);
                }
                int count = sqlcmd.ExecuteNonQuery();
                if (count == 0)
                  throw new Exception("Unable to insert row!");
              }
            }
            catch (Exception Exception) {
              string message = Exception.Message;
              int idx = message.IndexOf("Violation of PRIMARY KEY");
              if (idx < 0)
                throw;
            }
          }
        }
      }
    }

    private static bool SQLTableExists(string tablename)
    {
      using (SqlCommand cmd = new SqlCommand("SELECT * FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_NAME = '" + tablename + "'", m_sqlcon))
      {
        using (SqlDataReader reader = cmd.ExecuteReader())
        {
          if (reader.HasRows)
            return true;
        }
      }
      return false;
    }


    private static string ReplaceCaseInsensitive(string str, string oldValue, string newValue)
    {
      int prevPos = 0;
      string retval = str;
      // find the first occurence of oldValue
      int pos = retval.IndexOf(oldValue, StringComparison.InvariantCultureIgnoreCase);

      while (pos > -1)
      {
        // remove oldValue from the string
        retval = retval.Remove(pos, oldValue.Length);

        // insert newValue in its place
        retval = retval.Insert(pos, newValue);

        // check if oldValue is found further down
        prevPos = pos + newValue.Length;
        pos = retval.IndexOf(oldValue, prevPos, StringComparison.InvariantCultureIgnoreCase);
      }

      return retval;
    }

    static void Main(string[] args)
    {
      // Connect to SQLite and SQL Server database
      m_sqlitecon = new SQLiteConnection("Data Source=C:\\sqlitedatabases\\mydb.sqlite;Version=3;");
      m_sqlitecon.Open();
      m_sqlcon = new SqlConnection("Data Source=localhost;Initial Catalog=mydb;User Id="+userid+";password="+password+";MultipleActiveResultSets=True");
      m_sqlcon.Open();
      string sql = "SELECT * FROM sqlite_master WHERE type='table'";
      SQLiteCommand command = new SQLiteCommand(sql, m_sqlitecon);
      SQLiteDataReader reader = command.ExecuteReader();
      List<string> tables = new List<string>();
      // Loop through all tables
      while (reader.Read())
      {
        string tablename = reader["name"].ToString();
        string sqlstr = reader["sql"].ToString();
        // Only create and import table if it does not exist
        if (!SQLTableExists(tablename))
        {
          Console.WriteLine("Creating table: " + tablename);
          // Vi retter SQLite SQL til M$ SQL Server
          sqlstr = ReplaceCaseInsensitive(sqlstr,"] BOOLEAN", "] bit");
          sqlstr = ReplaceCaseInsensitive(sqlstr,"] BLOB", "] varbinary(max)"); // Note, maks 2 GB i varbinary(max) kolonner
          sqlstr = ReplaceCaseInsensitive(sqlstr,"] VARCHAR", "] nvarchar");
          sqlstr = ReplaceCaseInsensitive(sqlstr, "] nvarchar,", "] nvarchar(max),");
          sqlstr = ReplaceCaseInsensitive(sqlstr, "] nvarchar\r", "] nvarchar(max)\r"); // Case windiows
          sqlstr = ReplaceCaseInsensitive(sqlstr, "] nvarchar\n", "] nvarchar(max)\n"); // Case linux
          sqlstr = ReplaceCaseInsensitive(sqlstr, "] INTEGER", "] int");
          sqlstr = ReplaceCaseInsensitive(sqlstr, "] TEXT", "] nvarchar(max)");
          SqlCommand sqlcmd = new SqlCommand(sqlstr, m_sqlcon);
           sqlcmd.ExecuteNonQuery();
          sqlcmd.Dispose();
          List<KeyValuePair<string, string>> columns = getSQLiteSchema(tablename);
          // Copy all rows to MS SQL Server
          transfer(tablename, columns);
        }
        else
          Console.WriteLine("Table already exists: " + tablename);
      }
    }
  }
}
票数 2
EN

Stack Overflow用户

发布于 2013-03-20 03:53:18

存在用于SQLite的ODBC driver。如果您有权访问SSIS安装,则可以使用数据导入任务导入表。使用SQL Server导入/导出向导会更加简单。

另一种选择是为SQLite数据库创建一个ODBC DSN,然后使用OPENROWSET将数据直接从SQLite选择到SQL Server中。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/13076923

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档