1.0.1 • Published 5 months ago

authrix-widget v1.0.1

Weekly downloads
-
License
MIT
Repository
github
Last release
5 months ago

authrix widget

Виджет авторизации через протокол authrix для React-приложений.

Установка

npm install authrix-widget

Интерфейсы и типы

interface SignData {
    username: string;
    publicKeyHash: string;
    timestamp: number;
}

interface AuthResponseData {
    signData: SignData;
    userSignature: string;
    serviceSignature: string;
}

interface AuthRejectedData {
    message: 'AUTH_REJECTED';
}

type AuthWidgetData = AuthResponseData | AuthRejectedData;

interface AuthrixWidgetProps {
    locale?: 'ru' | 'en',
    text?: {
        buttonText?: string;
        confirmationText?: string;
    },
    isAuthenticating?: boolean,
    onAuthData?: (data: AuthWidgetData) => void,
}

interface AuthRequestEvent {
    detail: {
        message: string,
        domain: string,
    },
}

interface AuthResponseMessage {
    source: 'authrix-content-script';
    type: 'AUTH_RESPONSE';
    data: AuthWidgetData;
}

Примеры использования

Базовый пример

import { AuthrixWidget } from 'authrix-widget';


const App: React.FC = () => {
    const handleAuthData = (data: AuthWidgetData): void => {
        console.log('Данные авторизации:', data);
    };

    return (
        <AuthrixWidget 
            locale="ru"
            onAuthData={handleAuthData}
            text={{
                buttonText: 'Войти через authrix',
                confirmationText: 'Подтвердите вход'
            }}
        />
    );
}

Расширенный пример с верификацией подписи

import { AuthrixWidget } from 'authrix-widget';
import { useState } from 'react';
import { createHMACSignature } from '../helpers/crypto.helper';
import { AuthResponseData, AuthWidgetData } from '../interfaces/auth.interface';

function isAuthResponseData(data: AuthWidgetData): data is AuthResponseData {
    return 'signData' in data;
}

const AuthPage: React.FC = () => {
    const [isAuthenticating, setIsAuthenticating] = useState<boolean>(false);
    const serviceKey = 'your_service_key';

    const handleAuthData = async (data: AuthWidgetData): Promise<void> => {
        // Обработка отказа в авторизации
        if ('message' in data && data.message === 'AUTH_REJECTED') {
            setIsAuthenticating(false);
            return;
        }

        if (!isAuthResponseData(data)) {
            return;
        }

        const { signData, userSignature, serviceSignature } = data;
        const dataString = JSON.stringify(signData);
    
        // Проверка подписи пользователя
        const verificationSignature = await createHMACSignature(dataString, signData.publicKeyHash);
        const isUserSignatureValid = userSignature === verificationSignature;
    
        // Проверка подписи сервиса
        const verificationServiceSignature = await createHMACSignature(dataString, serviceKey);
        const isServiceSignatureValid = serviceSignature === verificationServiceSignature;
    
        if (isServiceSignatureValid && isUserSignatureValid) {
            console.log('Авторизация успешна');
            setIsAuthenticating(true);
        } else {
            const errorMessage = !isServiceSignatureValid ? 'Ошибка подписи сервиса' : 'Ошибка подписи пользователя';
            console.error(errorMessage);
        }
    };

    return (
        <div>
            <AuthrixWidget
                locale="ru"
                isAuthenticating={isAuthenticating}
                onAuthData={handleAuthData}
                text={{
                    buttonText: 'Войти через authrix',
                    confirmationText: 'Подтвердите вход на сайт'
                }}
            />
        </div>
    );
}

Обработка событий

window.addEventListener('authrix-request', (event: CustomEvent<AuthRequestEvent['detail']>) => {
    const { message, domain } = event.detail;
    console.log(`Запрос авторизации от домена ${domain}: ${message}`);
});

const sendAuthResponse = (data: AuthWidgetData): void => {
    window.postMessage({
        source: 'authrix-content-script',
        type: 'AUTH_RESPONSE',
        data
    } as AuthResponseMessage, '*');
};

Пропсы

ПропТипПо умолчаниюОписание
locale'ru' | 'en''en'Язык виджета
text{ buttonText?: string, confirmationText?: string }{}Кастомные тексты
isAuthenticatingbooleanfalseСостояние авторизации (блокирует кнопку и меняет текст)
onAuthData(data: AuthWidgetData) => voidundefinedCallback для получения данных авторизации

События

Виджет отправляет событие authrix-request при клике на кнопку. Событие содержит следующие данные в detail:

  • domain: домен текущего сайта
  • message: сообщение для подтверждения авторизации
1.0.1

5 months ago

1.0.0

5 months ago