RedGres MSSQL 到 PostgreSQL 的应用迁移 Migration Application from MSSQL to PostgreSQL Jerray.Huang
主要内容 1. 2. 3. 4. 迁移总体分析 数据迁移 - 类型与函数 语法与存储过程迁移 数据提供程序迁移
为什么要迁移 操作系统的问题 版权问题 经济问题 稳定性问题 客户要求 政府要求 硬件升级 其它
MS-SQL 与 PostgreSQL 相似度 SQL 文类似吗? 数据类型类似吗? 存储过程类似? 函数类似吗? 调用方法类似吗?
迁移总体分析 数据库迁移 数据 SQL 语法存储过程触发器函数应用 表 数据类型 Provider 应用层
主要内容 1. 2. 3. 4. 迁移总体分析 数据迁移 - 类型与函数 语法与存储过程迁移 数据提供程序迁移
数据类型区别 据统计,SQL SERVER 共有 28 种类型, 对应 Postgresql 9.0, 有 13 种类型无对应名字
数据类型区别 例 1 类型 datetime 执行成功 执行失败 PostgreSQL 不存在 datetime 类型
数据类型区别 例 2 类型 nvarchar 执行成功 执行失败 PostgreSQL 不存在 nvarchar 类型
数据类型迁移 要进行两类数据库的迁移, 目前有两种迁移的方法 手动替换 使用 sed/awk 脚本自动替换
数据类型迁移 手动替换 例 1 datetime 方法 : 将 datetime 类型修改为 PostgreSQL 支持的 timestamp 类型 修改后执行成功
数据类型迁移 手动替换 例 2 nvarchar 方法 : 将 nvarchar 类型修改为 PostgreSQL 支持的 varchar 类型 修改后执行成功 注 : 由于 PostgreSQL 不分本地文本类型及国际文本类型, 是否国际化 取决于数据库的文本编码
数据类型迁移 脚本替换 例 datetime nvarchar 方法 : 通过 sed 脚本制定规则进行类型替换 将其保存为一脚本, 在 linux 下输入命令 :sed -f < 规则替换脚本名 > < 需要替换的 TSQL 脚本 >, 即完成 TSQL 脚本的自动类型转换
函数区别 据统计,SQL SERVER 中的函数共 204 个, 有 164 个函数是无法直接使用的.
函数区别 例 1 时间日期函数 getdate() 执行成功 失败, 提示函数不存在 day() 执行成功 失败, 提示函数不存在
函数区别 例 2 字符串函数 len() 执行成功 失败, 提示函数不存在 left() 执行成功 失败, 提示函数不存在
函数迁移 目前, 能够手动修改的函数主要为非系统级函数, 主要方法为 : 通过 CREATE FUNCTION 创建 SQL Server 同名功能函数
函数迁移 例 1 时间日期函数迁移 getdate() 修改后执行成功 day() 修改后执行成功
函数迁移 例 2 字符串函数迁移 len() 修改后执行成功 left 修改后执行成功
函数迁移 例 3 reverse 函数迁移 修改前执行失败 修改后执行成功
主要内容 1. 2. 3. 4. 迁移总体分析 数据迁移 - 类型与函数 语法与存储过程迁移 数据提供程序迁移
语法迁移
语法差异 -- 常规标识符 MS- 变量名定义对比 -PG
语法差异 -- 符号 一些符号在 SQL Server 和 PostgreSQL 两边具有不同的功能, 如中括号 ([]) 数字符号 (#) MS- 中括号对比 -PG
语法差异 -- 操作符 MS- 字符串连接对比 -PG
语法差异 --SQL 语法点 12% 其它 DDL 44% 11% 子句 SQL 语法 DML 2% 30% 存储过程 14% DBCC DCL 1%
举例 :TOP 关键字 SQL Server PostgreSQL
存储过程迁移 控制流程结构 分句 执行结果 存储过程迁移
存储过程迁移 -- 分句 SQL Server 的存储过程语句之间分句可以使用分号 ( ; ), 也可以是空格 PostgreSQL 的语句之间分句必须使用分号 ( ; )
举例 : 分句 MS- 分句对比 -PG
存储过程迁移 控制流程结构 SQL Server 控制流程结构 PostgreSQL 有该控制结构 PostgreSQL 没有该控制结构 功能不同 语法不同 修改功能 修改语法 修改存储过程
MS- 控制流程结构 -PG
存储过程迁移 -- 执行结果 PostgreSQL SQL Server
SQL Server 存储过程执行结果 PostgreSQL 函数执行结果 OUT 参数 函数返回值, 三者必须相对应并且仅有一个返回值 存储过程执行状态 存储过程内
主要内容 1. 2. 3. 4. 迁移总体分析 数据迁移 - 类型与函数 语法与存储过程迁移 数据提供程序迁移
Postgresql Data Provider.NET 平台访问 PG 数据库有多种, 其中 Npgsql 最为方便.NET ASP VB C/C++ Application MS Office Any COM Client SQL Pr For PG ODBC Pr OLEDB Pr ADO OLEDB-ODBC Bridge 需要提供相应的面向 PG 的 SQL Provider, 以实现兼容 Psqlodbc Npgsql Pgoledb PGNP PG libpq
Sqlclient 与 Npgsql Data Provider.NET 平台访问 SQL Server 数据库使用 Sqlcient, 与访问 PG 数据库的 Npgsql 比较 System.Data.SqlClient SqlClientFactory SqlCommand SqlCommandBuilder SqlConnection SqlConnectionStringBuilder SqlDataAdapter SqlDataReader SqlParameter... VS Npgsql NpgsqlFactory NpgsqlCommand NpgsqlCommandBuilder NpgsqlConnection NpgsqlConnectionStringBuilder NpgsqlDataAdapter NpgsqlDataReader NpgsqlParameter...
Sqlclient 迁移 Npgsql Data Provider Sqlcliet 连接 SQL Server 应用程序 Npgsql 连接 PG 应用程序 至少经过以下几个步骤 : (1) 修改引用
Sqlclient 迁移 Npgsql Data Provider Using System.Data.SqlClient; SqlConnection conn = new SqlConnection(connStr); conn.open(); SqlCommand command = new SqlCommand("insert into dbo.table1 values(1, 1)", conn); rowsaffected = command.executenonquery(); conn.close(); (2) 修改命名空间 (3) 修改相关类 (4) 去除语法差异 using Npgsql; NpgsqlConnection conn = new NpgsqlConnection(connStr); conn.open(); NpgsqlCommand command = new NpgsqlCommand("insert into table1 values(1, 1)", conn); rowsaffected = command.executenonquery() ; conn.close();
Sqlclient 迁移 Npgsql Data Provider SqlParameter param = new SqlParameter(ParamName, SqlDbType. NVarChar, Size); (5) 修改 db 类型 NpgsqlParameter param = new NpgsqlParameter (ParamName, NpgsqlDbType. Text, Size); String ConnStr = "Data Source=192.168.10.38;User ID=sa;Password=111111;In itial Catalog=dnt36; ; (6) 修改连接字符串 String ConnStr = "Server=127.0.0.1;Port=54 32;User Id=joe;Password=secret;Da tabase=joedata; ;
直接使用 Npgsql 开发.NET 程序 至少经过以下几个步骤 : 连接 NpgsqlConnection conn = new NpgsqlConnection(connStr); conn.open(); 创建命令 NpgsqlCommand command = new NpgsqlCommand(cmdStr,conn); 处理参数 command.parameters.add(new NpgsqlParameter("column1", NpgsqlDbType.Integer); 执行命令 NpgsqlDataReader dr = command.executereader(); while(dr.read()) { for (i = 0; i < dr.fieldcount; i++) } 关闭连接 conn.close();
还有没有更简单的方案 完全支持存储过程方式 支持 TSQL 的语法 支持类型的差异 支持最少的应用程序的变化 支持 所有 一键式完成所有的所有! 请兴趣的朋友下来可以跟我交流
RedGres