Keycloak-js client with Quasar

So you’d like to use openid-connect (oidc), especially keycloak (kc) in your Quasar app.

There’s a package, @dsb-norge/vue-keycloak-js . I’d recommend you fork it and create your own version with the keycloak-js version that matches your Keycloak server. However it also works with just the version used in this git repository.

The git repository is available at
https://github.com/dsb-norge/vue-keycloak-js

This is for Quasar v1

Alright let’s get started.

1. Create a file named silent-check-sso.html with the following content:

Put that file in the public directory as its path is
public/silent-check-sso.html.

2. Create boot/keycloak.js

3. Reference the created boot file in quasar.conf.js

And that’s really all there is to it.

After this is done you can access the keycloak object via $keycloak in your template.

Spread the love
Published
Categorized as Entwicklung

By Darko Luketic

I'm a self-employed developer since 2004. I have been working professionally since 2000. My first contact with computers was the C64 at the age of 11 where I coded in machine code and assembler. I worked with PHP professionally for 11 years, nowadays I prefer Angular, Go and Flutter, but I'm open minded. However I would dislike taking a step back to PHP. My services are for hire I'm also looking for remote employment.

6 comments

  1. Thanks for the helpful post.

    I tried also to connect kecloak-js with quasar by using our tutorial but i cant get it work…

    By using your code:
    #boot/keycloak.js#
    import VueKeyCloak from ‘@dsb-norge/vue-keycloak-js’
    import axios from ‘axios’

    // eslint-disable-next-line @typescript-eslint/no-unused-vars
    export default async ({ Vue, router, store, app }) => {
    // eslint-disable-next-line @typescript-eslint/require-await
    async function tokenInterceptor () {
    axios.interceptors.request.use(config => {
    // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access,@typescript-eslint/restrict-template-expressions
    config.headers.Authorization = Bearer ${Vue.prototype.$keycloak.token}
    return config
    }, error => {
    return Promise.reject(error)
    })
    }

    return new Promise(resolve => {
    // eslint-disable-next-line @typescript-eslint/no-unsafe-call,@typescript-eslint/no-unsafe-member-access
    Vue.use(VueKeyCloak, {
    init: {
    onLoad: ‘login-required’, // or ‘check-sso’
    flow: ‘standard’,
    pkceMethod: ‘S256’,
    silentCheckSsoRedirectUri: window.location.origin + ‘/silent-check-sso.html’,
    checkLoginIframe: false // otherwise it would reload the window every so seconds
    },
    config: {
    url: ‘url’,
    realm: ‘realm’,
    clientId: ‘clientId’
    },
    // eslint-disable-next-line @typescript-eslint/no-unused-vars
    onReady: (keycloak) => {
    void tokenInterceptor()
    resolve()
    }
    })
    })
    }
    ###

    by using this i get console error:
    [Quasar] boot error: TypeError: Vue is undefined

    Also i dont get it, why you use ‘silent-check-sso.html’ instead of redirecting directly to the mainpage

    And i cant read out how to use it… maybe iam using it wrong:
    ###

    import {
    defineComponent
    } from ‘vue’;

    export default defineComponent({
    name: ‘LoginComponent’
    });

    ###

    Additionally the auth token didnt get refreshed like
    ###
    setInterval(() => {
    keycloak
    // If token is expiring in that many secs, from now, refresh it
    .updateToken(70)
    .then((refreshed) => {
    if (refreshed) {
    console.log(“Keycloak Token refreshed” + refreshed);
    } else {
    console.log(
    “Keycloak Token not refreshed, valid for another ” +
    Math.round(
    keycloak.tokenParsed.exp +
    keycloak.timeSkew –
    new Date().getTime() / 1000
    ) +
    ” seconds”
    );
    }
    })
    .catch(() => {
    console.log(“Failed to refresh Keycloak Token”);
    });
    // Recheck if the token is expired in order to refresh it (millis)
    }, 60000);
    ### from https://github.com/quasarframework/quasar/issues/4758

    Have a great day! 🙂

    1. 1. You use silent-check-sso.html to silently refresh the token before expiration in the background. That file is referenced in the keycloak.js file.

      2. Line 4 in keycloak.js you pass the {Vue,router,store,app} object so there Vue should be referenced. You don’t have to import Vue in this file since the reference is passed in this object.

      Only reason I can think of is that you’re using Quasar v2 and this is for Quasar v1. I have not done anything with v2 yet.

    2. And you use it like

    3. On 2nd thought I see all those //tslint comments so you’re using typescript.
      I’m not using typescript with Quasar so it’s likely you have to define or find the definition of the object passed in the initializer function.

      Something like
      { Vue, router, store, app } as PluginInitializerObject

      But you’ll have to ask the Quasar guys for details.

        1. Hmm 🙂 Thanks for feedback. Once summer has passed I’ll get back to work and probably play with Quasar v2 (and Vue 3 in general).
          Right now it’s just too hot here in Croatia.

          Thanks for posting a link to your Github issue regarding this in v2. Let’s hope someone from their team can help with it.
          Being stuck on the redirection URL like this means something failed.
          Check console log, http requests and responses. I usually have 3rd party cookies disabled and that also plays a role.
          Not using https on the keycloak server side might also be an issue since OIDC requires HTTPS and Chrome especially can be a princess when it comes to http and https and especially localhost.

Leave a comment

Your email address will not be published. Required fields are marked *