|
|
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
(powerBuilder 9.01 + msSqlServer 2000) У нас на фирме написана библиотека, аналогичная PFC.. и вот, хочу обсудить одну довольно общую проблему : ввод документа, состоящего из нескольких окон, связанных master-detail (один-ко-многим). Например, счёт-фактура может состоять из 1. заголовка 2. списка позиций 3. перечня дополнительных свойств для каждой позиции Пользователь должен иметь возможность сначала ввести документ целиком (или даже ввести несколько документов), и только потом -- сохранить (или отменить ввод). Собственно проблема: чтобы привязать строки подчинённых окон к главным, необходимо знать значение Primary Key главного окна (и это до сохранения!). У нас на фирме было (давно) принято такое решение: отказаться от автогенерации Primary Key и генерировать значение уникального поля до вставки в таблицу (пересечения с данными, вводимыми другими пользователями, исключаются использованием при генерации функции SQL-сервера, возвращающей номер соединения, @@uuid) , а после ввода уже спокойно сохранять. Коллизии такой генерации PK пока (за три-четыре года эксплуатации) не встречались. Вопрос: 1. какие ещё алгоритмы ввода многооконных документов предложите? 2. как это реализовано в PFC (в этой библиотеке тоже ведь есть службы связи окон (спрашиваю потому, что сам я ещё не пользовался этой библиотекой) 3. какие есть недостатки предложенного здесь метода ввода документов -- с помощью генерации первичного ключа до вставки? (подробности генерации там же . спасибо! ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 24.04.2005, 16:13 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Может это и неправильно, но последние десятилетия мои приложения, в основном, получают ID до формирования новой записи на клиенте. На псевдокоде - of_GetId () ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 24.04.2005, 17:30 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Sorry, не туда нажал Продолжу На псевдоколе: Код: plaintext 1. 2. 3. 4. Вот и все, собственно. Да, чуть не забыл. Для MS SQL был разработан механизм, реализующий аналог сиквенса в Oracle. Разумеется, в БД уникальность первичных ключей обеспечивается по всей БД, т.е. используется только один сиквенс, кроме каких-то специальных случаев ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 24.04.2005, 17:37 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Все-таки забыл :-) Разумеется, что функция of_GetId() обращается за ID к серверу. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 24.04.2005, 17:38 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Можно завести еще одно поле для связи в DataWindow, а поле PK не трогать. Внутри DataWindow осуществлять связь master-detail по значениям второго поля, используя для новых записей отрицательную нумерацию (в базу естественно ничего не сохраняя из этого второго поля). А при SELECT'е заполнять его значениями из PK, в этом случае никаких коллизий произойти просто не может. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 24.04.2005, 21:55 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Гм, у нас проблема была решена другим способом. При открытии окна документа в базу уже добавляется запись со всеми начальными значениями и сгенеренным идентификатором. Единственное запись помегена как "неактуальная". Соответственно при вставке перечня идентификатор известен, а при нажатии на клиенте кнопки OK идет обновление существующей записи введенными данными и изменение состояния записи на актуальное. Если "OK" не нажата, то в базе остается "паразитная" неактуальная запись. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 25.04.2005, 09:41 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Локшин МаркМожно завести еще одно поле для связи в DataWindow, а поле PK не трогать. Внутри DataWindow осуществлять связь master-detail по значениям второго поля, используя для новых записей отрицательную нумерацию (в базу естественно ничего не сохраняя из этого второго поля). А при SELECT'е заполнять его значениями из PK, в этом случае никаких коллизий произойти просто не может. Почти так же. Новых полей не использую - пишу отрицательные значения как раз в поле PK - а в событии UpdateStart() отрицательные значения заменяю на уникальные из SEQUENS-последовательности (Oracle) ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 25.04.2005, 09:43 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
gzПочти так же. Новых полей не использую - пишу отрицательные значения как раз в поле PK - а в событии UpdateStart() отрицательные значения заменяю на уникальные из SEQUENS-последовательности (Oracle) Можно и так, но шанс словить ошибку при кодировании таким образом выше. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 25.04.2005, 13:06 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
понятно, спасибо за примеры. а чем так генерация первичного ключа на сервере не нравится? Наши утверждают (я сам не пробовал), что если пользоваться генерацией ключа на сервере (сиквенсы, identity и что там в Sybase-вский СУБД?), то может измениться порядок строк после insert\retrieve, правда, я не понял, почему. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 25.04.2005, 13:08 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Локшин МаркМожно и так, но шанс словить ошибку при кодировании таким образом выше. А каким образом ? Сколько лет ловим, пока сетка пустая. Если перестраховываться, то уж в меру ... ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 25.04.2005, 13:20 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
gzА каким образом ? Сколько лет ловим, пока сетка пустая. Если перестраховываться, то уж в меру ... Допустим нужно будет откатиться, тогда это нужно тоже нужно учитывать при кодировании. Имееются ввиду ошибки программиста при реализации механизма на PB. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 25.04.2005, 13:35 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Локшин МаркДопустим нужно будет откатиться, тогда это нужно тоже нужно учитывать при кодировании. Имееются ввиду ошибки программиста при реализации механизма на PB. Что-й-то плохо соображаю. Вроде бы, и при откатах работает. Может быть, имеете ввиду просто "кривые ручки" программиста ? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 25.04.2005, 13:49 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
savosin_sergeyпонятно, спасибо за примеры. а чем так генерация первичного ключа на сервере не нравится? Наши утверждают (я сам не пробовал), что если пользоваться генерацией ключа на сервере (сиквенсы, identity и что там в Sybase-вский СУБД?), то может измениться порядок строк после insert\retrieve, правда, я не понял, почему. Смотря в какой Sybase СУБД. Если в ASA 9, то просто пишем в клиенте <SELECT GET_IDENTITY('TableName') >, получаем собственный зарезервированный ID, автоматом увеличивая инкримент в таблице без организации транзакции и вообще больше ни о чем не думаем :) ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 25.04.2005, 13:50 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Локшин Марк gzА каким образом ? Сколько лет ловим, пока сетка пустая. Если перестраховываться, то уж в меру ... Допустим нужно будет откатиться, тогда это нужно тоже нужно учитывать при кодировании. Имееются ввиду ошибки программиста при реализации механизма на PB. Откаты на SEQUENS и IDENTITY не влияют, так что ошибок не будет. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 25.04.2005, 13:51 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
ASCRUS Откаты на SEQUENS и IDENTITY не влияют, так что ошибок не будет. Не про те ошибки идет речь. gzМожет быть, имеете ввиду просто "кривые ручки" программиста ? Да, именно это я и пытался сказать :) Больше нюансов в реализации, а сл-но больше вероятность ошибки (программиста). ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 25.04.2005, 13:58 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Локшин Марк gzМожет быть, имеете ввиду просто "кривые ручки" программиста ? Да, именно это я и пытался сказать :) Больше нюансов в реализации, а сл-но больше вероятность ошибки (программиста). Как раз добавление в SELECT дополнительного поля (не поля базы данных + специальным образом заполняемого) и дает дополнительные навороты. Хотя, чего мы спорим ? У нас реализация совпала процентов на 90-95. Значит, "верным путем идем, товарищи" ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 25.04.2005, 14:06 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
savosin_sergeyпонятно, спасибо за примеры. а чем так генерация первичного ключа на сервере не нравится? Наши утверждают (я сам не пробовал), что если пользоваться генерацией ключа на сервере (сиквенсы, identity и что там в Sybase-вский СУБД?), то может измениться порядок строк после insert\retrieve, правда, я не понял, почему.Гм... Не понял. Порядок строк обеспечивается конструкцией ORDER BY в запросе или сортировкой на клиенте. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 25.04.2005, 14:47 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
PL99Гм... Не понял. Порядок строк обеспечивается конструкцией ORDER BY в запросе или сортировкой на клиенте. Случай из жизни. Армия. Вон, розетка - какой ток течет - постоянный или переменный ? Ответ - постоянный. Вышел товарищ. А ты, меня спрашивают - понял ? Ну, говорю, постоянный - прямая, а переменный - синусоида. Нет, говорят, вышедший товарищ имел ввиду, что постоянный - это 220 вольт не больше и не меньше. Так что PL99, не забивай себе голову, что имел ввиду товарищ ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 25.04.2005, 15:17 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
я имел ввиду порядок строк в таблице без order'а. то есть, добавили несколько новых записей, визуально они появились в конце datawindow, а после retrieve (=select col1, col2, ... from table1 where parent_id=xxx) -- некоторые записи могут своё место в DW изменить.. но я это не видел, передаю лишь слова.. и не могу понять, почему, ведь нет сортировки даже по первичному ключу.. Хотя, на мой взгляд, причины генерации первичного ключа другие (нежели простое соблюдение порядка строк в DW): 1. возможность заполнять несколько master'ов с detail'ами внутри (привязка строк в detail'е до сохранения master'а). 2. на сервере средства работы с identity (автогенератором числового первичного ключа) не понравились главному разработчику (напр., потому что реализованы кривова-то или, там, требуют вызова хранимой процедуры) Как выяснилось, у нас именно второй случай. а при вводе нового master'а происходит тихое сохранение введённых dateil'ов для строки, потерявшей фокус ввода. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 25.04.2005, 17:46 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
savosin_sergeyя имел ввиду порядок строк в таблице без order'а. то есть, добавили несколько новых записей, визуально они появились в конце datawindow, а после retrieve (=select col1, col2, ... from table1 where parent_id=xxx) -- некоторые записи могут своё место в DW изменить.. но я это не видел, передаю лишь слова.. и не могу понять, почему, ведь нет сортировки даже по первичному ключу.. Для любой реляционной операции порядок следования кортежей отношений никогда не определен. В конкретном частном случае записи по запросу Код: plaintext Или в порядке физического местоположения записей записей в таблице table1 (в зависимости от селективности условия parent_id). Но это никто и никому не обязан. Допустим, все может измениться от числа процессоров в системе savosin_sergey на сервере средства работы с identity (автогенератором числового первичного ключа) не понравились главному разработчику И какие же альтернативы? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 25.04.2005, 18:31 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
to savosin_sergey Выборка строк "без ордера". В общем-то, реляционная база не гарантирует последовательность вывода строк в порядке их ввода. Хотя некоторое подобие порядка при полупустой базе может и наблюдаться. Вопрос по сохранению сортировки при повторном вызове формы имеет иногда принципиальное значение. Можно, конечно, использовать уникальный ключ для сортировки (помучаться при этом), но лучше добавить просто поле "номер строки" в таблицу. "Тихое сохранение" - это что-то новое. Какие-то нехорошие ассоциации. Конечно, от ошибок никто не застрахован, однако, если таких ситуаций много, бежать надо скорее от таких разработчиков. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 25.04.2005, 18:34 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Локшин МаркИ какие же альтернативы? Вот алгоритм генерации нового уникального значения, применяемый у нас (в классах, работающих со связанными DW).. Правда, эта функция немного переделанная (работает лишь с одной таблицей bu_extravalues , но, жумаю, смысл будет ясен.. Переменные gnv_appl.i_step и gnv_appl.i_spid заполняются при запуске приложения. Код: plaintext 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. 21. 22. 23. 24. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 12:18 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
авторВот алгоритм генерации нового уникального значения, применяемый у нас (в классах, работающих со связанными DW).. Правда, эта функция немного переделанная (работает лишь с одной таблицей bu_extravalues, но, жумаю, смысл будет ясен.. Переменные gnv_appl.i_step и gnv_appl.i_spid заполняются при запуске приложения. И в чем же преимущества? Абсолютно не гарантируется никакой уникальности сгенерированных значений. Что, у одного пользователя не может быть несколько connect'ов к базе? Что достигается в результате такого извращения? Это если у вас главный разработчик такое пишет... ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 12:44 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
авторЧто, у одного пользователя не может быть несколько connect'ов к базе? Что достигается в результате такого извращения? Номер коннекшена (через который будет производиться insert) всегда уникальен, среди всех подключённых пользователей. У одного пользователя можут быт два коннекта, но с разными @@spid. Так что коллизий не наблюдается (уже больше трёх лет фурычит в минфине, там пользователей около 100, данные вводят человек 5) ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 13:14 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
другими словами, у SQLCA всегда один коннект, и у него есть уникальный номер на сервере (среди всез поключений к серверу). Как этот номер узнать в oracle или в sybase-вских СУБД я не знаю. в MsSqlServer это переменная @@spid ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 13:21 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
savosin_sergeyНомер коннекшена (через который будет производиться insert) всегда уникальен, среди всех подключённых пользователей. У одного пользователя можут быт два коннекта, но с разными @@spid. А если пользователь по два приложения запустит? savosin_sergeyТак что коллизий не наблюдается Это главное достоинство метода? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 13:24 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Вот наша процедура для MS/Syabse без всяких наворотов;) Код: plaintext 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. Таблица t_idgenerator имеет IDENTITY поле. Таблица t_sites используется для разделения диапазона по разным серверам. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 13:35 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
EstetsВот наша процедура для MS/Syabse без всяких наворотов;) ... Таблица t_idgenerator имеет IDENTITY поле. Таблица t_sites используется для разделения диапазона по разным серверам.Вот нечто подобное и я имел ввиду ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 13:40 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
EstetsТаблица t_idgenerator имеет IDENTITY поле. Таблица t_sites используется для разделения диапазона по разным серверам. А почему не использовать для этого identity seed? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 14:01 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Исторически сложилось ;) Вообще-то планировалось размножение баз дампами с изменением номера локального сервера. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 14:54 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Локшин МаркА если пользователь по два приложения запустит? Будет два SQLCA и два разных номера соединений Локшин МаркЭто главное достоинство метода? Это необходимое условие работы метода. 2 Estets: Estets Код: plaintext Код: plaintext Локшин МаркА почему не использовать для этого identity seed? Да на самом деле (это относится к MsSqlServer2000) можно использовать признак identity у колонки в таблице (чтобы она автоматически увеличивала значение) + функцию SCOPE_IDENTITY() -- она возвращает последнее значение identity-колонки в таблице, в которой произощёл последний insert.. я на этом сервере на форуме, посвящённом MsSqlServer-у читал всякие предложения по генерации уникальных значений.. там тоже было предложение с использованием временной таблицы и обсуждались какие-то проблемы.. /topic/103151&hl= ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 15:07 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
savosin_sergeyкакой же длины у вас ключевые поля? если шаг между серверами=10^17а если еще вспомнить что PB воспринимает не более 18 значащих разрядов, то вообще засада. и на десяток site_id может не хватить. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 15:23 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
А GUID кстати никто не пробовал использовать в качестве PK? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 15:24 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
savosin_sergeyБудет два SQLCA и два разных номера соединений А когда запустят по 4 копии, вот тут-то диапазоны и перекроются. savosin_sergeyДа на самом деле (это относится к MsSqlServer2000) можно использовать признак identity у колонки в таблице (чтобы она автоматически увеличивала значение) + функцию SCOPE_IDENTITY() -- она возвращает последнее значение identity-колонки в таблице, в которой произощёл последний insert. А чем более ранние версии SQL сервера не угодили. Вы описали принцип заполнения переменной @@IDENTITY, а она и раньше была. savosin_sergeyЭто необходимое условие работы метода. А в чем его преимущества? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 15:38 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
ЗоринАндрейА GUID кстати никто не пробовал использовать в качестве PK?Да, пробовал два раза (в двух проектах). Работает :-) ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 15:46 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Локшин Марк savosin_sergeyЭто необходимое условие работы метода.А в чем его преимущества?Старший приказал (с) :-) ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 15:50 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
PL99 ЗоринАндрейА GUID кстати никто не пробовал использовать в качестве PK?Да, пробовал два раза (в двух проектах). Работает :-) Ну их эти GUID ... попробовали в одном новом разрабатывающемся проекте ASA, потом плюнули, домен на unsigned int перевели с GLOBAL AUTOINCREMENT и решили больше никогда не связываться. Из реальных проблем - неоправданно большой размер PK и FK, неудобство ручного написания запросов (без Copy-Paste никуда), из за "скачущих" значений GUID неоптимальное хранение веток индексов в БД, из за этого проседания на join-ах при выборках, плюс еще кое какие мелкие баги самой ASA при работе с GUID, которые я им заявил, но исправить они еще не успели (например невозможность подключения таблицы удаленного сервера ASA, в которой есть GUID или выполнение SELECT * INTO Table). Единственное, где не было нареканий - так как использовалась ASA 9.0.2, то PB видел их как string и проблем в клиентской части не было. Так что я зарекся от их использования, GLOBAL AUTOINCREMENT на целых числах гораздо приятнее и привычнее получается. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 16:02 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
savosin_sergey 2 Estets: Estetsselect @id = @@identity + @site_id*10000000000000000 какой же длины у вас ключевые поля? если шаг между серверами=10^17 select @site_id=id from t_sites where is_local=1 что такое is_local=1? и где название таблицы? или у вас все таблицы получают "сквозной" идентификатор? Идентификатор numeric(18,0), Две цифры под сервер, 16 под Increment SSNNNNNNNNNNNNNNNN Таблица t_sites примерно такая: id srv_name is_local 1 'Server1' 1 1 'Server2' 0 1 'Server3' 0 Только в реальности данный механизм не понадобился ;-( Хотя были планы настроить репликацию. Угумс в этом есть своя прелесть, в какой бы таблице не находился документ, можно определить его тип по глобальному идентификатору. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 16:43 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Локшин МаркА когда запустят по 4 копии, вот тут-то диапазоны и перекроются. Да, если шаг=300 (в примере gnv_appl.i_step) и если все 100 пользователей запустят по 3-4 копии, то накроется. Хотя можно увеличить шаг до 1000... всё равно если для первичного ключа использовать integer, то 2 млрда / 1000 = 200 000 000 -- нашу систему это устраивает (максимальное наблюдаемое число проводок около 90 млн за год) Локшин МаркА чем более ранние версии SQL сервера не угодили. Вы описали принцип заполнения переменной @@IDENTITY, а она и раньше была. Так один пользователь считал @@identity (до сохранения), потом другой считал @@identity -- произойдёт совпадение. Можно считывать лишь после сохранения -- с тем, чтобы передать его подчинённым detail'ам.. Локшин МаркА в чем его преимущества? Другое преимущество: если использовать автоинкремент, то после сохранения в DW не будет значения уникального поля -- для этого надо сделать retrieve. Если записей много в таблице, то делать retrieve после каждого insert'а -- долгова-то. В этом случае придётся считывать @@identity из базы и присваивать полю DW.. ну или ещё что-нибудь придумывать.. У нас "ведущий" программер решил уникальное поле генерить на клиенте -- вот и я предложил для обсуждения его метод. На соседнем форуме (ссылка на него в начале этой темы) мне совсем другой метод предложили для ввода связанных таблиц.. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 18:30 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
savosin_sergeyДругое преимущество: если использовать автоинкремент, то после сохранения в DW не будет значения уникального поля -- для этого надо сделать retrieve. Если записей много в таблице, то делать retrieve после каждого insert'а -- долгова-то. В этом случае придётся считывать @@identity из базы и присваивать полю DW.. ну или ещё что-нибудь придумывать.. Да можно ничего не придумывать, а взять готовое ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 19:15 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
2 PL99: спасибо. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 19:46 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
savosin_sergey Так один пользователь считал @@identity (до сохранения), потом другой считал @@identity -- произойдёт совпадение. Можно считывать лишь после сохранения -- с тем, чтобы передать его подчинённым detail'ам.. За каким извините хреном считывать identity до сохранения? Оно вообще неизвестно что вернет. savosin_sergeyДругое преимущество: если использовать автоинкремент, то после сохранения в DW не будет значения уникального поля -- для этого надо сделать retrieve. Если записей много в таблице, то делать retrieve после каждого insert'а -- долгова-то. В этом случае придётся считывать @@identity из базы и присваивать полю DW.. ну или ещё что-нибудь придумывать.. Пользователь редко вводит больше 10 записей не сохраняясь. Вы думаете 10 SELECT @@identity сильно просадят производительность? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 20:59 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
savosin_sergey Хотя можно увеличить шаг до 1000... всё равно если для первичного ключа использовать integer, то 2 млрда / 1000 = 200 000 000 -- нашу систему это устраивает (максимальное наблюдаемое число проводок около 90 млн за год) Т.е. ваша система расчитана на то, чтобы проработать чуть больше 2-х лет? Кроме того, вы размениваете тривиальный запрос к переменной connect-а (@@identity) при сохранении (которое не всегда будет), на гарантированный запрос при добавлении строки в DataWindow к таблце, что гораздо более затратно. Какие еще преимущества, как вам кажется, есть у этого метода? (пока видны одни недостатки). ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 26.04.2005, 21:13 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
2 Локшин Марк: авторЗа каким извините хреном считывать identity до сохранения? Оно вообще неизвестно что вернет. Уважаемый Марк, ну а когда его, @@identity считывать? не после же сохранения? или я что-то не понимаю.. есть операция dw.update(boolean, boolean), есть операция select @@identity into :iid;.. даже если select @@identity повесить в event updatestart() -- разве гарантируется, что действия в updatestart() выполнятся в той же транзакции, что и реальное сохранение DW? авторПользователь редко вводит больше 10 записей не сохраняясь. Вы думаете 10 SELECT @@identity сильно просадят производительность? я имел ввиду retrieve DW целиком -- чтобы в неё, в DW, закачались значения автоинкрементного столбца (после dw.update()). И если в таблице много строк, то по-идее, retrieve будет проходить некотрое заметное время.. (даже если он один, общий для всех введённых записей) авторТ.е. ваша система расчитана на то, чтобы проработать чуть больше 2-х лет? Пример с 90млнами строк в год -- это таблица проводок, которая раз в год полностью чистится (остатки в сальдо)(если я не переборщил с числом строк). Таких большие таблице у нас в системе редко встречаются.. но если есть, то можно тип первичного ключа заменить на numeric(20).. авторКроме того, вы размениваете тривиальный запрос к переменной connect-а (@@identity) при сохранении (которое не всегда будет), на гарантированный запрос при добавлении строки в DataWindow к таблце, что гораздо более затратно. Извините, не понял.. в любом случае надо строку к DW добавлять (вопрос лишь в заполнении или в не заполнении поля с первичным ключём.). И в любом случае после нажатия "Сохранить" придётся делать update. Где гарантированный запрос ? спасибо! ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 27.04.2005, 10:44 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
яДа, если шаг=300 (в примере gnv_appl.i_step) и если все 100 пользователей запустят по 3-4 копии, то накроется. Хотя можно увеличить шаг до 1000... всё равно если для первичного ключа использовать integer, то 2 млрда / 1000 = 200 000 000 -- нашу систему это устраивает (максимальное наблюдаемое число проводок около 90 млн за год) чё-то меня дважды проглючило: 2 млрда/300 = около 6.6 млн записей. (может вместить в себя поле integer, если в него записывать значение с шагом 300). Второй глюк -- я видел таблицу самое большое в 9 млн строк. Для неё действительно надо либо последовательно генерить значения, либо использовать numeric(18). С другой стороны, указанная таблица не вводится в вручную пользователями -- это результат расчёта ХП, и для неё сойдёт обычный автоинкремент.. ЗоринАндрейа если еще вспомнить что PB воспринимает не более 18 значащих разрядов, то вообще засада. и на десяток site_id может не хватить. Откуда такая информация? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 27.04.2005, 10:55 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
savosin_sergeyУважаемый Марк, ну а когда его, @@identity считывать? не после же сохранения? именно после savosin_sergeyили я что-то не понимаю.. безусловно, при том, вам это уже несколько раз объясняли (в т.ч. в соседнем форуме). savosin_sergeyесть операция dw.update(boolean, boolean), есть операция select @@identity into :iid;.. даже если select @@identity повесить в event updatestart() -- разве гарантируется, что действия в updatestart() выполнятся в той же транзакции, что и реальное сохранение DW? Да гарантируется, если у вас там на обработке очередная чушь не написана. Транзакциями в PB управляете Вы сами. Если транзакция начата, то пока вы не сделаете commit или rollback все будет в рамках этой транзакции. Кроме того, если указать для таблицы identity column, то вообще ничего делать не нужно! После вставки каждой строки PB сам запросит значение автоинкремента и запишет его в нужную колонку DW. savosin_sergeyя имел ввиду retrieve DW целиком -- чтобы в неё, в DW, закачались значения автоинкрементного столбца (после dw.update()). И если в таблице много строк, то по-идее, retrieve будет проходить некотрое заметное время.. (даже если он один, общий для всех введённых записей) И для чего после сохранения делать retrieve DW целиком, чтобы получить значения автоинкрементов? Их не так получают. savosin_sergeyИзвините, не понял.. в любом случае надо строку к DW добавлять (вопрос лишь в заполнении или в не заполнении поля с первичным ключём.). И в любом случае после нажатия "Сохранить" придётся делать update. Где гарантированный запрос? Следите внимательно, объясняю последний раз. При добавлении пользователем строки в DataWindow вам всегда необходимо будет исполнить запрос типа select max(field) from table Вам это будет необходимо сдезать до записи в таблицу . Этот запрос необходимо будет исполнять всегда при вставке, в отличае от select @@identity, который нужно исполнять только после успешного insert (а еще пользователь может нажать "отмена"), и второй запрос занимает в сотни раз меньше ресурсов, чем первый. Так что Вам тоже необходимо два запроса к серверу для вставки строки. Первый на select, второй на insert. В случае автоинкремента - первый на insert, второй на select. Понятно? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 27.04.2005, 11:18 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
авторесли у вас там на обработке очередная чушь не написана Товарищ, воздержитесь от грубых выражений. Я на вас не наезжал. авторПри добавлении пользователем строки в DataWindow вам всегда необходимо будет исполнить запрос типа select max(field) from table Это сделано на updatestart() -- то есть, только при сохранении ввода пользователем. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 27.04.2005, 11:45 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
savosin_sergeyТоварищ, воздержитесь от грубых выражений. Я на вас не наезжал. То, каким образом у вас автоинкрементное поле вычисляется иначе как чушью назвать сложно. Ну не привели вы ни одного аргумента, почему так сделано. Если все приложение написано в том же духе, то может быть и на сохранение там свой "улучшенный" алгоритм написан. savosin_sergeyЭто сделано на updatestart() -- то есть, только при сохранении ввода пользователем. Хорошо, тогда запросов получится столько же. Но в этом случаее вообще не понятно, зачем Вам значение ключа до сохранения, если все-равно оно вычисляется непосредственно перед процедурой сохранения. Т.е. два документа шапка-подвал в одном окне не сохраняя у вас ввести нельзя? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 27.04.2005, 12:10 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
авторЗоринАндрей а если еще вспомнить что PB воспринимает не более 18 значащих разрядов, то вообще засада. и на десяток site_id может не хватить. savosin_sergey Откуда такая информация? Гм из горького опыта. На самом деле PB (по крайней мере 6.5, хотя не думаю что в старших версиях что-то изменилось) воспринимает только 17 значащих разрядов. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 27.04.2005, 12:50 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Локшин МаркКроме того, если указать для таблицы identity column, то вообще ничего делать не нужно! После вставки каждой строки PB сам запросит значение автоинкремента и запишет его в нужную колонку DW. Что-то у меня не получилось. Сервер msSqlServer2000 (personal), таблица примерно такая: Код: plaintext Коннекты проверялись такие: 1. DBMS="OLE DB", DBParm = "PROVIDER='SQLOLEDB'..." 2. DBMS = "MSS Microsoft SQL Server", DBParm = "" Поле id я пробовал указывать в Updateble Columns, пробовал не указывать.. короче, надо не гадать, а знать, как это делать, чтобы работало! В pbodb90.ini в разделе [MS_SQLSERVER_SYNTAX] указано GetIdentity='Select @@identity' . В обоих случая нету значения identity-поля, как это утверждалось здесь . Хотя бы из-за этого генерация id-поля вручную имеет право на жизнь, как работающий вариант. Альтернатива считыванию @@identity до сохранения.. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 27.04.2005, 18:32 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Понятия не имею, что Вы там сделали, но если создать DataWindow на основе этой таблицы по запросу Код: plaintext Указать Allow Updates, выбрать таблиуц bu_test, в updateable columns выбрать data, в unique и identity - id, то зайдя на вкладку preview, внеся пару строчек и сохраня в поле ID мы получим значения автоинкремента. И в программе точно также. Какая версия PB? savosin_sergey В обоих случая нету значения identity-поля, как это утверждалось здесь. К вашему случаю это не имеет ровно никакого отношения. savosin_sergey Хотя бы из-за этого генерация id-поля вручную имеет право на жизнь, как работающий вариант.Но уж точно не Ваш вариант. savosin_sergey Альтернатива считыванию @@identity до сохранения..СКОЛЬКО РАЗ МОЖНО ГОВОРИТЬ, ЧТО @@identity НУЖНО СЧИТЫВАТЬ ПОСЛЕ СОХРАНЕНИЯ!!! ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 27.04.2005, 22:50 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Но уж точно не Ваш вариант. Локшин Марк savosin_sergeyАльтернатива считыванию @@identity до сохранения.. СКОЛЬКО РАЗ МОЖНО ГОВОРИТЬ, ЧТО @@identity НУЖНО СЧИТЫВАТЬ ПОСЛЕ СОХРАНЕНИЯ!!! Да, я ошибся. Хотя имел ввиду "после созранения", полностью в вами, Марк согласен. Всязи с этим хотел бы обсудить такой вариант: - работают два пользователя с одним документом (допустим, состоящим из одной таблицы tbl1 (id int identity, data varchar(50)) - первый пользователь добавляет строку, заполянет жмёт сохранить - при этом второй пользователь в этом же документе добавляет строку, жмёт сохранить - первый пользователь после своего удачного сохранения считывает @@identity (например, на updateend()) -- и получает id для другой записи (записи, вставленной вторым пользователем) =>возможен конфликт (смотрим сюда) ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 28.04.2005, 12:23 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
Локшин МаркУказать Allow Updates, выбрать таблиуц bu_test, в updateable columns выбрать data, в unique и identity - id, то зайдя на вкладку preview, внеся пару строчек и сохраня в поле ID мы получим значения автоинкремента. И в программе точно также. Какая версия PB? pb9.01 build 7275 действительно, в dw-painter'е работает.. надо будет простое окно потестить, а то все мои тесты проходят не на обычных DW-control'ах, а на специальных наследниках (технология фирмы. аналог PFC) ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 28.04.2005, 12:27 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
savosin_sergeyНо уж точно не Ваш вариант. Локшин Марк savosin_sergeyАльтернатива считыванию @@identity до сохранения.. СКОЛЬКО РАЗ МОЖНО ГОВОРИТЬ, ЧТО @@identity НУЖНО СЧИТЫВАТЬ ПОСЛЕ СОХРАНЕНИЯ!!! Да, я ошибся. Хотя имел ввиду "после созранения", полностью в вами, Марк согласен. Всязи с этим хотел бы обсудить такой вариант: - работают два пользователя с одним документом (допустим, состоящим из одной таблицы tbl1 (id int identity, data varchar(50)) - первый пользователь добавляет строку, заполянет жмёт сохранить - при этом второй пользователь в этом же документе добавляет строку, жмёт сохранить - первый пользователь после своего удачного сохранения считывает @@identity (например, на updateend()) -- и получает id для другой записи (записи, вставленной вторым пользователем) =>возможен конфликт (смотрим сюда) @@IDENTITY вообще то сессионная переменная, то есть для каждой сессии в ней будет значение id последней вставленной записи в сессии. Поэтому о каких конфликтах может идти речь, лично я не понимаю. У Вас что - 2 программы через одну сессию что ли работают ??? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 28.04.2005, 12:36 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
savosin_sergey- работают два пользователя с одним документом (допустим, состоящим из одной таблицы tbl1 (id int identity, data varchar(50)) - первый пользователь добавляет строку, заполянет жмёт сохранить - при этом второй пользователь в этом же документе добавляет строку, жмёт сохранить - первый пользователь после своего удачного сохранения считывает @@identity (например, на updateend()) -- и получает id для другой записи (записи, вставленной вторым пользователем) =>возможен конфликт (смотрим сюда) Гм. Там я говорил про кривость реализации получения значения автоинкрементного поля в PowerBuilder'е. Но они это осознали Локшин МаркСм. help по AtAtIdentity DBParm parameter правда только к 7 версии PB. В случае его задания ситуация, подобная приведенной в ссылке принципиально невозможна. savosin_sergeyдействительно, в dw-painter'е работает.. надо будет простое окно потестить, а то все мои тесты проходят не на обычных DW-control'ах, а на специальных наследниках (технология фирмы. аналог PFC) О чем я и говорил... ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 28.04.2005, 12:53 |
|
||
|
генерация primary key до вставки
|
|||
|---|---|---|---|
|
#18+
ASCRUS@@IDENTITY вообще то сессионная переменная, то есть для каждой сессии в ней будет значение id последней вставленной записи в сессии. Действительно! спасибо. просто я невнимательно прочитал документацию. SCOPE_IDENTITY тоже ничего msSqlServer2k online books@@IDENTITY and SCOPE_IDENTITY will return the last identity value generated in any table in the current session. However, SCOPE_IDENTITY returns the value only within the current scope; @@IDENTITY is not limited to a specific scope. IDENT_CURRENT is not limited by scope and session; it is limited to a specified table. IDENT_CURRENT returns the identity value generated for a specific table in any session and any scope. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 28.04.2005, 14:07 |
|
||
|
|

start [/forum/topic.php?all=1&fid=15&tid=1338384]: |
0ms |
get settings: |
9ms |
get forum list: |
11ms |
check forum access: |
2ms |
check topic access: |
2ms |
track hit: |
55ms |
get topic data: |
9ms |
get forum data: |
2ms |
get page messages: |
60ms |
get tp. blocked users: |
1ms |
| others: | 215ms |
| total: | 366ms |

| 0 / 0 |
