Автор оригинала: Doyin Olarewaju.
Проблема
Когда я впервые начал с реагирования, у меня была проблема. Мне нужно было контролировать доступ к определенным страницам в спа-салоне, который я построил с использованием React и React Reader, и я не мог найти никаких библиотек, которые могли бы помочь мне с этим, поэтому я решил написать немного утилиту, чтобы помочь мне с этим вопросом. Я назвал это моим промежуточным программным обеспечением React Router. Сырный, верно?
Сценарий образца
Скажем, у меня есть два взгляда. Войти (
Скажем, у меня есть мои маршруты настроить этот путь:
console.log(a)}> } /> } /> } />
Промежуточное программное обеспечение
Мой код промежуточного программного обеспечения выглядит так
routeToDisplay (middlewares = [], routeToVisit, directedFrom = '', extra = {}) { const mware = { privateRoute: (routeToVisit, directedFrom) => this.privateRoute(routeToVisit, ), alreadyLoggedIn: (routeToVisit) => this.alreadyLoggedIn(routeToVisit), adminAccess: (routeToVisit) => this.adminAccess(routeToVisit), superAdminAccess: (routeToVisit, directedFrom) => this.superAdminAccess(routeToVisit, directedFrom), } let ret = null try{ for (let i = 0; i < middlewares.length; i++) { ret = mware[middlewares[i]](routeToVisit, directedFrom, extra) if (ret.status === false) { break } } return ret.routeObject }catch(e){ //handle error here } }
Смущает, верно? Не волнуйтесь, я сломаю это. Функция RouteToDisplay – это мозг за всеми промежуточным программным обеспечением. Сама функция ожидает трех аргументов
routeToDisplay (middlewares = [], route, directedFrom = '/') {
средние годы : Набор строк, представляющих названия протоколов доступа, я хотел бы реализовать на каждом маршруте. Например, частный маршрутизатор представляет маршруты, которые не должны быть разрешены доступом, не входя в вошении в первую очередь, ALLEADYLOGGEDIN представляет маршруты, я не хочу, чтобы пользователь доступен, как только они вошли в систему, вы можете угадать остальные.
RouteTovisit : Маршрут Пользователь желает посетить.
Директироваться : В случае, если разрешение не успешно, где мы направляем пользователя. Например, в случае частных маршрутов мы направляем пользователя обратно в систему.
Следующая строка имеет список доступных потенциальных гостей
const mware = { privateRoute: (routeToVisit, directedFrom) => this.privateRoute(routeToVisit, ), alreadyLoggedIn: (routeToVisit) => this.alreadyLoggedIn(routeToVisit), adminAccess: (routeToVisit) => this.adminAccess(routeToVisit), superAdminAccess: (routeToVisit, directedFrom) => this.superAdminAccess(routeToVisit, directedFrom), }
По сути, это просто список Admitwoares Maped в функцию, которая реализует протокол доступа к этому маршруту. Функция, которую она отображает, просто использует желаемую проверку нами, например, приваряет, будет проверять, вошел ли пользователь или нет и разрешить доступ или запретить доступ.
let ret = null try{ for (let i = 0; i < midwares.length; i++) { ret = mware[midwares[i]](routeToVisit, directedFrom, extra) if (ret.status === false) { break } } return ret.routeObject }catch(e){ //handle error here }
Функция выше просто петля через имена промежуточного программного обеспечения, в которую я передал и вызывает функцию, связанную с ними. Функции возвращают свойство состояния, которое верно, если доступ должен быть разрешен или ложь, если он не должен быть.
Поскольку я получаю массив с ограниченными возможностями, это означает, что я могу пройти несколько с ограниченными возможностями. Это для цикла может пройти через них, и все будет хорошо, пока статус правда, но как только будет обнаружен ложь, доступ будет отклонен доступ. Например, я могу пройти в приварении и администраторе. Частный маршрут может вернуть True и Adminaccess может вернуть ложь, доступ будет отказаться в этом случае.
Последняя строка Возврат Ret.routeObject Возвращает любой путь, которую функция возвращается мне. Дело в том, что если доступ должен быть отказан, функция вернет маршрут
privateRoute (component, pathname = '/') { return (auth.fetchCurrentUser !== null ? this._getRouteReturn(true, component) : this._getRouteReturn(false,) ) }
Функция принимает компонент, который мы хотели бы отобразить маршрут, который мы хотим перенаправить, в случае разрешения запрещено. Внутри функции мы проверяем, определяется ли текущий пользователь или если текущий пользователь вошел в систему в зависимости от того, как выглядит ваша аутентификация. Если пользователь мы называем функцию
_GetRouterTurn ()
Прохождение статуса и компонент он должен отправить обратно. Вот что выглядит _getrouterturn
_getRouteReturn (status, routeObject) { return {status, routeObject} }
Если разрешение было успешным, мы получим текущий маршрут обратно, если не получим перенаправленный маршрут обратно. В этом случае он будет перенаправлять нас назад, чтобы войти в систему. После того, как логин был успешным, мы будем доставлены на маршрут, который мы пытались получить доступ к тому, что нас отказано. Например, если мы попытались получить доступ к приборной панели администратора, не входите в систему, мы будем перенаправлены для входа в систему, и после успешного входа в систему мы будем направлены на приборную панель администратора.
Вы можете реализовать то же самое для других маршрутов, например, путь доступа администратора может выглядеть что-то подобное.
adminAccess (component, pathname = '/') { //in my case i stored my allowed roles in array form in my db, yours could be different if (utils.arrayContains(role, 'admin')) { return this._getRouteReturn(true, component) } return this._getRouteReturn(false,) }
Таким образом, вышеуказанный метод, как то, прежде чем он просто берет компонент, который мы хотим отображать. Я не пропускаю маршрут, который я хочу перенаправить, потому что это не проблема входа в систему. Скорее, я пропускаю путь к маршруту, который отображает информацию о том, что учетная запись администратора, поэтому пользователь знает, что должно быть сделано, чтобы быть администратором.
Я думаю, что это довольно прямо вперед.
Используя его на наших маршрутах
Теперь наши маршруты выглядели так, как это раньше
console.log(a)}> } /> } /> } />
Давайте дадим немного макияж. Скажем, я экспортировал мою промежуточную программу по умолчанию из своего собственного класса. Я импортирую это так раньше
import middleware from './middleware'
console.log(a)}> middleware.routeDisplay(['alreadyLoggedIn'], ) } /> middleware.routeDisplay(['privateRoute','adminAccess'], )} /> middleware.routeDisplay(['privateRoute','superAdminAccess'], ) } />
Вот и все. Давайте посмотрим на код для всего промежуточного программного обеспечения ниже.
import React from 'react' import { Redirect } from 'react-router-dom' import auth from './stores/authenticationStore' import utils from './stores/utils' class Middleware { routeToDisplay (middlewares = [], routeToVisit, directedFrom = '', extra = {}) { const mware = { privateRoute: (routeToVisit, directedFrom) => this.privateRoute(routeToVisit, ), alreadyLoggedIn: (routeToVisit) => this.alreadyLoggedIn(routeToVisit), adminAccess: (routeToVisit) => this.adminAccess(routeToVisit), superAdminAccess: (routeToVisit, directedFrom) => this.superAdminAccess(routeToVisit, directedFrom), } let ret = null try{ for (let i = 0; i < middlewares.length; i++) { ret = mware[middlewares[i]](routeToVisit, directedFrom, extra) if (ret.status === false) { break } } return ret.routeObject }catch(e){ //handle error here } } _getRouteReturn (status, routeObject) { return {status, routeObject} } adminAccess (component, pathname = '/') { //in my case i stored my allowed roles in array form in my db, yours could be different if (utils.arrayContains(role, 'admin')) { return this._getRouteReturn(true, component) } return this._getRouteReturn(false,) } privateRoute (component, pathname = '/') { return (auth.fetchCurrentUser !== null ? this._getRouteReturn(true, component) : this._getRouteReturn(false, ) ) } }