Oracle PL/SQL - 立即输出/控制台打印的提示
我有许多 pl/sql 过程,可能需要几分钟才能运行。在开发它们时,我添加了一些打印语句来帮助调试,并提供一些反馈和进度指示器。最初,我在小型测试集上运行这些,输出几乎是瞬时的。现在,我正在使用需要几分钟才能运行的较大测试集进行测试,我发现打印到控制台不再合适,因为在过程结束之前不会打印任何内容。我习惯于在不缓冲输出并立即打印它的环境中工作,并且添加简单的打印语句以进行简单的调试和诊断是很常见的。
pl/sql 是否可以立即打印输出(不缓冲)?如果没有,人们推荐什么替代方案来获得类似的结果?
I have a number of pl/sql procedures that can take several minutes to run. While developing them, I've added a few print statements to help debug and also provide some feedback and progress indicators. Initially, I ran these on small test sets and output was almost instantaneous. Now that I'm testing with larger test sets that take several minutes to run, I find that printing to the console is no longer suitable, because nothing gets printed until the procedure ends. I'm used to working in environments that do not buffer their output and print it immediately and adding simple print-statements for simple debugging and diagnostic is common.
Is it possible in pl/sql to print output immediately (not buffered)? If not, what alternatives do people recommend to get a similar result?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(8)
您可以有一个使用自治事务将消息写入表的过程,例如:
然后从另一个 Oracle 会话监视该表。
You can have a procedure that writes messages to a table using an autonomous transaction something like:
Then monitor the table from another Oracle session.
为此我们有一个小技巧。
您可以使用 DBMS_APPLICATION_INFO.set_client_info(" 这里有一些信息");
创建一些变量并替换“”内的字符串。
并使用 select client_info from v$session 来监控进度。
we have a small trick for this.
you can use DBMS_APPLICATION_INFO.set_client_info(" some information here");
creating some variables and replace the string inside " ".
and use select client_info from v$session to monitor the progress.
为此,我一直使用 dbms_pipe 。将消息发送到命名管道并从另一个会话中读取它们。在 RAC 环境中,当写入和读取进程可能连接到不同的节点时,此方法可能不起作用。
或者,您可以使用在其自己的会话中使用“pragmaautonomous_transaction”运行的过程将消息插入到表中。您可以从另一个会话查询这些消息
编辑:我看到我的第二个选项已经被提到。
I've been using dbms_pipe for this purpose. Send messages to a named pipe and read them from another session. This method may not work in a RAC environment when the writing and reading processes may connect to a different node.
Alternatively you can insert messages into a table using a procedure that runs in its own session using "pragma autonomous_transaction". You can the query these messages from another session
Edit: I see that my second option has already been mentioned.
通常有两个选项:
(或临时表)
如果您没有操作系统访问数据库主机的权限,您仍然可以写入 dbhost 文件系统并将 Oracle 外部定义的表绑定到该文件,以便它可以使用 SELECT 进行查询。
There are generally two options:
(or temporary table)
If you don't have OS access to the database host, you can still write to the dbhost filesystem and bind an Oracle externally-defined table to the file so it can be queried with a SELECT.
这可能取决于您的客户端工具。我有一段时间没有使用 SQL*Plus,但是当我在 PL/SQL Developer 中调试程序时,我打开一个命令窗口并发出
SET SERVEROUTPUT ON
命令。然后,当我执行该过程时,DBMS_OUTPUT.PUT_LINE
打印的任何内容都会立即显示。编辑:你是对的,我想我只是在大量输出或其他东西的情况下才看到这一点。无论如何,我在网上做了一些搜索,发现了这个 log4plsql - 可能有用。
It may depend on your client tool. I haven't used SQL*Plus in a while, but when I'm debugging procedures in PL/SQL Developer, I open a command window and issue a
SET SERVEROUTPUT ON
command. Then when I execute the procedure, anything printed byDBMS_OUTPUT.PUT_LINE
shows up right away.Edit: you're right, I guess I was only seeing that with larger amounts of output or something. Anyhow I did some searching online and came across this log4plsql - may be useful.
另一种方法是使用返回日志信息的管道函数。请参阅此处的示例:http://berxblog.blogspot。 com/2009/01/pipelined-function-vs-dbmsoutput.html 当您使用管道函数时,您不必使用另一个 SQLPLUS/Toad/sql Developer 等会话。
An alternative is to use a pipelined function that returns your logging information. See here for an example: http://berxblog.blogspot.com/2009/01/pipelined-function-vs-dbmsoutput.html When you use a pipelined function you don't have to use another SQLPLUS/Toad/sql developer etc... session.
您可以使用 DBMS Pipe 和 PL/SQL Developer 中的 Pipe Viewer 来异步捕获放入管道中的所有信息。
请小心,仅当有人读取时才将内容放入管道中。否则,当管道已满时,您的调用将会失败。
还可以使用事件,PL/SQL Developer 也有一个事件监视器。并且文档应该提供如何执行此操作的示例。
You can use DBMS Pipe and the Pipe Viewer in PL/SQL Developer to asynchronously catch all infos as they are put into the pipe.
Be careful to only put things into a pipe when there's someone to read it. Otherwise, your call will fail when the pipe is full.
There's also the possibility of using events, PL/SQL Developer has an event monitor as well. And the docs should provide an example of how to do it.
另一种选择是让 PL/SQL 调用一个过程来发送包含日志消息的电子邮件。这就要求你的数据库具有邮件发送功能,可以使用UTL_SMTP来添加。
Another option is to have your PL/SQL call a procedure to send an email with the log message in it. This requires that your database has email sending capability, which can be added using UTL_SMTP.