Слайд 2Введение
СУБД Oracle — большой и сложный механизм, требующий выполнения определенных плановых работ,
![Введение СУБД Oracle — большой и сложный механизм, требующий выполнения определенных плановых](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-1.jpg)
таких как сбор статистики о хранимых объектах или сбор/чистка внутренней информации. Необходимость осуществлять плановый запуск работ могут испытывать и пользователи БД.
Первый механизм планового запуска появился в версии 7 для поддержки автоматических обновлений снимков (snapshots), как поначалу именовались нынешние материализованные виртуальные таблицы (materialized views). В версии 8 этот механизм был открыт для обычных пользователей через посредство некоторых параметров СУБД, таблиц словаря, а также пакета DBMS_JOB. Пакет DBMS_JOB позволял (и позволяет) запускать хранимую процедуру, или же неименованный блок PL/SQL в моменты времени, вычисляемые по указанной пользователем формуле.
К версии 10 такое устройство имевшегося планировщика заданий было сочтено слишком примитивным, и в ней появился новый планировщик DBMS_SCHEDULER, значительно более проработанный.
Слайд 3Основные понятия планировщика
Schedule (расписание)
Program (программа)
Job (плановое задание = расписание +
![Основные понятия планировщика Schedule (расписание) Program (программа) Job (плановое задание = расписание](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-2.jpg)
программа)
Chain (последовательность заданий)
Слайд 4Объекты словаря данных
таблицы словаря LIKE '%SCHEDULER_%‘:
DBA_SCHEDULER_JOBS DBA_SCHEDULER_JOB_LOG
USER_SCHEDULER_PROGRAMS
USER_SCHEDULER_JOBS
и прочие
![Объекты словаря данных таблицы словаря LIKE '%SCHEDULER_%‘: DBA_SCHEDULER_JOBS DBA_SCHEDULER_JOB_LOG USER_SCHEDULER_PROGRAMS USER_SCHEDULER_JOBS и прочие](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-3.jpg)
Слайд 5Типы заданий (и программ)
PL/SQL – процедура (STORED_PROCEDURE)
PL/SQL - блок (PLSQL_BLOCK)
external OS-program (EXECUTABLE)
![Типы заданий (и программ) PL/SQL – процедура (STORED_PROCEDURE) PL/SQL - блок (PLSQL_BLOCK) external OS-program (EXECUTABLE)](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-4.jpg)
Слайд 6Пример (простое задание с PLSQL блоком)
BEGIN
DBMS_SCHEDULER.CREATE_JOB
( job_name => 'simple_job',
job_type => 'PLSQL_BLOCK',
![Пример (простое задание с PLSQL блоком) BEGIN DBMS_SCHEDULER.CREATE_JOB ( job_name => 'simple_job',](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-5.jpg)
job_action => 'UPDATE emp SET sal = sal +1;',
enabled => TRUE
);
END;
Слайд 7Пример (простое задание с вызовом хранимой процедуры)
CREATE PROCEDURE updatesal AS BEGIN UPDATE
![Пример (простое задание с вызовом хранимой процедуры) CREATE PROCEDURE updatesal AS BEGIN](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-6.jpg)
emp SET sal = sal - 1; END;
/
BEGIN
DBMS_SCHEDULER.CREATE_JOB
( job_name => 'simple_job',
job_type => 'STORED_PROCEDURE',
job_action => 'updatesal',
enabled => TRUE
) ;
END;
/
Слайд 8Пример (задание с внешним вызовом)
BEGIN
DBMS_SCHEDULER.CREATE_JOB
( job_name => 'simple_job',
job_type => 'EXECUTABLE',
job_action
![Пример (задание с внешним вызовом) BEGIN DBMS_SCHEDULER.CREATE_JOB ( job_name => 'simple_job', job_type](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-7.jpg)
=> 'cmd.exe /C dir > \temp\out.txt',
enabled => TRUE
);
END;
Слайд 9Возможности для указания запуска заданий
Следующие параметры процедуры CREATE_JOB:
start_date => SYSTIMESTAMP + INTERVAL
![Возможности для указания запуска заданий Следующие параметры процедуры CREATE_JOB: start_date => SYSTIMESTAMP](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-8.jpg)
'10' SECOND
end_date => SYSTIMESTAMP + INTERVAL ‘100' SECOND
repeat_interval => 'FREQ=MONTHLY; BYDAY=SUN, -1 SAT‘
(В результате задание будет исполняться ежемесячно по воскресениям и последним субботам месяца)
Слайд 10Примеры (использование языка для запуска заданий)
FREQ=HOURLY;INTERVAL=4 каждые 4 часа;
FREQ=MINUTELY;INTERVAL=5 каждые 5
![Примеры (использование языка для запуска заданий) FREQ=HOURLY;INTERVAL=4 каждые 4 часа; FREQ=MINUTELY;INTERVAL=5 каждые](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-9.jpg)
минут
FREQ=HOURLY;INTERVAL=4;BYMINUTE=10;BYSECOND=30 каждые 4 часа на 10-й минуте, 30-й секунде;
FREQ=YEARLY;BYYEARDAY=-276 каждое 31-е марта;
FREQ=YEARLY;BYMONTH=MAR;BYMONTHDAY=31 каждое 31-е марта;
Слайд 11Как проверить правильность составленного выражения?
DECLARE
next_run_date TIMESTAMP;
BEGIN
DBMS_SCHEDULER.EVALUATE_CALENDAR_STRING
(
![Как проверить правильность составленного выражения? DECLARE next_run_date TIMESTAMP; BEGIN DBMS_SCHEDULER.EVALUATE_CALENDAR_STRING ( 'FREQ=MINUTELY;INTERVAL=4',](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-10.jpg)
'FREQ=MINUTELY;INTERVAL=4',
SYSTIMESTAMP,
NULL,
next_run_date
) ;
DBMS_OUTPUT.PUT_LINE ( 'next_run_date: ' || next_run_date );
END;
Слайд 12Информация о заданиях
Если указать план запуска, задание появится в словаре уже надолго.
![Информация о заданиях Если указать план запуска, задание появится в словаре уже](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-11.jpg)
Удалить его при необходимости можно будет так:
EXECUTE DBMS_SCHEDULER.DROP_JOB ( 'simple_job', TRUE )
Информацию об имеющихся заданиях пользователь может посмотреть запросом:
SELECT job_name, state, enabled
FROM user_scheduler_jobs;
Более подробную информацию можно обнаружить в таблицах USER_SCHEDULER_%, а более общую – в обычной таблице USER_OBJECTS.
Слайд 13Скомпонованное задание
Более развитая возможность DBMS_SCHEDULER позволяет скомпоновать задание из независимых элементов: программы
![Скомпонованное задание Более развитая возможность DBMS_SCHEDULER позволяет скомпоновать задание из независимых элементов:](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-12.jpg)
и расписания. Характерная особенность в том, что оба эти элемента самостоятельны; их можно комбинировать в разных заданиях и изменять, не внося изменений в определения заданий.
Слайд 14Пример (создание программы)
BEGIN
DBMS_SCHEDULER.CREATE_PROGRAM
( program_name => 'simple_program',
program_type => 'STORED_PROCEDURE' ,
program_action
![Пример (создание программы) BEGIN DBMS_SCHEDULER.CREATE_PROGRAM ( program_name => 'simple_program', program_type => 'STORED_PROCEDURE'](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-13.jpg)
=> 'updatesal',
enabled => TRUE
);
END;
Слайд 15Примечания
Информация об имеющихся программах для планировщика присутствует в представлениях: DBA/ALL/USER_SCHEDULER_PROGRAMS.
Другими значениями
![Примечания Информация об имеющихся программах для планировщика присутствует в представлениях: DBA/ALL/USER_SCHEDULER_PROGRAMS. Другими](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-14.jpg)
параметра PROGRAM_TYPE могут быть 'PLSQL_BLOCK' и 'EXECUTABLE' (как и типов заданий).
Слайд 16Пример (процедуры с параметрами)
CREATE PROCEDURE salary ( deer NUMBER ) AS
![Пример (процедуры с параметрами) CREATE PROCEDURE salary ( deer NUMBER ) AS](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-15.jpg)
BEGIN
UPDATE emp SET sal = sal - deer;
END;
/
BEGIN
DBMS_SCHEDULER.CREATE_PROGRAM
( program_name => 'simple_program1',
program_type => 'STORED_PROCEDURE',
program_action => 'salary',
enabled => FALSE,
number_of_arguments => 1
) ;
END;
/
Слайд 17Пример(уточнение фактических параметров вызова программы)
BEGIN
DBMS_SCHEDULER.DEFINE_PROGRAM_ARGUMENT
( program_name => 'simple_program1',
argument_position => 1,
argument_name
![Пример(уточнение фактических параметров вызова программы) BEGIN DBMS_SCHEDULER.DEFINE_PROGRAM_ARGUMENT ( program_name => 'simple_program1', argument_position](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-16.jpg)
=> 'DELTA',
argument_type => 'NUMBER'
) ;
END;
/
BEGIN DBMS_SCHEDULER.ENABLE ( 'simple_program1' ); END
Слайд 18Пример(уточнение фактических параметров вызова программы)
BEGIN
DBMS_SCHEDULER.DEFINE_PROGRAM_ARGUMENT
( program_name => 'simple_program1',
argument_position => 1,
argument_name
![Пример(уточнение фактических параметров вызова программы) BEGIN DBMS_SCHEDULER.DEFINE_PROGRAM_ARGUMENT ( program_name => 'simple_program1', argument_position](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-17.jpg)
=> 'DELTA',
argument_type => 'NUMBER',
default_value => 8
) ;
END;
/
BEGIN DBMS_SCHEDULER.ENABLE ( 'simple_program1' ); END
Слайд 19Пример (создание расписания)
BEGIN
DBMS_SCHEDULER.CREATE_SCHEDULE
( schedule_name => 'simple_schedule',
start_date => SYSTIMESTAMP,
repeat_interval
![Пример (создание расписания) BEGIN DBMS_SCHEDULER.CREATE_SCHEDULE ( schedule_name => 'simple_schedule', start_date => SYSTIMESTAMP,](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-18.jpg)
=> 'FREQ=WEEKLY; BYDAY=MON, TUE, WED, THU, FRI',
end_date => SYSTIMESTAMP + INTERVAL '1' MONTH
) ;
END;
Слайд 20Информация о расписаниях
Информация об имеющихся расписаниях для планировщика находится в представлениях словаря:
![Информация о расписаниях Информация об имеющихся расписаниях для планировщика находится в представлениях словаря: DBA/ALL/USER_SCHEDULER_SCHEDULES](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-19.jpg)
DBA/ALL/USER_SCHEDULER_SCHEDULES
Слайд 21Пример (скомпонованное задание для программы без параметров)
BEGIN
DBMS_SCHEDULER.CREATE_JOB
( job_name => 'compound_job',
![Пример (скомпонованное задание для программы без параметров) BEGIN DBMS_SCHEDULER.CREATE_JOB ( job_name =>](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-20.jpg)
program_name => 'simple_program',
schedule_name => 'simple_schedule',
enabled => TRUE
);
END;
Слайд 22Пример (скомпонованное задание для программы с параметрами)
BEGIN
DBMS_SCHEDULER.CREATE_JOB
( job_name => 'compound_job1',
![Пример (скомпонованное задание для программы с параметрами) BEGIN DBMS_SCHEDULER.CREATE_JOB ( job_name =>](/_ipx/f_webp&q_80&fit_contain&s_1440x1080/imagesDir/jpg/1152421/slide-21.jpg)
program_name => 'simple_program1',
schedule_name => 'simple_schedule',
enabled => FALSE
);
END;
/
BEGIN
DBMS_SCHEDULER.SET_JOB_ANYDATA_VALUE
( job_name => 'compound_job1',
argument_name => 'DELTA',
argument_value => ANYDATA.CONVERTNUMBER ( 3 )
)
END;
/
BEGIN DBMS_SCHEDULER.ENABLE ( 'compound_job1' ); END