Keycloak object 属性 "authenticated" returns false 应该是 true

Keycloak object property "authenticated" returns false when should be true

所以,我正在开发一个 react-redux 应用程序,它需要一些用户进行身份验证,我使用 keycloak。

基本上有一个 public/not 安全的主页:
- localhost:3000/

现在,当用户点击 link 进入欢迎页面时,keycloak 登录页面应该弹出并询问身份验证详细信息,我已经做到了:
- localhost:3000/欢迎 -> localhost:8080/授权

如上所述,登录页面已经显示并正确验证注册用户。但是,一旦成功登录,我将被重定向到 localhost:3000/welcome(这很好),但没有任何内容(这不好)。

所以我继续将 keycloak.authenticated 的状态记录到控制台。在调用 "keycloak.init" 之前它是未定义的(这很好),在成功验证之后它是 false (:o?!?!)。

奇怪。

所以看来我必须手动更改 keycloak.authenticated 的状态。

2个问题: - 面对 reduxish 无状态组件 w/o 构造函数等,我如何更改 keycloak.authenticated - 我的问题是否正确?

一些手续:

keycloak.js 欢迎页面包裹的高阶组件代码:

import React from 'react';

const { Consumer, Provider } = React.createContext();
export const KeycloakProvider = Provider;
const withKeycloak = component =>
  function WithKeycloak(props) {
    return React.createElement(Consumer, null, keycloak => {
      console.log('before: ', keycloak.authenticated); -> undefined
      if (keycloak.authenticated) {
        return React.createElement(component, { ...props, keycloak }, null);
      }
      console.log('before init: ', keycloak.authenticated); // -> undefined
      keycloak.init({ onLoad: 'login-required' });
      console.log('after: ', keycloak.authenticated); // -> false!!
      return null;
    });
  };

export default withKeycloak;

main.jsx main.jsx 定义 keycloak 的代码:

/** @format */

import lots of stuff....;
import { KeycloakProvider } from './keycloak/provider';
import Keycloak from 'keycloak-js';

const store = ...

const keycloak = Keycloak({
  url: 'http://localhost:8080/auth',
  realm: 'Test-Jannis',
  clientId: 'test-bayron'
});

const Main = () => (
  <Provider store={store}>
    <BrowserRouter>
        <KeycloakProvider value={keycloak}>
          <Route exact path="/" component={Home} />
          <Route exact path="/welcome" component={WelcomePage} />
        </KeycloakProvider>
    </BrowserRouter>
  </Provider>
);

export default Main;

我最好的猜测是在 keycloak.js 中的 keycloak.init 下做这样的事情:

keycloak.init({ onLoad: 'login-required' });
   .then(authenticated => (keycloak.authenticated = authenticated));

但是...这不会将 keycloak.authenticated 变为错误。

请帮忙:)

更新

对 keycloak.js 使用以下代码:

const withKeycloak = component =>
  function WithKeycloak(props) {
    return React.createElement(Consumer, null, keycloak => {
      console.log('before: ', keycloak.authenticated);
      keycloak.init({ onLoad: 'login-required'}).success(function() {
        if ( keycloak.authenticated ) {
          console.log("return page: ", keycloak.authenticated);
          console.log(component);
          console.log(React.createElement(component, { ...props, keycloak }, null));
          return React.createElement(component, { ...props, keycloak }, null);
        }
        console.log("return null: ", keycloak.authenticated);
        return null;
      });
    });
  };

现在输出 keycloak.authenticated === 真! 但是,重定向的 localhost:3000/welcome 仍然不显示欢迎组件应该显示 的任何 html。

关注 KeyCloak JS adapter documentation:

By default, the JavaScript adapter creates a hidden iframe that is used to detect if a Single-Sign Out has occurred. This does not require any network traffic, instead the status is retrieved by looking at a special status cookie. This feature can be disabled by setting checkLoginIframe: false in the options passed to the init method.

您需要将您的 keycloak 初始化代码作为:

keycloak.init({checkLoginIframe: false}).success((authenticated) => {
  // Some stuff
})