реагировать не возвращает this.props - PullRequest
2 голосов
/ 28 апреля 2020

Мои компоненты отображаются с данными с сервера, если маршрут не защищен. Как только я защищаю маршрут, this.props возвращает неопределенное значение.

Приложение. js

import React, { Component } from 'react';
import {Route, withRouter} from 'react-router-dom';
import auth0Client from './Auth/Auth';
import NavBar from './NavBar/NavBar';
import Callback from './Callback/Callback';
import Customers from './Customers/Customers';
import Customer from './Customer/Customer';
import SecuredRoute from './SecuredRoute/SecuredRoute';

class App extends Component {
  constructor(props) {
    super(props);
    this.state = {
      checkingSession: true,
    }
  }

  async componentDidMount() {
    if (this.props.location.pathname === '/callback') {
      this.setState({checkingSession:false});
      return;
    }
    try {
      await auth0Client.silentAuth();
      this.forceUpdate();
    } catch (err) {
      if (err.error !== 'login_required') console.log(err.error);
    }
    this.setState({checkingSession:false});
  }

  render() {
    return (
      <div>
        <NavBar/>
        <Route exact path='/callback' component={Callback}/>
        <SecuredRoute exact path='/customers'
          component={CustomersComponent}
          checkingSession={this.state.checkingSession}
        />
        <SecuredRoute exact path='/customers/:customerId'
          component={CustomerComponent}
          checkingSession={this.state.checkingSession}
        />
        {/*<Route exact path='/customers/:customerId' component={CustomerComponent}/>*/} // this works
      </div>
    );
  }
}

const CustomersComponent = (props) => {
  return (
    <Customers {...props}
    />
  );
}

const CustomerComponent = (props) => {
  return (
    <Customer {...props}
    />
  );
}

export default withRouter(App);

Auth. js

import auth0 from 'auth0-js';

class Auth {
  constructor() {
    this.auth0 = new auth0.WebAuth({
      domain: 'domain.eu.auth0.com',
      audience: 'https://domain.eu.auth0.com/userinfo',
      clientID: 'clientID',
      redirectUri: 'http://localhost:3000/callback',
      responseType: 'id_token',
      scope: 'openid profile'
    });

    this.getProfile = this.getProfile.bind(this);
    this.handleAuthentication = this.handleAuthentication.bind(this);
    this.isAuthenticated = this.isAuthenticated.bind(this);
    this.signIn = this.signIn.bind(this);
    this.signOut = this.signOut.bind(this);
  }

  getProfile() {
    return this.profile;
  }

  getIdToken() {
    return this.idToken;
  }

  isAuthenticated() {
    return new Date().getTime() < this.expiresAt;
  }

  signIn() {
    this.auth0.authorize();
  }

  handleAuthentication() {
    return new Promise((resolve, reject) => {
      this.auth0.parseHash((err, authResult) => {
        if (err) return reject(err);
        if (!authResult || !authResult.idToken) {
          return reject(err);
        }
        this.setSession(authResult);
        resolve();
      });
    })
  }

  setSession(authResult) {
    this.idToken = authResult.idToken;
    this.profile = authResult.idTokenPayload;
    // set the time that the id token will expire at
    this.expiresAt = authResult.idTokenPayload.exp * 1000;
  }

  signOut() {
    this.auth0.logout({
      returnTo: 'http://localhost:3000',
      clientID: 'clientID',
    });
  }

  silentAuth() {
    return new Promise((resolve, reject) => {
      this.auth0.checkSession({}, (err, authResult) => {
        if (err) return reject(err);
        this.setSession(authResult);
        resolve();
      });
    });
  }
}

const auth0Client = new Auth();

export default auth0Client;

Клиенты. js

import React, {Component} from 'react';
import {Link} from 'react-router-dom';
import axios from 'axios';

class Customers extends Component {
  constructor(props) {
    super(props);

    this.state = {
      accounts: null,
      customers: null
    };
  }

  async componentDidMount() {
    const customers = (await axios.get('http://localhost:8081/customers/')).data;
    const accounts = (await axios.get('http://localhost:8081/accounts/')).data;
    this.setState({
      accounts,
      customers
    });
  }

  countAccounts(custid) {
    const accounts = this.state.accounts;
    let count = 0;
    accounts.forEach(function(element) {
      if (element.CustomerId === custid) {
        count = count + 1;
      }
    });
    return count;
  }

  countOverdueAccounts(custid) {
    const accounts = this.state.accounts;
    let count = 0;
    accounts.forEach(function(element) {
      if (element.CustomerId === custid && element.CurrentStatus !== "Active") {
        count = count + 1;
      }
    });
    return count;
  }

  listOfAccounts(custid) {
    const accounts = this.state.accounts;
    let arr = [];
    accounts.forEach(function(element) {
      if (element.CustomerId === custid) {
        arr.push(<p key={element.id}>{element.AccountNumber}</p>)
      }
    });
    return arr;
  }

  overdueCard(custid) {
    const accounts = this.state.accounts;
    let cardTheme = "card text-white bg-primary mb-3";
    accounts.forEach(function(element) {
      if (element.CustomerId === custid && element.CurrentStatus !== "Active") {
        cardTheme = "card text-white bg-danger mb-3";
      }
    });
    return cardTheme;
  }

  render() {
    return (
      <div className="container">
        <div className="row">
          {this.state.customers === null && <p>Loading customer records...</p>}
          {
            this.state.customers && this.state.customers.map(customer => (
              <div key={customer.id} className="col-sm-12 col-md-4 col-lg-3">
                <Link to={`/customers/${customer.id}`}>
                  <div className={this.overdueCard(customer.id)}>
                    <div className="card-header">
                      <p>Accounts: {this.countAccounts(customer.id)}</p>
                      <p>Overdue accounts: {this.countOverdueAccounts(customer.id)}</p>
                    </div>
                    <div className="card-body">
                      <h4 className="card-title">Current status: {customer.CurrentStatus}</h4>
                      <p className="card-text">{customer.FirstName} {customer.Surname}</p>
                      <p className="card-text">ID number: {customer.NationalIDNumber}</p>
                      <p className="card-text">Contact number: {customer.ContactNumber}</p>
                      <p className="card-text">Email: {customer.EmailAddress}</p>
                      <div className="card-text">List of accounts:{this.listOfAccounts(customer.id)}</div>
                    </div>
                  </div>
                </Link>
              </div>
            ))
          }
        </div>
      </div>
    )
  }
}

export default Customers;

Клиент. js

import React, {Component} from 'react';
import axios from 'axios';
import SubmitUpdate from './SubmitUpdate';
import auth0Client from '../Auth/Auth';

class Customer extends Component {
  constructor(props) {
    super(props);
    this.state = {
      account: null,
      customer: null
    };

    this.submitUpdate = this.submitUpdate.bind(this);
  }

  async componentDidMount() {
    await this.refreshCollection();
  }

  async refreshCollection() {
    //console.log('this.props: ', this.props);
    const { match: { params } } = this.props; // <----- fails here as this.props is not returned
    //console.log(`http://localhost:8081/customers/${params.customerId}`);
    const customer = (await axios.get(`http://localhost:8081/customers/${params.customerId}`)).data;
    const account = (await axios.get(`http://localhost:8081/accounts/${params.customerId}`)).data;
    this.setState({
      account: account,
      customer: customer
    });
  }

  async submitUpdate(update){
    await axios.post(`http://localhost:8081/update/${this.state.customer.id}`, {
      update,
    }, {
      headers: { 'Authorization': `Bearer ${auth0Client.getIdToken()}` }
    });
    await this.refreshCollection();
  }

  render() {
    const {customer} = this.state;
    const {account} = this.state;
    //console.log('customer: ', customer);
    //console.log('account: ', account);

    if (customer === null) return <p>Loading... </p>;
    return (
      <div className="container">
        <div className="row">
          <div className="jumbotron col-12">
            <p className="card-text">{customer[0].FirstName} {customer.Surname}</p>
            <p className="card-text">ID number: {customer[0].NationalIDNumber}</p>
            <p className="card-text">Contact number: {customer[0].ContactNumber}</p>
            <p className="card-text">Email: {customer[0].EmailAddress}</p>
            <hr className="my-4" />
            <SubmitUpdate accountId={customer.id} submitUpdate={this.submitUpdate} />
            <p>Notes</p>

          </div>
        </div>
      </div>
    );
  }
}

export default Customer;

SecuredRoute. js

import React from 'react';
import {Route} from 'react-router-dom';
import auth0Client from '../Auth/Auth';

function SecuredRoute(props) {
  const {component: Component, path, checkingSession} = props;
  return (
    <Route path={path} render={() => {
      if (checkingSession) return <h3 className="text-center">Validating session...</h3>;
      if (!auth0Client.isAuthenticated()) {
        auth0Client.signIn();
        return <div></div>;
      }
      return <Component />
    }} />
  );
}

export default SecuredRoute;

Пожалуйста, помогите мне понять, что я делаю неправильно , Я уверен, что это что-то простое, я просто не могу понять это.

1 Ответ

1 голос
/ 28 апреля 2020

Не забудьте передать реквизиты компонента , а также реквизиты маршрутизатора .

Как это

import React from 'react';
import {Route} from 'react-router-dom';
import auth0Client from '../Auth/Auth';

function SecuredRoute(props) {
    const {component: Component, path, checkingSession, ...rest} = props;
    return (
        <Route path={path} render={(routerProps) => { // <---- get the props
            if (checkingSession) return <h3 className="text-center">Validating session...</h3>;
            if (!auth0Client.isAuthenticated()) {
                auth0Client.signIn();
                return <div></div>;
            }
            return <Component {...rest} {...routerProps}/> // <---- include the routerProps
        }} />
    );
}

export default SecuredRoute;
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...