[Перевод] Защищенная маршрутизация и проверка разрешений с помощью React и Node.js

Node.js внешний интерфейс Программа перевода самородков
[Перевод] Защищенная маршрутизация и проверка разрешений с помощью React и Node.js

в прошлые выходные я хотел копать некоторые нетRedux-SagaАбсолютная чистота этих прибамбасовReact.

Поэтому я создал небольшой проект вStrapi— Работает с фреймворком Node.js, который включает в себя расширяемую панель администратора и некоторые встроенные функции (авторизация, загрузка, контроль разрешений...), используя толькоCreate React AppСоздайте небольшой шаблон для реализации потока авторизации.

React Nodejs

В этом уроке мы будем использоватьStrapiпредоставляется APIJSON Web TokensБыстро реализуйте базовый процесс авторизации и проведите вас через пошаговое руководство по использованию стороннего поставщика авторизации входа (Facebook, GitHub, Google...) в Strapi для авторизации ваших пользователей для входа в систему (это может быть Веселее).

Strapi authentication

Примечание. Исходный код этой статьи можно найти по адресуGitHubнайти на.

Создать проект

Прежде чем приступить к работе, вам необходимо создать API Strapi:

$ npm install strapi@alpha -g
$ strapi new my-app
$ cd my-app && strapi start

и ваше внешнее приложение:

$ npm install create-react-app -g
$ create-react-app good-old-react-authentication-flow

тебе следуетСначала зарегистрируйте первого пользователя, и вы готовы к работе!

Интерфейсная архитектура приложения

яReact BoilerplateБольшой поклонник фреймворков, поэтому я создал похожее приложение для организации своего кода:

/src
└─── containers // 与路由相关的 React 组件
|    └─── App // 应用的入口
|    └─── AuthPage // 负责所有授权页面的组件
|    └─── ConnectPage // 负责使用第三方提供器进行授权
|    └─── HomePage // 只能在用户登陆后访问到
|    └─── NotFoundPage // 404 组件
|    └─── PrivateRoute // 高阶组件
|
└─── components // 展示组件
|
└─── utils
     └─── auth
     └─── request // 使用 fetch 的网络请求辅助库

Настройте маршрутизацию и PrivateRoute

Чтобы реализовать аутентифицированное представление, нам нужно сначала создатьHoC:компоненты более высокого порядкачтобы проверить, может ли пользователь получить доступ к определенному URL-адресу. Для этого нам просто нужно следоватьофициальная документация,ИсправлятьfakeAuthпример, и используйте нашauth.jsВспомогательные файлы:

import React from 'react';  
import { Redirect, Route } from 'react-router-dom';

// Utils
import auth from '../../utils/auth';

const PrivateRoute = ({ component: Component, ...rest }) => (  
  <Route {...rest} render={props => (
    auth.getToken() !== null ? (
      <Component {...props} />
    ) : (
      <Redirect to={{
        pathname: 'auth/login',
        state: { from: props.location }
        }}
      />
    ):
  )} />
);

export default PrivateRoute;  

Затем создадим маршрут:

import React, { Component } from 'react';  
import { BrowserRouter as Router, Switch, Route } from 'react-router-dom';

// Components
import AuthPage from '../../containers/AuthPage';  
import ConnectPage from '../../containers/ConnectPage';  
import HomePage from '../../containers/HomePage';  
import NotFoundPage from '../../containers/NotFoundPage';

// 这个组件是用于防止未登录用户访问特定路由的高阶组件
import PrivateRoute from '../../containers/PrivateRoute';

// Design
import './styles.css';

class App extends Component {  
  render() {
    return (
      <Router>
        <div className="App">
          <Switch>
            {/* A user can't go to the HomePage if is not authenticated */}
            <PrivateRoute path="/" component={HomePage} exact />
            <Route path="/auth/:authType/:id?" component={AuthPage} />
            <Route exact path="/connect/:provider" component={ConnectPage} />
            <Route path="" component={NotFoundPage} />
          </Switch>
        </div>
      </Router>
    );
  }
}

export default App;

Создание представления авторизации

Теперь все маршруты, необходимые для создания представления, реализованы. То, как мы объявляем маршруты, позволяет нам создавать路径Создайте правильные компоненты формы.

Сначала создадимforms.jsonдля обработки создания формы в каждом представлении авторизации:

  • forgot-password
  • login
  • register
  • reset-password

JSONСтруктура такая (вы можете найти вInputкомпонентcustomBootstrapClassЭто знакомство необходимо):

{
  "views": {    
    "login": [
      {
        "customBootstrapClass": "col-md-12",
        "label": "Username",
        "name": "identifier",
        "type": "text",
        "placeholder": "johndoe@gmail.com"
      },
      {
        "customBootstrapClass": "col-md-12",
        "label": "Password",
        "name": "password",
        "type": "password"
      },
      {
        "customBootstrapClass": "col-md-6",
        "label": "Remember me",
        "name": "rememberMe",
        "type": "checkbox"
      }
    ]
  },
  "data": {
    "login": {
      "identifier": "",
      "password": "",
      "rememberMe": false
    }
  }
}

установить состояние при изменении маршрута

Если вы хотите, чтобы пользователь из маршрутизацииauth/loginпереключиться на маршрутизациюauth/registerПри настройке формы нам нужно использовать следующий жизненный цикл:

componentDidMount() {  
  // 使用一个函数生成表单以防
  // 表单在其他生命周期里重复
  this.generateForm(this.props);
}
componentWillReceiveProps(nextProps) {  
  // 因为我们对所有的 auth 视图使用同样的容器
  // 所以我们需要在路径改变的时候更新 UI
  if (nextProps.location.match.params.authType !== this.props.location.match.params.authType) {
    this.generateForm(nextProps);
  }
}

generateFormметод отвечает из вышеперечисленногоforms.jsonПолучить данные из файла.

Создать представление

Чтобы создать форму, нам просто нужно отобразитьforms.jsonданные в .

handleChange = ({ target }) => this.setState({ value: { ...this.state.value, [target.name]: target.value } });

render() {  
  const inputs = get(forms, ['views', this.props.match.params.authType, []);

  return (
    <div>
      <form onSubmit={this.handleSubmit}>
        {inputs.map((input, key) => (
          <Input
            autoFocus={key === 0}
            key={input.name}
            name={input.name}
            onChange={this.handleChange}
            type={input.type}
            value={get(this.state.value, [input.name], '')}
          />
        ))}
        <Button type="submit" />
      </form>
    </div>
  );
}

Strapi login view

К этому моменту все представления, необходимые авторизованным пользователям, должны быть созданы! Нам просто нужно сделать вызов API для доступа к приложению.

Публикация данных в API

Чтобы сделать вызов API, я написалrequestвспомогательные файлы (Вы можете посетить демо-приложение здесь), Нам нужно только нашиhandleSubmitИспользуйте его в функции:

handleSubmit = (e) => {  
  e.preventDefault();
  const body = this.state.value;
  const requestURL = 'http://localhost:1337/auth/local';

  request(requestURL, { method: 'POST', body: this.state.value})
    .then((response) => {
      auth.setToken(response.jwt, body.rememberMe);
      auth.setUserInfo(response.user, body.rememberMe);
      this.redirectUser();
    }).catch((err) => {
      console.log(err);
    });
}

redirectUser = () => {  
  this.props.history.push('/');
}

Здесь нет ничего сложного, когда мы получаем ответ от API, мы просто сохраняем необходимую информацию вlocalStorageилиsessionStorage, то мы можем перенаправить пользователя на домашнюю страницу.

Мы только что реализовали самую сложную часть, потому что так легко использовать стороннего поставщика авторизации, такого как Facebook!

Использование поставщика авторизации

Независимо от того, выбираете ли вы Facebook, GitHub или Google, использование стороннего поставщика авторизации на Strapi для авторизации ваших пользователей для входа в систему очень просто 🙈. В этом примере я покажу вам, как использовать стороннего поставщика авторизации Facebook.

Потому что Страпи (Также) не предоставляет Javascript SDK для взаимодействия с API Strapi и API Facebook.

Конкретный процесс выглядит следующим образом:

  • Пользователь "нажимает, чтобы войти в Facebook"
  • перенаправить пользователя на другую страницу, где он может авторизоваться
  • После авторизации Facebook будет перенаправлять пользователя в ваше приложение с кодом в URL
  • Отправьте этот код в Strapi

В этот момент нам нужно толькоcomponentDidMountИнициировать запросы API в жизненном цикле, а затем в соответствии сConnectPageСодержимое ответа в контейнере перенаправляет пользователя на соответствующую страницу:

componentDidMount() {  
  const { match: {params: { provider }}, location: { search } } = this.props;
  const requestURL = `http://localhost:1337/auth/${provider}/callback${search}`;

 request(requestURL, { method: 'GET' })
   .then((response) => {
      auth.setToken(response.jwt, true);
      auth.setUserInfo(response.user, true);
      this.redirectUser('/');
   }).catch(err => {
      console.log(err.response.payload)
      this.redirectUser('/auth/login');
   });
}

redirectUser = (path) => {  
  this.props.history.push(path);
}

Показать провайдера авторизации в AuthPage

Для этого нам понадобитсяSocialLinkКомпоненты:

/**
*
* SocialLink
*
*/

import React from 'react';  
import PropTypes from 'prop-types';

import Button from '../../components/Button'

function SocialLink({ provider }) {  
  return (
    <a href={`http://localhost:1337/connect/${provider}`} className="link">
      <Button type="button" social={provider}>
        <i className={`fab fa-${provider}`} />
        {provider}
      </Button>
    </a>
  );
}

SocialLink.propTypes = {  
  provider: PropTypes.string.isRequired,
};

export default SocialLink;

Затем нам нужно добавить его вAuthPageсередина:

render() {  
  const providers = ['facebook', 'github', 'google', 'twitter']; // 如果要把一个提供器移除,只要把它从这个数组中删除即可...

  return (
     <div>
       {providers.map(provider => <SocialLink provider={provider} key={provider} />)}
       {/* Some other code */}
     </div>
  );
}

Login page

Это все, что нам нужно сделать в нашем внешнем приложении, теперь нам просто нужно настроить Strapi для включения сторонних поставщиков авторизации 😎

Настройка провайдера авторизации Facebook для регистрации пользователей

прибытьFacebook developersи создатьtestПриложения.

  • Добавить в зону продуктаFacebook login
  • выберитеWeb
  • Установить URL-адрес сайта наhttp://localhost:3000

Facebook setup

  • Скопируйте идентификатор приложения и секрет приложения со страницы панели инструментов в свое приложение.

Facebook setup

  • существуетFacebook login > Advanced settings, Добавить:http://localhost:1337/connect/facebook/callbackприбытьValid OAuth redirect URIsполе.

Facebook setup

Настроить Страпи

Вы создали приложение на Facebook, которое можно использовать для настройки провайдера Facebook в вашем проекте.

прибытьВкладка «Поставщики» в области «Пользователи и разрешения», заполните форму следующим образом:

Admin FB setup

Не забудьте сохранить изменения.

В заключение

Надеюсь, что этот маленький учебник поможет вам использоватьReactа такжеStrapiВыполните авторизацию пользователя.

Я не думаю, что это много работы, и это легко! ты сможешьздесьНайдите шаблон, который я создал на этих выходных с помощью приложения Create React.

здесьЕсть и другое применениеReact BoilerplateПолный пример, он же полная реализация всего процесса авторизации. Во втором примере используются React и Redux-Saga, которые также являются шаблоном, который мы использовали для создания нашего административного интерфейса на основе Strapi.

Каждый может поделиться и оставить сообщение в комментариях!

Если вы обнаружите ошибки в переводе или в других областях, требующих доработки, добро пожаловать наПрограмма перевода самородковВы также можете получить соответствующие бонусные баллы за доработку перевода и PR. начало статьиПостоянная ссылка на эту статьюЭто ссылка MarkDown этой статьи на GitHub.


Программа перевода самородковэто сообщество, которое переводит высококачественные технические статьи из Интернета сНаггетсДелитесь статьями на английском языке на . Охват контентаAndroid,iOS,внешний интерфейс,задняя часть,блокчейн,товар,дизайн,искусственный интеллектЕсли вы хотите видеть более качественные переводы, пожалуйста, продолжайте обращать вниманиеПрограмма перевода самородков,официальный Вейбо,Знай колонку.