Fork me on GitHub

体系结构

简介

Oralce体系结构主要可以分为三个部分,对其分别进行深入理解可以很好得帮助理解oracle软件的运行和结构

  • 内存结构
  • 进程结构
  • 物理存储结构

Oracle服务器由数据库实例和数据库文件构成

数据库 = 数据文件 + 控制文件 + 日志文件

实例 = 内存池 + 后台进程

Oracle实例就是由一些内存区和后台进程构成的一个逻辑概念。
要访问数据库,先启动实例,分配内存区,然后启动后台进程

内存结构 SGA+PGA

SGA – system global area

由所有服务进程和后台进程共享

shared pool

缓存了各用户间可共享的各种结构


数据字典,执行计划

数据块相关性高,版本转换产生bug的几率更大

SQL执行计划,硬解析和软解析

语法语句检查,软解析去shared pool调用缓存的执行计划,硬解析,分析统计信息,生成执行计划执行,得到数据,缓存到buffer cache,执行计划缓存到shared pool,发送给客户,网络问题产生的等待事件

当客户端进程,将SQL语句通过监听器发送到Oracle时, 会触发一个Server process生成,来对该客户进程服务。Server process得到SQL语句之后,对SQL语句进行Hash运算,然后根据Hash值到library cache中查找,如果存在,则直接将library cache中的缓存的执行计划拿来执行,最后将执行结果返回该客户端,这种SQL解析叫做软解析;如果不存在,则会对该SQL进行解析parse,然后执行,返回结果,这种SQL解析叫做硬解析。

硬解析的步骤:


1)对SQL语句进行语法检查,看是否有语法错误。如果存在语法错误,则退出解析过程;

2)通过数据字典(row cache),检查SQL语句中涉及的对象和列是否存在,检查SQL语句的用户是否对涉及到的对象是否有权限。

3)通过优化器创建一个最优的执行计划。这个过程会根据数据字典中的对象的统计信息,来计算多个执行计划的cost,从而得到一个最优的执行计划。这一步涉及到大量的数据运算,从而会消耗大量的CPU资源;(library cache最主要的目的就是通过软解析来减少这个步骤);

4)将该游标所产生的执行计划,SQL文本等装载进library cache中的heap中。

软解析:就是因为相同文本的SQL语句存在于library cache中,所以本次SQL语句的解析就可以去掉硬解析中的一个或多个步骤,从而节省大量的资源的耗费。

软软解析:就是不解析。

buffer cache

缓存了从磁盘上检索的数据块

灌数据 内存或者进程读数据,server process
排数据 dbwr
某个表经常使用,放在keep池中,防止冲出去

user I/O 等待事件,都是往buffer cache里灌的时候引起的,
system I/O 等待事件,都是往出排的时候

redo log buffer

缓存了写到磁盘之前的重做信息

重做信息(用于实例恢复)在写入磁盘中存储的物理重做日志文件 之前,将缓存在此处
数据,undo的改变,会产生redo日志,写进logbuffer
触发事件后 lgwr 进程写出去,生成归档日志

PGA – process global area

由每个服务进程、后台进程专有;每个进程都有一个PGA

1.Private SQL area:包含绑定信息、运行时的内存结构。每个发出sql语句的会话,都有一个private SQL area(私有SQL区)

2.Session memory:为保存会话中的变量以及其他与会话相关的信息,而分配的内存区。

pga不足的时候使用临时表空间

SGA和PGA分配

Oracle官方文档推荐:

MEMORY_TARGET=物理内存 x 80%

MEMORY_MAX_SIZE=物理内存 x 80%

对于OLTP系统: 

SGA_TARGET=(物理内存 x 80%) x 80%

SGA_MAX_SIZE=(物理内存 x 80%) x 80%

PGA_AGGREGATE_TARGET=(物理内存 x 80%) x 20%

对于DSS系统:

SGA_TARGET=(物理内存 x 80%) x 50%

SGA_MAX_SIZE=(物理内存 x 80%) x 50%

PGA_AGGREGATE_TARGET=(物理内存 x 80%) x 50%

进程结构

五个主要后台进程

SQL> select name,description from v$bgprocess where paddr<>'00';

SMON – System monitor 系统监控进程

SMON启动后会自动的用于在实例崩溃时进行数据库实例自动恢复。

清除作废的排序临时段,回收整理碎片,合并空闲空间,释放临时段,维护闪回的时间点。

在老数据库版本中,当我们大量删除表的时候,会观测到SMON进程很忙,直到把所有的碎片空间都整理完毕。

PMON – Process monitor 进程监控

PMON在后台进程执行失败后负责清理数据库缓存和闲置资源,是Oracle的自动维护机制。

  • 清除死进程
  • 重新启动部分进程(如调度进程)
  • 监听的自动注册
  • 回滚事务
  • 释放锁
  • 释放其他资源

DBWR 数据写进程

Server process连接Oracle后,通过数据库写进程(DBWn)将数据缓冲区中的“脏缓冲区”的数据块写入到存储结构(数据文件、磁盘文件)

只做一件事,将数据写到磁盘。就是将数据库的变化写入到数据文件。
该进程最多20 个,即使你有36 个CPU 也只能最多有20 个数据库写进程。
进程名称DBW0-DBW9 DBWa-DBWj

LGWR 日志写进程

主要用于记录数据库的改变和记录数据库被改变之前的原始状态,所以应当对其作多重备份,用于恢复和排错。

激活LGWR的情况:

  • 提交指令
  • 日志缓冲区超过1/3
  • 每三秒
  • 每次DBWn执行之前

CKPT 校验点进程

主要用户更新数据文件头,更新控制文件和触发DBWn数据库写进程。
Ckpt 进程会降低数据库性能,但是提高数据库崩溃时,自我恢复的性能。我们可以理解为阶段性的保存数据,一定的条件满足就触发,执行DBWn存盘操作。

物理结构

oracle数据库是个运行在操作系统上最终目的是存储和管理相关数据的软件

每一个Oracle数据库都是由三种类型的文件组成:数据文件(Data File)、日志文件(Log File)和控制文件(Control File)。数据库的文件为数据库信息提供真正的物理存储。

一. 控制文件

为二进制文件,初始化大小由CREATE DATABASE指定,可以使用RMAN备份

记录了当前数据库的结构信息,同时也包含数据文件及日志文件的信息以及相关的状态,归档信息等等

在参数文件中描述其位置,个数等等。通常采用分散放开,多路复用的原则。在mount阶段被读取,open阶段一直被使用

维护数据库一致性(数据库启动时会比较控制文件与联机日志文件中的ckpt,即起始scn号,如相等则正常启动,否则需要介质恢复)

一个控制文件只能属于一个数据库

控制文件的任意修改将写入到初始化参数中指定的所有控制文件中,读取时则仅读取第一个控制文件

控制文件只能连接一个数据库,控制文件的大小一般不要超过MB,最多为个,最少一个,互为镜像

控制文件中包含的内容

数据库的名字、ID、创建的时间戳

表空间的名字

联机日志文件、数据文件的位置、个数、名字

联机日志的Sequence号码

检查点的信息

撤销段的开始或结束

归档信息

备份信息

一、何时创建新的控制文件

a、在控制文件发生永久性的损坏且之前未对控制文件进行备份

b、需要修改控制文件中的某些内容

二、多路复用控制文件

Oracle推荐最好将控制文件分布在不同的物理磁盘上。如果由于磁盘故障导致控制文件发生损坏,与之相关联的实例应被关闭。一旦磁盘被修复,可以通过其他磁盘上的控制文件恢复损坏的控制文件。待恢复完成后实例就可以重新启动,不需要进行介质恢复。
多路复用控制文件是如何进行工作的呢?
1、数据库启动时,仅读取control_file中第一个参数文件的信息
2、数据库打开时,将会向control_file中所有的控制文件更新信息
3、在数据库操作期间,如果任意一个控制文件不可用,实例将无法操作。

三、备份与恢复控制文件

1、何时需要备份控制文件:

a、添加、删除或重命名数据文件

b、添加、删除一个表空间或修改表空间的读写状态 //在添加,删除或重命名的前后都需要进行备份吗?文档没有说明,我认为应该这样。

c、添加、删除重做日志文件或组

2、备份控制文件的方法如下:

a、以二进制文件的形式备份控制文件:alter database backup controlfile to ‘/u02/backup’;

b、以SQL语句的形式备份控制文件便于以后可以重建:alter database backup controlfile to trace;该备份的存放位置可以通过查看alert告警日志获知。

3、恢复控制文件的方法如下:

a、假设control_file参数中的一个参数文件发生损坏,但是控制文件的存放目录仍然可以访问,这时可以:关闭数据库–>cp控制文件另一副本覆盖损坏控制文件–startup

b、假设control_file参数中的一个参数文件发生发生介质损坏,这时可以:关闭数据库 –在新介质上恢复控制文件 –修改control_file参数 –startup
4、删除控制文件
关闭数据库 –> 修改control_file参数(删除对于信息) –> startup,该系列操作不会删除操作系统上的物理文件,需要手动删除。

实验:rac+asm控制文件的多路复用

SQLshow parameter control_files;

$ srvctl stop database -d CHAOS #关闭集群数据库

SQL> startup nomount; # 单节点启动到nomount状态

使用rman连接nomount状态的数据库并且备份控制文件到指定路径

$ rman target /

RMAN> restore controlfile to '+ORADATA/chaos/controlfile/current.260' from '+ORADATA/chaos/controlfile/current.260.958910433';

进入asmcmd,可以看到已经在目标路径生成备份

su - grid

$ export ORACLE_SID=+ASM

$ asmcmd

ASMCMD> cd oradata/chaos/controlfile

ASMCMD> ls

SQL> alter system set control_files='+oradata/chaos/controlfile/current.270.963936137','+oradata/chaos/controlfile/current.260.958910433' scope=spfile sid='*'; #自动生成了两个备份文件curren.260和current.270.963936137,用哪个都一样

$ srvctl start database -d CHAOS #这个时候已经完成了对rac集群所有节点控制文件的多路复用

二.数据文件

每个数据库有一个或多个物理的数据文件。逻辑数据库结构(如表、索引等)的数据物理地存储在数据库的数据文件中,数据文件通常为*.dbf格式。
数据文件包含数据库中的实际数据,是数据库操作中数据的最终存储位置
数据文件有下列特征:

1、一个数据文件仅与一个数据库联系;

2、一旦建立,数据文件只增不减;

3、一个表空间(数据库存储的逻辑单位)由一个或多个数据文件组成。

Oracle数据库在逻辑上是由多个表空间组成的,表空间在物理上包含一个或多个数据文件。而数据文件大小是块大小的整数倍;表空间中存储的对象叫段,比如数据段,索引段和回退段。段由区组成,区是磁盘分配的最小单位。段的增大是通过增加区的个数来实现的。每个区的大小是数据块大小的整数倍,区的大小可以不相同;数据块是数据库中的最小的I/O单位,同时也是内存数据缓冲区的单位,及数据文件存储空间单位。块的大小由参数DB_BLOCK_SIZE设置,其值应设置为操作系统块大小的整数倍。

最后再来说一下Oracle的用户、表空间和数据文件之间的关系:
一个用户可以使用一个或多个表空间,一个表空间也可以供多个用户使用。用户和表空间没有隶属关系,表空间是一个用来管理数据存储的逻辑概念,表空间只和数据文件存在关系,数据文件是物理的,一个表空间可以包含多个数据文件,而一个数据文件只能隶属一个表空间。

解释数据库、表空间、数据文件、表、数据的最好办法,就是想象一个装满东西的柜子,数据库其实就是柜子,柜中的抽屉是表空间,抽屉中的文件夹是数据文件,文件夹中的纸是表,写在纸上的信息就是数据

表空间:是一个或多个数据文件的逻辑集合

表空间逻辑存储对象:

–永久段:如表与索引
–临时段:如临时表数据与排序段
–回滚段:用于事物回滚或闪回内存的撤销数据

表空间分类:

系统表空间(system、sysaux),非系统表空间,一个表空间至少包含一个数据文件,一个数据文件只能属于一个表空间。

–SYSTEM :字典表空间,不能被损坏

–UNDO :dml,ddl把数据快照到此,数据提交即消失(用于恢复)

–SYSAUX :10g 高并发系统繁忙时,会造成system争用,将工具放到SYSAUX,减轻system的压力,SYSAUX不影响系统(影响性能)

–TEMP :临时数据相关的内容

–USERS :10g 用户数据从system拨离出来

逻辑结构是Oracle内部管理数据库中对象的方式
database数据库—>tablespace表空间—> segment段—>extent区间—-> block块

Schema: 用户—>创建相关对象、表、视图、序列、函数、存储过程、包等

举例描述scott用户创建对象的组织方式,scott用户创建一张emp表,数据定义于system,数据逻辑存储于user表空间: 表段: 区间: 内存块/索引段: 区间: 内存块,user表空间
物理存储于user01.dbf数据文件,采用本地管理,包含头部信息,可用,已用等位图信息,buffer cache满或者commit之后dbwr进程将数据从内存写到物理文件中

`SQL> select username,default_tablespace,temporary_tablespace from dba_users where username='SCOTT';`

SQL> select t1.name tbname,t2.name from v$tablespace t1,v$datafile t2 where t1.ts# = t2.ts#;#查看当前数据库所有表空间及其数据文件路径

SQL> select file_name,tablespace_name from dba_data_files; # 某人竟然嘲讽我,哼哼

表空间管理

创建表空间的条件

1.具有create tablespace权限,dba,sysdba,sysoper拥有改权限,可授予

2.创建的是bigfile/smallfile,超过T级应考虑bigfile

3.新建的表空间的I/O,是否会导致磁盘I/O不够用

4.oracle需要具有创建表空间时指定datafile路径的写权限

SQL> select PROPERTY_NAME,PROPERTY_VALUE from database_properties where PROPERTY_NAME like '%TBS%'; #查看表空间创建缺省状态时bigfile还是smallfile

SQL> alter database set default bigfile/smallfile tablespace; #修改创建表空间缺省为大/小文件状态

大表文件(bigfile)最大可以存放个T的容量。头文件的大小达到了G-->block,普通的头文件大小为M—->block。
好处:减少了数据文件的个数,管理方便,大的对象的存放得到了优化。减少了control文件的信息,控制文件定义了datafile的个数。
bigfile只能存在一个数据文件,所以要保证分配的的磁盘具有足够的空间。

SQL> create tablespace TBS1 datafile '+ORADATA/chaos/datafile/tbs1.dbf' size 100m;   #创建数据文件路径为 '~tbs1.dbf'的名为TBS1的表空间

SQL> create temporary tablespace TMP1 tempfile '+ORADATA/chaos/datafile/tmp1.dbf' size 10m; 创建数据文件路径为 '~tmp1.dbf'的名为TBS2的临时表空间,临时表空间文件不能设置为只读,不能重命名数据文件,日志方式总是nologing,主要用途是在数据库进行排序运算,管理索引,访问视图等操作时提供临时的运算空间,当运算完成之后系统会自动清理,因为用途不同所以才有了默认表空间和临时表空间区分,实际上数据库都是有默认临时空间的,但实际应用中很难满足需求,所以才需要自己创建临时空间。

SQL> alter database tempfile '+ORADATA/chaos/tempfile/tmp1.dbf' resize 15m; #重置大小

SQL> alter database tempfile '+ORADATA/chaos/tempfile/tmp1.dbf' autoextend on next 10m maxsize 100m;#打开自动扩展

SQL> alter tablespace tmp1 add tempfile '+ORADATA/chaos/datafile/tmp2.dbf' size 10m;   #给临时表空间增加临时文件,增加到表空间中的数据文件不能直接从表空间中删除,除非删掉整个表空间,增加数据文件将有助于均衡I/O

SQL> alter database default temporary tablespace tmp1;   #设置tmp1为默认临时表空间,如果没有指定默认临时表空间,那么将使用system表空间作为排序区

SQL> SELECT dbms_metadata.get_ddl('TABLESPACE','SYSTEM') FROM dual;  #查看创建表空间语句

SQL> CREATE UNDO TABLESPACE tablespace_name DATAFILE '+ORADATA/chaos/datafile/undotbs2.dbf' size 10m;  #创建undo表空间

SQL> ALTER SYSTEM SET UNDO_TABLESPACE=tablespace_name;   #修改默认undo表空间

SQL> alter tablespace TABLESPACE_NAME rename to TBS2; # 表空间改名

undo表空间扩容,重置表空间大小,添加数据文件,自动扩展,跟临时表空间操作没有区别

SQL> drop tablespace tbs2;  #删除表空间,注意,system,sysaux,user表空间强烈不建议删除,会崩,默认表空间和当前undo表空间无法删除

表空间的管理方式

SQL> select TABLESPACE_NAME,EXTENT_MANAGEMENT,BLOCK_SIZE,STATUS,CONTENTS,FORCE_LOGGING,BIGFILE from dba_tablespaces;

字典管理:字典管理表空间-DMT,指oracle的表空间分配和回收是通过数据库中的数据字典表来记录和管理,用于管理的两个数据字典分别是 UET$(used extents)和FET$(freeextents),其工作方式是当建立一个新的段或者表空间时,oracle通过一系列SQL语句来完成这个工作,更新
上述两个字点的信息,在繁忙系统中会造成竞争和等待(另一个DMT会带来的问题是空间碎片)

本地管理:LMT的表空间数据文件头部加入了一个位图区域,在其中记录每个extent的使用状况,当extent被使用或者被释放,oracle会更新头部的记录来反映这个变化,不产生回滚信息,因为仅仅操作数据文件头部的几个数据块,不用操作数据字典,LMT比DMT要快,尤其是数据库繁忙的时候更明显

通过使用PL/SQL 完成表空间转换

exec dbms_space_admin.tablespace_migrate_to_local('USERS');
exec dbms_space_admin.tablespace_migrate_from_local('USERS');

表空间的四种状态:

online

offline

read only

read write

一个表空间的正常状态是联机(online),有时需要将某表空间进行脱机,以进行数据库维护

如:在数据打开的状态下移动数据文件,恢复一个表空间或数据文件,执行表空间的脱机备份,在数据库正常工作情况下使数据库的某部分不可访问

SQL> alter tablespace tbs1 offline;

SQL> alter tablespace tbs1 online;

read only状态不能执行DML语句,可以使用DDL,DQL语句

SQL> alter tablespace tbs1 read only;

SQL> alter tablespace tbs1 read write;

system 必须online 必须read write

sysaux 可以offline 不能read only

undo 不能offline 不能read only

SQL> select tablespace_name,file#,v.status,v.enabled from dba_data_files d,v$datafile v where d.file_id = v.file#;  #查看表空间的状态

表空间重定位

open且archive状态,先offline,移动数据文件位置,修改控制文件该数据文件路径,online

表空间相关视图

表空间数据字典视图:DBA_TABLESPACES
表空间动态性能视图:V$TABLESPACE
数据字典视图:DBA_DATA_FILES
动态性能视图:V$DATAFILE
数据字典视图:DBA_TEMP_FILES
动态性能视图:V$TEMPFILE
被段分配的区:DBA_EXTENTS
没有被段分配的区: DBA_FREE_SPACE
系统表空间默认设置:database_properties

三.归档文件

在重做日志分成2部分,一个是在线重做日志文件,另外一个就是归档日志文件。在线重做日志大小毕竟是有限的,当都写满了的时候,就面临着2个选择,第一个就是把以前在线重做日志从头擦除开始继续写,第二种就是把以前的在线重做日志先进行备份,然后对被备份的日志擦除开始写新的在线Redo File。这种备份的在线重做日志就是归档日志。而数据库如果采用这种生成归档日志的模式的话,就是归档日志模式(ARCHIVELOG模式),反之如果不生成归档日志,就是非归档日志模式(NOARCHIVELOG模式)。

归档日志(Archive Log)是非活动的重做日志备份.通过使用归档日志,可以保留所有重做历史记录,当数据库处于ARCHIVELOG模式并进行日志切换式,后台进程ARCH会将重做日志的内容保存到归档日志中.当数据库出现介质失败时,使用数据文件备份,归档日志和重做日志可以完全恢复数据库.

实验: rac环境下修改归档模式

rac环境的归档模式切换和单实例稍有不同,主要是共享存储所产生的差异,将rac数据库切换到非集群状态下,在一个实例上实施归档模式切换即可完成rac数据库归档模式转换问题,非切归与归切非为镜像操作,这里仅描述切成归档模式的具体操作

1.主要步骤

  • 备份spfile,防止参数修改失败导致数据库无法启动
  • 修改集群参数cluster_database为false
  • 关闭集群数据库
  • 启动单实例到mount状态
  • 修改该实例为归档模式(alter database archivelog/noarchivelog)
  • 修改集群参数cluster_database为true
  • 关闭单实例,启动集群数据库

2.操作

查看归档模式

SQL> archive log list;

SQL> select instance_name,host_name,status from gv$instance;

SQL> show parameter cluster;

SQL> create pfile='/u01/app/oracle/spfileback.ora' from spfile;  #备份spfile

SQL> alter system set cluster_database=false scope=spfile sid='*';  #修改为非集群数据库,该参数为静态参数,需要使用scope=spfile

退出sql命令行在linux命令行下面执行集群和单节点的起停操作

$ srvctl stop database -d CHAOS#停集群数据库

$ srvctl start instance -d CHAOS -i CHAOS1 -o mount   #起单个实例到mount状态

SQL> select instance_name,status from v$instance;   #查看启动的单实例的数据库的状态,这个时候应该是mounted状态

SQL> alter database archivelog;   #在mount状态下设置该单实例为归档模式

SQL> alter system set cluster_database=true scope=spfile sid='*';   #修改为集群数据库

$ srvctl stop instance -d CHAOS -i CHAOS1#关闭当前操作的单实例数据库

$ srvctl start database -d CHAOS#起集群数据库

以上操作按顺序执行,已经在本机实验环境中实际操作验证,执行完最后的起集群操作之后双节点上数据库都处于open状态,并成功修改为归档模式。
双节点实验环境是这样,实际生产环境多节点操作也是同理,多节点rac修改归档模式笨办法就是挨个节点启动到mount状态并修改,好处是不影响其他节点的工作,缺点是工作量略大,并且得执行节点数*2的起停数据库操作,风险稍大。
这样修改集群状态,更改单实例归档模式,让其他节点自动同步的方式不管有多少节点都一次到位,并且只要操作一次集群的起停操作和一次单实例的起停操作,安全高效

一些归档文件的操作

SQL> alter system switch logfile; # 手工切归档

SQL> select inst_id,name,thread#,sequence#,status from gv$archived_log;   #查看归档日志

SQL> select * from v$log;#查看v$log视图里的归档文件信息

SQL> alter system set log_archive_dest = '/u01/app/oracle/arch1/' scope = spfile;  #修改归档文件路径

SQL> alter system set log_archive_duplex_dest = '/u01/app/oracle/arch2' scope = spfile;   #归档到本机且大于等于两个归档位置

SQL> alter system set log_archive_format = 'arch_%t_%s_%r.arc';  #修改归档文件命名格式

归档日志相关视图

v$archived_log  #从控制文件中获得归档的相关信息

v$archive_dest  #归档路径及状态

v$log_history   #控制文件中日志的历史信息

v$archive_processes #归档相关的后台进程信息

rac起停操作

进程正常

如图,双节点RAC进程正常,端口监听正常,可以对外提供服务

停止HAS(High Availability Services)

必须以root用户操作,每个rac节点都得执行,在执行过程中vip会不断漂移到正常节点,直到所有节点服务都被关闭,执行完成后所有节点1521端口不再监听,所有相关进程全部清除,集群无法被访问

# cd /u01/app/11.2/grid/bin

# ./crsctl stop has -f

启动HAS

root在每个rac节点执行起has的命令,可以在单一节点启动集群数据库

# crsctl start has 

$ srvctl status database -d racdb   oracle用户

可以看到所有的rac相关进程都已经启动,可以通过sqlplus本地登陆,用开发工具访问vip也正常,这是一次完整的rac起停过程