All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.wavemaker.runtime.security.token.WMTokenBasedAuthenticationService Maven / Gradle / Ivy

The newest version!
/*******************************************************************************
 * Copyright (C) 2022-2023 WaveMaker, Inc.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 ******************************************************************************/
package com.wavemaker.runtime.security.token;

import java.util.Collection;
import java.util.UUID;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.util.StringUtils;

import com.wavemaker.app.security.models.TokenAuthConfig;
import com.wavemaker.runtime.security.WMAuthentication;
import com.wavemaker.runtime.security.WMUser;
import com.wavemaker.runtime.security.token.exception.TokenGenerationException;
import com.wavemaker.runtime.security.token.repository.TokenRepository;
import com.wavemaker.runtime.security.token.repository.WMTokenRepository;
import com.wavemaker.runtime.util.MessageDigestUtil;

/**
 * Generate Token encoded by this implementation adopts the following form:
 * 
 * username + ":" + expiryTime + ":" + Md5Hex(username + ":" + expiryTime + ":" + password + ":" + key)
 * 
*

* Persist generated token with authentication in repository.And if any request comes with auth token which is * there in repository,then authentication retrieved from repository instead of hitting to its providers again. *

* InMemoryPersistentAuthTokenRepository which is used to persist token and authentication in memory. * It is recommended to persist token in repository. * * @author Sunil Kumar * @since 7/2/16 */ public class WMTokenBasedAuthenticationService { @Autowired private TokenAuthConfig tokenAuthConfig; @Autowired private TokenRepository tokenRepository; private static final Logger LOGGER = LoggerFactory.getLogger(WMTokenBasedAuthenticationService.class); public static final int DEFAULT_VALIDITY_SECONDS = WMTokenRepository.DEFAULT_VALIDITY_SECONDS; public static final String DEFAULT_KEY = "WM_TOKEN"; private int tokenValiditySeconds = DEFAULT_VALIDITY_SECONDS; private String key = DEFAULT_KEY; public WMTokenBasedAuthenticationService() { } public WMTokenBasedAuthenticationService(int tokenValiditySeconds) { this.tokenValiditySeconds = tokenValiditySeconds; } public Token generateToken(Authentication successfulAuthentication) { String username = retrieveUserName(successfulAuthentication); if (!StringUtils.hasLength(username)) { LOGGER.debug("Unable to retrieve username"); return null; } int tokenLifetime = calculateLoginLifetime(); long expiryTime = System.currentTimeMillis(); expiryTime += 1000L * (tokenLifetime < 0 ? DEFAULT_VALIDITY_SECONDS : tokenLifetime); String signatureValue = makeTokenSignature(expiryTime, username); Token token = new Token(signatureValue); WMUser wmUser = toWMUser(successfulAuthentication); tokenRepository.addToken(token.getWmAuthToken(), wmUser); return token; } public Authentication getAuthentication(Token token) { WMUser wmUser = tokenRepository.loadUser(token.getWmAuthToken()); return toAuthentication(wmUser); } public void setTokenValiditySeconds(final int tokenValiditySeconds) { this.tokenValiditySeconds = tokenValiditySeconds; } public String getParameter() { return tokenAuthConfig.getParameter(); } public void setKey(String key) { this.key = key; } public boolean isEnabled() { return tokenAuthConfig.isEnabled(); } protected WMUser toWMUser(final Authentication authentication) { if (authentication instanceof WMAuthentication) { String username = (String) authentication.getPrincipal(); String userId = ((WMAuthentication) authentication).getUserId(); return toWMUser(userId, username, "", authentication.getAuthorities()); } throw new TokenGenerationException("Unknown authentication,failed to build token for current user"); } private WMUser toWMUser(final String userId, final String username, final String password, Collection authorities) { return new WMUser(userId, username, password, username, 0, true, true, true, true, authorities, System.currentTimeMillis()); } protected Authentication toAuthentication(final WMUser wmUser) { if (wmUser != null) { return new UsernamePasswordAuthenticationToken(wmUser, null, wmUser.getAuthorities()); } return null; } protected String retrieveUserName(Authentication authentication) { if (isInstanceOfUserDetails(authentication)) { return ((UserDetails) authentication.getPrincipal()).getUsername(); } else { return authentication.getPrincipal().toString(); } } protected int calculateLoginLifetime() { return tokenValiditySeconds; } /** * Calculates the digital signature to be put in the cookie. Default value is * MD5 ("username:tokenExpiryTime:password:key") */ protected String makeTokenSignature(long tokenExpiryTime, String username) { String data = username + ":" + tokenExpiryTime + ":" + UUID.randomUUID() + ":" + key; return MessageDigestUtil.getDigestedData(data); } private boolean isInstanceOfUserDetails(Authentication authentication) { return authentication.getPrincipal() instanceof UserDetails; } }





© 2015 - 2024 Weber Informatics LLC | Privacy Policy