/******************************************************************************* * Copyright (c) 2012-2017 Codenvy, S.A. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html * * Contributors: * Codenvy, S.A. - initial API and implementation *******************************************************************************/ package org.eclipse.che.api.factory.server; 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.factory.Factory; import org.eclipse.che.api.factory.server.model.impl.AuthorImpl; import org.eclipse.che.api.factory.server.model.impl.FactoryImpl; import org.eclipse.che.api.factory.server.snippet.SnippetGenerator; import org.eclipse.che.api.factory.server.spi.FactoryDao; import org.eclipse.che.commons.lang.NameGenerator; import org.eclipse.che.commons.lang.Pair; import javax.inject.Inject; import javax.inject.Singleton; import javax.ws.rs.core.UriBuilder; import java.net.URI; import java.util.List; import java.util.Set; import java.util.stream.Collectors; import static com.google.common.base.MoreObjects.firstNonNull; import static com.google.common.base.Strings.isNullOrEmpty; import static java.util.Objects.requireNonNull; import static org.eclipse.che.api.factory.shared.Constants.HTML_SNIPPET_TYPE; import static org.eclipse.che.api.factory.shared.Constants.IFRAME_SNIPPET_TYPE; import static org.eclipse.che.api.factory.shared.Constants.MARKDOWN_SNIPPET_TYPE; import static org.eclipse.che.api.factory.shared.Constants.URL_SNIPPET_TYPE; /** * @author Anton Korneta */ @Singleton public class FactoryManager { private final FactoryDao factoryDao; @Inject public FactoryManager(FactoryDao factoryDao) { this.factoryDao = factoryDao; } /** * Stores {@link Factory} instance. * * @param factory * instance of factory which would be stored * @return factory which has been stored * @throws NullPointerException * when {@code factory} is null * @throws ConflictException * when any conflict occurs (e.g Factory with given name already exists for {@code creator}) * @throws ServerException * when any server errors occurs */ public Factory saveFactory(Factory factory) throws ConflictException, ServerException { return saveFactory(factory, null); } /** * Stores {@link Factory} instance and related set of {@link FactoryImage}. * * @param factory * instance of factory which would be stored * @param images * factory images which would be stored * @return factory which has been stored * @throws NullPointerException * when {@code factory} is null * @throws ConflictException * when any conflict occurs (e.g Factory with given name already exists for {@code creator}) * @throws ServerException * when any server errors occurs */ public Factory saveFactory(Factory factory, Set<FactoryImage> images) throws ConflictException, ServerException { requireNonNull(factory); final FactoryImpl newFactory = new FactoryImpl(factory, images); newFactory.setId(NameGenerator.generate("factory", 16)); if (isNullOrEmpty(newFactory.getName())) { newFactory.setName(NameGenerator.generate("f", 9)); } return factoryDao.create(newFactory); } /** * Updates factory accordance to the new configuration. * * <p>Note: Updating uses replacement strategy, * therefore existing factory would be replaced with given update {@code update} * * @param update * factory update * @return updated factory * @throws NullPointerException * when {@code update} is null * @throws ConflictException * when any conflict occurs (e.g Factory with given name already exists for {@code creator}) * @throws NotFoundException * when factory with given id not found * @throws ServerException * when any server error occurs */ public Factory updateFactory(Factory update) throws ConflictException, NotFoundException, ServerException { requireNonNull(update); return updateFactory(update, null); } /** * Updates factory and its images accordance to the new configuration. * * <p>Note: Updating uses replacement strategy, * therefore existing factory would be replaced with given update {@code update} * * @param update * factory update * @return updated factory * @throws NullPointerException * when {@code update} is null * @throws ConflictException * when any conflict occurs (e.g Factory with given name already exists for {@code creator}) * @throws NotFoundException * when factory with given id not found * @throws ServerException * when any server error occurs */ public Factory updateFactory(Factory update, Set<FactoryImage> images) throws ConflictException, NotFoundException, ServerException { requireNonNull(update); final AuthorImpl creator = factoryDao.getById(update.getId()).getCreator(); return factoryDao.update(FactoryImpl.builder() .from(new FactoryImpl(update, images)) .setCreator(new AuthorImpl(creator.getUserId(), creator.getCreated())) .build()); } /** * Removes stored {@link Factory} by given id. * * @param id * factory identifier * @throws NullPointerException * when {@code id} is null * @throws ServerException * when any server errors occurs */ public void removeFactory(String id) throws ServerException { requireNonNull(id); factoryDao.remove(id); } /** * Gets factory by given id. * * @param id * factory identifier * @return factory instance * @throws NullPointerException * when {@code id} is null * @throws NotFoundException * when factory with given id not found * @throws ServerException * when any server errors occurs */ public Factory getById(String id) throws NotFoundException, ServerException { requireNonNull(id); return factoryDao.getById(id); } /** * Gets factory images by given factory and image ids. * * @param factoryId * factory identifier * @param imageId * image identifier * @return factory images or empty set if no image found by given {@code imageId} * @throws NotFoundException * when specified factory not found * @throws ServerException * when any server errors occurs */ public Set<FactoryImage> getFactoryImages(String factoryId, String imageId) throws NotFoundException, ServerException { requireNonNull(factoryId); requireNonNull(imageId); return getFactoryImages(factoryId).stream() .filter(image -> imageId.equals(image.getName())) .collect(Collectors.toSet()); } /** * Gets all the factory images. * * @param factoryId * factory identifier * @return factory images or empty set if no image found for factory * @throws NotFoundException * when specified factory not found * @throws ServerException * when any server errors occurs */ public Set<FactoryImage> getFactoryImages(String factoryId) throws NotFoundException, ServerException { requireNonNull(factoryId); return factoryDao.getById(factoryId).getImages(); } /** * Get list of factories which conform specified attributes. * * @param maxItems * max number of items in response * @param skipCount * skip items. Must be equals or greater then {@code 0} * @param attributes * skip items. Must be equals or greater then {@code 0} * @return stored data, if specified attributes is correct * @throws ServerException * when any server errors occurs */ @SuppressWarnings("unchecked") public <T extends List<? extends Factory>> T getByAttribute(int maxItems, int skipCount, List<Pair<String, String>> attributes) throws ServerException { return (T)factoryDao.getByAttribute(maxItems, skipCount, attributes); } /** * Gets factory snippet by factory id and snippet type. * If snippet type is not set, "url" type will be used as default. * * @param factoryId * id of factory * @param snippetType * type of snippet * @param baseUri * URI from which will be created snippet * @return snippet content or null when snippet type not found. * @throws NotFoundException * when factory with specified id doesn't not found * @throws ServerException * when any server error occurs during snippet creation */ public String getFactorySnippet(String factoryId, String snippetType, URI baseUri) throws NotFoundException, ServerException { requireNonNull(factoryId); final String baseUrl = UriBuilder.fromUri(baseUri) .replacePath("") .build() .toString(); switch (firstNonNull(snippetType, URL_SNIPPET_TYPE)) { case URL_SNIPPET_TYPE: return UriBuilder.fromUri(baseUri) .replacePath("factory") .queryParam("id", factoryId) .build() .toString(); case HTML_SNIPPET_TYPE: return SnippetGenerator.generateHtmlSnippet(baseUrl, factoryId); case IFRAME_SNIPPET_TYPE: return SnippetGenerator.generateiFrameSnippet(baseUrl, factoryId); case MARKDOWN_SNIPPET_TYPE: final Set<FactoryImage> images = getFactoryImages(factoryId); final String imageId = (images.size() > 0) ? images.iterator().next().getName() : null; try { return SnippetGenerator.generateMarkdownSnippet(baseUrl, getById(factoryId), imageId); } catch (IllegalArgumentException e) { throw new ServerException(e.getLocalizedMessage()); } default: // when the specified type is not supported return null; } } }