/*
 * Copyright (c) 2012-2018 Red Hat, Inc.
 * This program and the accompanying materials are made
 * available under the terms of the Eclipse Public License 2.0
 * which is available at https://www.eclipse.org/legal/epl-2.0/
 *
 * SPDX-License-Identifier: EPL-2.0
 *
 * Contributors:
 *   Red Hat, Inc. - initial API and implementation
 */
package org.eclipse.che.api.user.server;

import static java.util.Objects.requireNonNull;

import javax.inject.Inject;
import javax.inject.Singleton;
import org.eclipse.che.api.core.ConflictException;
import org.eclipse.che.api.core.NotFoundException;
import org.eclipse.che.api.core.ServerException;
import org.eclipse.che.api.core.model.user.Profile;
import org.eclipse.che.api.core.model.user.User;
import org.eclipse.che.api.user.server.model.impl.ProfileImpl;
import org.eclipse.che.api.user.server.spi.ProfileDao;

/**
 * Preferences manager layer, simplifies prefernces service by taking all the business logic out
 * from the service and making that logic easily reusable throughout the system.
 *
 * <p>The manager doesn't perform any bean validations and it is expected that all the incoming
 * objects are valid, nevertheless this exactly the right place for performing business validations.
 *
 * @author Yevhenii Voevodin
 */
@Singleton
public class ProfileManager {

  @Inject private ProfileDao profileDao;

  /**
   * Finds the profile related to the user with given {@code userId}.
   *
   * @param userId the id to search the user's profile
   * @return found profile
   * @throws NullPointerException when {@code userId} is null
   * @throws NotFoundException when there is no profile for the user with the id {@code userId}
   * @throws ServerException when any other error occurs
   */
  public Profile getById(String userId) throws NotFoundException, ServerException {
    requireNonNull(userId, "Required non-null user id");
    return profileDao.getById(userId);
  }

  /**
   * Creates a new user's profile .
   *
   * @param profile new profile
   * @throws NullPointerException when profile is null
   * @throws ConflictException when profile for the user {@code profile.getUserId()} already exists
   * @throws ServerException when any other error occurs
   */
  public void create(Profile profile) throws ServerException, ConflictException {
    requireNonNull(profile, "Required non-null profile");
    profileDao.create(new ProfileImpl(profile));
  }

  /**
   * Updates current profile using replace strategy.
   *
   * <p>Note that {@link Profile#getEmail()} can't be updated using this method as it is mirrored
   * from the {@link User#getEmail()}.
   *
   * @param profile profile update
   * @throws NullPointerException when {@code profile} is null
   * @throws NotFoundException when there is no profile for the user with the id {@code
   *     profile.getUserId()}
   * @throws ServerException when any other error occurs
   */
  public void update(Profile profile) throws NotFoundException, ServerException {
    requireNonNull(profile, "Required non-null profile");
    profileDao.update(new ProfileImpl(profile));
  }

  /**
   * Removes the user's profile.
   *
   * <p>Note that this method won't throw any exception when user doesn't have the corresponding
   * profile.
   *
   * @param userId the id of the user, whose profile should be removed
   * @throws NullPointerException when {@code id} is null
   * @throws ServerException when any other error occurs
   */
  public void remove(String userId) throws ServerException {
    requireNonNull(userId, "Required non-null user id");
    profileDao.remove(userId);
  }
}
