ReactJS - axios 拦截器 onSubmit

ReactJS - axios interceptor onSubmit

结构:

ApiService.js
components/
          TrackComponent.jsx

TrackComponent.jsx

我在 render() 的 React 中有这个表单,它触发了一个到达一个端点的事件:

<form onSubmit={ (event) => this.handleEditPlaylist(event) }>
 <div className="field">
   <input
     name="artist"
     className="input is-dark is-large"
     type="text"
   />
  </div>
</form>

句柄函数:

handleEditPlaylist(event) {
    event.preventDefault();
    const formType = this.props.formType
    var headers = {
        'Content-Type': 'application/json',
        Authorization: `Bearer ${window.localStorage.authToken}`
      }
    const {userId} = this.props
    const data = {
      value: this.state.formData.value,
      spotify_token: this.props.spotifyToken
    };
    const url = `${process.env.REACT_APP_WEB_SERVICE_URL}/handle_edit_playlist/${this.state.artist}/${userId}`;

    axios.post(url, data, {headers: headers})
      .then((res) => {
        console.log(data);
        if(data){this.clearForm();}
      })
      .catch((err) => {
    });

    axios.get(url, { 
      headers: {
        'Content-Type': 'application/json',
        Authorization: `Bearer ${window.localStorage.authToken}`
      }
      }).then((res) => {
          console.log(res.data);
          this.setState({
            seeds: res.data.data[0].seeds,
            artist: res.data.data[0].artist,
          })
      })
  };

这有效。


Api instance inside component

现在,我必须在上面的组件中实例化这个 axios 拦截器,以便处理具有两个端点的访问令牌。

import Axios from 'axios';

class ApiService {
  constructor() {
    this.axios = Axios.create();
    this.axios.interceptors.response.use(null, this.authInterceptor.bind(this));

    this.get = this.axios.get.bind(this.axios);
    this.post = this.axios.post.bind(this.axios);
  }

  async authorize() {
    console.log('Async in authorize')
    const { accessToken } = await this.axios.post('/get_token/1', {});
    this.setAccessToken(accessToken);
    return accessToken; // return it to the component that invoked it to store in some state
  }

  async getTrack(userId, spotifyToken, artist) { // <---------------------------
    console.log('getAroma in ApiService', userId, spotifyToken, artist)
    return this.axios.get(
      `${process.env.REACT_APP_WEB_SERVICE_URL}/get-tracks/${artist}/${userId}/${spotifyToken}`
    );
  }

  async updateAccessToken(userId) {
    const { accessToken } = await this.axios.post(`/refresh-token/1`, {});
    this.setAccessToken(accessToken);
  }

  (...)

export const apiService = new ApiService(); // this is a single instance of the service, each import of this file will get it

我希望上面的 onSubmit 事件也触发拦截器实例化调用。就其本身而言,我可以这样做:

import {apiService} from '../ApiService';

async getTrack(event) {
    if (this.props.isAuthenticated) {
      const {userId, spotifyToken} = this.props;
      const {artist} = this.state.artist
      const aromaticTracks = await apiService.getTracks(userId, spotifyToken, artist);
      this.setState({newTracks});
    } else {
      this.setState({newTracks: []});
    }
  }

如果我在 handleEditPlaylist 中插入这个异步 getTrack,就在提交表单之后,就像这样:

(...)

axios.post(url, data, {headers: headers})
      .then((res) => {
        this.getTrack(); // <----------- HERE
        console.log(data);
        if(data){this.clearForm();}
      })
(...)

我在 async getTrack console.log('getTrack in ApiService', userId, spotifyToken, artist) 中为表单提交的值(艺术家)得到 'undefined',但在下面打印在 console.log(data) 中提交的值。 .


如何正确处理这个拦截器onSubmit

您的代码中唯一的问题是因为您正试图从您已经访问的状态中解构一个值

async getTrack(event) {
    if (this.props.isAuthenticated) {
      const {userId, spotifyToken} = this.props;
      const {artist} = this.state; // this needs to be this.state and not this.state.artist
      const aromaticTracks = await apiService.getTracks(userId, spotifyToken, artist);
      this.setState({newTracks});
    } else {
      this.setState({newTracks: []});
    }
  }

destructuring 赋值语法是一个 JavaScript 表达式,可以将数组中的值或对象中的属性解压缩到不同的变量中。

阅读 object destructuring

的文档