Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Аварда с точки зрения чайника.doc
Скачиваний:
19
Добавлен:
06.03.2016
Размер:
274.94 Кб
Скачать

Глава 1. Это нельзя понять, это нужно запомнить.

IbExpert. Хранимые процедуры.

IBExpert мощный инструмент разработки хранимых процедур, и не только их. Очень мощный. Иногда – слишком мощный. Для работы очень полезно его мощность ограничить разумными пределами. Поэтому три совета.

Первый – сразу уберите флажок «Всегда приводить имена объектов к верхнему регистру».

Второй – в настройках редактора ХП и триггеров отключите «ленивый» режим.

Третий – если редактор Вам что-то подсказывает не нажимайте enter или пробел, вводите слово до конца, нажмите esc, затем пишите дальше.

Соблюдение этих советов позволит Вам избежать проблем с прыганием регистров символов. Точнее сказать – избежать систематического повторения этих проблем.

К базе надо подключаться от TWUSER, если Вы читали документацию, то это понятно. Но, допустим, что Вы, по привычке, подключились от SYSDBA и разработали великолепную ХП. Не расстраивайтесь, просто в закладке “права” у этой ХП поставьте шарик в Execute у TWUSERа. А потом, все-таки, переставьте свои подключения на TWUSER.

Всегда пишите имена переменных, имена таблиц, имена полей таблиц, алиасы только в нижнем регистре, а ключевые слова в верхнем. После написания просмотрите текст, IBExpert мог поменять регистры, не удивляйтесь, Вам же говорили, что это очень мощный инструмент. После выгрузки ХП полезно посмотреть, на предмет соответствия регистров, соответствующий файл. Вы конечно будете смеяться, но это иногда позволяет обнаружить, что в выгруженной ХП регистры не везде те, на которые Вы рассчитывали.

В

CREATE PROCEDURE MY_PROCEDURE(

IDDOC INTEGER,

IDUSER INTEGER)

RETURNS (

RESULT INTEGER,

MSG VARCHAR(255))

сегда пишите имена параметров и переменных только в нижнем регистре. Кроме объявления входных и выходных параметров в шапке процедуры.

н

DECLARE VARIABLE result INTEGER;

DECLARE VARIABLE msg VARCHAR(80);

о:

и

result = 6;

msg = '';

now_time = CAST('NOW' AS DATE);

now_date = extractdate(now_time);

в тексте процедуры:

Почему это надо делать так? Если Вы найдете ответ на этот вопрос, отправьте, пожалуйста, ответ мне на адрес iannenkov@ansoft.ru.

Перед и после знаков операций должны быть пробелы. Пробелов должно быть ровно по одному. Два пробела подряд это ошибка. Почему это так? Если Вы найдете ответ на этот вопрос, напишите мне, пожалуйста. Да, не каждый тимлидер обнаружит эту ошибку. Да, не каждый сочтет это ошибкой. Ну, что сказать, мне с тимлидером повезло.

Ключевые слова надо отделять тоже, ровно одним пробелом. После знаков препинания надо ставить пробел, один. И все об этом. Ну а если Вы узнаете почему, то…, ну Вы меня понимаете.

Если SELECT помещается в одну строку, то все в порядке. Если SELECT в одну строку не помещается, то начинайте с новой строки ВСЕ его ключевые слова.

Т

SELECT koef_def_ed_izm, prec_def_ed_izm FROM dll_get_default_ed_izm (:eid1)

WHERE prec_def_ed_izm = 0

INTO :koef_def_ed_izm, :prec_def_ed_izm;

ак не правильно:

Правильно так:

SELECT koef_def_ed_izm, prec_def_ed_izm

FROM dll_get_default_ed_izm (:eid1)

WHERE prec_def_ed_izm = 0

INTO :koef_def_ed_izm, :prec_def_ed_izm;

Е

SELECT koef_def_ed_izm, prec_def_ed_izm FROM dll_get_default_ed_izm (:eid1)

INTO :koef_def_ed_izm, :prec_def_ed_izm;

динственное, известное мне исключение из этого правила, это переносINTO, вот так тоже правильно:

Хотя, я бы предложил, для поддержания единства стиля, не злоцпотреблять этим вариантом написания.

Отступ ключевых слов от SELECT – два пробела.

Все ваши связи должны быть левыми, это легко запомнить, но не всем легко принять. Поверьте, левые связи не портят Ваш моральный облик, наоборот, улучшают репутацию. Если Вы пишете запрос к нескольким таблицам то всегда связывайте их с помощью LEFT JOIN.

Т

SELECT SUM(enum1 * nnum2) /* брутто */, SUM(enum1 * nnum3) /* нетто */

FROM lin, nab

WHERE eiddoc = :iddoc AND nidlib = eid1 AND

nconcept = 100800 AND nid1 = eid2

INTO :calc1, :calc2;

ак плохо:

Т

SELECT SUM(enum1 * nnum2) /* брутто */, SUM(enum1 * nnum3) /* нетто */

FROM lin

LEFT JOIN nab ON nidlib = eid1 AND

nconcept = 100800 AND nid1 = eid2

WHERE eiddoc = :iddoc

INTO :calc1, :calc2;

ак хорошо:

С левыми связями закономерно возникают два вопроса. Первое – что делать, если по связи обязательно должно что-то быть? В этом случае можно использовать проверку на NULL.

Н

WHERE eiddoc = :iddoc AND nidlib IS NOT NULL

апример,WHERE в предыдущем примере можно переписать так:

Второе – куда воткнуть LEFT JOIN? Однозначного ответа на этот вопрос у меня нет. В существующих ХП мне попадались разные варианты написания.

Б

FROM lin sb

LEFT JOIN lin rn ON sb.eid1 = rn.eiddoc

LEFT JOIN xecint ON rn.eid1 = owner

ывает (AE_SEL_SERTIF_TOVAR) так:

Б

FROM doc LEFT JOIN lin ON lin.eiddoc = doc.did

ывает (A_6001_TRANZIT_A_REFRESH_6951) так:

*

FROM lin vz

LEFT JOIN rma ON rid = vz.eint2 AND rconcept = 24021

LEFT JOIN lin r ON r.eid = reid2

)Бывает (A_6002_KORREKT_PODTVERDIT) так:

А

FROM find_lins(:ieid1, :ieid2, :ieid3, :ieid4, :ieid5, :ieid6) fl

LEFT JOIN

find_docs_did

(fl.eiddoc,

:idconcept, :idstate, :idrange, :idid1, :idid2, :idid3, :idid4,

:idid5, :idid6, :idid7, :idid8, :idid9, :idid10,

:ibdate1, :iedate1, :idauthor, :id_user, :in_conf, :id_zone) fdd

ON fdd.did = fl.eiddoc

вот еще интереснее (FIND_DOCS_LIN_G):

Наиболее распространен вариант, когда все LEFT JOIN пишутся с новой строки, и располагаются на одном уровне с именем таблицы в предложении FROM. Все написанное мной в таком стиле принималось без замечаний об ошибке. Пример с этим вариантом помечен *). Лучше будет признать такой вариант единственно правильным, и использовать только его. Все остальные варианты не надо использовать, если к этому не будет какой-нибудь очень-очень веской причины.

Для уточнения принадлежности поля в запросе всегда используйте алиас, и никогда - имя таблицы.

Н

SELECT FIRST 1 d2.d2id

FROM lnk i

LEFT JOIN doc d ON d.did = i.idid1 AND d.dstate = 20208

LEFT JOIN doc2 d2 ON d2.d2id = i.idid1 AND d2.d2id4 = 78523

WHERE i.idid2 = :iddoc AND d.did IS NOT NULL AND

d2.d2id IS NOT NULL

INTO :id_6101_b;

апример, если запрос:

изменить так:

SELECT FIRST 1 doc2.d2id

FROM lnk

LEFT JOIN doc ON doc.did = lnk.idid1 AND doc.dstate = 20208

LEFT JOIN doc2 ON doc2.d2id = lnk.idid1 AND doc2.d2id4 = 78523

WHERE lnk.idid2 = :iddoc AND doc.did IS NOT NULL AND

doc2.d2id IS NOT NULL

INTO :id_6101_b;

то это будет ошибка.

О комментариях в ХП.

Как писать стандартную шапку-комментарий очень хорошо описано в “Требования к разрабатываемому ПО”, за одним, известным мне, исключением: и входные и выходные параметры и их описания должны располагаться на одном уровне.

Вот так:

* INPUT PARAMS:

* IDDOC ID документа

* IDUSER ID пользователя

* DID1 ID контрагента документа Расходная накладная

*

* OUTPUT PARAMS:

* RESULT if IsBitSet(Result, 0) then Commit

* else Rollback;

* if IsBitSet(Result, 1) then Inf(Msg);

* if IsBitSet(Result, 2) then RefreshDoc;

* if IsBitSet(Result, 3) then CloseDoc;

* MSG Сообщение

* IDSKID ID выданной скидки

Н

* INPUT PARAMS:

* IDDOC ID документа

* IDUSER ID пользователя

* DID1 ID контрагента документа Расходная накладная

*

* OUTPUT PARAMS:

* RESULT if IsBitSet(Result, 0) then Commit

* else Rollback;

* if IsBitSet(Result, 1) then Inf(Msg);

* if IsBitSet(Result, 2) then RefreshDoc;

* if IsBitSet(Result, 3) then CloseDoc;

* MSG Сообщение

* IDSKID ID выданной скидки

о не так:

- Комментарии в ХП всегда начинайте с заглавной буквы.

- Комментарии всегда пишите в /* */, не используйте комментарии с двух минусов (--).

- В комментарии после /*, и перед */должен быть пробел, причем один.

- В комментариях хп использовать инфинитив или герундий.

Вы поняли последнее замечание? Вот и я его тоже не сразу. Оно не мое, оно от моего тимлидера. Ну, если старшина сказал, что бурундук – птичка, то никаких тебе зверьков. На самом деле все очень просто, не пишите, например “создадим документ”, пишите “создать документ” или “создание документа”.

Инфинитив, (неопределенная форма), одна из неличных форм глагола, близкая к отглагольному имени.

Герундий, лат., граммат., форма латинского глагола, соответствующая причастию.

<<C> Энциклопедия “Кругосвет”>

Используйте уже разработанные ХП. Используйте их всегда, когда это возможно. Используйте их во всех смыслах, и как образец, и для вызова. При выполнении этого совета возникает две проблемы. Первая – как узнать, что нужная Вам процедура имеется в базе и вторая – как ее(процедуру) найти. Для решение обеих этих проблем в IBExpert есть прекрасное средство ALT+SHIFT+F - поиск в метаданных, ищет по ключевому слову. Так как в процедуре обязательно комментируется назначение(идея) процедуры, то найти можно практически все, что нужно.

И последнее по этой теме. Не пересылайте текст ХП по Skype или ISQ или тому подобное. Разве что Вы хотите повеселить адресата пересылки. Текст на выходе получается, как правило, веселый, но работать с ним - не самое большое удовольствие.