当前位置: 首页 > news >正文

postgresql数据库|数据整合的好工具--Oracle-fdw的部署和使用

概述
Oracle_fdw 是一种postgresql外部表插件,可以读取到Oracle上面的数据。是一种非常方便且常见的pg与Oracle的同步数据的方法

Oracle_fdw 适用场景:

Oracle_fdw 是一个开源的 Foreign Data Wrapper (FDW),主要用于在 PostgreSQL 数据库中访问和操作 Oracle 数据库中的数据。适用场景包括但不限于:

  1. 跨数据库查询整合: 当你有一个混合数据库环境,既有 PostgreSQL 又有 Oracle 数据库,需要在 PostgreSQL 中直接查询或联合查询 Oracle 数据库中的表,无需手动数据迁移或ETL流程。

  2. 数据迁移与同步: 在迁移项目中,Oracle_fdw 可以作为一个临时解决方案,让你在迁移过程中逐步将数据迁移到 PostgreSQL,同时保持业务连续性,期间可以继续在 PostgreSQL 中查询和使用 Oracle 中的数据。

  3. 数据仓库与 BI 场景: 如果你的数据仓库基于 PostgreSQL 构建,但一部分数据源还在 Oracle 数据库中,可以使用 Oracle_fdw 把 Oracle 数据作为外部表集成到数据仓库中,便于统一进行数据分析和报表生成。

  4. 应用集成: 在企业应用集成场景下,如果有遗留系统依赖于 Oracle 数据库,而新的应用使用 PostgreSQL,Oracle_fdw 可以帮助新旧系统之间实现平滑过渡,减少直接接口对接的工作量。

  5. 异构数据库备份与冗余: Oracle_fdw 可以用于在 PostgreSQL 中建立 Oracle 数据库的实时或定期备份,提高数据冗余性和可用性。

总之,Oracle_fdw 在需要跨越 PostgreSQL 和 Oracle 数据库边界进行数据交互和操作的场景中发挥着重要作用。通过它,可以简化数据集成、查询和管理工作,同时保持数据源的独立性和灵活性。

简单来说,Oracle_fdw 就像是一个“翻译官”,专门用来帮助 PostgreSQL 数据库跟 Oracle 数据库交朋友、说“同一种语言”。在实际使用中,比如:

  • 当你的公司里,一部分数据存放在了 Oracle 数据库里,另一部分在 PostgreSQL 中,如果想在一个地方(比如 PostgreSQL)直接查询两个数据库的数据,就像查自家的东西一样方便,这时候就需要 Oracle_fdw 这个工具帮忙,它能让 PostgreSQL 理解并获取到 Oracle 数据库中的信息。

  • 或者,在升级系统时,新的软件用的是 PostgreSQL,但是老系统数据在 Oracle 里面,不需要先把所有数据都搬到新数据库,而是可以直接通过 Oracle_fdw 让新系统边工作边读取老系统的数据。

  • 再比如做数据分析时,你可以把 Oracle 里的数据当作是 PostgreSQL 数据库的一部分来处理,这样就不必每次分析前都手动搬数据,大大提高了效率。

所以,Oracle_fdw 主要就是解决不同数据库之间数据共享、查询和整合的问题,让数据库之间的交流不再困难。

案例简介:
Oracle_fdw 的编译依赖pg_config和Oracle的客户端环境

pg_config 是什么呢?其实就是postgresql的一个可执行程序,该程序提供postgresql服务的基本信息,包括各类运行库

[root@centos7 oracle_fdw-ORACLE_FDW_2_2_0]# pg_config 
BINDIR = /usr/pgsql-12/bin
DOCDIR = /usr/pgsql-12/doc
HTMLDIR = /usr/pgsql-12/doc/html
INCLUDEDIR = /usr/pgsql-12/include
PKGINCLUDEDIR = /usr/pgsql-12/include
INCLUDEDIR-SERVER = /usr/pgsql-12/include/server
LIBDIR = /usr/pgsql-12/lib
PKGLIBDIR = /usr/pgsql-12/lib
LOCALEDIR = /usr/pgsql-12/share/locale
MANDIR = /usr/pgsql-12/share/man
SHAREDIR = /usr/pgsql-12/share
SYSCONFDIR = /etc/sysconfig/pgsql
PGXS = /usr/pgsql-12/lib/pgxs/src/makefiles/pgxs.mk
CONFIGURE = '--enable-rpath' '--prefix=/usr/pgsql-12' '--includedir=/usr/pgsql-12/include' '--libdir=/usr/pgsql-12/lib' '--mandir=/usr/pgsql-12/share/man' '--datadir=/usr/pgsql-12/share' '--with-icu' '--with-llvm' '--with-perl' '--with-python' '--with-tcl' '--with-tclconfig=/usr/lib64' '--with-openssl' '--with-pam' '--with-gssapi' '--with-includes=/usr/include' '--with-libraries=/usr/lib64' '--enable-nls' '--enable-dtrace' '--with-uuid=e2fs' '--with-libxml' '--with-libxslt' '--with-ldap' '--with-selinux' '--with-systemd' '--with-system-tzdata=/usr/share/zoneinfo' '--sysconfdir=/etc/sysconfig/pgsql' '--docdir=/usr/pgsql-12/doc' '--htmldir=/usr/pgsql-12/doc/html' 'CFLAGS=-O2 -g -pipe -Wall -Wp,-D_FORTIFY_SOURCE=2 -fexceptions -fstack-protector-strong --param=ssp-buffer-size=4 -grecord-gcc-switches -m64 -mtune=generic' 'LDFLAGS=-Wl,--as-needed' 'LLVM_CONFIG=/usr/lib64/llvm5.0/bin/llvm-config' 'CLANG=/opt/rh/llvm-toolset-7/root/usr/bin/clang' 'PKG_CONFIG_PATH=:/usr/lib64/pkgconfig:/usr/share/pkgconfig' 'PYTHON=/usr/bin/python2'
CC = gcc -std=gnu99
CPPFLAGS = -D_GNU_SOURCE -I/usr/include/libxml2 -I/usr/include
CFLAGS = -Wall -Wmissing-prototypes -Wpointer-arith -Wdeclaration-after-statement -Werror=vla -Wendif-labels -Wmissing-format-attribute -Wformat-security -fno-strict-aliasing -fwrapv -fexcess-precision=standard -O2 -g -pipe -Wall -Wp,-D_FORTIFY_SOURCE=2 -fexceptions -fstack-protector-strong --param=ssp-buffer-size=4 -grecord-gcc-switches -m64 -mtune=generic
CFLAGS_SL = -fPIC
LDFLAGS = -Wl,--as-needed -L/usr/lib64/llvm5.0/lib -L/usr/lib64 -Wl,--as-needed -Wl,-rpath,'/usr/pgsql-12/lib',--enable-new-dtags
LDFLAGS_EX = 
LDFLAGS_SL = 
LIBS = -lpgcommon -lpgport -lpthread -lselinux -lxslt -lxml2 -lpam -lssl -lcrypto -lgssapi_krb5 -lz -lreadline -lrt -lcrypt -ldl -lm 
VERSION = PostgreSQL 12.4
[root@centos7 oracle_fdw-ORACLE_FDW_2_2_0]# whereis pg_config
pg_config: /usr/pgsql-12/bin/pg_config

Oracle的客户端环境指的是Oracle的客户端,接口sdk,Oracle客户端运行时需要的库 这些东西

在本例中,安装的postgresql版本是12.4版本,Oracle安装的版本是12c,而oracle-fdw安装的版本是2.2,经实验,2.2版本以上和postgresql12版本有冲突,主要是某些新功能方面的冲突

而操作系统仍然是centos7,下面将就Oracle服务器的安装部署和oracle-fdw的安装部署以及初步使用做一个介绍

Oracle服务器部署在192.168.123.13这个服务器上,以docker形式部署

postgresql服务器部署在192.168.123.17这个服务器上,以yum形式部署

Oracle客户端环境当然是在哪个postgresql服务器上使用就在哪部署了,是在192.168.123.17这个服务器上,以编译方式部署

链接:https://pan.baidu.com/s/11W_QqZNOIogigHIxp7byNQ?pwd=post 
提取码:post 
本次实践的所有文件都放在了百度网盘,有需要复现的可自由下载使用

一,

Oracle服务端的部署(在13服务器上部署)

使用docker急速搭建Oracle测试环境(完全离线)_docker-entrypoint-initdb.d-CSDN博客

这篇博客写的比较久远,有些地方和概念讲的并不是特别清楚,因此,本文再次重复一遍

1,

docker环境部署

将docker-19.03.9.tgz这个压缩包上传到服务器13上并解压,将解压的所有文件放置到/usr/local/bin 这个系统目录下:

mv  docker/* /usr/local/bin/

将docker-compose这个docker镜像编排部署工具也放置到/usr/local/bin 目录下,并赋予可执行权限:

mv docker-compose /usr/loca/bin/
chmod a+x /usr/local/bin/docker-compose

将docker加入系统服务,设置开启启动并启动docker服务。

 文件内容如下:

cat > /etc/systemd/system/docker.service<<EOF
[Unit]
Description=Docker Application Container Engine
Documentation=https://docs.docker.com
After=network-online.target firewalld.service
Wants=network-online.target[Service]
Type=notify
ExecStart=/usr/local/bin/dockerd --graph=/var/lib/docker
ExecReload=/bin/kill -s HUP $MAINPID
LimitNOFILE=infinity
LimitNPROC=infinity
LimitCORE=infinity
TimeoutStartSec=0
Delegate=yes
KillMode=process
Restart=on-failure
StartLimitBurst=3
StartLimitInterval=60s[Install]
WantedBy=multi-user.target
EOF

 创建docker的配置文件,该文件作用是国内的镜像站加速,以及docker日志控制作用:

mkdir /etc/docker

cat >/etc/docker/daemon.json<<EOF
{"registry-mirrors": ["https://b0j89uo8.mirror.aliyuncs.com"],"exec-opts":["native.cgroupdriver=systemd"],"log-driver":"json-file","log-opts": {"max-size": "100m"
},"storage-driver": "overlay2"
}
EOF

 将docker服务加入开机自启并启动docker服务,最后查看docker服务是否正常:

systemctl enable docker
systemctl start docker
systemctl status docker

输出如下:

[root@centos3 ~]# systemctl status docker
● docker.service - Docker Application Container EngineLoaded: loaded (/etc/systemd/system/docker.service; enabled; vendor preset: disabled)Active: active (running) since Fri 2024-04-05 07:34:39 CST; 1min 14s agoDocs: https://docs.docker.comMain PID: 11621 (dockerd)Tasks: 54Memory: 54.2MCGroup: /system.slice/docker.service├─11621 /usr/local/bin/dockerd --graph=/var/lib/docker├─11631 containerd --config /var/run/docker/containerd/containerd.toml --log-level info├─11779 /usr/local/bin/docker-proxy -proto tcp -host-ip 0.0.0.0 -host-port 53432 -container-ip 172.18.0.2 -container-port 1521├─11793 /usr/local/bin/docker-proxy -proto tcp -host-ip 0.0.0.0 -host-port 36888 -container-ip 172.18.0.2 -container-port 8080└─11799 containerd-shim -namespace moby -workdir /var/lib/docker/containerd/daemon/io.containerd.runtime.v1.linux/moby/0453420a43f67ede8380d091ec3b2a1c0c642034c2a216d358ce4c62c96a12c0 -address /var/run/docker/containerd/containerd.sock -containerd-binary /usr/local/bin/containerd -runtime-root /var/run/docker/runtime-...Apr 05 07:34:39 centos3 dockerd[11621]: time="2024-04-05T07:34:39.038900657+08:00" level=info msg="ccResolverWrapper: sending update to cc: {[{unix:///var/run/docker/containerd/containerd.sock 0  <nil>}] <nil>}" module=grpc
Apr 05 07:34:39 centos3 dockerd[11621]: time="2024-04-05T07:34:39.038906301+08:00" level=info msg="ClientConn switching balancer to \"pick_first\"" module=grpc
Apr 05 07:34:39 centos3 dockerd[11621]: time="2024-04-05T07:34:39.060247914+08:00" level=info msg="Loading containers: start."
Apr 05 07:34:39 centos3 dockerd[11621]: time="2024-04-05T07:34:39.144252791+08:00" level=info msg="Default bridge (docker0) is assigned with an IP address 172.17.0.0/16. Daemon option --bip can be used to set a preferred IP address"
Apr 05 07:34:39 centos3 dockerd[11621]: time="2024-04-05T07:34:39.203429342+08:00" level=info msg="shim containerd-shim started" address="/containerd-shim/moby/0453420a43f67ede8380d091ec3b2a1c0c642034c2a216d358ce4c62c96a12c0/shim.sock" debug=false pid=11799
Apr 05 07:34:39 centos3 dockerd[11621]: time="2024-04-05T07:34:39.445592599+08:00" level=info msg="Loading containers: done."
Apr 05 07:34:39 centos3 dockerd[11621]: time="2024-04-05T07:34:39.458986835+08:00" level=info msg="Docker daemon" commit=9d988398e7 graphdriver(s)=overlay2 version=19.03.9
Apr 05 07:34:39 centos3 dockerd[11621]: time="2024-04-05T07:34:39.459046661+08:00" level=info msg="Daemon has completed initialization"
Apr 05 07:34:39 centos3 dockerd[11621]: time="2024-04-05T07:34:39.472766064+08:00" level=info msg="API listen on /var/run/docker.sock"
Apr 05 07:34:39 centos3 systemd[1]: Started Docker Application Container Engine.

2,

Oracle12c服务端的部署

docker-12c-oracle.tar 这个镜像包上传到13服务器上后,直接导入,导入命令为:

docker load <docker-12c-oracle.tar

生成docker-compose使用的编排文件,命令如下:

cat >test.yaml<<EOF
version: '3'
services:oracle:restart: alwaysimage: hub.c.163.com/springwen/oracle12ccontainer_name: oraclevolumes:- /usr/local/oracle/data:/u01/app/oracle- /usr/local/oracle/source:/docker-entrypoint-initdb.denvironment:- "TZ=Asia/Shanghai"- "DBCA_TOTAL_MEMORY=16192"- "IMPORT_FROM_VOLUME=true"ports:- 53432:1521- 36888:8080logging:driver: "json-file"options:max-size: "1g"
EOF

 通过docker-compose 启动镜像,并测试连接是否正常,如果命令不带d参数,将会是前台启动,占用一个shell窗口:

docker-compose -f test.yaml up -d

 日志以如下结尾表示初始化并启动成功:

oracle    | Import finished
oracle    | 
oracle    | Database ready to use. Enjoy! ;)

那么,假如这个数据库初始化的并不满意,想要重新初始化 ,如何操作呢?

这个就比较简单了,先停止容器,然后将挂载目录删除后,在强制删除容器就可以了,命令如下:

docker-compose -f test.yaml down
rm -rf /usr/local/oracle/*
docker rm -f $(docker ps -aq)

 删除后,在执行上面的up命令就可以重新初始化了,剩下的就是在Windows使用  0 sqldeveloper.zip这个客户端连接了,该客户端使用非常简单

只需要解压就可以了,连接的配置界面是这样的:

连接名随意,自己高兴就可以了,用户名是sys,这个是超级特权用户,口令是oracle,点击保存口令,连接类型是基本的,角色是sysdba,服务器IP是13,端口是上面的yaml文件定义的

53432,选择sid,sid是xe

在Oracle数据库中,SID(System Identifier)和服务名(Service Name)都用于标识数据库实例,但它们的用途和表现形式有所不同:

  1. SID (System Identifier)

    • SID是Oracle早期版本中用于标识数据库实例的唯一标识符,它是Oracle数据库实例启动时分配的一个内部数字标识。
    • 在数据库的配置文件(如init.oraspfile)中指定。
    • 在连接字符串中,使用传统的连接方式时,可以用SID来标识要连接的数据库实例,例如jdbc:oracle:thin:@hostname:port:SID
  2. 服务名 (Service Name)

    • 自Oracle Database 9i及以后版本,服务名逐渐取代了SID作为连接数据库的标准方式。
    • 服务名不仅标识了数据库实例,还反映了数据库的逻辑服务层次,它可以与多个数据库实例相关联(如在Oracle RAC环境中)。
    • 服务名在Oracle Net服务配置文件(如tnsnames.ora或通过LDAP)中定义,可以包含数据库实例的别名,便于管理和识别。
    • 在连接字符串中,使用服务名连接数据库,例如jdbc:oracle:thin:@//hostname:port/service_name

总结来说,SID更多是数据库实例内在的标识,而服务名是面向客户端连接时更加灵活且易于管理的逻辑服务标识。在现代Oracle数据库管理中,推荐使用服务名而非SID进行连接。

查询SID,需要超级权限用户查询,例如sys用户

SELECT DISTINCT service_name FROM v$services;

查询service名称,如果有多个的话,同样需要超级权限用户:

SELECT value FROM v$parameter WHERE name = 'service_names';

那么,如果是使用服务名配置navicat的连接的话,就需要改成大写了,大小写是敏感的

这里还有一个概念是比较特殊的,那就是schema 模式,可以简单的认为一个用户就是一个模式,模式之间相互隔离,除非连接的用户是超级用户 

在Oracle数据库中,Schema是一个逻辑概念,它代表了一组相关的数据库对象的集合。这些对象可能包括但不限于:

  1. 表(Tables)
  2. 视图(Views)
  3. 序列(Sequences)
  4. 存储过程(Stored Procedures)
  5. 函数(Functions)
  6. 包(Packages)
  7. 同义词(Synonyms)
  8. 索引(Indexes)
  9. 表簇(Clusters)
  10. 数据库链接(Database Links)

每个Oracle数据库用户都有一个与其同名的默认Schema。当创建一个Oracle用户时,实际上也创建了一个Schema。用户和Schema是绑定在一起的,一个用户拥有的所有数据库对象都在其自身的Schema内。不同用户创建的对象分别存放在各自对应的Schema中,而且各个Schema是相互隔离的,一个用户如果没有授权就不能访问另一个用户的Schema中的对象。

在Oracle中,通过以下方式可以明确地引用Schema中的对象:

 

<schema_name>.<object_name>

例如,如果有一个名为HR的Schema,其中有一个名为EMPLOYEES的表,那么完整地引用这个表的语法将是:

 

HR.EMPLOYEES

这样设计的好处在于可以实现数据的逻辑隔离,方便不同用户或应用程序之间的数据管理和安全性控制。每个Schema都可以有自己的权限体系,确保数据的安全和完整性。

./sqlplus sys/oracle@'(DESCRIPTION=(ADDRESS=(PROTOCOL=TCP)(HOST=192.168.123.13)(PORT=53432))(CONNECT_DATA=(SERVER=DEDICATED)(SERVICE_NAME=xe)))' as sysdba

二、

Oracle客户端的部署(在数据库所在服务器17上部署) 

在安装Oracle的客户端之前,需要确保postgresql服务是正常的,postgresql的安装见博客:Linux|centos7-postgresql数据库|yum安装数据库和配置repmgr高可用集群以及repmgr的日常管理工作-CSDN博客

1,

上传instantclient-basic-linux.x64-19.20.0.0.0dbru.zip,instantclient-sdk-linux.x64-19.20.0.0.0dbru.zip,instantclient-sqlplus-linux.x64-19.20.0.0.0dbru.zip,oracle_fdw-ORACLE_FDW_2_2_0.zip 这四个文件到17服务器上,全部解压

创建目录/opt/oracle 将上述解压的目录移动到此目录下并改名为instantclient:

mkdir /opt/oracle
mv instantclient_19_20 /opt/oracle/

编辑环境变量文件/etc/profile ,末尾添加如下内容:

export ORACLE_HOME=/opt/oracle/instantclient
export OCI_LIB_DIR=$ORACLE_HOME
export OCI_INC_DIR=$ORACLE_HOME/sdk/include
export LD_LIBRARY_PATH=$ORACLE_HOME:$LD_LIBRARY_PATH

激活环境变量:

source /etc/profile

进入oracle_fdw-ORACLE_FDW_2_2_0.zip解压后的目录,执行编译,这里我就把命令和输出都放一起了:

[root@centos10 ~]# cd oracle_fdw-ORACLE_FDW_2_2_0
[root@centos10 oracle_fdw-ORACLE_FDW_2_2_0]# make
gcc -std=gnu99 -Wall -Wmissing-prototypes -Wpointer-arith -Wdeclaration-after-statement -Werror=vla -Wendif-labels -Wmissing-format-attribute -Wformat-security -fno-strict-aliasing -fwrapv -fexcess-precision=standard -O2 -g -pipe -Wall -Wp,-D_FORTIFY_SOURCE=2 -fexceptions -fstack-protector-strong --param=ssp-buffer-size=4 -grecord-gcc-switches -m64 -mtune=generic -fPIC -I/opt/oracle/instantclient/sdk/include -I/opt/oracle/instantclient/oci/include -I/opt/oracle/instantclient/rdbms/public -I/usr/include/oracle/19.3/client -I/usr/include/oracle/19.3/client64 -I/usr/include/oracle/18.5/client -I/usr/include/oracle/18.5/client64 -I/usr/include/oracle/18.3/client -I/usr/include/oracle/18.3/client64 -I/usr/include/oracle/12.2/client -I/usr/include/oracle/12.2/client64 -I/usr/include/oracle/12.1/client -I/usr/include/oracle/12.1/client64 -I/usr/include/oracle/11.2/client -I/usr/include/oracle/11.2/client64 -I/usr/include/oracle/11.1/client -I/usr/include/oracle/11.1/client64 -I/usr/include/oracle/10.2.0.5/client -I/usr/include/oracle/10.2.0.5/client64 -I/usr/include/oracle/10.2.0.4/client -I/usr/include/oracle/10.2.0.4/client64 -I/usr/include/oracle/10.2.0.3/client -I/usr/include/oracle/10.2.0.3/client64 -I. -I./ -I/usr/pgsql-12/include/server -I/usr/pgsql-12/include/internal  -D_GNU_SOURCE -I/usr/include/libxml2  -I/usr/include  -c -o oracle_utils.o oracle_utils.c
gcc -std=gnu99 -Wall -Wmissing-prototypes -Wpointer-arith -Wdeclaration-after-statement -Werror=vla -Wendif-labels -Wmissing-format-attribute -Wformat-security -fno-strict-aliasing -fwrapv -fexcess-precision=standard -O2 -g -pipe -Wall -Wp,-D_FORTIFY_SOURCE=2 -fexceptions -fstack-protector-strong --param=ssp-buffer-size=4 -grecord-gcc-switches -m64 -mtune=generic -fPIC -I/opt/oracle/instantclient/sdk/include -I/opt/oracle/instantclient/oci/include -I/opt/oracle/instantclient/rdbms/public -I/usr/include/oracle/19.3/client -I/usr/include/oracle/19.3/client64 -I/usr/include/oracle/18.5/client -I/usr/include/oracle/18.5/client64 -I/usr/include/oracle/18.3/client -I/usr/include/oracle/18.3/client64 -I/usr/include/oracle/12.2/client -I/usr/include/oracle/12.2/client64 -I/usr/include/oracle/12.1/client -I/usr/include/oracle/12.1/client64 -I/usr/include/oracle/11.2/client -I/usr/include/oracle/11.2/client64 -I/usr/include/oracle/11.1/client -I/usr/include/oracle/11.1/client64 -I/usr/include/oracle/10.2.0.5/client -I/usr/include/oracle/10.2.0.5/client64 -I/usr/include/oracle/10.2.0.4/client -I/usr/include/oracle/10.2.0.4/client64 -I/usr/include/oracle/10.2.0.3/client -I/usr/include/oracle/10.2.0.3/client64 -I. -I./ -I/usr/pgsql-12/include/server -I/usr/pgsql-12/include/internal  -D_GNU_SOURCE -I/usr/include/libxml2  -I/usr/include  -c -o oracle_gis.o oracle_gis.c
gcc -std=gnu99 -Wall -Wmissing-prototypes -Wpointer-arith -Wdeclaration-after-statement -Werror=vla -Wendif-labels -Wmissing-format-attribute -Wformat-security -fno-strict-aliasing -fwrapv -fexcess-precision=standard -O2 -g -pipe -Wall -Wp,-D_FORTIFY_SOURCE=2 -fexceptions -fstack-protector-strong --param=ssp-buffer-size=4 -grecord-gcc-switches -m64 -mtune=generic -fPIC -shared -o oracle_fdw.so oracle_fdw.o oracle_utils.o oracle_gis.o -L/usr/pgsql-12/lib  -Wl,--as-needed -L/usr/lib64/llvm5.0/lib  -L/usr/lib64 -Wl,--as-needed -Wl,-rpath,'/usr/pgsql-12/lib',--enable-new-dtags  -L/opt/oracle/instantclient -L/opt/oracle/instantclient/bin -L/opt/oracle/instantclient/lib -L/opt/oracle/instantclient/lib/amd64 -lclntsh -L/usr/lib/oracle/19.3/client/lib -L/usr/lib/oracle/19.3/client64/lib -L/usr/lib/oracle/18.5/client/lib -L/usr/lib/oracle/18.5/client64/lib -L/usr/lib/oracle/18.3/client/lib -L/usr/lib/oracle/18.3/client64/lib -L/usr/lib/oracle/12.2/client/lib -L/usr/lib/oracle/12.2/client64/lib -L/usr/lib/oracle/12.1/client/lib -L/usr/lib/oracle/12.1/client64/lib -L/usr/lib/oracle/11.2/client/lib -L/usr/lib/oracle/11.2/client64/lib -L/usr/lib/oracle/11.1/client/lib -L/usr/lib/oracle/11.1/client64/lib -L/usr/lib/oracle/10.2.0.5/client/lib -L/usr/lib/oracle/10.2.0.5/client64/lib -L/usr/lib/oracle/10.2.0.4/client/lib -L/usr/lib/oracle/10.2.0.4/client64/lib -L/usr/lib/oracle/10.2.0.3/client/lib -L/usr/lib/oracle/10.2.0.3/client64/lib 
/opt/rh/llvm-toolset-7/root/usr/bin/clang -Wno-ignored-attributes -fno-strict-aliasing -fwrapv -O2  -I/opt/oracle/instantclient/sdk/include -I/opt/oracle/instantclient/oci/include -I/opt/oracle/instantclient/rdbms/public -I/usr/include/oracle/19.3/client -I/usr/include/oracle/19.3/client64 -I/usr/include/oracle/18.5/client -I/usr/include/oracle/18.5/client64 -I/usr/include/oracle/18.3/client -I/usr/include/oracle/18.3/client64 -I/usr/include/oracle/12.2/client -I/usr/include/oracle/12.2/client64 -I/usr/include/oracle/12.1/client -I/usr/include/oracle/12.1/client64 -I/usr/include/oracle/11.2/client -I/usr/include/oracle/11.2/client64 -I/usr/include/oracle/11.1/client -I/usr/include/oracle/11.1/client64 -I/usr/include/oracle/10.2.0.5/client -I/usr/include/oracle/10.2.0.5/client64 -I/usr/include/oracle/10.2.0.4/client -I/usr/include/oracle/10.2.0.4/client64 -I/usr/include/oracle/10.2.0.3/client -I/usr/include/oracle/10.2.0.3/client64 -I. -I./ -I/usr/pgsql-12/include/server -I/usr/pgsql-12/include/internal  -D_GNU_SOURCE -I/usr/include/libxml2  -I/usr/include -flto=thin -emit-llvm -c -o oracle_fdw.bc oracle_fdw.c
/opt/rh/llvm-toolset-7/root/usr/bin/clang -Wno-ignored-attributes -fno-strict-aliasing -fwrapv -O2  -I/opt/oracle/instantclient/sdk/include -I/opt/oracle/instantclient/oci/include -I/opt/oracle/instantclient/rdbms/public -I/usr/include/oracle/19.3/client -I/usr/include/oracle/19.3/client64 -I/usr/include/oracle/18.5/client -I/usr/include/oracle/18.5/client64 -I/usr/include/oracle/18.3/client -I/usr/include/oracle/18.3/client64 -I/usr/include/oracle/12.2/client -I/usr/include/oracle/12.2/client64 -I/usr/include/oracle/12.1/client -I/usr/include/oracle/12.1/client64 -I/usr/include/oracle/11.2/client -I/usr/include/oracle/11.2/client64 -I/usr/include/oracle/11.1/client -I/usr/include/oracle/11.1/client64 -I/usr/include/oracle/10.2.0.5/client -I/usr/include/oracle/10.2.0.5/client64 -I/usr/include/oracle/10.2.0.4/client -I/usr/include/oracle/10.2.0.4/client64 -I/usr/include/oracle/10.2.0.3/client -I/usr/include/oracle/10.2.0.3/client64 -I. -I./ -I/usr/pgsql-12/include/server -I/usr/pgsql-12/include/internal  -D_GNU_SOURCE -I/usr/include/libxml2  -I/usr/include -flto=thin -emit-llvm -c -o oracle_utils.bc oracle_utils.c
/opt/rh/llvm-toolset-7/root/usr/bin/clang -Wno-ignored-attributes -fno-strict-aliasing -fwrapv -O2  -I/opt/oracle/instantclient/sdk/include -I/opt/oracle/instantclient/oci/include -I/opt/oracle/instantclient/rdbms/public -I/usr/include/oracle/19.3/client -I/usr/include/oracle/19.3/client64 -I/usr/include/oracle/18.5/client -I/usr/include/oracle/18.5/client64 -I/usr/include/oracle/18.3/client -I/usr/include/oracle/18.3/client64 -I/usr/include/oracle/12.2/client -I/usr/include/oracle/12.2/client64 -I/usr/include/oracle/12.1/client -I/usr/include/oracle/12.1/client64 -I/usr/include/oracle/11.2/client -I/usr/include/oracle/11.2/client64 -I/usr/include/oracle/11.1/client -I/usr/include/oracle/11.1/client64 -I/usr/include/oracle/10.2.0.5/client -I/usr/include/oracle/10.2.0.5/client64 -I/usr/include/oracle/10.2.0.4/client -I/usr/include/oracle/10.2.0.4/client64 -I/usr/include/oracle/10.2.0.3/client -I/usr/include/oracle/10.2.0.3/client64 -I. -I./ -I/usr/pgsql-12/include/server -I/usr/pgsql-12/include/internal  -D_GNU_SOURCE -I/usr/include/libxml2  -I/usr/include -flto=thin -emit-llvm -c -o oracle_gis.bc oracle_gis.c
[root@centos10 oracle_fdw-ORACLE_FDW_2_2_0]# make install
/usr/bin/mkdir -p '/usr/pgsql-12/lib'
/usr/bin/mkdir -p '/usr/pgsql-12/share/extension'
/usr/bin/mkdir -p '/usr/pgsql-12/share/extension'
/usr/bin/mkdir -p '/usr/pgsql-12/doc/extension'
/usr/bin/install -c -m 755  oracle_fdw.so '/usr/pgsql-12/lib/oracle_fdw.so'
/usr/bin/install -c -m 644 .//oracle_fdw.control '/usr/pgsql-12/share/extension/'
/usr/bin/install -c -m 644 .//oracle_fdw--1.1.sql .//oracle_fdw--1.0--1.1.sql  '/usr/pgsql-12/share/extension/'
/usr/bin/install -c -m 644 .//README.oracle_fdw '/usr/pgsql-12/doc/extension/'
/usr/bin/mkdir -p '/usr/pgsql-12/lib/bitcode/oracle_fdw'
/usr/bin/mkdir -p '/usr/pgsql-12/lib/bitcode'/oracle_fdw/
/usr/bin/install -c -m 644 oracle_fdw.bc '/usr/pgsql-12/lib/bitcode'/oracle_fdw/./
/usr/bin/install -c -m 644 oracle_utils.bc '/usr/pgsql-12/lib/bitcode'/oracle_fdw/./
/usr/bin/install -c -m 644 oracle_gis.bc '/usr/pgsql-12/lib/bitcode'/oracle_fdw/./
cd '/usr/pgsql-12/lib/bitcode' && /usr/lib64/llvm5.0/bin/llvm-lto -thinlto -thinlto-action=thinlink -o oracle_fdw.index.bc oracle_fdw/oracle_fdw.bc oracle_fdw/oracle_utils.bc oracle_fdw/oracle_gis.bc

可以看到上面配置的环境变量也在编译过程里,例如-I/opt/oracle/instantclient/sdk/include -I/opt/oracle/instantclient/oci/include 

现在使用Oracle的客户端试着主动连接一下Oracle的服务端,连接成功代表Oracle客户端没有什么问题,可以正常使用

[root@centos10 instantclien]# pwd
/opt/instantclien
[root@centos10 instantclien]# ./sqlplus sys/oracle@'(DESCRIPTION=(ADDRESS=(PROTOCOL=TCP)(HOST=192.168.123.13)(PORT=53432))(CONNECT_DATA=(SERVER=DEDICATED)(SERVICE_NAME=xe)))' as sysdbaSQL*Plus: Release 19.0.0.0.0 - Production on Sat Apr 6 05:05:18 2024
Version 19.20.0.0.0Copyright (c) 1982, 2022, Oracle.  All rights reserved.Connected to:
Oracle Database 12c Standard Edition Release 12.1.0.2.0 - 64bit ProductionSQL> 

三,

创建Oracle数据库的测试表

1,创建普通用户zsk,并赋予建表,建索引,连接数据库等权限

CREATE USER zsk  IDENTIFIED BY "123456"
DEFAULT TABLESPACE users
TEMPORARY TABLESPACE temp;
ALTER USER zsk QUOTA UNLIMITED ON USERS;-- 授予用户基本的连接权限
GRANT CREATE SESSION TO zsk;-- 如果用户需要创建表、序列等对象,还需进一步授予资源权限
GRANT CREATE TABLE TO zsk;
GRANT CREATE SEQUENCE TO zsk;-- 如果用户需要执行DML操作,如INSERT, UPDATE, DELETE等
GRANT INSERT ANY TABLE TO zsk;
GRANT UPDATE ANY TABLE TO zsk;
GRANT DELETE ANY TABLE TO zsk;
-- 若用户需要执行DDL操作,如创建索引、触发器等
GRANT CREATE ANY INDEX TO zsk;
GRANT CREATE TRIGGER TO zsk;

2,

切换为普通用户zsk后,创建相关表和索引,总共创建了5个表,分别是department,jobs,employees,test,t100

CREATE TABLE department( dept_id    INTEGER NOT NULL PRIMARY KEY, dept_name  VARCHAR(50) NOT NULL) ;
CREATE TABLE jobs( job_id         INTEGER NOT NULL PRIMARY KEY, job_title      VARCHAR(50) NOT NULL) ;
CREATE TABLE employees( emp_id    INTEGER NOT NULL PRIMARY KEY, emp_name  VARCHAR(50) NOT NULL, sex       VARCHAR(10) NOT NULL, dept_id   INTEGER NOT NULL, manager   INTEGER, hire_date DATE NOT NULL, job_id    INTEGER NOT NULL, salary    NUMERIC(8,2) NOT NULL, bonus     NUMERIC(8,2), email     VARCHAR(100) NOT NULL, CONSTRAINT ck_emp_sex CHECK (sex IN ('男', '女')), CONSTRAINT ck_emp_salary CHECK (salary > 0), CONSTRAINT uk_emp_email UNIQUE (email), CONSTRAINT fk_emp_dept FOREIGN KEY (dept_id) REFERENCES department(dept_id), CONSTRAINT fk_emp_job FOREIGN KEY (job_id) REFERENCES jobs(job_id), CONSTRAINT fk_emp_manager FOREIGN KEY (manager) REFERENCES employees(emp_id)) ;
CREATE INDEX idx_emp_name ON employees(emp_name);
CREATE INDEX idx_emp_dept ON employees(dept_id);
CREATE INDEX idx_emp_jobs ON employees(job_id);
CREATE INDEX idx_emp_manager ON employees(manager);
INSERT INTO department(dept_id, dept_name) VALUES (1, '行政管理部');
INSERT INTO department(dept_id, dept_name) VALUES (2, '人力资源部');
INSERT INTO department(dept_id, dept_name) VALUES (3, '财务部');
INSERT INTO department(dept_id, dept_name) VALUES (4, '研发部');
INSERT INTO department(dept_id, dept_name) VALUES (5, '销售部');
INSERT INTO department(dept_id, dept_name) VALUES (6, '保卫部');INSERT INTO jobs(job_id, job_title) VALUES (1, '总经理');
INSERT INTO jobs(job_id, job_title) VALUES (2, '副总经理');
INSERT INTO jobs(job_id, job_title) VALUES (3, '人力资源总监');
INSERT INTO jobs(job_id, job_title) VALUES (4, '人力资源专员');
INSERT INTO jobs(job_id, job_title) VALUES (5, '财务经理');
INSERT INTO jobs(job_id, job_title) VALUES (6, '会计');
INSERT INTO jobs(job_id, job_title) VALUES (7, '开发经理');
INSERT INTO jobs(job_id, job_title) VALUES (8, '程序员');
INSERT INTO jobs(job_id, job_title) VALUES (9, '销售经理');
INSERT INTO jobs(job_id, job_title) VALUES (10, '销售人员');INSERT INTO employees VALUES (1, '刘备', '男', 1, NULL, TO_DATE('2000-01-01', 'YYYY-MM-DD'), 1, 30000, 10000, 'liubei@shuguo.com');
INSERT INTO employees VALUES (2, '关羽', '男', 1, 1, TO_DATE('2000-01-01', 'YYYY-MM-DD'), 2, 26000, 10000, 'guanyu@shuguo.com');
INSERT INTO employees VALUES (3, '张飞', '男', 1, 1, TO_DATE('2000-01-01', 'YYYY-MM-DD'), 2, 24000, 10000, 'zhangfei@shuguo.com');
INSERT INTO employees VALUES (4, '诸葛亮', '男', 2, 1, TO_DATE('2006-03-15', 'YYYY-MM-DD'), 3, 24000, 8000, 'zhugeliang@shuguo.com');
INSERT INTO employees VALUES (5, '黄忠', '男', 2, 4, TO_DATE('2008-10-25', 'YYYY-MM-DD'), 4, 8000, NULL, 'huangzhong@shuguo.com');
INSERT INTO employees VALUES (6, '魏延', '男', 2, 4, TO_DATE('2007-04-01', 'YYYY-MM-DD'), 4, 7500, NULL, 'weiyan@shuguo.com');
INSERT INTO employees VALUES (7, '孙尚香', '女', 3, 1, TO_DATE('2002-08-08', 'YYYY-MM-DD'), 5, 12000, 5000, 'sunshangxiang@shuguo.com');
INSERT INTO employees VALUES (8, '孙丫鬟', '女', 3, 7, TO_DATE('2002-08-08', 'YYYY-MM-DD'), 6, 6000, NULL, 'sunyahuan@shuguo.com');
INSERT INTO employees VALUES (9, '赵云', '男', 4, 1, TO_DATE('2005-12-19', 'YYYY-MM-DD'), 7, 15000, 6000, 'zhaoyun@shuguo.com');
INSERT INTO employees VALUES (10, '廖化', '男', 4, 9, TO_DATE('2009-02-17', 'YYYY-MM-DD'), 8, 6500, NULL, 'liaohua@shuguo.com');
INSERT INTO employees VALUES (11, '关平', '男', 4, 9, TO_DATE('2011-07-24', 'YYYY-MM-DD'), 8, 6800, NULL, 'guanping@shuguo.com');
INSERT INTO employees VALUES (12, '赵氏', '女', 4, 9, TO_DATE('2011-11-10', 'YYYY-MM-DD'), 8, 6600, NULL, 'zhaoshi@shuguo.com');
INSERT INTO employees VALUES (13, '关兴', '男', 4, 9, TO_DATE('2011-07-30', 'YYYY-MM-DD'), 8, 7000, NULL, 'guanxing@shuguo.com');
INSERT INTO employees VALUES (14, '张苞', '男', 4, 9, TO_DATE('2012-05-31', 'YYYY-MM-DD'), 8, 6500, NULL, 'zhangbao@shuguo.com');
INSERT INTO employees VALUES (15, '赵统', '男', 4, 9, TO_DATE('2012-05-03', 'YYYY-MM-DD'), 8, 6000, NULL, 'zhaotong@shuguo.com');
INSERT INTO employees VALUES (16, '周仓', '男', 4, 9, TO_DATE('2010-02-20', 'YYYY-MM-DD'), 8, 8000, NULL, 'zhoucang@shuguo.com');
INSERT INTO employees VALUES (17, '马岱', '男', 4, 9, TO_DATE('2014-09-16', 'YYYY-MM-DD'), 8, 5800, NULL, 'madai@shuguo.com');
INSERT INTO employees VALUES (18, '法正', '男', 5, 2, TO_DATE('2017-04-09', 'YYYY-MM-DD'), 9, 10000, 5000, 'fazheng@shuguo.com');
INSERT INTO employees VALUES (19, '庞统', '男', 5, 18, TO_DATE('2017-06-06', 'YYYY-MM-DD'), 10, 4100, 2000, 'pangtong@shuguo.com');
INSERT INTO employees VALUES (20, '蒋琬', '男', 5, 18, TO_DATE('2018-01-28', 'YYYY-MM-DD'), 10, 4000, 1500, 'jiangwan@shuguo.com');
INSERT INTO employees VALUES (21, '黄权', '男', 5, 18, TO_DATE('2018-03-14', 'YYYY-MM-DD'), 10, 4200, NULL, 'huangquan@shuguo.com');
INSERT INTO employees VALUES (22, '糜竺', '男', 5, 18, TO_DATE('2018-03-27', 'YYYY-MM-DD'), 10, 4300, NULL, 'mizhu@shuguo.com');
INSERT INTO employees VALUES (23, '邓芝', '男', 5, 18, TO_DATE('2018-11-11', 'YYYY-MM-DD'), 10, 4000, NULL, 'dengzhi@shuguo.com');
INSERT INTO employees VALUES (24, '简雍', '男', 5, 18, TO_DATE('2019-05-11', 'YYYY-MM-DD'), 10, 4800, NULL, 'jianyong@shuguo.com');
INSERT INTO employees VALUES (25, '孙乾', '男', 5, 18, TO_DATE('2018-10-09', 'YYYY-MM-DD'), 10, 4700, NULL, 'sunqian@shuguo.com');
create table test as
select rownum as id,
to_char(sysdate + rownum/24/3600, 'yyyy-mm-dd hh24:mi:ss') as inc_datetime,
trunc(dbms_random.value(0, 100)) as random_id,
dbms_random.string('x', 20) random_string
from dual
connect by level <= 500000;create table t100 (id number not null,address varchar(500) not null,sales number not null);
insert into t100 select trunc(dbms_random.value(1,1000000)) as id,(dbms_random.string('a',500)) as address,trunc(dbms_random.value(1,3000000)) as sales from dual connect by level <=10000

四、

在17服务器上创建外部表

总共需要分三步,第一步是创建server,第二步是创建用户映射,第三步是创建外部表

1、创建server

CREATE SERVER oradb FOREIGN DATA WRAPPER oracle_fdw OPTIONS (dbserver '//192.168.123.13:53432/xe',read_only 'true');

-- oradb: 自定义一个 SERVER NAME

-- OPTIONS: 有3个参数--dbserver、isolation_level、nchar

-- dbserver(必需):定义连接 Oracle 数据库的连接字符串。

-- isolation_level(可选,默认为 serializable): 在 Oracle 数据库中使用的事务隔离级别,可设置的参数值 serializable、read_committed、read_only。

-- nchar(可选,默认为 off): 是否开启 Oracle 端的字符转换,这个参数的开启对性能有很大影响。

-- 这个 SERVER 可以赋权给普通用户使用

例如普通用户pguser   GRANT USAGE ON FOREIGN SERVER oradb TO pguser;

 2、创建用户映射

postgres=# create user MAPPING FOR  postgres server oradb OPTIONS (user 'zsk', password '123456');
CREATE USER MAPPING

-- postgres: PostgreSQL 中已存在的用户

-- oradb: 已创建的 SERVER NAME

-- OPTIONS: 有2个参数--user、password -- user(必需):Oracle 用户名 -- password(必需):Oracle 用户的密码

可以查看到连接密码

postgres=# \deu+
                    List of user mappings
 Server | User name |              FDW options               
--------+-----------+----------------------------------------
 oradb  | postgres  | ("user" 'zsk', password '123456')
 zsk    | postgres  | ("user" 'zsk', password '123456')
(2 rows)

🆗,这个名为zsk的server需要删除,命令为:

postgres=# drop server zsk cascade ;
NOTICE:  drop cascades to 4 other objects
DETAIL:  drop cascades to user mapping for postgres on server zsk
drop cascades to foreign table department
drop cascades to foreign table employees
drop cascades to foreign table jobs
DROP SERVER
 


 

3、创建外部表

两种方式,第一种是create命令创建,第二种是import命令创建

(1)

create命令创建

DROP FOREIGN TABLE ora_emp_list
CREATE FOREIGN TABLE ora_emp_list( empno        NUMERIC(4,0) OPTIONS (key 'true') NOT NULL, ename        VARCHAR(10), sex						VARCHAR(10) NOT NULL, dept_id       VARCHAR(10) NOT NULL, manager   VARCHAR(10), hire_date     TIMESTAMP, jobid          VARCHAR(9), sal          VARCHAR(9), bonus     VARCHAR(9), email     VARCHAR(100) NOT NULL)  
SERVER oradb OPTIONS (schema 'ZSK', table 'EMPLOYEES');

 输出如下:

需要注意:

如果数据的长度超过了实际的列长度,就会出现运行时错误。另外请注意,数据类型的行为可能不同,例如浮点数据类型和日期时间数据类型中的分数舍入。
请记住,默认情况下,Oracle 中 CHAR 和 VARCHAR2 类型的长度以字节为单位指定,而 PostgreSQL 的 CHAR、VARCHAR 和 TEXT 类型的长度以字符为单位指定。

  • 外部表的字段名不需要与 Oracle 的表保持一致,但是字段顺序需要与 Oracle 的表保持一致
  • 外部表的主键需要与 Oracle 的表保持一致
  • OPTIONS 属性里的 schema 和 table 名称必须大写,不然 PostgreSQL 端操作外部表会报 ‘ORA-00942: table or view does not exist’。
  • OPTIONS 属性里的 schema 和 table 必须用单引号
  • 必须定义 oracle_fdw 可以转换的列,对应关系如下

    image.png

查询一下,看看外部表是否正确获取到了,可以看到确实获取到了,但列名和Oracle的是不一样的,还算🆗:

 PostgreSQL 外部表是否可以只关联 Oracle 表的某几个字段呢?比如示例中的 emp_list 表有10个字段,我只想关联3个字段(emp_id,emp_name,dept_id)

DROP FOREIGN TABLE ora_emp_listCREATE FOREIGN TABLE ora_emp_list( empno        NUMERIC(4,0) OPTIONS (key 'true') NOT NULL, ename        VARCHAR(10), deptno       NUMERIC(2,0))  
SERVER oradb OPTIONS (table '(SELECT emp_id,emp_name,dept_id FROM EMPLOYEES)');

🆗,查询一下,可以正确获取到外部表

 但此时有一个问题,外部表的更改会作用到Oracle的源表,如何将外部表更改为只读表呢?

如果您想限制在PostgreSQL中对ora_emp_list外部表的写入操作,可以考虑以下方案:

  1. 权限控制: 限制对包含该外部表的数据库角色的写权限,使其只能执行查询操作,在本例中,当然是在Oracle服务器端对zsk这个映射用户的权限做限制就可以只读了

  2. 应用程序层面限制: 在应用程序代码中确保只执行读取操作,而不执行任何插入、更新或删除操作。

  3. 元数据注释: 虽然不直接影响行为,但可以在表上添加注释说明这是一个只读外部表,作为一种提醒。

2、

import方式

需要注意:

  • 这种方式不需要指定表结构,但是外部表名需要一致,也就是当前 PostgreSQL 的 SCHEMA 下不能存在同名表,否则创建失败。
  • 从 PostgreSQL 9.5 开始,支持 IMPORT FOREIGN SCHEMA 为 Oracle 模式中的所有表批量导入表定义。
  • IMPORT FOREIGN SCHEMA 将为在 ALL_TAB_COLUMNS 中找到的所有对象创建外部表。这包括表、视图和物化视图,但不包括同义词。
  • Oracle SCHEMA 名称通常为大写。由于 PostgreSQL 在处理之前将名称转换为小写,因此您必须用双引号保护 SCHEMA 名称(例如"SCOTT")。
  • LIMIT TO 导入括号内包含的表,多个表以逗号分隔,EXCEPT 导入不包含(排除)括号内的表,多个表以逗号分隔

-- 导入单表 IMPORT FOREIGN SCHEMA "SCOTT" limit to (EMP) from server oradb into public;

-- 导入多表 IMPORT FOREIGN SCHEMA "SCOTT" LIMIT TO (EMP,DEPT) from server oradb into public OPTIONS (readonly 'true', prefetch '100');

-- 排除表导入 IMPORT FOREIGN SCHEMA "SCOTT" EXCEPT (EMP,DEPT) from server oradb into public;

-- IMPORT FOREIGN SCHEMA 支持的选项:

-- case(默认:smart):控制导入期间表名和列名的大小写,参数值:

-- keep: 保留 Oracle 中的名称,通常为大写。 -- lower: 将所有表名和列名转换为小写。

-- smart: 仅转换 Oracle 中全部大写的名称。

-- collat​​ion(默认:default):用于 case 选项的 lower 和 smart 选项的排序规则

-- dblink -- readonly -- max_long -- sample_percent -- prefetch

例如,ZSK用户下的五张表都导入到postgresql数据库下的public 这个模式下:

IMPORT FOREIGN SCHEMA "ZSK" from server oradb into public;

导入单张表:

IMPORT FOREIGN SCHEMA "ZSK" limit to (employees) from server oradb into public OPTIONS (readonly 'true' );

可以看到导入比较方便,字段值转换什么的都给搞好了:

删除外部表:

drop FOREIGN TABLE employees

相关文章:

postgresql数据库|数据整合的好工具--Oracle-fdw的部署和使用

概述 Oracle_fdw 是一种postgresql外部表插件&#xff0c;可以读取到Oracle上面的数据。是一种非常方便且常见的pg与Oracle的同步数据的方法 Oracle_fdw 适用场景&#xff1a; Oracle_fdw 是一个开源的 Foreign Data Wrapper (FDW)&#xff0c;主要用于在 PostgreSQL 数据库中…...

让php开发更优雅-Laravel篇

前言 随着开发经验的增加&#xff0c;也伴随团队开发的积累&#xff0c;规范开发显得越来越重要&#xff0c;本文给大家提供一些laravel开发的进阶思路和经验&#xff0c;让大家开发更加统一规范&#xff0c;代码看起来更加优雅。 1.更多使用第三方库。团队开发的时候&#xf…...

自动化测试之httprunner框架hook函数实操

本篇介绍httprunner中hook函数的使用&#xff0c;以及通过编程能力实现建设自动化测试更全面的场景覆盖 前置&#xff1a; 互联网时代让我们更快的学习到什么是Httprunner 正文&#xff1a; 经过上文了解到这个框架怎么使用之后&#xff0c;我们开始来探讨一下我们为什么要用…...

物联网实战--入门篇之(七)嵌入式-MQTT

目录 一、MQTT简介 二、MQTT使用方法 三、MQTT驱动设计 四、代码解析 五、使用过程 六、总结 一、MQTT简介 MQTT因为其轻量、高效和稳定的特点&#xff0c;特别适合作为物联网系统的数据传输协议&#xff0c;已经成为物联网事实上的通信标准了。关于协议的具体内容看看这…...

跑模型——labelme的json文件转成yolo使用的txt文件(语义分割)

前言 将labelme多边形标注的json文件转换成yolo使用的txt文件 import os import json import numpy as np from tqdm import tqdm#实现函数 def json2txt(path_json, path_txt): # 可修改生成格式with open(path_json, r) as path_json:jsonx json.load(path_json)with open…...

一个项目仿京东商场代码

git clone http://git.itcast.cn/heimaqianduan/erabbit-uni-app-vue3-ts.git...

计算机网络——WEB服务器编程实验

实验目的 1. 处理一个 http 请求 2. 接收并解析 http 请求 3. 从服务器文件系统中获得被请求的文件 4. 创建一个包括被请求的文件的 http 响应信息 5. 直接发送该信息到客户端 具体内容 一、C 程序来实现 web 服务器功能。 二、用 HTML 语言编写两个 HTML文件&#xff0c;并…...

蓝桥杯算法题:最大比例

题目描述&#xff1a; X星球的某个大奖赛设了 M 级奖励。 每个级别的奖金是一个正整数。 并且&#xff0c;相邻的两个级别间的比例是个固定值。 也就是说&#xff1a;所有级别的奖金数构成了一个等比数列。 比如&#xff1a;16,24,36,54&#xff0c;其等比值为&#xff1a;3/2。…...

【堡垒机】堡垒机的介绍

目前&#xff0c;常用的堡垒机有收费和开源两类。 收费的有行云管家、纽盾堡垒机&#xff1b; 开源的有jumpserver&#xff1b; 这几种各有各的优缺点&#xff0c;如何选择&#xff0c;大家可以根据实际场景来判断 什么是堡垒机 堡垒机&#xff0c;即在一个特定的网络环境下&…...

通过 ffmpeg命令行 调节视频播放速度

1. 仅调整视频速率 视频调速原理&#xff1a;修改视频的pts&#xff0c;dts # 可能会丢帧 ffmpeg -i input.mkv -an -filter:v "setpts0.5*PTS" output.mkv # 可用-r参数指定输出视频FPS以防止丢帧 ffmpeg -i input.mkv -an -r 60 -filter:v "setpts2.0*PTS&q…...

SQLite数据库在Linux系统上的使用

SQLite是一个轻量级的数据库解决方案&#xff0c;它是一个嵌入式的数据库管理系统。SQLite的特点是无需独立的服务器进程&#xff0c;可以直接嵌入到使用它的应用程序中。由于其配置简单、支持跨平台、服务器零管理&#xff0c;以及不需要复杂的设置和操作&#xff0c;SQLite非…...

Spring中依赖注入的方法有几种,分别是什么?

依赖注入的目的&#xff1a; 都是为了减少对象之间的紧密耦合 1. 构造函数注入&#xff1a;通过在类的构造函数中接受依赖对象作为参数&#xff0c;Spring在创建对象时将依赖注入。 2. Setter方法注入&#xff1a;在类中提供setter方法&#xff0c;Spring通过调用这些setter方法…...

【面试精讲】MyBatis设计模式及源码分析,MyBatis设计模式实现原理

【面试精讲】MyBatis设计模式及源码分析&#xff0c;MyBatis设计模式实现原理 目录 本文导读 一、MyBatis中运用的设计模式详解 1. 工厂模式&#xff08;Factory Pattern&#xff09; 2. 单例模式&#xff08;Singleton Pattern&#xff09; 3. 建造者模式&#xff08;Bu…...

Acrel-1000DP光伏监控系统在尚雷仕(湖北)健康科技有限公司5.98MW分布式光伏10KV并网系统的应用

摘 要&#xff1a;分布式光伏发电特指在用户场地附近建设&#xff0c;运行方式多为自发自用&#xff0c;余电上网&#xff0c;部分项目采用全额上网模式。分布式光伏全额上网的优点是可以充分利用分布式光伏发电系统的发电量&#xff0c;提高分布式光伏发电系统的利用率。发展分…...

电脑远程控制esp32上的LED

1、思路整理 首先esp32需要连接上wifi 然后创建udp socket 接受udp数据 最后解析数据&#xff0c;控制LED 2、micropython代码实现 import network from socket import * from machine import Pin p2Pin(2,Pin.OUT)def do_connect(): #连接wifi wlan network.WLAN(network.…...

ARXML处理 - C#的解析代码(一)

目的 本文介绍通过AUTOSAR组织提供的xsd文件&#xff0c;自动生成对应的C#解析代码的框架。 自动生成方法&#xff1a;Microsoft SDKs\Windows\v7.0A\bin\xsd.exe 命令&#xff1a;xsd.exe AUTOSAR_4-0-3.xsd /c /l:CS /n:AUTOSAR4 AUTOSAR_4-0-3.xsd 是需要生成代码的xsd文…...

OJ 栓奶牛【C】【Python】【二分算法】

题目 算法思路 要求的距离在最近木桩与最远木桩相隔距离到零之间&#xff0c;所以是二分法 先取一个中间值&#xff0c;看按照这个中间值可以栓多少奶牛&#xff0c;再与输入奶牛数比较&#xff0c;如果大于等于&#xff0c;则增大距离&#xff0c;注意这里等于也是增大距离…...

Spring6-单元测试:JUnit

1. 概念 在进行单元测试时&#xff0c;特别是针对使用了Spring框架的应用程序&#xff0c;我们通常需要与Spring容器交互以获取被测试对象及其依赖。传统做法是在每个测试方法中手动创建Spring容器并从中获取所需的Bean。以下面的两行常见代码为例&#xff1a; ApplicationCo…...

ubuntu系统安装k8s1.28精简步骤

目录 一、规划二、环境准备2.1 配置apt仓库配置系统基本软件仓库配置k8s软件仓库安装常用软件包 2.2 修改静态ip、ntp时间同步、主机名、hosts文件、主机免密2.3 内核配置2.4 关闭防火墙、selinux、swap2.5 安装软件安装docker安装containerd安装k8s软件包 三、安装配置k8s3.1 …...

探讨Java和Go语言的缺点

文章目录 Java的缺点Go语言的缺点 通常我们都会讨论Java和GO的优点&#xff0c;如果讨论缺点往往能让人们更清楚优点的重要性&#xff0c;Java和Go的缺点或许往往就是对方优点所在 Java的缺点 冗长的代码&#xff1a;相较于一些现代编程语言&#xff0c;Java 的语法相对冗长&am…...

MATLAB实战:如何用最小二乘法搞定系统辨识(附完整代码)

MATLAB实战&#xff1a;最小二乘法在系统辨识中的工程应用指南 在工业控制、信号处理等领域&#xff0c;系统辨识是建立数学模型的关键步骤。想象一下&#xff0c;当你面对一组输入输出数据&#xff0c;却不知道背后的系统规律时&#xff0c;最小二乘法就像一把瑞士军刀&#x…...

Janus-Pro-7B案例展示:同一张设计稿→品牌调性分析→竞品风格迁移生成

Janus-Pro-7B案例展示&#xff1a;同一张设计稿→品牌调性分析→竞品风格迁移生成 Janus-Pro-7B 是一个统一的多模态理解与生成AI模型&#xff0c;能够同时处理图像理解和文生图生成任务。本文将展示如何利用这个强大的模型&#xff0c;从一张设计稿出发&#xff0c;完成品牌调…...

GTE中文-large企业落地实践:政务文本分类+事件抽取在公文处理中的应用案例

GTE中文-large企业落地实践&#xff1a;政务文本分类事件抽取在公文处理中的应用案例 1. 引言&#xff1a;当公文处理遇上AI 想象一下&#xff0c;每天有成千上万份政府公文、报告、通知在各个部门间流转。一份关于“老旧小区改造”的请示文件&#xff0c;需要被快速准确地分…...

刚学单片机的小白,聊聊我的学习目标和职业期待

大家好&#xff0c;我是一名智能科学与技术专业的大二学生&#xff0c;目前刚刚开始接触单片机&#xff0c;还是个实打实的小白。开这篇博客&#xff0c;主要是想记录自己的学习历程&#xff0c;也希望能和同样入门的同学一起交流、互相鼓励。一、自我介绍我目前大二&#xff0…...

Qwen3-ASR-1.7B在数学建模竞赛中的语音数据处理应用

Qwen3-ASR-1.7B在数学建模竞赛中的语音数据处理应用 数学建模竞赛&#xff0c;听起来是不是有点“高大上”&#xff1f;其实说白了&#xff0c;就是给你一个现实世界的问题&#xff0c;让你用数学和计算机的方法去解决。这几年&#xff0c;竞赛题目越来越贴近生活&#xff0c;…...

倒立摆背后的控制哲学:为什么LQR能稳住这根‘杆’?用日常现象解析最优控制

倒立摆背后的控制哲学&#xff1a;为什么LQR能稳住这根‘杆’&#xff1f;用日常现象解析最优控制 想象一下骑自行车时微调把手保持平衡的瞬间&#xff0c;或是用手指顶住铅笔不让它倒下的场景。这些看似简单的动作背后&#xff0c;隐藏着与火箭姿态控制、机器人行走相同的数学…...

智能家居开发实战:用RxAndroidBle3实现多设备扫描与信号过滤(附完整Demo)

智能家居BLE开发进阶&#xff1a;RxAndroidBle3多设备扫描与动态过滤实战 在智能家居场景中&#xff0c;蓝牙低功耗&#xff08;BLE&#xff09;设备的高效扫描与筛选是构建稳定物联网系统的关键技术。本文将深入探讨如何利用RxAndroidBle3框架实现多设备并发扫描、动态信号过滤…...

Qwen3-ForcedAligner-0.6B入门必看:start_time为0.00s的边界条件处理

Qwen3-ForcedAligner-0.6B入门必看&#xff1a;start_time为0.00s的边界条件处理 1. 为什么需要关注边界条件 当你使用Qwen3-ForcedAligner-0.6B进行音文对齐时&#xff0c;可能会遇到一个看似简单但很重要的问题&#xff1a;为什么有些词的开始时间是0.00秒&#xff1f;这种…...

零基础搭建知识库:5分钟部署通义千问3-Embedding-4B向量模型

零基础搭建知识库&#xff1a;5分钟部署通义千问3-Embedding-4B向量模型 1. 引言&#xff1a;为什么选择Qwen3-Embedding-4B&#xff1f; 想象一下&#xff0c;你手头有大量文档、报告或网页内容&#xff0c;想要快速建立一个能理解语义的智能知识库。传统的关键词搜索已经无…...

OpenCV图像拼接避坑指南:为什么你的特征点总是匹配失败?

OpenCV图像拼接避坑指南&#xff1a;为什么你的特征点总是匹配失败&#xff1f; 当你第一次尝试用OpenCV实现图像拼接时&#xff0c;可能会遇到一个令人沮丧的问题&#xff1a;明明按照教程一步步操作&#xff0c;特征点匹配的结果却惨不忍睹。要么匹配点对寥寥无几&#xff0c…...