在开发过程中,我发现数据库有大量的生命连接:
SELECT username, COUNT(*) FROM v$session GROUP BY username;
为了找到实际持有连接的人,我想获得一个IP地址列表。
在一般网络搜索和阅读official docs期间,我构建了查询:
SELECT username, seconds_in_wait, machine, port, terminal, program, module, service_name
FROM v$session
WHERE type = 'USER';
其中machine
是select
最重要的部分。但遗憾的是,machine
字段显示客户端操作系统已知的主机名。
互联网上充满了使用UTL_INADDR.GET_HOST_ADDRESS的建议,这在我的案例中并不适用。首先是因为 ORA-24247:访问控制列表(ACL)拒绝网络访问,其次是因为客户端操作系统主机名通常在 / etc / hostname中定义并且我们的Intranet中的DNS服务器不可用...
检索到Oracle DB的开放会话的IP的任何其他方法(数据库实例在任何情况下都保存有关其套接字的信息......)。
更新
我在受信任的Intranet下,但网络层次结构未知。
我试图找到哪些应用程序使用我的表(几个应用程序服务器,我不知道所有这些)。他们中的一些过度使用连接,需要修复。但首先应该确定它们......
答案 0 :(得分:4)
请记住,Oracle会话不需要知道,当然也不需要信任您来自的客户端名称/ IP地址;它位于网络传输层之上,并不关心您是通过TCP / IP还是其他方式连接。 (我甚至不确定监听器是否必须传递信息,或者它是否有效地传递了现成的套接字)。正如您所见,machine
正是客户所宣称的内容,例如program
和v$session
视图中的其他字段;它可能与DNS或您的服务器的/etc/hosts
无法解决的任何内容有任何相似之处,特别是如果客户端是Windows框。
你可以做的是,在Unix / Linux级别(因为你引用/ etc / hosts,我假设你不在Windows上),寻找port
并查看显示的地址;例如v$session
将port
显示为50527
,如果我netstat -an | grep 50527
,我会看到:
tcp 0 0 192.168.1.1:1521 192.168.1.23:50527 ESTABLISHED
所以我可以看到我从192.168.1.23
连接到了。如果您在服务器上运行SQL * Plus,则可以使用host
命令执行此操作,但它仍然有点不方便。如果您需要定期执行此操作,并且添加登录触发器以将其捕获到审计表不是一个选项,并且您必须从数据库中执行此操作,您可能可以编写Java存储过程来执行查找那个港口给你。但是编写一个shell脚本来查询来自port
的{{1}}数字并以此方式进行查找可能更容易。
答案 1 :(得分:2)
感谢所有人挖掘我的问题(这仍然是一般目的,而不是我的!!)。
简短回答:您无法从Oracle系统表中获得真正的IP。
对于此任务,您可以使用netstat
或lsof -p <pid-of-oracle>
等通用实用程序,但仅限于服务器端!
一些帮助可能来自v$session.port
值......
帮助者的一个好建议 - 使用DB客户端的好名字。它们填充到v$session
表行:
machine, terminal, program, module, service_name
所以他们可以帮助识别客户......
答案 2 :(得分:2)
传入连接的IP地址通常可以在监听器日志中找到。这就是我在需要时跟踪这些信息的方式。
答案 3 :(得分:1)
我从2001年开始发现我的审核脚本,当时登录触发器不存在AFAIK。它解析SYS.AUD $的COMMENT $ TEXT列,其中ACTION#= 100以获取客户端的IP地址。该列仍包含 Authenticated by:DATABASE;客户地址:(ADDRESS =(PROTOCOL = tcp)(HOST = a.a.a.a )(PORT = p ))在我们的环境中。