fruitcake / laravel-cors

Adds CORS (Cross-Origin Resource Sharing) headers support in your Laravel application
MIT License
6.27k stars 614 forks source link

Not working with laravel 5.6 passport and vue js axios #293

Closed t0n1zz closed 6 years ago

t0n1zz commented 6 years ago

hello, i read so many reference for my cors problem that this package gonna solve everything, but until now i tried to do anything related to this and got no solution.

So the error i get is

Failed to load https://bkcuvue.dev/api/v1/userData: Response to preflight request doesn't pass access control check: No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'https://bkcuvuelv56.dev' is therefore not allowed access.

and here is my kernel.php

<?php

namespace App\Http;

use Illuminate\Foundation\Http\Kernel as HttpKernel;

class Kernel extends HttpKernel
{
    /**
     * The application's global HTTP middleware stack.
     *
     * These middleware are run during every request to your application.
     *
     * @var array
     */
    protected $middleware = [
        \Illuminate\Foundation\Http\Middleware\CheckForMaintenanceMode::class,
        \Illuminate\Foundation\Http\Middleware\ValidatePostSize::class,
        \App\Http\Middleware\TrimStrings::class,
        \Illuminate\Foundation\Http\Middleware\ConvertEmptyStringsToNull::class,
        \App\Http\Middleware\TrustProxies::class,
        \Barryvdh\Cors\HandleCors::class,
    ];

    /**
     * The application's route middleware groups.
     *
     * @var array
     */
    protected $middlewareGroups = [
        'web' => [
            \App\Http\Middleware\EncryptCookies::class,
            \Illuminate\Cookie\Middleware\AddQueuedCookiesToResponse::class,
            \Illuminate\Session\Middleware\StartSession::class,
            // \Illuminate\Session\Middleware\AuthenticateSession::class,
            \Illuminate\View\Middleware\ShareErrorsFromSession::class,
            \App\Http\Middleware\VerifyCsrfToken::class,
            \Illuminate\Routing\Middleware\SubstituteBindings::class,
            \Laravel\Passport\Http\Middleware\CreateFreshApiToken::class,
        ],

        'api' => [
            'throttle:60,1',
            'bindings',
        ],
    ];

    /**
     * The application's route middleware.
     *
     * These middleware may be assigned to groups or used individually.
     *
     * @var array
     */
    protected $routeMiddleware = [
        'auth' => \Illuminate\Auth\Middleware\Authenticate::class,
        'auth.basic' => \Illuminate\Auth\Middleware\AuthenticateWithBasicAuth::class,
        'bindings' => \Illuminate\Routing\Middleware\SubstituteBindings::class,
        'cache.headers' => \Illuminate\Http\Middleware\SetCacheHeaders::class,
        'can' => \Illuminate\Auth\Middleware\Authorize::class,
        'guest' => \App\Http\Middleware\RedirectIfAuthenticated::class,
        'throttle' => \Illuminate\Routing\Middleware\ThrottleRequests::class,
    ];
}

and here is my route in api.php

Route::group(['prefix'=>'v1','middleware'=>'auth:api'],function(){
// Route::group(['prefix'=>'v1'],function(){

    // user
    Route::get('/profile', 'UserController@getUser');
    Route::get('/userData', 'UserController@userData');

});

and in my vue js side this is my app.js

import Vue from 'vue';
import Admin from './admin.vue';
import VueRouter from 'vue-router';
import routes from './routes';
import { store } from './store/store';
import Axios from 'axios';
import id from 'vee-validate/dist/locale/id';
import VeeValidate, { Validator } from 'vee-validate';

Validator.localize('id',id); //localization
Vue.use(VueRouter);
Vue.use(VeeValidate, {fieldsBagName: 'formFields'});

window.axios = Axios;
axios.defaults.headers.common = { 'X-Requested-With': 'XMLHttpRequest'};
let token = document.head.querySelector('meta[name="csrf-token"]');

if (token) {
    window.axios.defaults.headers.common['X-CSRF-TOKEN'] = token.content;
} else {
    console.error('CSRF token not found: https://laravel.com/docs/csrf#csrf-x-csrf-token');
}

const router = new VueRouter({
    base: '/admins',
    mode: 'history',
    routes
});

router.beforeEach((to, from, next) => {
    window.scrollTo(0, 0);
    if (to.fullPath !== "/login") {
        axios.get('/api/v1/profile').then(response => {       
            next();
        }).catch(error => {
            router.push('/login');
        })
    }else{
        next();
    }
});

Vue.directive('tooltip', function(el, binding){
    $(el).tooltip({
            title: binding.value,
            placement: binding.arg,
            trigger: 'hover'             
        })
});

export const bus = new Vue();

const app = new Vue({
    store,
    router,
    render: h => h(Admin)
}).$mount('#app');

and here is my login.vue

<template>
    <div class="login-container">
        <!-- Page container -->
        <div class="page-container">
            <!-- Page content -->
            <div class="page-content">
                <!-- Main content -->
                <div class="content-wrapper">

                    <!-- login form -->
                    <div class="panel panel-body login-form">
                        <div class="text-center">
                            <h5 class="content-group">SIMO
                                <small class="display-block">Sistem Informasi Manajemen Organisasi</small>
                            </h5>
                        </div>

                        <message :show="message.show">
                            <p>{{message.content}}</p>
                        </message>

                        <message :show="errors.any()" v-if="submited">
                            <h4>
                                <i class="icon-cancel-circle2"></i> Oops terjadi kesalahan</h4>
                            <ul>
                                <li v-for="error in errors.items">{{error.msg}}</li>
                            </ul>
                        </message>

                        <div class="form-group has-feedback has-feedback-right" :class="{'has-error' : errors.has('Username')}">
                            <div class="input-group">
                                    <div class="input-group-addon">
                                        <i class="icon-user text-muted"></i>
                                    </div>
                                    <input type="text" class="form-control" placeholder="Username" v-model="username" name="Username" v-validate="'required|min:5'" @keyup.enter="login" autofocus>
                            </div>

                            <div class="form-control-feedback" v-if="errors.has('Username')">
                                <i class="icon-cancel-circle2"></i>
                            </div>
                        </div>

                        <div class="form-group has-feedback has-feedback-right" :class="{'has-error' : errors.has('Password')}">
                            <div class="input-group">
                                <div class="input-group-addon">
                                    <i class="icon-lock2 text-muted"></i>
                                </div>
                                <input type="password" class="form-control" placeholder="Password" v-model="password" name="Password" v-validate="'required'"
                              @keyup.enter="login">
                            </div>

                            <div class="form-control-feedback" v-if="errors.has('Password')">
                                <i class="icon-cancel-circle2"></i>
                            </div>
                        </div>

                        <div class="form-group">
                            <button type="button" class="btn btn-primary btn-block" disabled v-if="loading">
                                <i class="icon-spinner2 spinner"></i>
                            </button>
                            <button type="button" class="btn btn-primary btn-block" @click.prevent="login"  v-else>Login
                                <i class="icon-circle-right2 position-right"></i>
                            </button>
                        </div>
                    </div>
                    <!-- /simple login form -->
                </div>
                <!-- /main content -->
            </div>
            <!-- /page content -->
        </div>
        <!-- /page container -->
    </div>
</template>

<script type="text/javascript">
    import Message from "../components/message.vue";
    import Progress from '../assets/plugins/loaders/progressbar.min.js'
    export default {
        components: {
            Message
        },
        data() {
            return {
                username: "",
                password: "",
                loading: false,
                submited: '',
                message: {
                    show: false,
                    className: '',
                    content: ''
                }
            }
        },
        mounted() {
            Progress.progressbar();
        },
        methods: {
            login() {
                this.$validator.validateAll().then((result) => {
                    if(result){
                        this.message.show = false;
                        this.loading = true;
                        axios.post('/login', {
                                username: this.username,
                                password: this.password
                            })
                            .then(response => {
                                this.$router.push('/');
                            }).catch(error => {
                                this.message.show = true;
                                this.message.className = 'bg-danger';
                                if (error.response.status === 422) {
                                    this.message.content = "Username atau password anda salah.";
                                } else {
                                    this.message.content = error.response.data.message;
                                }
                                this.loading = false;
                            });
                            this.submited = false;
                    }else{
                        window.scrollTo(0, 0);
                        this.submited = true;
                    }
                });
            }
        }
    }
</script>
t0n1zz commented 6 years ago

I am really sorry, after inspecting header response in chrome and i just remember that in my vue i am configuring api path and those api path just referenced to my old laravel 5.4 project before i am upgrading and that is what make things weird...