If you're using REXX then why don't you just use the parse instruction to scrape the report file? The parse instruction uses a template pattern which is very simple but powerful.
Here's an example:
/* REXX */
queue "ADSTART ACTION(ADD)"
queue " ADID(ABCD0B ) ADVALFROM(111230) CALENDAR(CALSEM7J )"
queue " DESCR('DESCRIPTION ')"
queue " ADTYPE(A)"
queue " GROUP(PBQOPC )"
queue " OWNER('OWNER1')"
queue " PRIORITY( 5) ADSTAT(A)"
queue " ODESCR('ALADIN ')"
queue "ADRUN ACTION(ADD)"
queue " PERIOD(HEB ) RULE(3) VALFROM(091230) VALTO(711231)"
queue " SHIFT( 0) SHSIGN(F)"
queue " DESCR('DESCRIPTION')"
queue " TYPE(N)"
queue " IADAYS( 1, 2, 3, 4, 5, 6, 7)"
queue " IATIME(1700) DLDAY( 1) DLTIME(0600)"
do while queued() > 0
parse pull rec
select
when startswith(rec,"ADSTART") then do
p. = '' /* the output record */
parse var rec with . 'ACTION('p.action')'
do queued()
parse pull rec
if left(rec,1) /= ' ' then do
/* End of parameter group. Re-queue the record and break */
push rec
leave
end
select
when startswith(rec, " ADID") then do
parse var rec with . "ADID("p.adid") ADVALFROM("p.advalfrom")" ,
"CALENDAR("p.calendar")"
end
when startswith(rec, " DESCR") then do
parse var rec with "DESCR('"p.desc"')"
end
when startswith(rec, " PRI") then do
parse var rec with "PRIORITY("p.priority") ASTAT("p.adstat")"
end
otherwise nop
end
end
/* write out the record in 1 line */
say strip(p.action) strip(p.adid) strip(p.advalfrom) strip(p.calendar),
strip(p.desc) strip(p.priority) strip(p.adstat)
end
when startswith(rec,"ADRUN") then do
/* do some stuff to parse this */
end
otherwise nop
end
end
exit 0
startswith:
parse arg input, prefix
input_len = length(input)
if input_len = 0 then return 0
prefix_len = length(prefix)
if prefix_len = 0 then return 0
return input_len >= prefix_len & left(input,prefix_len) = prefix
Seeing as you're comfortable in z/OS UNIX environment, if you want something a little bit more powerful than REXX and/or AWK you should checkout my z/OS port of Lua. It comes with an LPeg package which makes it trivially easy to write lexers and parsers with very few lines of code.
If all you want to do is text flow the TWS control statements onto one line without capturing the fields then that's very simple to do.
/* REXX */
queue "ADSTART ACTION(ADD)"
queue " ADID(ABCD0B ) ADVALFROM(111230) CALENDAR(CALSEM7J )"
queue " DESCR('DESCRIPTION ')"
queue " ADTYPE(A)"
queue " GROUP(PBQOPC )"
queue " OWNER('OWNER1')"
queue " PRIORITY( 5) ADSTAT(A)"
queue " ODESCR('ALADIN ')"
queue "ADRUN ACTION(ADD)"
queue " PERIOD(HEB ) RULE(3) VALFROM(091230) VALTO(711231)"
queue " SHIFT( 0) SHSIGN(F)"
queue " DESCR('DESCRIPTION')"
queue " TYPE(N)"
queue " IADAYS( 1, 2, 3, 4, 5, 6, 7)"
queue " IATIME(1700) DLDAY( 1) DLTIME(0600)"
do while queued() > 0
parse pull rec
if left(rec,1) /= ' ' then do
line = rec
do queued()
parse pull rec
if left(rec,1) /= ' ' then do
push rec;leave
end
line = line rec
end
say space(line,1)
end
end
exit 0