org.jbb.security.impl.password.DefaultPasswordService.java Source code

Java tutorial

Introduction

Here is the source code for org.jbb.security.impl.password.DefaultPasswordService.java

Source

/*
 * Copyright (C) 2018 the original author or authors.
 *
 * This file is part of jBB Application Project.
 *
 *  Licensed under the Apache License, Version 2.0 (the "License");
 *  You may obtain a copy of the License at
 *        http://www.apache.org/licenses/LICENSE-2.0
 */

package org.jbb.security.impl.password;

import com.google.common.collect.Sets;
import com.google.common.eventbus.Subscribe;
import java.util.Optional;
import java.util.Set;
import javax.validation.ConstraintViolation;
import javax.validation.Validator;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.Validate;
import org.jbb.lib.commons.vo.Password;
import org.jbb.lib.eventbus.JbbEventBus;
import org.jbb.lib.eventbus.JbbEventBusListener;
import org.jbb.members.event.MemberRemovedEvent;
import org.jbb.security.api.password.PasswordException;
import org.jbb.security.api.password.PasswordPolicy;
import org.jbb.security.api.password.PasswordService;
import org.jbb.security.event.PasswordChangedEvent;
import org.jbb.security.event.PasswordPolicyChangedEvent;
import org.jbb.security.impl.password.dao.PasswordRepository;
import org.jbb.security.impl.password.data.NewPassword;
import org.jbb.security.impl.password.model.PasswordEntity;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

@Slf4j
@Service
@RequiredArgsConstructor
public class DefaultPasswordService implements PasswordService, JbbEventBusListener {

    private static final String MEMBER_NOT_NULL_MESSAGE = "Member id cannot be null";

    private final PasswordRepository passwordRepository;
    private final PasswordEntityFactory passwordEntityFactory;
    private final PasswordEqualsMatcher passwordEqualsMatcher;
    private final PasswordPolicyManager policyManager;
    private final Validator validator;
    private final JbbEventBus eventBus;

    @Subscribe
    @Transactional
    public void removePasswordEntity(MemberRemovedEvent event) {
        log.debug("Remove password entity for member id {}", event.getMemberId());
        passwordRepository.removeByMemberId(event.getMemberId());
    }

    @Override
    @Transactional
    public void changeFor(Long memberId, Password newPassword) {
        Validate.notNull(memberId, MEMBER_NOT_NULL_MESSAGE);
        Validate.notNull(newPassword, "Password cannot be null");

        PasswordEntity passwordEntity = passwordEntityFactory.create(memberId, newPassword);

        Set<ConstraintViolation<NewPassword>> passwordValidationResult = validator
                .validate(new NewPassword(String.valueOf(newPassword.getValue())));
        Set<ConstraintViolation<PasswordEntity>> entityValidationResult = validator.validate(passwordEntity);

        if (!passwordValidationResult.isEmpty() || !entityValidationResult.isEmpty()) {
            Set<ConstraintViolation<?>> validationResult = Sets.newHashSet();
            validationResult.addAll(passwordValidationResult);
            validationResult.addAll(entityValidationResult);
            throw new PasswordException(validationResult);
        }

        passwordRepository.save(passwordEntity);

        if (passwordRepository.countByMemberId(memberId) > 0) {
            publishEvent(passwordEntity);
        }
    }

    private void publishEvent(PasswordEntity password) {
        eventBus.post(new PasswordChangedEvent(password.getMemberId()));
    }

    @Override
    @Transactional(readOnly = true)
    public boolean verifyFor(Long memberId, Password typedPassword) {
        Validate.notNull(memberId, MEMBER_NOT_NULL_MESSAGE);
        Validate.notNull(typedPassword, "Password cannot be null");

        Optional<PasswordEntity> currentPasswordEntity = passwordRepository.findTheNewestByMemberId(memberId);
        return currentPasswordEntity.filter(passwordEntity -> passwordEqualsMatcher.matches(typedPassword,
                passwordEntity.getPasswordValueObject())).isPresent();
    }

    @Override
    public Optional<String> getPasswordHash(Long memberId) {
        Validate.notNull(memberId, MEMBER_NOT_NULL_MESSAGE);
        return passwordRepository.findTheNewestByMemberId(memberId).map(PasswordEntity::getPassword);
    }

    @Override
    public PasswordPolicy currentPolicy() {
        return policyManager.currentPolicy();
    }

    @Override
    public void updatePolicy(PasswordPolicy policy) {
        Validate.notNull(policy);
        policyManager.update(policy);
        eventBus.post(new PasswordPolicyChangedEvent());
    }

}