提前声明:本篇文章讨论的是专用服务器模式下的session和process;不讨论共享服务器模式,因为共享服务器现在真的应用的很少了,独占才是主流。共享服务器往往都是用在资源紧张的场合 ,而且独占服务器模式有独立的PGA;而共享服务器的PGA里只有一个松散的栈区,其余结构都在SGA中。
目录
session的生成
session与processes的关系
session与processes的查看
processes的设置思路
processes的修改
开局一张图,故事慢慢讲。上面这张图是对于一个Oracle数据库而言,是第一次与process和session接触。这张图是在部署Oracle进行DBCA建库时的配置选项;Oracle对它的描述是:指定操作系统用户进程可以同时连接到数据库的最大数量,这个参数的值包括用户进程和Oracle的后台进程。这个界面是在配置processes数;同时这个配置也决定了session的大小。关于它们的详细信息,请大家耐心阅读下面的描述。
session的生成
在叙述session生成之前,大家先想象一个场景:
①我本人,需要去医院看病。
②到了医院后,因为对医院并不了解,所以先去了导医台;工作人员告诉了我医院的大概情况。
③了解完情况,我开始去挂号,申请预约医生给我看病。
④医院此时正好有处于闲暇状态的医生,于是通过叫号系统反馈给我可以过来看病了。
⑤我在收到通知后,赶往指定科室和医生碰面,开始看病。
上面这个例子是我结合我的工作环境编的,细节上大家不必纠结。在流程上,我本人就相当于“用户进程”,医生就相当于“server process”;我和医生碰面就相当于产生了“会话” 。在我和医生见面之前发生了很多步骤,那么Oracle在产生会话前也发生了很多的步骤。这些步骤可以总结如下:
①客户端产生一个用户进程(user process),开始向Oracle服务端发出连接请求。
②用户进程在监听上的实例注册区找到目标Oracle数据库的实例信息。
③获取到实例信息后,向Oracle申请server process进程。
④Oracle生成server process进程,且将准许连接信息通过实例注册区反馈给用户进程。
⑤用户进程收到准许连接信息后找到server process,生成会话(session)。
以上是会话生成的全过程,从这个过程中是可以提取出几个关键的要点:
- Oracle生成server process
Oracle收到请求后,生成server process;那是在哪里生成的呢?【在内存区域PGA中的UGA中生成】UGA,user global area:用户全局会话区。
- Oracle通过监听连接到Oracle
用户进程通过监听,获取到实例信息后,向Oracle正式发出server process请求。那么如果监听崩溃了,会话是否会受到影响呢?【新的会话无法产生,已经产生的会话不会受到影响】
- Oracle生成server process
Oracle产生server process的数量是有上限的,还记得我们开局的那张图吗?上面就配置了process的最大值,而且Oracle的后台进程还占用了一部分的process。所以当process总量达到Oracle配置的上限时,就不能再生成process了。此时Oracle就会报错 “ORA-00020: maximum number of processes (2048) exceeded”。
session与processes的关系
再强调一遍;在独占(专用)服务器和共享服务器两种模式中,session和processes的关系是不一样的。本篇只会针对独占服务器模式进行叙述。
关于共享和独占模式我也在另一篇文章里简单介绍过了,有需要的同学可以去看下:
文章链接:Oracle体系结构:网络管理-CSDN博客
数量关系
数量关系其实很好理解,这篇文章的第一张DBCA建库配置图大家还记得吧,上面只配置了processes的最大数量,没有配置session的值。因为session的最大值不需要配置,记住哦,是压根不需要我们动手去配置,它会根据processes的最大值去自动设置。而且它们之间的数量比例关系在各个版本中的算法都略有差异,我在这里总结了一下。
10g
session = 1.1 * processes + 5
11g
session = 1.1 * processes + 22
12c,19c
session = 1.5 * processes + 22
我负责的其中一个项目用的是11g,但现在夜深人静,没有了远程方式....;所以只能给各位同学看下我自己本地的12C、19C的session和processes的值。
12C
同学们可以看到这是12C版本,processes值是300(和DBCA建库配置中的一样哦),session的值是472 = 1.5 * 300 + 22;符合我们上面的公式。
[oracle@oracle12ctwo ~]$ sqlplus / as sysdba
SQL*Plus: Release 12.2.0.1.0 Production on Mon Apr 8 22:03:29 2024
Copyright (c) 1982, 2016, Oracle. All rights reserved.
Connected to an idle instance.
SQL> startup
ORACLE instance started.
Total System Global Area 838860800 bytes
Fixed Size 8626240 bytes
Variable Size 322965440 bytes
Database Buffers 499122176 bytes
Redo Buffers 8146944 bytes
Database mounted.
Database opened.
SQL> SELECT value FROM v$parameter WHERE name = 'processes';
VALUE
--------------------------------------------------------------------------------
300
SQL> SELECT value FROM v$parameter WHERE name = 'sessions';
VALUE
--------------------------------------------------------------------------------
472
19C
同学们可以看到这是19C版本,processes值是300,session的值是472 = 1.5 * 300 + 22;也符合我们上面的公式。
[oracle@oracle19c ~]$ sqlplus / as sysdba
SQL*Plus: Release 19.0.0.0.0 - Production on Tue Apr 9 22:32:10 2024
Version 19.3.0.0.0
Copyright (c) 1982, 2019, Oracle. All rights reserved.
Connected to an idle instance.
SQL> startup
ORACLE instance started.
Total System Global Area 838858176 bytes
Fixed Size 8902080 bytes
Variable Size 373293056 bytes
Database Buffers 448790528 bytes
Redo Buffers 7872512 bytes
Database mounted.
Database opened.
SQL> SELECT value FROM v$parameter WHERE name = 'processes';
VALUE
--------------------------------------------------------------------------------
300
SQL> SELECT value FROM v$parameter WHERE name = 'sessions';
VALUE
--------------------------------------------------------------------------------
472
对应关系
在本篇【session的生成】章节中,已经叙述了在独占模式下,user process 找到对应 server process 产生会话。那么在数据库层面,此时对于已经建立的session,一个session对应一个process。
说到这里,不晓得大家有咩有疑问?不应该是一个session对应两个process吗?user process 和 server process。那么又回到开局那张DBCA建库配置图了,图中英文描述的意思是“指定操作系统用户进程可以同时连接到数据库的最大数量,这个参数的值包括用户进程和Oracle的后台进程”。这句话讲的很清楚,processes 限制的是同时连接到Oracle的user process数量。
session与processes的查看
上文已经叙述了session和process的关系。对于数据库运维来讲,我们咋可能记得住建库的时候设置的processes最大值是多少。那么我们可以通过查询下面的SQL来查看。
- 查看当前数据库process最大值
select value from v$parameter where name = 'processes';
- 查看当前数据库session最大值
SELECT value FROM v$parameter WHERE name = 'sessions';
- 查看当前已使用进程数
select count(*) from v$process;
- 查看当前已使用会话数
select count(*) from v$session;
- 查看process、session历史最大值
SELECT
resource_name,
max_utilization,--自上次启动以来,达到的最大值
limit_value --最大限制
FROM v$resource_limit
WHERE resource_name IN ('processes','sessions');
- 查看当前连接最多的主机是哪些
SELECT machine,COUNT(*) FROM v$session GROUP BY machine ORDER BY 2 DESC;
其实上面写来写去都是对 v$session、v$process、v$resource三个动态性能视图的查询;可写的花样太多了,大家想要再进一步深入研究就必须得对这三张视图特别熟悉。
另外:
除了对session和process进行监控之外,以上视图还可以联合v$sql等视图将查询效率低下的SQL是在哪台机器上运行的给揪出来、或者可以将哪台机器最近做了什么删表删字段操作给揪出来等等。因为本篇重点还是讲会话和进程,在这块就不多展开了。
processes的设置思路
processes的大小是非常重要的!设置的太大没有意义。
如果设置的太小,就不能满足实际业务的需要,一旦用户进程接近processes最大值,应用系统就会开始变的很卡(实际经历); 一旦超过processes的最大值,数据库就会开始报错:ORA-00020: maximum number of processes (2048) exceeded;而如果并发用户已经达到SESSIONS的值时,又有新会话连接进来,就会报错:ORA-00018:maximum number of sessions exceeded 。此时数据库会发生宕机,我们再次启动数据库后只能通过AWR报告来查看分析这段时间内哪些主机连接较高。
所以在设置processes值的时候,必须充分考虑该Oracle数据库所承担的业务压力。在最高峰时,最大可能会有多少用户进程连接;并在此基础上再增加一些(可以增加个小几百)。
而且最好在DBCA建库时就思考清楚给多少processes值!
processes的修改
在确保您当前的用户有足够的权限之后,执行以下SQL。执行完后,需要重启数据库才能生效哦。这也是为什么上文提到最好在DBCA建库时就思考清楚给多少processes值的原因,因为生产数据库怎么能随便重启呢!
alter system set processes=500 scope=spfile;
那么session的参数该怎样修改呢?当然是不用手工修改啦,前文提到过session的值是根据process的值自动设置的,设置的规则请看上文【session与process的关系】章节。
❀❀❀ 感谢您的阅读哦!❀❀❀