Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit 640806b

Browse files
committed
work in progress
1 parent 217913e commit 640806b

6 files changed

Lines changed: 103 additions & 38 deletions

File tree

source/core/types/ut_output_dbms_pipe.tpb

Lines changed: 5 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ create or replace type body ut_output_dbms_pipe as
33
constructor function ut_output_dbms_pipe(self in out nocopy ut_output_dbms_pipe) return self as result is
44
begin
55
self.output_type := $$plsql_unit;
6-
self.output_id := ut_output_dbms_pipe.generate_output_id;
6+
self.output_id := self.generate_output_id;
77
return;
88
end;
99

@@ -21,12 +21,11 @@ create or replace type body ut_output_dbms_pipe as
2121
end;
2222

2323
overriding member procedure send(self in out nocopy ut_output_dbms_pipe, a_text clob) is
24-
--we're assuming bax of 4 bytes per char
25-
c_size_limit_chars constant integer := 1000;
26-
l_text_part varchar2(4000 byte);
27-
l_timeout_occured boolean;
28-
i integer := 0;
24+
c_size_limit_chars constant integer := ut_output_pipe_helper.gc_size_limit_chars;
25+
l_text_part ut_output_pipe_helper.t_pipe_item;
26+
i integer := 0;
2927
begin
28+
--split test into pieces of a size valid for pipe and send to pipe
3029
while i <= length(a_text) loop
3130
l_text_part := substr( a_text, i + 1, c_size_limit_chars );
3231
ut_output_pipe_helper.send( self.output_id, l_text_part);

source/core/types/ut_output_dbms_pipe.tps

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,6 @@ create or replace type ut_output_dbms_pipe under ut_output (
33
overriding member procedure open(self in out nocopy ut_output_dbms_pipe),
44
overriding member procedure send(self in out nocopy ut_output_dbms_pipe, a_text clob),
55
overriding member procedure close(self in out nocopy ut_output_dbms_pipe),
6-
static function generate_output_id return varchar2,
76
static function get_lines(a_output_id varchar2, a_timeout_sec integer := 60*60*4) return ut_output_clob_list pipelined,
87
member procedure to_screen(self in ut_output_dbms_pipe),
98
static procedure to_screen(a_output_id varchar2)

source/core/ut_output_pipe_helper.pkb

Lines changed: 76 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -1,52 +1,95 @@
11
create or replace package body ut_output_pipe_helper is
22

33

4-
type t_pipe_buffer is table of varchar2(4000);
5-
type t_outputs_buffer is table of t_pipe_buffer index by varchar2(128);
4+
type tt_pipe_buffer is table of varchar2(4000);
65

7-
g_outputs_buffer t_outputs_buffer;
6+
type t_output_buffer is record(
7+
to_close boolean := false,
8+
data tt_pipe_buffer
9+
);
810

9-
procedure send_from_buffer(a_output_id varchar2) is
10-
l_timeout_occured boolean;
11+
type tt_outputs_buffer is table of t_output_buffer index by varchar2(128);
12+
13+
g_outputs_buffer tt_outputs_buffer;
14+
15+
function send_from_buffer(a_output_id varchar2, a_buffer in out nocopy tt_pipe_buffer) return boolean is
16+
l_is_successful boolean := true;
17+
l_first_item integer;
18+
l_last_item integer;
1119
i integer;
1220
begin
13-
if g_outputs_buffer.exists(a_output_id) then
14-
i := g_outputs_buffer(a_output_id).first;
21+
if a_buffer is not null then
22+
l_first_item := a_buffer.first;
23+
i := l_first_item;
24+
--iterate through buffer and try to sent all data from buffer
25+
-- exit loop on timeout
1526
while i is not null loop
16-
dbms_pipe.pack_message( g_outputs_buffer(a_output_id)(i) );
17-
l_timeout_occured := dbms_pipe.send_message(a_output_id, 0) != 0;
18-
if l_timeout_occured then
19-
dbms_pipe.reset_buffer;
20-
return;
21-
end if;
27+
dbms_pipe.pack_message( a_buffer(i) );
28+
l_is_successful := dbms_pipe.send_message(a_output_id, 0) = 0;
29+
exit when not l_is_successful;
30+
l_last_item := i;
31+
i := a_buffer.next(i);
2232
end loop;
33+
34+
--remove from buffer messages alrady sent
35+
if not l_is_successful then
36+
a_buffer.delete(l_first_item, i-1);
37+
else
38+
a_buffer.delete();
39+
end if;
40+
dbms_pipe.reset_buffer;
41+
return l_is_successful;
42+
end if;
43+
return false;
44+
end;
45+
46+
function send_from_buffer(a_output_id varchar2) return boolean is
47+
begin
48+
if g_outputs_buffer.exists(a_output_id) then
49+
return send_from_buffer(a_output_id, g_outputs_buffer(a_output_id).data);
2350
end if;
51+
return false;
2452
end;
2553

2654
--sends a message to a named pipe
2755
--and if sending fails it writes the message to the end of the buffer for pipe
28-
procedure send(a_output_id varchar2, a_text varchar2) is
29-
l_timeout_occured boolean;
56+
procedure send(a_output_id varchar2, a_text t_pipe_item) is
57+
l_is_successful boolean;
3058
begin
31-
send_from_buffer(a_output_id);
32-
dbms_pipe.pack_message( a_text );
33-
l_timeout_occured := dbms_pipe.send_message(a_output_id, 0) != 0;
34-
if l_timeout_occured then
35-
dbms_pipe.reset_buffer;
36-
buffer(a_output_id, a_text);
37-
end if;
59+
buffer(a_output_id, a_text);
60+
l_is_successful := send_from_buffer(a_output_id);
3861
end;
3962

4063
--writes the message to the end of the buffer for pipe
41-
procedure buffer(a_output_id varchar2, a_text varchar2) is
64+
procedure buffer(a_output_id varchar2, a_text t_pipe_item) is
4265
begin
4366
if not g_outputs_buffer.exists(a_output_id) then
44-
g_outputs_buffer(a_output_id) := t_pipe_buffer();
67+
g_outputs_buffer(a_output_id).data := tt_pipe_buffer();
4568
end if;
46-
g_outputs_buffer(a_output_id).extend;
47-
g_outputs_buffer(a_output_id)(g_outputs_buffer(a_output_id).last) := a_text;
69+
g_outputs_buffer(a_output_id).data.extend;
70+
g_outputs_buffer(a_output_id).data(g_outputs_buffer(a_output_id).data.last) := a_text;
71+
end;
72+
73+
procedure cleanup_outputs_to_close is
74+
l_output_id varchar2(128);
75+
l_output_id_to_delete varchar2(128);
76+
begin
77+
l_output_id := g_outputs_buffer.first;
78+
while i is not null loop
79+
l_output_id_to_delete := null;
80+
if g_outputs_buffer(l_output_id).to_close then
81+
if send_from_buffer(l_output_id) = true then
82+
l_output_id_to_delete := l_output_id;
83+
end if;
84+
end if;
85+
l_output_id := g_outputs_buffer.next(l_output_id);
86+
g_outputs_buffer.delete(l_output_id_to_delete);
87+
end loop;
4888
end;
4989

90+
--procedure cleanup_aged_pipes() - check for pipes that are aged out.
91+
92+
5093
--registers a close request and tries to close a pipe
5194
--by first sending out all messages remaining in the buffers
5295
--the procedure holds infomrmation about closure requests
@@ -73,7 +116,13 @@ create or replace package body ut_output_pipe_helper is
73116
-- two buffers used: output_1, output_2
74117
procedure request_close(a_output_id varchar2, a_text varchar2) is
75118
begin
76-
null;
119+
cleanup_outputs_to_close;
120+
--if there is any output in a state to_close = false
121+
--exit
122+
--else loop with a wait time of 20 seconds for each to_close output
123+
124+
--if unable to send all messages after timeout, then finish?
125+
77126
end;
78127

79128
end;

source/core/ut_output_pipe_helper.pks

Lines changed: 11 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,18 @@
11
create or replace package ut_output_pipe_helper is
22

3-
--sends a message to a named pipe
4-
--and if sending fails it writes the message to the end of the buffer for pipe
5-
procedure send(a_output_id varchar2, a_text varchar2);
3+
--the limit size for pipe message is 4096, we want to make sure we're below that limit
4+
subtype t_pipe_item is varchar(4000 byte);
5+
6+
--we're assuming max of 4 bytes per char
7+
gc_size_limit_chars constant integer := 1000;
8+
9+
--adds message to pipe buffer and tries to sent all messages from the buffer
10+
--exists immediately when sending timesout (pipe full)
11+
--the messages that were sent are removed from buffer
12+
procedure send(a_output_id varchar2, a_text t_pipe_item);
613

714
--writes the message to the end of the buffer for pipe
8-
procedure buffer(a_output_id varchar2, a_text varchar2);
15+
procedure buffer(a_output_id varchar2, a_text t_pipe_item);
916

1017
--registers a close request and tries to close a pipe
1118
--by first sending out all messages remaining in the buffers

source/install.sql

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,8 +23,11 @@ whenever oserror exit failure rollback
2323
@@core/types/ut_executable.tps
2424
@@core/types/ut_assert_result.tps
2525
@@core/types/ut_assert_list.tps
26+
@@core/types/ut_output_clob_list.tps
2627
@@core/types/ut_output.tps
2728
@@core/types/ut_output_dbms_output.tps
29+
@@core/ut_output_pipe_helper.pks
30+
@@core/types/ut_output_dbms_pipe.tps
2831
@@core/types/ut_reporter.tps
2932
@@core/types/ut_reporters_list.tps
3033
@@core/types/ut_composite_reporter.tps
@@ -48,6 +51,8 @@ whenever oserror exit failure rollback
4851
@@core/types/ut_assert_result.tpb
4952
@@core/types/ut_output.tpb
5053
@@core/types/ut_output_dbms_output.tpb
54+
@@core/ut_output_pipe_helper.pkb
55+
@@core/types/ut_output_dbms_pipe.tpb
5156
@@core/types/ut_reporter.tpb
5257
@@core/types/ut_object.tpb
5358
@@core/types/ut_composite_object.tpb

source/uninstall.sql

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -96,10 +96,16 @@ drop type ut_reporters_list;
9696

9797
drop type ut_reporter force;
9898

99+
drop type ut_output_dbms_pipe;
100+
101+
drop package ut_output_pipe_helper;
102+
99103
drop type ut_output_dbms_output;
100104

101105
drop type ut_output;
102106

107+
drop type ut_output_clob_list;
108+
103109
drop type ut_assert_list;
104110

105111
drop type ut_assert_result;

0 commit comments

Comments
 (0)