Управление диалогом подписания через API

Добавлен специальный API для управления диалогом подписания.

Входная точка — сервис $DigitalSignature. Для настройки диалога следует использовать события beforeSignatureDialogShown и afterSignatureDialogShown указанного сервиса. В первом событии можно настроить свойства диалога, во втором получить доступ к управлению диалогом. В событиях доступна информация о карточке, из которой осуществляется подпись: вид, тип, состояние и другая информация.

Свойства диалога позволяют:
  • Скрывать выбор метки.

  • Скрывать выбор сертификата.

  • Отключать простую подпись.

  • Скрывать кнопку настройки способов подписания.

  • Скрывать сам диалог: диалог открывается, но оказывается невидим на экране для пользователя.

  • Добавлять содержимое в нижней и верхней части диалога.

  • Обрабатывать доступные способы подписания: фильтровать, модифицировать, добавлять свои.

  • Управлять отрисовкой кнопок: добавлять свои, заменять стандартные.

Управление диалогом через IDigitalSignatureDialogManagement позволяет получать информацию о загруженных метках и способах подписания:
  • Программно выбирать метку и способ подписания

  • Изменять видимость диалога для пользователя

  • Динамически менять свойства диалога (см. п. 3)

  • Программно подтверждать или отменять операцию подписания

  • Также событие beforeSignatureDialogShown позволяет подменять логику формирования подписи и прикрепления к документу. Это можно использовать для подключения сторонних провайдеров подписания.

Следующий пример кода демонстрирует автоматический выбор сертификата для документов вида Исходящий и подписание без показа диалога:

export function initExtension(app) {
        app.digitalSignature.beforeSignatureDialogShown.watch(args => { (1)
            if (args.cardInfo.kindId == '8e40f327-9517-4a43-998d-bf2bd619588d') {
                 args.dialogProps.showHidden = true;
            }
        });
        app.digitalSignature.afterSignatureDialogShown.watch(async (args) => { (2)
            let methods = await args.management.getSignatureMethods();
            let outgoingMethod = methods.find(x => x?.certificateInfo?.friendlyName.includes('для исходящего'));
            if (outgoingMethod) {
                args.management.selectSignatureMethod(outgoingMethod);
                args.management.accept();
            } else {
                const props = args.management.getDialogProps();
                props.footer = "Не удалось найти сертификат для исходящих документов.";
                args.management.update(props);
                args.management.setDialogVisible(true);
            }
        });
}
1 По умолчанию скрываем диалог для документов вида Исходящий.
2 Автоматически выбираем сертификат и нажимаем подписать.

Можно вставить в метод init при вызове registerExtension, либо просто скопировать в консоль браузера и вызвать initExtension(WebClient.app).

Пример интеграции со сторонним облаком:
export function initExtension(app) {
    app.digitalSignature.beforeSignatureDialogShown.watch(args => {
       args.options.onCreateSignature = (options) => { return signByCustomCloud(options); }
    });
}
Свойства диалога:
    hideLabelSelection?: boolean; (1)
    hideSignatureMethodsSetup?: boolean; (2)
    hideSimpleSign?: boolean; (3)
    hideSignatureMethodsSelect?: boolean; (4)

    showHidden?: boolean; (5)
    footer?: React.ReactNode; (6)
    header?: React.ReactNode; (7)

    onSign?: (options: IDigitalSignOptions) => Promise<void>(8)
    onCancel?: () => void; (9)
    onPrepareSignatureMethods?: (methods: GenModels.SignatureMethod[]) => GenModels.SignatureMethod[]; (10)
    onRenderButtons?: (props: ISignatureDialogButtonsProps, defaultButtons: JSX.Element[]) => JSX.Element[]; (11)
1 Не отображать выбор метки.
2 Не отображать кнопку настройки вариантов подписания.
3 Скрыть метод простой подписи.
4 Не отображать раскрывающийся список выбора способа подписания. В таком случае будет выбран первый вариант по умолчанию.
5 Чтобы не отображать диалог на экране, используйте API @link IDigitalSignatureDialogManagement.
6 Сообщение, показываемое в нижней части диалога
7 Сообщение, показываемое в верхней части диалога
8 Вызывается при подписи.
9 Вызывается при отмене подписи.
10 Вызывается для обработки отображаемого списка доступных способов подписания.
11 Вызывается при отрисовке кнопок диалога.
Управление диалогом:
    close(reason?: unknown): Promise<void>(1)
    accept?(data?: IDigitalSignOptions): Promise<void>(2)
    getSignatureMethods(): Promise<GenModels.SignatureMethod[]>(3)
    getLabels(): Promise<ISignatureLabel[]>(4)
    selectSignatureMethod(method: GenModels.SignatureMethod): void; (5)
    selectLabel(label: ISignatureLabel): void; (6)
    getDialogVisible(): boolean; (7)
    setDialogVisible(visible: boolean): void; (8)
    getDialogProps(): ISignatureDialogProps; (9)
    update(props?: ISignatureDialogProps): void; (10)
1 Закрыть диалог без сохранения данных.
2 Применить изменения и закрыть диалог. Параметр не обязателен.
3 Возвращает список доступных сертификатов и других способов подписания.
4 Возвращает список доступных меток подписи.
5 Выбирает в раскрывающемся списке указанный способ подписания.
6 Выбирает в раскрывающемся списке указанную метку подписи.
7 Возвращает значение свойства видимости диалога для пользователя.
8 Устанавливает видимость диалога для пользователя.
9 Возвращает текущие свойства диалога подписания.
10 Обновляет диалог с указанными свойствами. См. @link getDialogProps.
Примеры тестирования:
WebClient.app.digitalSignature.beforeSignatureDialogShown.watch(args => {

	if (args.cardInfo.kindId == '8e40f327-9517-4a43-998d-bf2bd619588d') {

		 args.dialogProps.showHidden = true;

	}

});

WebClient.app.digitalSignature.afterSignatureDialogShown.watch(async (args) => {

	let methods = await args.management.getSignatureMethods();

	let outgoingMethod = methods.find(x => x?.isSimple);

	args.management.selectSignatureMethod(outgoingMethod);

	args.management.accept();

});

WebClient.app.digitalSignature.beforeSignatureDialogShown.watch(args => {

	args.dialogProps.hideLabelSelection = true;

});

WebClient.app.digitalSignature.afterSignatureDialogShown.watch(async (args) => {

	const props = args.management.getDialogProps();

	props.footer = "Привет, медвед!";

	args.management.update(props);

});

WebClient.app.digitalSignature.afterSignatureDialogShown.watch(async (args) => {

	let labels = await args.management.getLabels();

	if (args.cardInfo.kindId == '8e40f327-9517-4a43-998d-bf2bd619588d') {

		args.management.selectLabel(labels[1]);

	}

});

WebClient.app.digitalSignature.beforeSignatureDialogShown.watch(args => {

       args.options.onCreateSignature = (options) => { return alert('custom sign create'); }

});