Keycloak Roles: Uncaught TypeError: Cannot read properties of undefined (reading 'roles') – React

I have the following code:

class Secured extends Component {

import React, { Component } from 'react';
import Keycloak from 'keycloak-js';

constructor(props) {
    super(props);
    this.state = { keycloak: null, authenticated: false, roles: [] };
}

componentDidMount() {
    const keycloak = Keycloak('/keycloak.json');
    keycloak.init({onLoad: 'login-required'}).then(authenticated => {
        this.setState({ keycloak: keycloak, authenticated: authenticated, roles: keycloak.tokenParsed.realm_access.roles})
    })
}

render() {
    if(this.state.keycloak) {
      if(this.state.authenticated)
      { if(this.state.roles.includes("prototype-user")){
        return ( //the rest of the code here

I always get an error Uncaught TypeError: Cannot read properties of undefined (reading 'roles') when the keycloak.tokenParsed.realm_access.roles does not have value. If it has value, the error does not appear.

I just started React.js last week and not quite familiar with JavaScript/TypeScript so I find it really hard to implement solutions I found with the same issue.

What is causing the error and how will I fix it?

>Solution :

To prevent your code from failing when keycloak.tokenParsed.realm_access is undefined, you need to use a feature of javascript called optional chaining.

Here’s how this works.

Let’s say you have are trying to access an object property(or call on the object property) but you’re not sure the object would always have that property for instance you can see that the code below doesn’t have the realm_access as a property of the nested tokenParsed object and it fails when we try to access it.

const user = { 
  keycloak: null, 
  authenticated: false,
  tokenParsed: {
    token: '1245'
  }
}

const roles = user.tokenParsed.realm_access.roles //This would throw a TypeError

But say you want to prevent this error when the property is not there, that’s where optional chaining comes in

const roles = user?.tokenParsed?.realm_access?.roles

By inserting a ? between the property name and the period before the next property, it’ll just return undefined instead of throwing an ugly error

Leave a Reply