Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "Базы";
Текущий архив: 2005.07.11;
Скачать: [xml.tar.bz2];

Вниз

Автоматическая номерация документов   Найти похожие ветки 

 
Ярослав   (2005-05-31 08:21) [0]

Подскажите как автоматически назначать номера документов, т.е. записям БД. Они могут состоять как только из цифр, так и смешанные, т.е. буквенно цифровые, но это не есть особая проблемма, как сделать так чтобы они были уникальные и монотонно возрастающие.
Например когда два пользователя одновременно создают записи в одной таблице, чтобы им не назначилось одинакового номера. И если один из пользователей создовал документ и передумал, а номер документу был уже назначен, то другому пользователю был бы назначен это номер, т.е. небыло разрывов в нумерации.
Может есть какие нибудь статейки по этому поводу, поделитесь ссылками.


 
Danilka ©   (2005-05-31 08:40) [1]

Самый простой способ - формировать номер триггером, в момент записи документа в базу.


 
Тучудище   (2005-05-31 08:48) [2]

Имхо на счет разрывов нумерации проблема актуальная по сей день...


 
DenK_vrtz ©   (2005-05-31 09:04) [3]

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

эта проблема уже давно решена, но каждый решает ее своим способом :)


 
Anatoly Podgoretsky ©   (2005-05-31 09:07) [4]

Что бы не было разрывов в нумерации надо запретить изменение и удаление.


 
Ярослав   (2005-05-31 09:17) [5]

Danilka ©   (31.05.05 08:40) [1]
А два триггера не могут одновременно сработать?

>> DenK_vrtz ©   (31.05.05 09:04) [3]
А можно поинтересоваться как...

Anatoly Podgoretsky ©   (31.05.05 09:07) [4]
Ну с запретом на удаление то все ясно, а изменение то зачем запрещать?

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


 
msguns ©   (2005-05-31 09:17) [6]

№ документа состоит из 2-х частей: числовая и символьная.
Числовой № получается автоинкрементом, символьная часть вводится ручками.
Для униакльности создается индекс
Числовой номер "вытягивается с сервера на клиент, но может корректиться юзером перед вставкой. Вариант Danilka ©   (31.05.05 08:40) [1] не советую категорически, т.к. юзер не видит № при добавлении документа, а сие не есть гуд (очередной холивар ?)


 
Anatoly Podgoretsky ©   (2005-05-31 09:22) [7]

Ярослав   (31.05.05 09:17) [5]
Имеется ввиду изменение номера, если мы имеем его, то имеем и дыру, кроме этого еще имеем и подделку.


 
Ярослав   (2005-05-31 09:28) [8]

msguns ©   (31.05.05 09:17) [6]
Это все хорошо, но веть тогда о монотонности можно забыть ведь автоинкремент будет всегда новый, а она монотонность нужна бывает, иначе бы я о ней и не спрашивал, например номера приказов на предприятии как правило по порядку идут, да и много других таких документов.
А то что не видно номера в момент добавления так это не беда, в MS SQL его и так не видно... Да и ползователь готовя документ не знает о его будующем номере, да как правило и не надо ему его знать.
Но меня интересует могут ли одновременно сработать на сервере две ХП или триггера и назначить одинаковые номера?


 
Sergey13 ©   (2005-05-31 09:28) [9]

А по мне так вариант Danilka ©   (31.05.05 08:40) [1] наиболее приемлем. Нафига тот номер узеру до записи?


 
Anatoly Podgoretsky ©   (2005-05-31 09:29) [10]

Ярослав   (31.05.05 09:28) [8]
Считай что они работают одновременно, поэтому могут если сделаешь неправильно.


 
Sergey13 ©   (2005-05-31 09:34) [11]

2 [8] Ярослав   (31.05.05 09:28)
Во первых срабатывать будут не две ХП или триггера, а один тригер 2 раза. Кроме того есть еще транзакции и ограничения. Это (при правильном применении) практически непробиваемая защита.
Во вторых, я бы все таки посоветовал разнести номера документов и их ИДшники.


 
msguns ©   (2005-05-31 09:34) [12]

>Ярослав   (31.05.05 09:28) [8]
>Но меня интересует могут ли одновременно сработать на сервере две ХП или триггера и назначить одинаковые номера?

1.Одновременно две ХП (и просто 2 запроса) на сервере не работют.
2. Для того и придуман автоинкремент, чтобы номера не повторялись.
3. Для "непрерывности" автоинкремент не походит, как и вся описанная технология. Необходимо делать самому автонумерацию (через спец. таблицу) для каждого типа документов.
4. А зачем именно непрерывность ?


 
ANB ©   (2005-05-31 09:39) [13]


> Ярослав   (31.05.05 09:28) [8]
- предлагаю вариант для приказов :
- В момент создания документа присваиваем ему только ИД, а номер оставляем Null.
- Когда пользователь документ полностью оформит, он отправляет его на регистрацию. Журнал регистрации можно оформить в виде отдельной таблички с автоинкрементом. Автоинкремент, если его не дергать спец.процедурами, более - менее гарантирует уникальность, а монотонность ты обеспечиваешь явной операцией регистрации и проверками до вставки.
- С момента регистрации запретить пользователю удалять документ. И вообще не разрешать менять номер ручками.
Все имхо.


 
Ярослав   (2005-05-31 09:42) [14]

>> Anatoly Podgoretsky ©   (31.05.05 09:29) [10]
А как правильно сделать?


 
Anatoly Podgoretsky ©   (2005-05-31 09:56) [15]

Ну например как в 13, естественно на поле наложить ограничение уникальности. Вместо удалений документа использовать понятие аннулирование, с указанием причины. Дырок не будет, поскольку документы не удаляются, номер не изменяется. Требуемое изменение номера делается через анулирование и создание нового документа. В MSSQL есть много механизмов генерации "номеров", identity, тригера, хранимые процедуры.
Номер естественно присваивается только при регистрации.


 
Nikolay M. ©   (2005-05-31 10:00) [16]

Один из вариантов: придумать алгоритм, который на основе ПК-Identity-поля и, возможно, некоторых других полей таблицы (например, дата-время создания документа, его тип, юзер и тд) формирует буквенно-цифровой код. Алгоритм реализовать в функции и подставить вызов этой ф-ции в вычисляемое поле таблицы. Если номер документа нужно видеть сразу до момента физической вставки записи, такое решение будет довольно геморойным.


 
DenK_vrtz ©   (2005-05-31 10:02) [17]

Еще один "древний" способ.

Имеем уникальный индекс по номеру документа.
При вставке данных таблица блокируется, ищется максимальное значение номера документа, значение увеличивается на единицу. После вставки блокировка таблицы снимается.
У способа есть как свои плюсы, так и минусы.

Либо играть со спец. таблицей.


 
ANB ©   (2005-05-31 10:22) [18]


> DenK_vrtz ©   (31.05.05 10:02) [17]
- положим, автоинкремент в мсскуле практически заменяет сиквенсы оракла. Имхо, их таки проще всего юзать. И быстрее, чем блокировка. Я блокировку только для DBF юзал, в клиппере, но там другого способа не было.


 
Anatoly Podgoretsky ©   (2005-05-31 10:29) [19]

DenK_vrtz ©   (31.05.05 10:02) [17]
И идем вешаться.


 
Petr V. Abramov ©   (2005-05-31 15:10) [20]

> msguns ©   (31.05.05 09:17) [6]
> очередной холивар ?
 Да :)
> Числовой № получается автоинкрементом
 Не стоит. Откатится транзакция по каким-либо причинам, и дырка готова


 
msguns ©   (2005-05-31 15:27) [21]

>Petr V. Abramov ©   (31.05.05 15:10) [20]
>> очередной холивар ?
> Да :)

Ща.. шаблю прадедову возьму.. ;)

>Не стоит. Откатится транзакция по каким-либо причинам, и дырка готова

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

Строить же специально какие-то таблицы по крайней мере нерационально, т.к. придется учитывать ВСЕ ВИДЫ документов, а это не всегда удобно и даже возможно. Написать же запрос (ХП), который будет резервировать № для указанного вида документа, причем с учетом возобновления нумерации с начала года, не проблема. Конфликт же уникальности опять же легко блокируется предваряющей перед вставку проверкой.

(Шаблю зачехлил, достал щит +6 к интеллекту ;))


 
msguns ©   (2005-05-31 15:29) [22]

Т.е. я хочу сказать, что, конечно, не автоинкремент ;))


 
Нулевой ©   (2005-05-31 15:36) [23]

Я делал так:
таблица 2 поля: 1-номер док., 2-год (для того чтобы год начинать с документа № 1,... новый год опять 1)
Start транзакция
блокировка таблицы
Update записи
ОК - Commit
иначе RollBack
транзакция короткая
полученный номер присваиваю номеру док. в другой табл. имеющей свой отдельный ID записи.
работает 2-3 пользователя введено 700 записей без проблем пока,
без разрывов.


 
Sergey13 ©   (2005-05-31 15:39) [24]

2[23] Нулевой ©   (31.05.05 15:36)
>полученный номер присваиваю номеру док. в другой табл
А если это отменить?


 
Нулевой ©   (2005-05-31 15:42) [25]

Это уже не отменить так как все связано с кнопкой Сохранить или ОК или Добавить и т.д., отменить можно только Update в первой таблице.


 
Нулевой ©   (2005-05-31 15:42) [26]

Сняв естественно блокир.


 
Sergey13 ©   (2005-05-31 15:48) [27]

2[25] Нулевой ©   (31.05.05 15:42)
>Это уже не отменить так как все связано с кнопкой
Связь с кнопкой еще не гарантирует невозможность отмены (хотя бы аварийной) если внутри транзакции только апдейт первой таблицы.


 
msguns ©   (2005-05-31 15:55) [28]

>Нулевой ©   (31.05.05 15:36) [23]
>Я делал так:
таблица 2 поля: 1-номер док., 2-год (для того чтобы год начинать с документа № 1,... новый год опять 1)
Start транзакция
блокировка таблицы
Update записи
ОК - Commit
иначе RollBack
транзакция короткая
полученный номер присваиваю номеру док. в другой табл. имеющей свой отдельный ID записи.
работает 2-3 пользователя введено 700 записей без проблем пока,
без разрывов.

Круто.
Вопросы тов.лектору:
1. А если надо номер писать вот так: 2005/10 или 10/2005 или 10-05 и т.д. (что, какмправило и наблюдается в реальной жизни) ?
2. Что такое "Update записи" - это когда юзер получает формочку и срочно бежит в тулет до обеда ? Или когда он уже нажал кнопульку ? В последнем случае номера, очевидно, он не еще знает.
Если второе, то как быть с такой ситуевиной. Менагер по продажам по телефону выписывает счет (или сразу накладную), в котором надо заполнить 30 полей, а его заказчик спрашивает № чтобы бежать в банк платить. Что ему скажет менагер,- мол, обожди, паря, щас тут у меня стартанет транзакция, сработает триггерец и, ежели не будет конфликта, то я скажу тебе номер ?
3. Если есть другая таблица только для номеров, то зачем тогда в первой поле "Год" ?
4. 2-3 пользователя весьма маловероятнисто начнут ввод документов одновременно (в интервале 1-2 сек, которого вполне хватит серверу, чтобы "зарезервировать" № даже если он не autoinc
. Так что не очень убедительно.
5. Как решен вопрос о раздельной нумерации разных видов документов ?
6. Можно ли поменять № в документе ? А если нет, то как быть, если это все же необходимо ? Удалять старый и перезаводить по новому ?
7. Чем же так страшны разрывы ?


 
Anatoly Podgoretsky ©   (2005-05-31 15:58) [29]

Они больны головой.


 
Нулевой ©   (2005-05-31 17:21) [30]


> msguns ©   (31.05.05 15:55) [28]

1. Без проблем
2. именно второе, ситуация со счетом не канает, у меня другая ситуация.
3. так проще.
5. раздельная нумерация не нужна.
6. можно, без проблем (во второй таблице)
7. не понял?
Все написано о лично моей задаче, так что нечего пинать.
Из всего никто автору ничего не предложил, кроме как использовать Autoinc. Но он не подходит, как и мне не подходит.
100% даст разрыв в номерах, мне это важней всего (верной для пользователя это было под №1).


> Anatoly Podgoretsky ©   (31.05.05 15:58) [29]

Чем хамить, что-нибудь предложите автору, причем бесплатно!


 
Polevi ©   (2005-05-31 17:58) [31]

для номеров документов непрерывность не нужна
для счетов фактур см [13] + возможность всеже редактировать этот номер, для того чтобы бухгалтер мог при желании сделать "дробный" номер счета-фактуры - 1234/5 - без этого иногда никак


 
Anatoly Podgoretsky ©   (2005-05-31 19:15) [32]

Нулевой ©   (31.05.05 17:21) [30]
У тебя есть проблемы, хочешь поговорить?


 
Fay ©   (2005-05-31 20:22) [33]

Polevi ©   (31.05.05 17:58) [31]
>> для номеров документов непрерывность не нужна
Но всё меняется, когда приходят ОНИ - заказчики, считающие иначе!
8)


 
anatolyk   (2005-05-31 21:46) [34]

Я попытался сделать что-то вроде этого (MSSQL):

CREATE PROCEDURE [sp_GetFirstEmptyCodeByRecid]
@Recid Int
AS
select top 1 (Код+1)
from dbo.СтрокиПрайсЛистов T1
where (p_recid = @recid) and
((select top 1 Код from dbo.СтрокиПрайсЛистов T2 where (p_recid = @recid) and (код > T1.Код) order by код) - код) > 1
order by код
GO
где Код-понятно,
p_recid - id прайс-листа (с которым связаны СтрокиПрайсЛистов)

Не идеально, но работает.


 
Johnmen ©   (2005-06-01 09:17) [35]

Вот тут много чего наговорили, только создаётся впечатление, что многие пытаются совместить две различные сущности - суррогатный ключ, по большому счёту никакого отношения к "жизненному" номеру документа не имеющий, и собственно сам этот номер.
Не стОит этого делать.


 
ANB ©   (2005-06-01 09:21) [36]


> Johnmen ©   (01.06.05 09:17) [35]
- смотри мой пост [13]. Я там разношу понятия ключа и номера. Имхо, никто не давал советов объединять эти понятия. Просто нужна уникальная нумерация без дырок. Проблема старая и по человечески - плохо решаемая. Например, мой способ не очень подходит для счетов (когда нужно быстро сообщить клиенту номер). На одной из работ решили проблему просто - забили на дырки.


 
Johnmen ©   (2005-06-01 09:32) [37]

>ANB ©   (01.06.05 09:21) [36]

Не стОило так однозначно относить себя ко "многим". :)


 
ANB ©   (2005-06-01 09:37) [38]


> Не стОило так однозначно относить себя ко "многим". :)
- да вроде ветку посмотрел - никто и не советует номер документа за суррогат держать. Имхо. Може чего и не углядел. А вот сам я раз на грабли наступил капитально. До сих пор старый проект с такими ключами. Ух и задрался я потом перебивать ключи при изменении даты документа. Молодой был, глупый, теорию не читал, да ее тогда толком и не было, как не было автоинкрементов и сиквенсов в Clipper.


 
Anatoly Podgoretsky ©   (2005-06-01 09:43) [39]

Johnmen ©   (01.06.05 09:17) [35]
Вот тут много чего наговорили, только создаётся впечатление, что многие пытаются совместить две различные сущности - суррогатный ключ, по большому счёту никакого отношения к "жизненному" номеру документа не имеющий, и собственно сам этот номер.

Сообственно и сам номер документа - это не номер, а шифр/код документа. Номером называют по привычке и путают еще и с идентификатором записи.


 
Тучудище   (2005-06-01 10:04) [40]

Давайие посмотрим в сторону 1Ц... что же мы там видим???? А видим мы там вот что....
1) Имеется табличка (1SDNLOCK.DBF для DBF) или (_1SDNLOCK для MSSQL)
2) В этой табличке имеется всего 2 поля
  а) тип документа
  б) номер документа
3) При создании пользователем нового документа формируется новый номер и добавляется в эту табличку
4) В случает отмены ввода документа, удалении документа номер так же изымается из вышеупомянутой таблицы
5) Большой минус всего этого в следующем:
  Пусть пользователь А открыл документ и получил номер для него
  Пусть пользователь Б открыл документ и получил номер для него
  Пользователь Б сохранил документ
  Пользователь А не сохранил документ
  Номер пользователя Б стал последним
  Когда номер пользователя А просто исчез
  Вот пробел в нумерации готов
Это что касается присвоения номера в момент открытия нового документа.... хотя на практике 1Ц-шная система сбоя не давала(я не видел такого сопровождаю ее уже около 5 лет)
Как бы сделал я:
1) Не стал бы использовать генераторы ни в коем случае
2) Не стал бы использовать autoincrement котегорично
3) Далее идем по разветвлению,
   a)если номер документа требуется в момент открытия документа(чем черт не шутит)... то ввел бы доп таблицу и последовал бы по
пути 1Ц
   б)если номер присваивается после вставки документа, что менее капризно и риск пробелов в нумерации более менее ниже чем у варианта "а" то создал бы механизм который присваивает новый номер документа в момент вставки нового документа в БД
   в)проводил присвоение нумерации документов в конец дня(идеально), но фиг кто даст такое сделать! :-) а жаль! :-)



Страницы: 1 2 вся ветка

Форум: "Базы";
Текущий архив: 2005.07.11;
Скачать: [xml.tar.bz2];

Наверх





Память: 0.58 MB
Время: 0.043 c
3-1116857149
Николай
2005-05-23 18:05
2005.07.11
Два DblookupCombobox - последвательно.


1-1118668995
mmms
2005-06-13 17:23
2005.07.11
Компанент кнопки-2


3-1117285895
Darkmaster
2005-05-28 17:11
2005.07.11
XML и сохранение базы


1-1119447563
Максим
2005-06-22 17:39
2005.07.11
ListBox, GetShortPathName, exe-file


5-1089704943
doma
2004-07-13 11:49
2005.07.11
Сужение списка property в наследнике





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский