遷移Oracle SH 示例 schema 到 PostgreSQL

接著上一篇文章:遷移Oracle HR 示例 schema 到 PostgreSQL中,本文做Oracle SH(Sales History)示例 schema的遷移,SH schema比HR schema更大更復雜,本次遷移的重點是:

  • 分區表
  • 外部數據加載

使用的是Oracle 19c的示例 schema,下載命令如下:

git clone --depth 1 --branch v19c https://github.com/oracle-samples/db-sample-schemas.git

SH schema的安裝腳本為sales_history/sh_main.sql,其主要構成按序為(以下省略.sql后綴):

  1. csh_v3:創建表
  2. lsh_v3:加載數據到表
  3. psh_v3:加載后的操作

我們也按以上順序來遷移。依次形成了以下腳本:

  • csh_v3.sql:創建表
  • lsh_v3.sql:加載數據
  • cons_v3.sql:創建約束
  • idx_v3.sql:創建索引
  • views_v3.sql:創建視圖,物化視圖
  • cmnts_v3.sql:創建注釋

csh_v3:創建表

這部分比較容易,分區的語法對應上就好,另外建立約束的部分放在數據加載后來做。

還有PG并沒有Oracle的OLTP表壓縮功能。

Oracle的分區語法豐富,普適性較強。例如范圍分區支持VALUES LESS THAN。PG只支持FOR VALUES FROM … TO。不過問題不大。

看一個sales表的示例。

Oracle語法:

CREATE TABLE sales (prod_id             NUMBER          NOT NULL,cust_id             NUMBER          NOT NULL,time_id             DATE            NOT NULL,channel_id          NUMBER          NOT NULL,promo_id            NUMBER          NOT NULL,quantity_sold       NUMBER(10,2)    NOT NULL,amount_sold         NUMBER(10,2)    NOT NULL)PARTITION BY RANGE (time_id)( partition sales_1995 VALUES LESS THAN(TO_DATE('1996-01-01 00:00:00','SYYYY-MM-DD HH24:MI:SS','NLS_CALENDAR=GREGORIAN')) COMPRESS,partition sales_1996 VALUES LESS THAN(TO_DATE('1997-01-01 00:00:00','SYYYY-MM-DD HH24:MI:SS','NLS_CALENDAR=GREGORIAN')) COMPRESS,
...

PostgreSQL的語法:

CREATE TABLE sales (prod_id             NUMERIC                 NOT NULL,cust_id             NUMERIC                 NOT NULL,time_id             DATE            NOT NULL,channel_id          NUMERIC         NOT NULL,promo_id            NUMERIC                 NOT NULL,quantity_sold       NUMERIC(10,2)   NOT NULL,amount_sold         NUMERIC(10,2)   NOT NULL)PARTITION BY RANGE (time_id);CREATE TABLE sales_1995 PARTITION OF salesFOR VALUES FROM (MINVALUE) TO ('1996-01-01');CREATE TABLE sales_1996 PARTITION OF salesFOR VALUES FROM ('1996-01-01') TO ('1997-01-01');...

lsh_v3:加載數據到表

這部分消耗時間最多,主要在數據文件的格式轉換。Oracle是用SQL Loader,PostgreSQL則用COPY。

💡 先厘清一個概念。對于DATE數據類型,PG的精度是到天,而Oracle的精度是到秒。

本部分處理的主要問題:

  • 1:Oracle示例表中用DATE定義的列,實際只需要到天就可以了,但數據文件中的值卻是1998-12-27-00-00-00,而非1998-12-27。所以我們需要去掉尾部的00-00-00
  • 2:多余的分隔符。按說3個字段只需要2個分隔符,但Oracle也支持尾部再多放一個分隔符。而PG不認,我們只需要去掉行末的分隔符即可。
  • 3:數據文件的字段比表的字段多
  • 4:建立外部表

問題1的處理較簡單,例如對于times表:

\copy times from program 'sed "s/-00-00-00//g" time_v3.dat'WITH (FORMAT csv,DELIMITER '|'
);

用元命令而非SQL命令的原因在于要使用相對路徑。

問題2的處理也是用sed,例如對于countries表:

\copy countries from program 'sed "s/|$//g" coun_v3.dat'WITH (FORMAT csv,DELIMITER '|'
);

有些表同時出現了問題1和2,例如customers表和products表:

\copy customers from program 'sed "s/-00-00-00//g;s/|$//g" cust1v3.dat'WITH (FORMAT csv,DELIMITER '|'
);

問題3的處理稍微不同,出于性能考慮,預處理生成了中間文件,而非之前的即時處理。例如對于sales表,他只有7個字段,而數據文件有9個字段。

即時處理如下,但結果1小時后也沒出來,所以放棄了:

\copy sales from program 'sed "s/-*[0-9]\+\(\.[0-9]\+\)\?|$//g"|sed "s/|-*[0-9]\+\(\.[0-9]\+\)\?|$//g" sale1v3.dat'WITH (FORMAT csv,DELIMITER '|'
);

預處理方式如下:

sampledb=> \timing
Timing is on.sampledb=> \! time sed "s/-*[0-9]\+\(\.[0-9]\+\)\?|$//g" sale1v3.dat > 1real    0m34.503s
user    0m33.504s
sys     0m0.271s
sampledb=> \! time sed "s/|-*[0-9]\+\(\.[0-9]\+\)\?|$//g" 1 > 2real    0m19.119s
user    0m18.517s
sys     0m0.226s
sampledb=> \! mv 2 sale1v3_pg.dat
sampledb=> \copy sales from sale1v3_pg.datWITH (FORMAT csv,DELIMITER '|'
);
COPY 916039
Time: 9422.693 ms (00:09.423)

可以看到,預處理用了近54秒,導入用了9秒。

問題4的例子是costs表。他其實用到了之前9個字段的數據文件。

外部表的建立用了file_fdw擴展,這是PG原生的擴展,詳見這里。

CREATE FOREIGN TABLE sales_transactions_ext
( PROD_ID               NUMERIC,CUST_ID               NUMERIC,TIME_ID               DATE,CHANNEL_ID    NUMERIC,PROMO_ID              NUMERIC,QUANTITY_SOLD   NUMERIC,AMOUNT_SOLD   NUMERIC(10,2),UNIT_COST     NUMERIC(10,2),UNIT_PRICE    NUMERIC(10,2)
) SERVER file_server
OPTIONS
(
format 'csv', filename 'sale1v3_fdw.dat', delimiter '|'
);

需要特別說明,我用的是相對路徑,因此需要把數據文件拷貝到PG服務器可訪問的目錄,如$PGDATA。不過還是建議用絕對路徑。

psh_v3:加載后的操作

我沒有psh_v3.sql,而是用idx_v3.sql,views_v3.sql和cmnts_v3.sql對應。

最后

所有的腳本都在Github上了,下一篇我們遷Customer Orders 示例 schema。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/bicheng/88328.shtml
繁體地址,請注明出處:http://hk.pswp.cn/bicheng/88328.shtml
英文地址,請注明出處:http://en.pswp.cn/bicheng/88328.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

1.1 ARMv8/ARMv9安全擴展

目錄1.1.1 ARM架構安全演進1.1.2 ARMv8安全特性異常級別(EL)安全模型關鍵安全擴展1.1.3 ARMv9安全創新機密計算架構(CCA)增強的隔離機制1.1.4 安全擴展的TF-A支持1.1.5 安全擴展配置示例1.1.1 ARM架構安全演進 ARM架構從v7到v9的安全演進路線: ARMv7:引…

更新用戶隱私協議后還是 ail api scope is not declared in the privacy agreement怎么辦??!

saveImageToPhotosAlbum:fail api scope is not declared in the privacy agreement昨天明明可以了,開了個會出來,又不行了,真要命啊啊啊啊啊啊啊啊啊啊(現在回想起來可能是因為我把發布的那個版本刪了,因為那個只是用來測試用的e…

練習:對象數組 5

定義一個長度為 3 的數組,數組存儲 1~3 名學生對象作為初始數據,學生對象的學號,姓名各不相同。學生的屬性:學號,姓名,年齡。要求 1:再次添加一個學生對象,并在添加的時候進行學號的…

Linux 中的 .bashrc 是什么?配置詳解

如果你使用過 Linux 終端,那么你很可能接觸過 .bashrc 文件。這個功能強大的腳本是個性化命令行環境并使其更高效運行的關鍵。 在本文中,我們將向你介紹這個文件是什么,在哪里可以找到它,以及如何安全地編輯它。你還將學到一些實…

JVM運行時數據區深度解析

💾 JVM運行時數據區深度解析 文章目錄💾 JVM運行時數據區深度解析🎯 引言📚 方法區📋 方法區存儲內容🔄 從永久代到元空間的演進永久代時期(JDK 8之前)元空間時期(JDK 8及…

.NET nupkg包的深度解析與安全防護指南

在.NET開發領域,nupkg包是開發者們不可或缺的工具。它不僅是代碼分發和資源共享的核心載體,還貫穿了開發、構建、部署的全流程。今天,我們將深入探討nupkg包的核心功能、打包發布流程以及安全防護措施,幫助你在.NET開發中更加得心…

Cursor 快速入門指南:從安裝到核心功能

引言 Cursor 是一款融合 AI 能力的現代代碼編輯器,旨在提升開發者的編碼效率。本文將帶您從零開始,快速掌握 Cursor 的完整使用流程 - 包括安裝配置、項目初始化以及核心 AI 功能的應用。 正文 1. 安裝與初始配置 1.1 下載與安裝 Cursor 支持跨平臺…

自然語言處理中probe探測是什么意思。

文章目錄🔹 1. 英文單詞的基本含義(動詞 & 名詞)? 作為動詞(to probe):? 作為名詞(a probe):🔹 2. 不同領域的具體含義🔹 3. 在機器學習/NL…

【記錄】Ubuntu掛載home文件夾到磁盤

問題描述 服務器裝好后,home文件夾一般存放各個用戶的文件,默認的存儲磁盤為系統磁盤,一般比較小,可能幾百G,這對于服務器來講,相當小了,所以需要對home文件夾進行重新調整。 我之前的博文 點擊進入 相關配置在重啟機器后,磁盤配置自動失效,即配置好后,home在大的磁…

【注意避坑】基于Spring AI 開發本地天氣 mcp server,通義靈碼測試MCP server連接不穩定,cherry studio連接報錯

springboot 版本: 3.5.4 cherry studio版本:1.4.7 通義靈碼版本: 2.5.13 文章目錄 問題描述:1. 通義靈碼添加mcp server ,配置測試2. cherry studio工具添加mcp server ,配置測試 項目源代碼:解…

Paimon LSM Tree Compaction 策略

壓縮怎么進行的這里的操作都是KValue,內部有row kind,標記了刪除和插入MergeTreeCompactManager 是 Paimon 中 Merge-Tree 結構壓縮任務的總調度中心。它的核心職責就是監控文件的層級狀態(Levels),并在合適的時機&…

小米路由器3C刷OpenWrt,更換系統/變磚恢復 指南

基礎篇看這里: 小米路由器3C如何安裝OpenWrt官方編譯的ROM - 嗶哩嗶哩 小米路由器 3C 刷入 Breed 和 OpenWrt - Snoopy1866 - 博客園 一、路由器注入 如果按照上面的文章, telnet、ftp一直連接失敗,那么可以嘗試看 這里: 獲取路由器root權…

Spring Boot 項目啟動時按需初始化加載數據

1、新建類,類上添加注解 Component ,該類用于在項目啟動時處理數據加載任務; 2、該類實現 ApplicationRunner 接口,并重寫 run 方法; 3、在重寫的 run 方法里處理數據加載任務; 注意: 有定時加載…

MCP快速入門—快速構建自己的服務器

引言 隨著大語言模型(LLM)技術的快速發展,如何擴展其能力邊界成為開發者關注的重點。MCP(Model Capability Protocol)作為一種協議標準,允許開發者構建自定義服務器來增強LLM的功能。 正文內容 1. MCP核心概念與技術背景 MCP服務器主要提供三種能力類…

Vue 事件總線深度解析:從實現原理到工程實踐

在 Vue 組件通信體系中,事件總線(Event Bus)是處理非父子組件通信的輕量解決方案。本文將從技術實現細節、工程化實踐、內存管理等維度展開,結合源碼級分析與典型場景,帶你全面掌握這一核心技術點。?一、事件總線的技…

CMake Qt靜態庫中配置qrc并使用

CMake Qt序言環境代碼序言 看網上這資料較少,且我理解起來有歧義,特地補充 環境 CMake:3.29.2 Qt:5.15.2 MSVC:2022 IDE:QtCreator 代碼 方式一: 在CMakeLists.txt里,add_libr…

記錄一下:成功部署k8s集群(部分)

前提條件:安裝了containerd、docker 關閉了firewalld、selinux 配置了時間同步服務 chronyd 關閉swap分區等1、在控制節點、工作節點,安裝kubelet、kubeadm、kubectlyum install -y kubelet-1.26.0 kubeadm-1.26.0 kubectl-1.26.0 …

Idea如何解決包沖突

Idea如何解決包沖突1.Error信息:JAR列表。 在掃描期間跳過不需要的JAR可以縮短啟動時間和JSP編譯時間。SLF4J: Class path contains multiple SLF4J bindings.SLF4J: Found binding in [jar:file:/E:/javapojects/stww-v4-gjtwt-seal/target/stww--v4-platform-proj…

python 協程學習筆記

目錄 python 協程 通俗理解 Python 的 asyncio 協程,最擅長的是: 批量下載文件的例子: 協程的優勢: python 協程 通俗理解 def my_coroutine():print("開始")x yield 1print("拿到了:", x)yi…

【學習筆記】蒙特卡洛仿真與matlab實現

概述 20 世紀 40 年代,由于電子計算機的出現, 借助計算機可以實現大量的隨機抽樣試驗,為利用隨機試驗方法解決實際問題提供了便捷。 非常具代表性的例子是, 美國在第二次世界大戰期間研制原子彈的“曼哈頓計劃”中,為了…