Войти
 
 
   
 
  
Новости Notes.ру Библиотека Биржа труда Вопрос - ответ Форум Регистрация Поиск О проекте
Разделы
О Notes
Советы
Шаблоны и примеры
Литература
Презентации
 
Дополнительные инструменты в панели инструментов   
Шаблоны и примеры Читать статью
 
Классы для работы со стабами удалённых документов для Windows64   
Шаблоны и примеры Читать статью
 
Базовые компоненты XPages Extension Library: Widget Container   Серия статьей дающая представление о базовых компонентах Extension Library, их основных свойствах и мест применения
О Notes Читать статью
 


О Notes

Главная   Библиотека   О Notes

Защита произвольного набора данных при помощи цифровой подписи

Николай Норкин
Вятские Информационные Технологии
nickanor@mail.ru

Защита произвольного набора данных при помощи цифровой подписи

В настоящем материале рассматривается решение по использованию электронной подписи для защиты данных
С первоначальной идеей такого решения автор ознакомился в изложении Глеба Ноздрачёва
Системное поле $Signature, получающееся при подписании документа и содержащее электронную подпись, сохраняется в документе под другим именем. Перед подписанием в соответствующих полях устанавливается свойство isSigned, выполняется подписание документа методом sign, после этого поле $Signature сохраняется в документе под другим именем, свойство isSigned с полей снимается. Проверка подписи осуществляется опять же поднятием флага isSigned в соответствующих полях, копированием подписи в системное поле. Если свойство signer документа пусто, подпись нарушена, иначе свойство вернёт каноническое имя пользователя, выполнившего подписание
В отличие от системного подписания документа, решение позволяет установить несколько подписей на один документ, в принципе, модернизировав код, можно подписывать данные из различных документов
Отсутствует привязка к интерфейсу (форме, по которой открывается документ) - установленным в полях формы атрибутам Sign if mailed or saved in section

В отличие от подписания разделов, отсутствует привязка к интерфейсу, подписываемые поля не привязываются к какому-либо участку формы, ограниченному рамками раздела
Это позволяет выполнить проверку подписи back-end'ными методами (агентом по расписанию), позволит модифицировать дизайн или гибко управлять набором подписываемых полей (подпись проверяется по списку полей, установленных в момент подписания, а не в момент проверки подписи)
Следует совмещать описываемый механизм защиты с интерфейсной защитой данных (скрытием элементов формы по формуле hide-when)

Для реализации механизма разместите в форме две интерфейсные кнопки и два скрытых поля

Поле dspSignedFields_<suffix> - computed for display, text, allow multiple values содержит список защищаемых подписью полей
"begin_price" : "date_xp" : "date_lim" : "number_claim" : "date_claim" : "vidPur" : "pers_spec" : "pers_xper"
Поле dspViewSigned_<suffix> с теми же опциями может содержать список подписей к этим полям. В этом случае можно перекрыть метод verifySignStep и отобразить пользователю, какие поля были защищены
Кнопка Отправить на следующий этап содержит вызов исполняемого кода, оформленного в виде агента @Command([ToolsRunMacro]; "(sign_2)")
А вот и код агента:
Option Public
Use "SignatureDocumentPart"
Sub Initialize
Dim signVar As New SignatureDocumentPart()
Dim ws As New NotesUIWorkspace
Dim uidoc As NotesUIDocument
Dim doc As NotesDocument

Set uidoc = ws.CurrentDocument
Set doc = uidoc.Document

suf$ = signVar.getSuffixAgent()
Call signVar.signStep(doc, suf$)
Call uidoc.Refresh()
End Sub

В результате в документ записываются дополнительные поля signedFields_<suffix> и viewSigned_<suffix>, содержащие информацию из описанных выше дисплейных полей, поля signed_<suffix> и signer_<suffix>, содержащие информацию о времени подписания и подписавшем пользователе и поле $Signature_<suffix>, содержащее подпись, защищающую пользовательскую информацию в полях, описанных в списке signedFields_<suffix>. Кроме этого, подписью защищаются и описанные дополнительные поля: signedFields_<suffix> и viewSigned_<suffix>, signed_<suffix> и signer_<suffix>

Проверка подписи осуществляется агентом со следующим кодом
Option Public
Use "SignatureDocumentPart"
Sub Initialize
Dim signVar As New SignatureDocumentPart()
Dim ws As New NotesUIWorkspace
Dim uidoc As NotesUIDocument
Dim doc As NotesDocument

Set uidoc = ws.CurrentDocument
Set doc = uidoc.Document

suf$ = signVar.getSuffixAgent()
Call signVar.verifySignStep(doc, suf$)
End Sub


Библиотека LotusScript SignatureDocumentPart
Public Class SignatureDocumentPart
Private session As NotesSession
Private curdb As NotesDatabase
Private item As NotesItem
Private debugMode As String
Private log As NotesStream

Sub New ()
Set Me.session = New NotesSession
Set Me.curdb = Me.session.currentDatabase
End Sub
Public Sub signStep(doc As NotesDocument, suffix As String)
If Not Me.validation Then Exit Sub
'Подписать
Dim dialog As NotesDocument
If Not doc.HasItem("dspSignedFields_" & suffix) Then Print "Не получен список подписываемых полей" : Exit Sub
fields = doc.GetItemValue("dspSignedFields_" & suffix)
If fields(0) = "" Then Print "Список подписываемых полей пустой" : Exit Sub
Set dialog = Me.curdb.createDocument
Call dialog.replaceItemValue("SaveOptions", "0")
'Print "Список подписываемых полей:", Implode(fields, "|")
Forall fname In fields
If Not fname = "Signer_" & suffix Then
Call Me.copyItemToDialogDoc(doc, dialog, Cstr(fname))
End If
End Forall
Set item = dialog.replaceItemValue("Signer_" & suffix, Me.signer)
item.IsSigned = True
Set item = dialog.replaceItemValue("SignedFields_" & suffix, doc.GetItemValue("dspSignedFields_" & suffix))
item.IsSigned = True
Set item = dialog.replaceItemValue("viewSigned_" & suffix, doc.GetItemValue("dspViewSigned_" & suffix))
item.IsSigned = True
Set item = dialog.replaceItemValue("$signed_" & suffix, Now())
item.IsSigned = True
Call dialog.Sign()
If dialog.HasItem("$Signature") Then
'Print "$Signature есть"
Set item = dialog.GetFirstItem("$Signature")
Call item.CopyItemToDocument(doc, "$Signature_" & suffix)
Set item = doc.replaceItemValue("Signer_" & suffix, dialog.GetItemValue("Signer_" & suffix))
' item.IsProtected = True
Set item = doc.replaceItemValue("SignedFields_" & suffix, dialog.GetItemValue("SignedFields_" & suffix))
' item.IsProtected = True
Set item = doc.replaceItemValue("viewSigned_" & suffix, dialog.GetItemValue("viewSigned_" & suffix))
' item.IsProtected = True
Set item = dialog.GetFirstItem("$signed_" & suffix)
Call item.CopyItemToDocument(doc, "$signed_" & suffix)
Else
Print "Нет поля $Signature"
End If
Me.postSign
Me.openLog
End Sub
Private Sub copyItemToDialogDoc(doc As NotesDocument, dialog As NotesDocument, fname As String)
If Not doc.hasItem(fname) Then Exit Sub
Set item = doc.GetFirstItem(fname)
Call item.CopyItemToDocument(dialog, fname)
Set item = dialog.GetFirstItem(fname)
item.IsSigned = True
End Sub
Private Function signer As Variant
Dim usernamelist As Variant
usernamelist = Me.session.usernameList
Dim v As Variant
Dim ub%
If Ubound(usernamelist) > 0 Then ub% = 1 Else ub% = 0
Redim v(ub%)
v(0) = usernamelist(0).canonical
If ub% = 1 Then v(1) = usernamelist(1).canonical
signer = v
End Function
Public Sub verifySignStep(doc As NotesDocument, suffix As String)
Dim dialog As NotesDocument
If Not doc.HasItem("SignedFields_" & suffix) Then Me.Print "Не получен список подписанных полей" : Exit Sub
fields = doc.GetItemValue("SignedFields_" & suffix)
If fields(0) = "" Then Me.Print "Список подписанных полей пустой" : Exit Sub
Set dialog = Me.curdb.createDocument
Call dialog.replaceItemValue("SaveOptions", "0")
Forall fname In fields
Call copyItemToDialogDoc(doc, dialog, Cstr(fname))
End Forall
Set item = dialog.replaceItemValue("Signer_" & suffix, doc.getItemValue("Signer_" & suffix))
item.IsSigned = True
Set item = dialog.replaceItemValue("SignedFields_" & suffix, doc.getItemValue("signedFields_" & suffix))
item.IsSigned = True
Set item = dialog.replaceItemValue("viewSigned_" & suffix, doc.getItemValue("viewSigned_" & suffix))
item.IsSigned = True
Set item = dialog.replaceItemValue("$signed_" & suffix, doc.getItemValue("$signed_" & suffix))
item.IsSigned = True
Set item = doc.GetFirstItem("$Signature_" & suffix)
Call item.CopyItemToDocument(dialog, "$Signature")
If dialog.IsSigned Then
If dialog.Signer = "" Then Messagebox "Подпись нарушена", MB_OK, "Проверить подпись" : Exit Sub
Dim nam As NotesName
Set nam = Me.session.CreateName(dialog.Signer)
Messagebox "Подписано: " & nam.Abbreviated, MB_OK, "Проверить подпись"
Else
Messagebox "Документ не подписан", MB_OK, "Проверить подпись"
End If
Me.openLog
End Sub
Public Function getSuffixAgent() As String
Dim currentAgent As notesagent
Dim n As String
Set currentAgent = Me.session.CurrentAgent
n = currentAgent.Name
If Instr(Strrightback(n, "_"), ")") > 0 Then suf$ = Strleft(Strrightback(n, "_"), ")") Else suf$ = Strrightback(n, "_")
'Print "suf$", suf$
getSuffixAgent = suf$
End Function
Private Function validation As Variant
validation = True
End Function
Private Sub postSign

End Sub

Public Sub debugPrint
Me.debugMode = "Print"
End Sub
Public Sub debugAlert
Me.debugMode = "Alert"
End Sub
Public Sub debugLog(level As Integer)
Me.debugMode = "Log" & Cstr(level)
End Sub
Private Sub openLog
End Sub
Private Sub print (message As String)
Select Case Me.debugMode
Case "Print": Print message
Case "Alert": Messagebox message
End Select
End Sub
End Class

Читайте на Notesnet.ru
Средства защиты информации в Notes >>>
Почтовый клиент Lotus Notes. Шифрование и электронная подпись документа >>>
 
  Опубликовано — 01/30/2010 |    

Николай Норкин, 18.05.2010 13:35:56:
Проверил на подписание на различных клиентах - на восьмом отлично проверяется подпись, сделанная в шестёрке

Ник Норкин, 18.05.2010 13:34:00:
Для подписи rt-поля, содержащего файлы, пришлось изменить функцию верификации - добавить две строчки. Теперь окончание функции verifySigner выглядит:
...
Set item = dialog.replaceItemValue("$signed_" & suffix, doc.getItemValue("$signed_" & suffix))
item.IsSigned = True
>> Call dialog.sign()
>> Call dialog.removeItem("$Signature")
Set item = doc.GetFirstItem("$Signature_" & suffix)
Call item.CopyItemToDocument(dialog, "$Signature")
If dialog.IsSigned Then
If dialog.Signer = "" Then Exit Function
Dim nam As NotesName
Set nam = Me.session.CreateName(dialog.Signer)
verifySigner = nam.canonical
Else
Messagebox "Документ не подписан", MB_OK, "Проверить подпись"
End If

Ник Норкин, 25.03.2010 10:16:03:
To Klido:
Коллеги, простите за молчание - занят в проекте, делаем эл.регистратуру для медиков www.medkirov.ru/e-reg/
Про rtf-поля - вначале на лабораторных испытаниях вроде как получалось, вернусь к этому вопросу в течение месяца - там надо доделать одну вещь, в частности, с подписью вложений
Также ещё интересует протестировать подпись/проверку на разных клиентах/разных осях

Constantin, 23.03.2010 01:15:47:
Каскадные подписи в Колином подходе реализуются лёгким движением левой задней ноги: к док-ту добавляется поле с именем предыдущего подписанта (полученным через verifySignStep) и подписывается вместе с полями предыдущего уровня

Klido, 11.03.2010 17:29:44:
Да, весьма интересный подход изложен.
Как оно себя показывает на ртф-полях? Или это предстоит дополнительно копнуть?

VladSh, 08.02.2010 15:03:42:
Инкапсулирует.
Только я пока не знаю, как это делается.. Там, как мне рассказывали есть куча вариантов: с добавлением сертификата в подпись, без добавления, и куча разных опций. Надо разбираться.

Ник, 05.02.2010 14:17:39:
>> 2. Полей $Signature много... т.е. включение предыдущей подписи в список полей для подписания, т.о. в документе хранится всего лишь одно поле $Signature
не понимаю, к чему ты клонишь?
"финальная" подпись (поле финальной подписи) инкапсулирует все собранные подписи ($signature как контейнер для хранения всех подписей)
или же заменяет ранешнюю подпись?
или это ты ведёшь речь о частном случае "экспорта" подписанного документа, чтобы на нём стояла подпись

VladSh, 04.02.2010 19:20:52:
Интересное решение и у тебя и у твоих коллег!
Я только высказал проблемы, которые скорее всего будут стоять передо мной в будущем; если что-то накопаю, то конечно поделюсь.
Хотелось бы копать в сторону того, чтобы любая система понимала подпись стандартными средствами, как будто ты отправляешь кому-то подписанное письмо.
Единственное, что решение возможно "ручное" (кнопками), а не автомат, как Лотус проверяет при открытии дока. Для автомата надо делать хуки, а с юридической точки зрения это нечестное решение.

Ник, 04.02.2010 13:46:22:
Влад, привет!
У меня такое смутное ощущение, что о поднимаемых тобой вопросах ты имеешь большее представление, чем я
Поэтому, если есть соображения - не стесняйся
Я к вопросу встраивания подписи или отчуждения подписи от системы вплотную не подходил
Тут один из аспектов проблемы, думаю, в цели
В этом моём решении цель - защита данных от изменения, и решение справляется с этой задачей
Если рассматривать внешнюю подпись, то здесь цель - получение юридически значимой подписи, простыми словами - чтобы в суде можно было предъявить что-то, что воспринималось как неоспоримое и "вещественное"
Для соблюдения этого условия мои коллеги используют лом - импортируют данные в файл, его подписывают и прикрепляют и файл, и файл подписи в систему

VladSh, 03.02.2010 20:37:34:
Очень интересно, Ник! Спасибо!
Какие бы вопросы хотелось бы дополнительно увидеть освещёнными:
1. Применение внешних алгоритмов подписи (не Lotus). Возможна ли модификация кода в сторону универсальности и настройки, каким алгоритмом производить подпись?
2. Полей $Signature много... Обычно во внешних системах для таких случаев используются каскадные подписи, т.е. включение предыдущей подписи в список полей для подписания, т.о. в документе хранится всего лишь одно поле $Signature. Возможно ли это в Lotus'е? Если нет, то каким образом производить модификацию документа при отправке его за пределы организации (при этом механизмы проверки подписи на принимающей стороне должны работать стандартно, т.е. без проблем должны разбирать такую подпись)?



Добавить комментарий
Имя * :
e-mail
Комментарий * :
Код подтверждения * :

Мероприятия
18.12.2012   Опыт реализованных проектов на базе технологий IBM
24.10.2012   Решения IBM для построения надежной ИТ-инфраструктуры и сервисов
09.10.2012   Форум «Ударим СЭДом по бездорожью, разгильдяйству и непрозрачным бизнес-процессам! Система электронного документооборота CompanyMedia 4.0: вперед в будущее!»
Пресс-релизы
02.06.2011   ООО "АДБ.РУ" выпустило очередную версию системы управления контентом для Lotus Domino - Logosphere 2.7.
21.01.2010   Компания «Поликом Про» выполнила для компании «Синергия» пилотный проект по внедрению системы защиты электронной почты IBM Lotus Protector for Mail Security
22.12.2009   Новые технологии разработки приложений на базе Lotus Domino
Биржа труда
18.04.2012 - разработчик Lotus Notes (ОАО "УРАЛСИБ")
26.07.2011 - Программист Lotus (удаленная работа) ()
06.06.2011 - Эксперт (Lotus Notes/Domino) (Крупный банк (ТОП-5))
Последнее на форуме
 
А так же:
Скопировать в буфер поле документа
24.05.2015 08:55:52
Импорт DXL-описания документов в Lotus Domino. Одноимённые поля
16.04.2015 16:49:58
Использование WebDAV в приложениях Domino
18.03.2015 13:11:26
 
© LOGOSPHERE.RU