ОБСУЖДЕНИЕ

Генерация UNID

22 ответов 9,6 тыс.
AI-выжимка обсуждения скоро
Добрый день всем!

Есть ли какя-нибудь документация в сети по алгоритму генерации ид лотусного документа?
Есть потребность генерации лотусной ид-шки вне лотуса, в частности на пхп.
Как обеспечить уникальность 32-х значного ключа без проверок на уникальность?
 
The UNID is made up of 32 hex digyts as follows:
The first 16 digyts are random
The next 2 digyts are based on the time zone where the document is created
The next 6 digyts are based on the GMT date when the document is created
The last 8 digyts are the number of hundredths of seconds that have passed in the day (again) based on the GMT.
 
  • Нравится
Реакции: Murtas
alexas1, Спасибо! ... хотя бы и так
примитивненько, где-то уже встречал такое (кто-то пытался на лотус скрипте или VBA такое сделать) ... думаю пока так и поступим
 
alexas1, Спасибо! ... хотя бы и так
примитивненько, где-то уже встречал такое (кто-то пытался на лотус скрипте или VBA такое сделать) ... думаю пока так и поступим
по крупному счёту, Random из "0123456789ABCDEF0123456789ABCDEF" даст замечательный UNID) нотус его сожрёт за милую душу))
или, совсем по взрослому Random из "0123456789ABCDEF" длиной 32
кста, простой @Password даёт UNID совместимую строку
 
по крупному счёту, Random из "0123456789ABCDEF0123456789ABCDEF" даст замечательный UNID) нотус его сожрёт за милую душу))
или, совсем по взрослому Random из "0123456789ABCDEF" длиной 32
кста, простой @Password даёт UNID совместимую строку

нам не крупный счет нужен и не совместимость, а гарантия того, что генерируемый ключ никогда не встретит дубликата в базе, среди уже существующих лотусных документов ... даже наверное сразу заложим возможность перегенерации в случае проблем
 
нам не крупный счет нужен и не совместимость, а гарантия того, что генерируемый ключ никогда не встретит дубликата в базе, среди уже существующих лотусных документов ... даже наверное сразу заложим возможность перегенерации в случае проблем
"совместимость" будет) а проверять всё равно надо - просто попытаться взять док по этому юниду
 
а гарантия того, что генерируемый ключ никогда не встретит дубликата в базе
она будет опираться на время компа! (в любом случае) + затравка (рэндомная), точность времени (до мс) обеспечит достаточную вероятность несовпадения, если генерация будет происходить реже чем 1мс

"совместимость" будет) а проверять всё равно надо - просто попытаться взять док по этому юниду
я так понимаю - основное - нежелание отправлять запросы (это м.б. в районе 20мс)...
да и бомбить домну запросами (по хттп) - тоже может тормознуть её
 
она будет опираться на время компа! (в любом случае) + затравка (рэндомная), точность времени (до мс) обеспечит достаточную вероятность несовпадения, если генерация будет происходить реже чем 1мс
вообще не принципиально, по крупному счёту - нотус при сохранении нового дока в бвзу всегда проверяет уникальность
я так понимаю - основное - нежелание отправлять запросы (это м.б. в районе 20мс)...
да и бомбить домну запросами (по хттп) - тоже может тормознуть её
вероятность дубля крайне мала, ну получил ошибку при сохранении - перегенерил и повторил
да и этого не будет в ближайшие сто лет)
 
я так понимаю - основное - нежелание отправлять запросы (это м.б. в районе 20мс)...
да и бомбить домну запросами (по хттп) - тоже может тормознуть её

Ну как вы все догадались :) речь идет о миграции приложения, которое в настоящий момент является мастер системой и раздает всем другим системам свои идш-ки. Во все других системах уже нет возможности избавиться от лотусного формата, поэтому новая мастер система должна будет продолжать выделять их в том же формате. Более того, какое-то неограниченное время, лотус всеравно будет мастер системой и работать совместно с новой, в которой будут постепенно замещать лотусные фишки.

делать запросы в лотус на выделение ид для новых документов - изврат по-моему, хотя не самый ущербный вариант, который гарантировано сделает то что надо ... и здесь представляется такой расклад, когда лотус уже совсем не нужен, кроме как для выделения идишек для какой-то системы )))
 
можно оставить domino для генерации, почему бы и нет.
docker + webservice, даже документы сохранять не надо, просто создать пустой и вернуть его юнид.
там от силы будет взаимодействие на 1 секунду.
нормальный вариант, тем более что система еще будет жить некоторое время. Этакий микросервис.
Просто сразу это сделайте рядом, именно в докере, можете даже не обновлять потом версию и не продлевать лицензии.
для докера там сейчас образ comunity (или как там) используется, который и так платным не был.
ну генерит он и генерит, раз в год базу, где генерация проходит пересоздаем тьолько , чтобы наверняка не поймать дублей.
 
можно оставить domino для генерации, почему бы и нет.
docker + webservice, даже документы сохранять не надо, просто создать пустой и вернуть его юнид.
А смысл?? Это, по крупному счёту, не гарантирует уникальности в сторонней базе - нотус уникальность контролит только для базы где создаётся юнид. Это если совсем тоненько подходить...
Алгоритм ясен - генерить надо самому.
 
А смысл?? Это, по крупному счёту, не гарантирует уникальности в сторонней базе - нотус уникальность контролит только для базы где создаётся юнид. Это если совсем тоненько подходить...
Алгоритм ясен - генерить надо самому.
Во все других системах уже нет возможности избавиться от лотусного формата, поэтому новая мастер система должна будет продолжать выделять их в том же формате.
Одна система => одна база => веб-сервис для системы.
а так то, смотря что проще.
 
Одна система => одна база => веб-сервис для системы.
а так то,
Одна система => одна база => веб-сервис для системы.
а так то, смотря что проще.
"и здесь представляется такой расклад, когда лотус уже совсем не нужен, кроме как для выделения идишек для какой-то системы )))"(с) - держать домино-комбайн только для юнидов совсем не комильфо. База любого уникального ключа - таймштамп. Централизованная генерация юнида всегда обеспечит уникальность с точностью, зависящей только от надёжности системных часов и способа получения времени от них. Ну а обеспечить ключу "правильный" формат - дело техники.
 
На @Password неожиданно стала сыпаться ошибка 221, оказалось, что у данной @-формулы есть недокументированное ограничение по размеру обрабатываемых данных. Делать LeftB$(sData, 2480) не вариант.
Что посоветуете для LS?
Единственное, что приходит на ум - порезать данные порциями в 2480, вычислить хеш каждой, склеить и вычислить ещё раз...
 
На @Password неожиданно стала сыпаться ошибка 221, оказалось, что у данной @-формулы есть недокументированное ограничение по размеру обрабатываемых данных. Делать LeftB$(sData, 2480) не вариант.
Что посоветуете для LS?
Единственное, что приходит на ум - порезать данные порциями в 2480, вычислить хеш каждой, склеить и вычислить ещё раз...
Интересно. У @Hashpassword такие же ограничения? Если нет - то комбинация @Password(@Hashpassword ...
 
У @Hashpassword такие же ограничения? Если нет - то комбинация @Password(@Hashpassword ...
Да, то же ограничение.
Можно было бы использовать NotesSession.HashPassword, у которой нет таких проблем, но в моём случае нужен статический хеш, - генерю ID для БД, и по этому ID в дальнейшем должен быть доступ к записи, а HashPassword генерит динамический - разный при каждом вызове на одних и тех же данных.

Короче как-то так:
Visual Basic:
%REM
    Function encryptPassword
    Description: генерирует статический хеш (контрольную сумму) из 32-х символов;
        может использоваться для проверки целостности данных либо в качестве UNID
    sData - данные, по которым нужно сгенерировать хеш
%END REM
Public Function encryptPassword(sData As String) As String
    On Error GoTo ErrH
    'если строка содержит > 1113 байт, то Lotus генерирует Err=221 'Invalid formula @Password(...)'
    Const PORTION_LIMIT = 1000        'про запас, и для простоты отладки; не менять, т.к. изменится хеш!
    Dim nDataLen As Long, nStart As Long, sPortion As String
    nDataLen = Len(sData)
    'Print "nDataLen = " & nDataLen
    For nStart = 1 To nDataLen Step PORTION_LIMIT
        sPortion = Mid$(sData, nStart, PORTION_LIMIT)
        'Print nStart, Len(sPortion)
        encryptPassword = encryptPassword + Mid(Join(Evaluate(|@Password({| + sPortion + |})|) ), 2, 32)
    Next
    If nDataLen <= PORTION_LIMIT Then Exit Function
    encryptPassword = encryptPassword(encryptPassword)
Quit:
    Exit Function
ErrH:
    'MsgBox sPortion,, CStr(Len(sPortion))
    Error Err, GetThreadInfo(1) & " (" & Erl & ") -> " & Error$
End Function

Добавлено: ерунда какая-то феерическая. На клиентской части код работает, а на серверной бьёт ту же ошибку. Заработал, когда уменьшил лимит ровно вдвое - на 1240.
Непонятно, ведь использую LenB, это ведь LenBP платформозависимая. Да и непонятно, ведь что клиент, что сервер - Винда... Может это из-за разных версий Винды такое?..

Добавлено 2021.11.16:
Иногда стала вылетать ошибка encryptPassword(19) -> Operation failed {221}.
1. Причина ошибки: 3-й параметр для Mid ненужно было высчитывать, из-за чего размер порции данных "гулял" в цикле и иногда превышал максимально допустимый. Нужно было просто передавать максимальную длину порции.
2. Переделал функцию с LenB и MidB$ на Len и Mid$, т.к. B-функции на сервере берут вдвое меньшую порцию, из-за чего для данных, превышающих половину указанной в константе порции, на сервере и клиенте невозможно было добиться генерации одинакового кеша. Также B-функции не рекомендуемы к использованию после Lotus R3 для работы со строками. Переход на Len и Mid$ позволил вдвое уменьшить количество циклов обработки.
3. Уменьшил размер порции с 1240 до 1000, т.к. Domino 8.5.x на Win2003 и полностью всех русских символах в предложениях (обычный текст - есть точки, запятые и пробелы) не может без ошибки выполнить @Password для порции более чем 1113 символов одновременно.
 
Последнее редактирование:
А использовать MD5 есть возможность? тоже 32 символа будет.
 

Статистика тем

Создано
Murtas,
Последний ответ от
VladSh,
Ответы
22
Просмотры
9 619