Упрощение задания DF/Sort с чтением SMF для анализа жизненного цикла набора данных

Таким образом, у меня есть пакетное задание, которое извлекает записи SMF типа 14, 15 и 17 в 3 отдельных файла, а затем форматирует файлы, чтобы получить список наборов данных, которые были прочитаны, записаны и удалены какими заданиями. Затем он сортируется по отметке времени, чтобы вы могли увидеть "жизненный цикл" для определенного набора данных.

Тем не менее, я знаю, что DF/Sortt довольно мощный, и я думаю, что мой начальный шаг по разделению записей типов 14, 15 и 17 не является необходимым, и это можно сделать за один шаг, но я не совсем уверен с чего начать, так как DFSort/ICETOOL стал довольно сложным.

Вот мой текущий JCL:

//JBSP03DL JOB (JSDBBSP,P10),'SMF F NOW',                              
//         NOTIFY=&SYSUID,
//         CLASS=L,
//         MSGCLASS=X,
//         REGION=8M                                            
//*
//DELETE   EXEC PGM=IEFBR14
//OUTDSN DD DISP=(MOD,DELETE),DSN=JSDBSP.JBSP03.DSLIFE.TXT,
//       UNIT=SYSDA
//*
//SMFDUMP  EXEC PGM=IFASMFDP,REGION=6M
//*
//SYSPRINT DD SYSOUT=*
//* Extract type 14, 15 and 17 records into 3 temporary datasets
//DUMPIN   DD DISP=SHR,DSN=JSHSMF.SMF.JXSF.MANDUMP
//*
//DUMP14   DD  DISP=(,PASS),DSN=&&TYPE14,
//            UNIT=SYSDA,SPACE=(CYL,(500,200),RLSE),
//            BUFNO=20,BLKSIZE=27998,LRECL=32760,RECFM=VBS
//DUMP15   DD  DISP=(,PASS),DSN=&&TYPE15,
//            UNIT=SYSDA,SPACE=(CYL,(500,200),RLSE),
//            BUFNO=20,BLKSIZE=27998,LRECL=32760,RECFM=VBS
//DUMP17   DD  DISP=(,PASS),DSN=&&TYPE17,
//            UNIT=SYSDA,SPACE=(CYL,(500,200),RLSE),
//            BUFNO=20,BLKSIZE=27998,LRECL=32760,RECFM=VBS
//*
//SYSIN    DD *
INDD(DUMPIN,OPTIONS(DUMP))
OUTDD(DUMP14,TYPE(14))
OUTDD(DUMP15,TYPE(15))
OUTDD(DUMP17,TYPE(17))
//*
//SORTPROC PROC
//SORTWRTE EXEC PGM=SORT,REGION=8M
//SORTOUT  DD  DISP=MOD,DSN=&&SORTTMP,
//             SPACE=(CYL,(20,20)),UNIT=SYSDA
//SYSOUT   DD   SYSOUT=*
//SYSPRINT DD   SYSOUT=*
//SORTWK01 DD   DISP=(NEW,DELETE),DSN=&&TEMPSORT,UNIT=SYSDA,
//  SPACE=(CYL,(50,50))
//         PEND
//*
//* Process the type 14 records
//TYPE14   EXEC SORTPROC
//SORTIN   DD   DISP=SHR,DSN=&&TYPE14
//SORTOUT  DD  DISP=(,PASS),DSN=&&SORTTMP,
//             SPACE=(CYL,(20,20)),UNIT=SYSDA,
//             LRECL=133
//SYSIN    DD   *
  SORT FIELDS=(11,4,PD,A,7,4,PD,A)
  SUM FIELDS=NONE
  OUTREC BUILD=(11,4,DT1,EDIT=(TTTT-TT-TT),   DATE OF RECORD
                C' AT ',
                7,4,TM4,EDIT=(TT:TT:TT.TT), TIME OF RECORD
                C' ',
                69,44,
                C' was opened by ',
                19,8),CONVERT
//*
//* Process the type 15 records
//TYPE15   EXEC SORTPROC
//SORTIN   DD   DISP=SHR,DSN=&&TYPE15
//SYSIN    DD   *
  SORT FIELDS=(11,4,PD,A,7,4,PD,A)
  SUM FIELDS=NONE
  OUTREC BUILD=(11,4,DT1,EDIT=(TTTT-TT-TT),   DATE OF RECORD
                C' AT ',
                7,4,TM4,EDIT=(TT:TT:TT.TT), TIME OF RECORD
                C' ',
                19,8,
                C' opened ',
                69,44,
                C' for output'),CONVERT
//*
//* Process the type 17 records
//TYPE17   EXEC SORTPROC
//SORTIN   DD   DISP=SHR,DSN=&&TYPE17
//SYSIN    DD   *
  SORT FIELDS=(11,4,PD,A,7,4,PD,A)
  SUM FIELDS=NONE
  OUTREC BUILD=(11,4,DT1,EDIT=(TTTT-TT-TT),   DATE OF RECORD
                C' AT ',
                7,4,TM4,EDIT=(TT:TT:TT.TT), TIME OF RECORD
                C' ',
                19,8,
                C' deleted ',
                44,44),CONVERT
//*
//*  Finally sort the output file by the date & time stamp 
//*
//FINAL   EXEC SORTPROC
//SORTIN   DD   DISP=(OLD,DELETE),DSN=&&SORTTMP
//SORTOUT  DD   DISP=(NEW,CATLG),DSN=JSDBSP.JBSP03.DSLIFE.TXT,
//            UNIT=SYSDA,LRECL=121,RECFM=FB,SPACE=(CYL,(20,30))
//SYSIN    DD   *
SORT FIELDS=(1,23,CH,A)

Можно ли это сделать, не разделяя записи 14, 15 и 17 на отдельные файлы?

Редактировать: вышеупомянутый JCL делает именно то, что я хочу, но я хотел бы иметь возможность фильтровать по имени набора данных или имени задания, если это возможно, так как это может привести к большому выводу, который затем будет слишком большим для редактирования или просмотра ISPF для дальнейшего использования. анализ

Редактировать:

    Type 14 : 
5   5   SMF14RTY    1   binary  Record type 14 (X'0E').
18  12  SMF14JBN    8   EBCDIC  Job name.
68  44  SMF14_JFCBDSNM  44  EBCDIC DATA SET NAME (DSNAME=)

    Type 15 : 
5   5   SMF14RTY    1   binary  Record type 14 (X'0F').
18  12  SMF15JBN    8   EBCDIC Jobname
68  44  SMF15_JFCBDSNM  44  EBCDIC DATA SET NAME (DSNAME=)

    Type 17:
5   5   SMF17RTY    1   binary  Record type 17 (X'11').
18  12  SMF17JBN    8   EBCDIC  Job name.
44  2C  SMF17DSN    44  EBCDIC  Data set name.

Еще одним улучшением будет проверка того, действительно ли OPEN создает набор данных. Я также должен добавить RENAMES, иначе вы можете потерять отслеживание того, что случилось с конкретным набором данных.

Редактировать:

Следуя указаниям Билла, мой JCL теперь:

//DELETE   EXEC PGM=IEFBR14                                   
//OUTDSN DD DISP=(MOD,DELETE),DSN=JSDBSP.JBSP03.DSLIFE.TXT,   
//       UNIT=SYSDA                                           
//*                                                           
//SORTWRTE EXEC PGM=SORT,REGION=8M                            
//*                                                           
//SORTIN   DD   DISP=SHR,DSN=JSHSMF.SMF.JXSG.MANDUMP          
//SORTOUT  DD  DISP=(MOD,CATLG),DSN=JSDBSP.JBSP03.DSLIFE.TXT, 
//             SPACE=(CYL,(20,20)),                           
//             UNIT=SYSDA,LRECL=133                           
//*                                                           
//SYSOUT   DD   SYSOUT=*                                      
//SYSPRINT DD   SYSOUT=*                                      
//SYMNOUT  DD   SYSOUT=*                                      
//SYMNAMES DD   *                                             
 SMF-RECORD-TYPE,5,1,BI                                       
 SMF-JOB-NAME,19,8,CH                                         
 SMF-14-15-DSN,69,44,CH                                       
 SMF-17-DSN,44,44,CH                                          
 SMF-DATE,11,4,DT1                                            
 SMF-TIME,7,4,TM4                                             
//*                                                           
//SYSIN    DD   *                                             
  SORT FIELDS=(11,4,PD,A,7,4,PD,A)                            
  OUTREC IFTHEN=(WHEN=(SMF-RECORD-TYPE,EQ,14),                
              BUILD=(SMF-DATE,EDIT=(TTTT-TT-TT),              
                     C' AT ',                                 
                     SMF-TIME,EDIT=(TT:TT:TT.TT),             
                     C' ',                                    
                     SMF-14-15-DSN,                           
                     C' was opened by ',                      
                     SMF-JOB-NAME)),CONVERT                   

Но это дает:

OUTREC IFTHEN=(WHEN=(5,1,BI,EQ,14),BUILD=(11,4,DT1,EDIT=(TTTT-TT-TT),C' AT ',7,4
,TM4,EDIT=(TT:TT:TT.TT),C' ',69,44,C' was opened by ',19,8)),CONVERT            
                                                            *                                  
WER268A  OUTREC STATEMENT  : SYNTAX ERROR  

Оставляя

,ПЕРЕРАБАТЫВАТЬ

дает мне:

WER235A  OUTREC   RDW NOT INCLUDED

Редактировать - последнее обновление:

Просто пытаюсь изолировать записи типа 14, поэтому текущий ввод теперь:

//SYMNAMES DD   *       
 SMF-RECORD-TYPE,6,1,BI 
 SMF-JOB-NAME,11,8,CH   
 SMF-14-15-DSN,65,44,CH 
 SMF-17-DSN,44,44,CH    
 SMF-DATE,11,4,DT1      
 SMF-TIME,7,4,TM4       

SYSIN DD *
    SORT FIELDS=(11,4,PD,A,7,4,PD,A)                  
    OUTFIL IFTHEN=(WHEN=(SMF-RECORD-TYPE,EQ,14),      
                BUILD=(1,4,SMF-DATE,EDIT=(TTTT-TT-TT),
                       C' AT ',                       
                       SMF-TIME,EDIT=(TT:TT:TT.TT),   
                       C' ',                          
                       SMF-14-15-DSN,                 
                       C' was opened by ',            
                       SMF-JOB-NAME))    

3 ответа

Решение

Да, и это довольно безболезненно.

IFTHEN=(WHEN= допускаются различные виды условного процесса.

Здесь вы можете использовать IFTHEN=(WHEN=(logicalexpression), чтобы создать структуру case/select/valu-type:

IFTHEN=(WHEN=(5,1,B,EQ,14),
         ...),
IFTHEN=(WHEN=(5,1,B,EQ,15),
         ...),
IFTHEN=(WHEN=NONE,
         ...)

WHEN=NONE является "ловушкой", когда ни один из предыдущих тестов не соответствует действительности. IFTHEN=(WHEN=(logicalexpression) останавливается для текущей записи, когда один тест является истинным. Даже если второе условие для текущей записи должно быть истинным, оно не будет выполнено. Если вы хотите два или более "попаданий" в IFTHEN=(WHEN=(logicalexpression), тогда вы должны использовать HIT=NEXT в конце каждого теста, где вы можете захотеть "передать его" следующему тесту. Здесь это не имеет значения, так как это то же поле проверено на одно значение.

ЕСЛИ может появиться на INREC, OUTREC, или же OUTFIL, У вас есть обработка на OUTREC, так что вы бы (хотя см. Мой более поздний комментарий):

OUTREC IFTHEN=(WHEN=(5,1,B,EQ,14),
                ...),
       IFTHEN=(WHEN=(5,1,B,EQ,15),
                ...),
       IFTHEN=(WHEN=NONE,
                ...)

BUILD, OVERLAY а также PARSE можно использовать в IFTHEN.

Несколько мыслей и советов.

Я с подозрением отношусь к вашему SUM FIELDS=NONE, Это приведет к удалению любых записей с дубликатом ключа. Какая из записей из входного файла, который сохраняется, зависит. Если вы используете OPTION EQUALS или же EQUALS на SORT (или же MERGE) тогда первая запись всегда будет сохранена. Если вы этого не сделаете, запись, которая сохраняется, когда ключ дублируется, может варьироваться от запуска к запуску. РАВНЫЕ имеет некоторое влияние на производительность.

Во всяком случае, я не уверен, почему у вас есть поля = нет здесь. Вы даже можете получить "случайное" совпадение для совершенно разных наборов данных.

Если вы собираетесь выполнить сортировку, а затем выбрать только часть данных (в OUTREC или OUTFIL), всегда рассматривайте возможность "вырезания" записи, которая должна быть отсортирована, чтобы она включала в себя только те данные, которые вы позже будете использовать. При сортировке, чем меньше данных, тем меньше времени, памяти и временного хранилища используется.

Рассмотреть возможность использования DYNAM для временного хранения, и удалите SORTWKn ДД имена из JCL (у вас есть только один здесь, но...). Динамическое выделение рабочего пространства означает, что вам вообще не нужно много думать о рабочем пространстве (если только у вас нет огромных наборов данных с широко варьируемыми длинами записей для данных), и вы не "перераспределяете".

Сортировка символов. Символы позволяют вам называть ваши данные, так что ссылки на одно и то же поле могут быть сделаны по имени, и SORT заботится о менее захватывающей задаче - вводить начальную позицию и длину каждый раз. Это также уменьшает количество необходимых комментариев, потому что поле уже имеет имя, которое вы можете сделать описательным.

Символы определяются в отдельном наборе данных (F/FB 80) с DD SYMNAMES. Переведенные символы (которые также предоставляют запись о том, что использовалось) содержатся в наборе данных SYMNOUT, который не является обязательным, но полезен.

SORT затем применяет символы к вашим контрольным картам, а также показывает ваш исходный источник в SYSOUT, показывает вам переведенные карты.

Символы для этой задачи могут быть указаны вдоль этих линий

SMF-RECORD-TYPE,5,1,BI
SMF-JOB-NAME,18,8,CH
SMF-14-15-DSN,68,44,CH
SMF-17-DSN,44,44,CH
SMF-DATE,11,4,DT1
SMF-TIME,7,4,TM4

Затем вы можете заменить несколько определений одного и того же поля символом, и пусть SORT сделает всю работу.

Если вы хотите сделать выборку для наборов данных, вы можете посмотреть на использование PARM и специальных символов JP0-JP9, Или жесткий код Или создание контрольных карт SORT из списка наборов данных, или с помощью JOINKEYS,

О, и я знаю, что вы знаете, но вы на самом деле используете SYNCSORT. DFSORT не имеет CONVERT на OUTREC, но это на OUTFIL. Чтобы быть транспортабельным, просто измените ваш OUTREC на OUTFIL.

"Можно ли сделать это, не разделяя записи 14, 15 и 17 на отдельные файлы?"

Согласно http://publibz.boulder.ibm.com/cgi-bin/bookmgr_OS390/BOOKS/IEA2G2C0/3.2.1

... заявление DD

//DUMP   DD  DISP=(,PASS),...

... с контрольной выпиской

OUTDD(DUMP,TYPE(14,15,17))

... объединит все типы в один файл.

ОК - с помощью Билла (чей ответ я принимаю, когда он меня заставил) и после принятия решения застрять в руководствах, это мой результат:

//jobname JOB (acct_code),'pgmr_name',                               
//         NOTIFY=&SYSUID,
//         CLASS=L,
//         MSGCLASS=X,
//         REGION=8M
//*
// SET OUTFILE=your.results.file
//*
//DELETE   EXEC PGM=IEFBR14
//OUTDSN DD DISP=(MOD,DELETE),DSN=&OUTFILE,
//       UNIT=SYSDA
//*
//SMFDUMP  EXEC PGM=IFASMFDP,REGION=6M
//*
//SYSPRINT DD SYSOUT=*
//*
//DUMPIN   DD DISP=SHR,DSN=your.smf.dataset
//*
//DUMPOUT  DD  DISP=(,PASS),DSN=&&SMFTEMP,
//            UNIT=SYSDA,SPACE=(CYL,(500,200),RLSE),
//            BUFNO=20,DCB=*.DUMPIN
//*
//SYSIN    DD *
INDD(DUMPIN,OPTIONS(DUMP))
OUTDD(DUMPOUT,TYPE(14,15,17,18))
//*
//SORTPROC PROC
//SORTWRTE EXEC PGM=SORT,REGION=8M
//SORTIN   DD   DUMMY
//SORTOUT  DD   DUMMY
//SYSOUT   DD   SYSOUT=*
//SYSPRINT DD   SYSOUT=*
//SYMNAMES DD   *
 RDW,1,4,BI
 SMF-RECORD-TYPE,6,1,BI
 SMF-JOB-NAME,19,8,CH
 SMF-14-15-DSN,69,44,CH
 SMF-17-18-DSN,45,44,CH
 SMF-17-DSN,45,44,CH
 SMF-18-DSN,45,44,CH
 SMF-18-NDSN,89,44,CH
 SMF-DATE,11,4,DT1
 SMF-TIME,7,4,TM4
 SMFDEBOP,253,1
//         PEND
//*
//PROCESS  EXEC SORTPROC
//SORTIN   DD   DISP=OLD,DSN=&&SMFTEMP
//SORTOUT  DD  DISP=(,PASS),DSN=&&SORTTMP,
//             SPACE=(CYL,(20,20)),UNIT=SYSDA
//SYSIN    DD   *
  SORT FIELDS=(11,4,PD,A,7,4,PD,A)
  OUTREC IFTHEN=(WHEN=(SMF-RECORD-TYPE,EQ,14),
            BUILD=(RDW,SMF-DATE,EDIT=(TTTT-TT-TT),
                C' AT ',
                SMF-TIME,EDIT=(TT:TT:TT.TT),
                C' ',
                SMF-14-15-DSN,
                C' was opened by ',
                SMF-JOB-NAME)),
         IFTHEN=(WHEN=(SMF-RECORD-TYPE,EQ,15),
            BUILD=(RDW,SMF-DATE,EDIT=(TTTT-TT-TT),
                C' AT ',
                SMF-TIME,EDIT=(TT:TT:TT.TT),
                C' ',
                SMF-JOB-NAME,
                C' opened ',
                SMF-14-15-DSN,
                C' for output')),
         IFTHEN=(WHEN=(SMF-RECORD-TYPE,EQ,17),
            BUILD=(RDW,SMF-DATE,EDIT=(TTTT-TT-TT),
                C' AT ',
                SMF-TIME,EDIT=(TT:TT:TT.TT),
                C' ',
                SMF-JOB-NAME,
                C' deleted ',
                SMF-17-DSN)),
         IFTHEN=(WHEN=(SMF-RECORD-TYPE,EQ,18),
            BUILD=(RDW,SMF-DATE,EDIT=(TTTT-TT-TT),
                C' AT ',
                SMF-TIME,EDIT=(TT:TT:TT.TT),
                C' ',
                SMF-JOB-NAME,
                C' renamed ',
                SMF-18-DSN,
                C' to ',
                SMF-18-NDSN))
//*
//FINAL   EXEC SORTPROC
//SORTIN   DD   DISP=OLD,DSN=&&SORTTMP
//SORTOUT  DD   DSN=&OUTFILE,
//           DISP=(NEW,CATLG),UNIT=SYSDA,SPACE=(CYL,(20,30),RLSE)
//SYSIN    DD   *
  OPTION VLSHRT,VLSCMP
  SORT FIELDS=(5,25,CH,A)
  INCLUDE COND=(1,125,SS,EQ,C'PEEL',
                AND,
                1,125,SS,EQ,C'XCOM')
  OUTFIL FNAMES=SORTOUT,VTOF,OUTREC=(5,126)

Я не мог понять, можно ли было включить заключительный шаг в основной шаг, но я доволен этим, как есть. Обратите внимание, что на самом деле мы используем Syncsort, а не DF/Sort, поэтому помните, что изменения могут потребоваться, если вы работаете в DF / Sort.

INCLUDE COND присутствует, потому что большую часть времени выходной набор данных слишком велик для редактирования или просмотра ISPF, в противном случае вы можете просто отредактировать выходные данные и отфильтровать их там.

Другие вопросы по тегам