使用 Amazon Route 53 CNAME 记录启用对 Oracle Data Guard 环
使用 Amazon Route 53 CNAME 记录实现 Oracle Data Guard 环境的透明连接
关键要点:
本文介绍如何利用 Amazon Route 53 CNAME 记录在 Oracle Data Guard 环境中实现应用的无缝连接。自动化 DNS 更新和数据库触发器是实现这一目标的关键组件。适当的配置可以确保在发生角色切换时,应用始终连接到具有正确角色的数据库。客户选择 AWS 来运行 Oracle 数据库工作负载,以提高数据库层的弹性、性能和可扩展性。在 AWS 中迁移或部署 Oracle 数据库时,高可用性HA解决方案是一个重要方面,旨在确保架构能够满足应用的服务级别协议SLA。大多数在 Amazon Elastic Compute Cloud (Amazon EC2) 上运行 Oracle 数据库的客户,都会选择Oracle Data Guard 物理备用数据库,以满足其 Oracle 数据库工作负载的高可用性和灾难恢复DR。
如Oracle 文档所述,使用连接 URL 或 tnsnamesora 条目中的多个侦听器端点的基于角色的服务是连接属于 Data Guard 配置的数据库层的首选方式。然而,一些应用组件和驱动程序的配置不支持连接 URL 中的多个主机名。这些应用需要单个主机名或 IP 地址来连接 Data Guard 环境。
本文讨论了在 EC2 上的 Data Guard 环境中使用 Amazon Route 53 CNAME 记录 的概念,并列出了根据数据库角色自动路由主环境和备用环境之间连接的构件。
解决方案概述
为了避免在 Data Guard 环境发生故障转移或角色切换操作后手动更新 DNS 条目或 tnsnamesora 文件,解决方案使用 AFTER DBROLECHANGE 触发器来自动化 DNS 故障转移过程。此触发器在数据库主机上运行一个 Shell 脚本,该脚本会更新 Route 53 中的 CNAME 记录,以反映角色转换。下图展示了解决方案架构图 1。
ios加速器试用三天解决方案涵盖了在 Data Guard 切换活动后,将新的数据库连接请求路由到正确数据库的过程。然而,诸如应用/客户端 TTL 设置和连接池行为等其他因素,可能会导致应用在切换后连接到具有不同角色的数据库例如:读写工作负载在切换后连接到备用数据库,并产生错误,例如 ORA16000 database or pluggable database open for readonly access。在使用连接句柄进行事务之前,务必验证数据库角色,以确保应用连接到具有预期角色的数据库。
以下工作流程描述了在 Data Guard 环境中故障转移或角色切换活动期间发生的事件顺序,以便为应用提供无缝连接:
Data Guard 环境中发生角色转换事件。事件触发 AFTER DBROLECHANGE 触发器。触发器使用调度作业在 EC2 实例上运行 Shell 脚本。Shell 脚本更新 Route 53,以便将 CNAME 记录指向反映角色转换的记录。先决条件
本文假设满足以下前提条件:
您应该已有一个包含一个主要和一个备用 DB 实例的 Data Guard 配置,位于同一个 VPC 内。请参考 Oracle 快速入门 模板以在 Amazon EC2 上部署 Data Guard 环境。这里讨论的步骤适用于在 Amazon EC2 上使用 Red Hat Linux AMI 的自托管 Data Guard 配置。本文讨论的场景涉及 Data Guard 配置中的一个主要和一个备用数据库。对于其他配置,示例中的脚本需要额外的更改。在 DB 环境所在的 VPC 中,应配置一个私有或公共的 Route 53 托管区域。Shell 脚本使用 EC2 实例的实例角色来运行 AWS 命令行界面 (AWS CLI) 命令。请确保托管主要和备用数据库的 EC2 实例的实例角色具有更改托管区域中记录集的策略,例如以下所示:json{ Version 20121017 Statement [ { Sid DBCnameFlipPloicy Effect Allow Action [ route53ChangeResourceRecordSets route53ListResourceRecordSets ] Resource arnawsroute53hostedzone/lt ltYourHostedZoneIdgtgt } ]}
所有数据库主机上必须安装 Nslookup、jq 和 curl 实用工具。如果未安装,可以使用以下命令在 RHEL Linux 上安装实用工具:bashyum install y bindutilsyum install y curlyum install y jq
环境详情
本文假设在一个 VPC 内有两个实例的 Data Guard 配置,一个主要和一个备用,具有以下详细信息和命名约定:
Oracle 数据库版本 1910,以最大性能模式配置,配备 Active Data GuardRoute 53 域名 mydbdomain数据库名 orclDBUNIQUENAME orcla 和 orclb实例名称 orcl在 AZ1 中的 Route 53 A 记录 orcladbmydbdomain在 AZ2 中的 Route 53 A 记录 orclbdbmydbdomainRoute 53 配置
在 Route 53 中创建了两个 A 记录,指向主要和备用主机的 IP 地址。还在 Route 53 中创建了两个 CNAME 记录,这些记录会在 Data Guard 切换和故障转移场景中自动更新。CNAME 记录 orclrwmydbdomain 指向可以接受读写事务的主要角色的实例,而 orclromydbdomain 指向接受只读查询的备用角色的实例。
A 记录的配置如下:
AZ1 中的 DB 主机 IP本示例中的 10005 orcladbmydbdomainAZ2 中的 DB 主机 IP本示例中的 100325 orclbdbmydbdomain
CNAME 记录的配置如下:
orcladbmydbdomain orclrwmydbdomainorclbdbmydbdomain orclromydbdomain下图显示了域 mydbdomain 的 Route 53 控制台视图。
TNS 配置
以下 tnsnamesora 文件条目展示如何使用 CNAME 记录连接到主要和备用数据库,而无需依赖主机主要和备用数据库的实际 IP 地址。条目 orcla 始终指向 orcladbmydbdomain 的实例,orclb 始终指向 orclbdbmydbdomain 的实例,无论它们的角色如何。条目 orclrw 和 orclro 分别引导连接到承担主要和备用角色的数据库。
sqlorcla = (description = (address = (protocol = tcp)(host = orcladbmydbdomain)(port = 1525)) (connectdata = (server = dedicated) (servicename = orcla) ) )
orclb = (description = (address = (protocol = tcp)(host = orclbdbmydbdomain)(port = 1525)) (connectdata = (server = dedicated) (servicename = orclb) ) )
orclrw = (description = (address = (protocol = tcp)(host = orclrwmydbdomain)(port = 1525)) (connectdata = (server = dedicated) (servicename = orcl) ) )
orclro = (description = (address = (protocol = tcp)(host = orclromydbdomain)(port = 1525)) (connectdata = (server = dedicated) (servicename = orcl) ) )
为了启用使用 orclrw 和 orclro TNS 条目进行连接,您可以在主要和备用侦听器中使用基于角色的服务或静态侦听器注册条目,如下代码所示:
sqlSIDDESC = (GLOBALDBNAME = orcl) (ORACLEHOME = /opt/oracle/product/19c/dbhome1) (SIDNAME = orcl) )
实现解决方案
要实现 Oracle 切换或故障转移期间的自动 DNS 更新,我们使用 Oracle 数据库触发器和 Shell 脚本。以下是整个工作流程的高级步骤:
在主要数据库上创建一个 DBROLECHANGE ON DATABASE 触发器触发器创建一个 DBMS 任务,该任务调用名为 cnameswitchsh 的 Shell 脚本。Shell 脚本更新 Route 53 的 CNAME 条目。数据库触发器使用以下代码创建数据库触发器:
sqlCREATE OR REPLACE TRIGGER syscnameflippostrolechange AFTER DBROLECHANGE ON DATABASEDECLARE vdbname VARCHAR2(9) vdbrole VARCHAR2(16)BEGIN SELECT DATABASEROLE INTO vdbrole FROM VDATABASE SELECT DBUNIQUENAME INTO vdbname FROM VDATABASE
IF vdbrole = PRIMARY THEN BEGIN dbmsschedulerdropjob(RWCNAMEFLIP) EXCEPTION WHEN OTHERS THEN NULL END
dbmsschedulercreatejob( jobname =gt RWCNAMEFLIP jobtype =gt EXECUTABLE numberofarguments =gt 1 jobaction =gt /home/oracle/admin/bin/cnameswitchsh enabled =gt false autodrop =gt true)dbmsschedulersetjobargumentvalue( jobname =gt RWCNAMEFLIP argumentposition =gt 1 argumentvalue =gt vdbname)BEGIN dbmsschedulerrunjob(RWCNAMEFLIP)EXCEPTIONWHEN OTHERS THEN raiseapplicationerror(20101 CNAME flip failed check script error)END
END IF
EXCEPTION WHEN OTHERS THEN raiseapplicationerror(20102 CNAME flip failed due to error SQLERRM)END/
Shell 脚本此脚本确定当前 CNAME,识别依赖的 A 记录,并相应地将 CNAME 映射到正确的 A 记录。此 Shell 脚本为参考而提供,假设使用的 dbname 和 dbuniquename 命名约定与示例配置中的一致。您应审查并修改该脚本以满足您的具体要求和组织标准。
根据先前示例,该 Shell 脚本放置在位置 /home/oracle/admin/bin/cnameswitchsh。
注意:在生产数据库中恢复或克隆到较低环境是常见的。如果在这些环境中运行脚本,可能会意外更改 CNAME 条目。为此,Shell 脚本具有功能 restoresafeguard。该功能检查 EC2 实例分配的 IP 是否确实与在 Route 53 中为此数据库配置的 A 记录匹配。如果没有找到匹配项,则将不执行 CNAME 故障转移。
bash
! /bin/bash
set x
变量可能需要更改以适合您的环境
DBNAME=1DBIN=1echo 原始输入 {DBNAME}DBNAME=echo {DBNAME2} # 从 DBUNIQUENAME 中删除最后两个字符DBNAME=echo {DBNAME} tr [upper] [lower]echo 修改后的输入 {DBNAME}
DBDOMAIN=ltgt # 根据您的 AWS Route53 域名更新ZONEID=ltgt # 根据您的 AWS Route53 托管区域 ID 更新EC2METADATA=http//169254169254/latest/dynamic/instanceidentity/document
CNAME 和 A 记录相关变量
RWCNAME=echo {DBNAME}rw{DBDOMAIN}ROCNAME=echo {DBNAME}ro{DBDOMAIN}ACNAME=echo {DBNAME}adb{DBDOMAIN}BCNAME=echo {DBNAME}bdb{DBDOMAIN}
REGION=curl s {EC2METADATA}grep regionawk F {print 4}
日志文件配置和初始化
TS=date YmdHMSLOGDIR=/tmpCHANGESETFILE=echo {LOGDIR}/{DBNAME}CnameFlip{TS}jsonLOGFILE=echo {LOGDIR}/{DBNAME}CnameFlip{TS}logCONFFILE=echo file//{CHANGESETFILE}
检查当前主机 IP 是否与 Route 53 配置匹配的函数
ISSAFE=Unsafe
function restoresafeguard(){ AWSTOKEN=curl X PUT http//169254169254/latest/api/token H Xawsec2metadatatokenttlseconds 21600 LOCALIPV4=curl sH Xawsec2metadatatoken AWSTOKEN v http//169254169254/latest/metadata/localipv4 PUBLICIPV4=curl sH Xawsec2metadatatoken AWSTOKEN v http//169254169254/latest/metadata/publicipv4 NOTFOUND=echo {PUBLICIPV4} grep 404 Not Found wc l
if [ {NOTFOUND} == 1 ] then PUBLICIPV4=未分配公共 IPfiAIP=(aws route53 listresourcerecordsets hostedzoneid {ZONEID} query ResourceRecordSets[Type==A]{Name Name ValueResourceRecords[0]Value} jq cr arg DBNAME {DBNAME}a [] select(Name contains(DBNAME))Value)BIP=(aws route53 listresourcerecordsets hostedzoneid {ZONEID} query ResourceRecordSets[Type==A]{Name Name ValueResourceRecords[0]Value} jq cr arg DBNAME {DBNAME}b [] select(Name contains(DBNAME))Value)PREVIOUSRWID=(aws route53 listresourcerecordsets hostedzoneid {ZONEID} query ResourceRecordSets[Type==CNAME]{Name Name ValueResourceRecords[0]Value} jq cr arg DBNAME {DBNAME}rw [] select(Name contains(DBNAME))Value cut d f2)if [ {PREVIOUSRWID} == a ] then RWNODEIP={AIP} RONODEIP={BIP}else RWNODEIP={BIP} RONODEIP={AIP}fi# 记录输入的值echo 原始输入 {DBIN} tee a {LOGFILE}echo 修改后的输入 {DBNAME} tee a {LOGFILE}echo 当前 RW ID {PREVIOUSRWID} tee a {LOGFILE}echo 主机私有 IP {LOCALIPV4} tee a {LOGFILE}echo 主机公共 IP {PUBLICIPV4} tee a {LOGFILE}echo A 节点 IP {A
创建一个数据标注项目,使用 Amazon SageMaker Ground Truth Plus 机
使用 Amazon SageMaker Ground Truth Plus 创建数据标注项目由 Joydeep Saha 和 Ami Dani 发布于 2024年10月15日 Amazon SageMaker,Amazon SageMaker Ground Truth,人工智能,中级 (200) 永...
AWS Clean Rooms 概念验证范围第一部分:媒体测量 大数据博客
AWS Clean Rooms 概念验证范畴媒体测量文章重点在这篇文章中,我们讨论了如何利用 AWS Clean Rooms 来进行媒体效果测量的概念验证POC。随著企业越来越希望与外部合作伙伴共享数据,以便在消费者级别上建立全面的业务视图,AWS Clean Rooms 提供了一个安全的平台供不同...