Move Laravel Auth Views to VueJS with Vuetify
This is a topic alot of people (including myself) struggle with. I see the same question posted to forums everywhere. Trying to get Laravel Passport to work with VueJS is kind of a nightmare. This is why I prefer web authentication when building SPAs. Laravel has some very convenient middleware that handles all of the tokens, but the only catch is users need to authenticate using web auth. I will cover this specific scenario
This article will focus on moving the Laravel Auth views completely to VueJS with the exception of Login. We will keep the Laravel backend mostly the same, but will only serve the index file from Laravel.
We will also be utilizing Vue Router for all page routing and domain filtering for the Dashboard, Auth, and Landing Page views. Some routes will only work for certain domains and we will accomplish this by loading routes depending on the request domain.
You can find the full code example at github
This example builds off of a previous series. Check out the first article here.
Package Installations
We will need to validate input prior to sending it to the API. We can utilize a great VueJS package called VeeValidate. It is easy to use and it keeps the components clean of complex validation logic. Run the below command in the project root.
npm install vee-validate --save-dev
We can also use a great package for UI development called Vuetify. This will greatly simplify the frontend and make component creation a breeze. Run the below command to install it.
npm install vuetify --save-dev
Check out the documentation for VeeValidate and Vuetify for more info.
Folder structure
I will be using this folder structure to organize components. You can modify this to your liking.
Auth API File
We need a method for interacting with the Laravel Auth routes. We can create an auth.js
file that can take care of this. We will import this file into our components whenever we need to do any auth-like tasks. It is pretty simple.
Layout Components
Since there are multiple sites being served from our frontend, we need to create some Layouts. This will cleanup the App.vue and make it more general. Below you will see the DashboardLayout and the AuthLayout.
DashboardLayout.vue
AuthLayout.vue
App.vue
The new slimmed down App.vue
file
Auth Components
Here are the new Auth Vue Components. I just copied the original blade views and placed them in a Vue Single File Component. Not much has changed except for the validation logic and the data properties. I did add some loading indications to make for a better user experience.
Register.vue
Login.vue
One thing to note here is we are still making a web post request to the normal Laravel endpoint. This will trigger a page reload, but this is something that the user should expect.
ResetEmail.vue
Reset password.vue
Welcome.vue
This is just the Laravel Welcome page. I moved that over as well.
NotFound.vue
This component will be used with the catchall route in Vue Router.
Vue router changes
We will now conditionally load routes depending on the domain used in the request. We will also switch history mode on so that the # sign is removed from the URL. This will help with any redirects on the Laravel side.
app.js
routes.js
Here we are importing all of the View Components and conditionally returning a set of routes depending on the hostname used. This is pretty slick.
Laravel Route Changes
We will now direct all page traffic to the Vue frontend. We do this with a catch-all route in web.php that points to the index.blade.php view.
I will still keep the post routes for login and logout. See the updated web.php
and api.php
route files below
web.php
api.php
Laravel Auth Controllers
We can now adjust the controllers to return json responses to our Vue app. The format that the View Components are looking for is:
{
status: 'success',
message: 'Status Message'
}
Register Controller
Password Reset Controller
Password Email Controller
Login Controller
Some Minor Tweaks
Axios Configuration
We can automatically add 422 validation errors to our VeeValidate error object by using an interceptor. I am also redirecting to the login page on 401 errors. Modify the axios.js file as shown below.
Fix password reset emails
Laravel’s password reset emails use a named password.reset route to generate the reset link. We can create a new notification that will be used instead that generates the correct tenant URL. We will also need to specify the database connection to be used to store the password reset requests. See the changes below.
ResetPassword.php
config/auth.php
Add a connection entry and put in tenant
as shown below
Update the Tests
So I ran my tests after all of the above changes and most didn’t pass. It was mainly due to the redirect URLs and views not matching. I updated everything in the Github Repo. You can also check out the article about optimizes tests here.
Conclusion
There are a tons of changes in this article, but I feel like the frontend will be more consistent and streamlined this way. It also separates the frontend and the API fully except for the Login/Logout routes.
Hopefully this helped you out! If you have any questions, comments, suggestions please let me know down in the comments.
Check out the Series below!
Part 1 — Laravel Passport and Hyn\Tenancy
Part 2 — VueJS and Laravel API
Part 3 — Laravel Multi-Tenant Testing