lundi 11 septembre 2017

401 Unauthorized error in rails api-only app when using React

I'm trying to use a rails api-ony app as back-end and React js as front-end. I'm using axios to send/ receive requests. Initially I wasn't able to even login then after much googling I came across this gem it was regarding CORS, it solved my POST request error.
I am able to successfully login when I do POST request in the rails app and I am getting token in return (Which works fine with POSTMAN app). Now, when I do GET request and pass that token as Header using react app it keeps on giving me 401 Unauthorized error, then again after much googling I saw this SO post. It didn't solved the issue. What am I missing? Kindly shed some light about the cause of this issue.
This is application_controller.rb:

class ApplicationController < ActionController::API
    include ActionController::MimeResponds

    before_action :authenticate_request, :current_user, :cors_preflight_check
    attr_reader :current_user

    #before_filter :current_user, :cors_preflight_check
  after_action :cors_set_access_control_headers

# For all responses in this controller, return the CORS access control headers.

def cors_set_access_control_headers
    headers['Access-Control-Allow-Origin'] = '*'
    headers['Access-Control-Allow-Methods'] = 'POST, PUT, DELETE, GET, OPTIONS'
    headers['Access-Control-Request-Method'] = '*'
    headers['Access-Control-Allow-Headers'] = 'Origin, X-Requested-With, Content-Type, Accept, Authorization'
  headers['Access-Control-Max-Age'] = "1728000"
end

# If this is a preflight OPTIONS request, then short-circuit the
# request, return only the necessary headers and return an empty
# text/plain.

def cors_preflight_check
  if request.method == :options
        headers['Access-Control-Allow-Origin'] = '*'
        headers['Access-Control-Allow-Methods'] = 'POST, PUT, DELETE, GET, OPTIONS'
        headers['Access-Control-Request-Method'] = '*'
        headers['Access-Control-Allow-Headers'] = 'Origin, X-Requested-With, Content-Type, Accept, Authorization'
    headers['Access-Control-Max-Age'] = '1728000'
    render :text => '', :content_type => 'text/plain'
  end
end

    require 'date'
            require 'json'
            require 'groupdate'

    @@PRESENT_DATE=Date.parse('2016-12-31T00:00:00.000Z')
    @@MONTHLY_SELECTOR="SELECT CONCAT(MONTHNAME(invoiceDate),' - ',YEAR(invoiceDate)), SUM(invoiceAmt) FROM invoices GROUP BY YEAR(invoiceDate), MONTH(invoiceDate)"
    @@QUARTERLY_SELECTOR="SELECT SUM(invoiceAmt) AS invoiceTotal, CONCAT('Q',QUARTER(invoiceDate), '(', YEAR(invoiceDate), ')') FROM invoices GROUP BY YEAR(invoiceDate), QUARTER(invoiceDate) ORDER BY YEAR(invoiceDate), QUARTER(invoiceDate)"
    @@YEARLY_SELECTOR="SELECT SUM(invoiceAmt) AS invoiceTotal, YEAR(invoiceDate) AS Year FROM invoices GROUP BY YEAR(invoiceDate) ORDER BY YEAR(invoiceDate)"

    private

    def authenticate_request
        @current_user = AuthorizeApiRequest.call(request.headers).result
        render json: { error: 'Not Authorized' }, status: 401 unless @current_user
    end
end

In my react app I have this:

import React, { Component } from 'react';
import '../App.css';
var axios = require('axios');

class Login extends Component {
  constructor(props){
    super(props);
    //this.state = {isToggleOn: true};
    this.loadDashboard = this.loadDashboard.bind(this);
    this.handleOnSubmit = this.handleOnSubmit.bind(this);
  }

  loadDashboard(token){
    axios({
      method:'get',
      url:'http://localhost:3000/api/dashboard',
      data: {
        Authorization: token,
      },
    })
     .then(function (response) {
       console.log(response);
     })
     .catch(function (error) {
       console.log("Error in loading Dashboard "+error.response.status);
     });
  }

  handleOnSubmit = () => {
     console.log("submittwed");
     axios({
       method:'post',
       url:'http://localhost:3000/authenticate',
       data: {
         email: 'test@mail.com',
         password: 'apple'
       },
     })
      .then((response) => {
        var token = response.data.auth_token;
        console.log(token);
        this.loadDashboard(token);
      })
      .catch(function (error) {
        console.log("Error in login "+error);
      });
   }

  render() {
    return (
      <div>
         Username: <input type="email" name="fname" /><br />
         Password: <input type="password" name="lname" /><br />
         <button onClick={this.handleOnSubmit}>LOG IN</button>
      </div>
    );
  }
}

export default Login;

  • Did any one else faced something similar??
  • How do I solve this?
  • Is there any less messy/better approach?

Please help me to solve this.

Aucun commentaire:

Enregistrer un commentaire