CHE-2937. Add ability to create batch of projects
parent
f1710e6a9b
commit
2339b0dd6e
|
|
@ -0,0 +1,46 @@
|
|||
/*******************************************************************************
|
||||
* Copyright (c) 2012-2016 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.core.model.project;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* Defines configuration for creating new project
|
||||
*
|
||||
* @author Roman Nikitenko
|
||||
*/
|
||||
public interface NewProjectConfig extends ProjectConfig {
|
||||
/** Sets project name */
|
||||
void setName(String name);
|
||||
|
||||
/** Sets project path */
|
||||
void setPath(String path);
|
||||
|
||||
/** Sets project description */
|
||||
void setDescription(String description);
|
||||
|
||||
/** Sets primary project type */
|
||||
void setType(String type);
|
||||
|
||||
/** Sets mixin project types */
|
||||
void setMixins(List<String> mixins);
|
||||
|
||||
/** Sets project attributes */
|
||||
void setAttributes(Map<String, List<String>> attributes);
|
||||
|
||||
/** Sets options for generator to create project */
|
||||
void setOptions(Map<String, String> options);
|
||||
|
||||
/** Returns options for generator to create project */
|
||||
Map<String, String> getOptions();
|
||||
}
|
||||
|
|
@ -33,4 +33,4 @@ public interface ProjectConfig {
|
|||
|
||||
SourceStorage getSource();
|
||||
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -12,11 +12,10 @@ package org.eclipse.che.ide.api.project;
|
|||
|
||||
import com.google.common.annotations.Beta;
|
||||
|
||||
import org.eclipse.che.api.core.model.project.NewProjectConfig;
|
||||
import org.eclipse.che.api.core.model.project.ProjectConfig;
|
||||
import org.eclipse.che.api.core.model.project.SourceStorage;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
|
|
@ -37,6 +36,7 @@ public class MutableProjectConfig implements ProjectConfig {
|
|||
private Map<String, List<String>> attributes;
|
||||
private MutableSourceStorage sourceStorage;
|
||||
private Map<String, String> options;
|
||||
private List<NewProjectConfig> projects;
|
||||
|
||||
public MutableProjectConfig(ProjectConfig source) {
|
||||
name = source.getName();
|
||||
|
|
@ -90,7 +90,7 @@ public class MutableProjectConfig implements ProjectConfig {
|
|||
@Override
|
||||
public List<String> getMixins() {
|
||||
if (mixins == null) {
|
||||
mixins = new ArrayList<>();
|
||||
mixins = newArrayList();
|
||||
}
|
||||
|
||||
return mixins;
|
||||
|
|
@ -128,7 +128,7 @@ public class MutableProjectConfig implements ProjectConfig {
|
|||
|
||||
public Map<String, String> getOptions() {
|
||||
if (options == null) {
|
||||
options = new HashMap<>();
|
||||
options = newHashMap();
|
||||
}
|
||||
return options;
|
||||
}
|
||||
|
|
@ -137,6 +137,28 @@ public class MutableProjectConfig implements ProjectConfig {
|
|||
this.options = options;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the list of configurations to creating projects
|
||||
*
|
||||
* @return the list of {@link NewProjectConfig} to creating projects
|
||||
*/
|
||||
public List<NewProjectConfig> getProjects() {
|
||||
if (projects == null) {
|
||||
return newArrayList();
|
||||
}
|
||||
return projects;
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the list of configurations to creating projects
|
||||
*
|
||||
* @param projects
|
||||
* the list of {@link NewProjectConfig} to creating projects
|
||||
*/
|
||||
public void setProjects(List<NewProjectConfig> projects) {
|
||||
this.projects = projects;
|
||||
}
|
||||
|
||||
public class MutableSourceStorage implements SourceStorage {
|
||||
private String type;
|
||||
private String location;
|
||||
|
|
|
|||
|
|
@ -0,0 +1,173 @@
|
|||
/*******************************************************************************
|
||||
* Copyright (c) 2012-2016 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.ide.api.project;
|
||||
|
||||
import org.eclipse.che.api.core.model.project.NewProjectConfig;
|
||||
import org.eclipse.che.api.core.model.project.SourceStorage;
|
||||
import org.eclipse.che.api.project.templates.shared.dto.ProjectTemplateDescriptor;
|
||||
import org.eclipse.che.api.workspace.shared.dto.NewProjectConfigDto;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* Implementation of {@link NewProjectConfig} for creating project
|
||||
*
|
||||
* @author Roman Nikitenko
|
||||
*/
|
||||
public class NewProjectConfigImpl implements NewProjectConfig {
|
||||
private String name;
|
||||
private String path;
|
||||
private String description;
|
||||
private String type;
|
||||
private SourceStorage sourceStorage;
|
||||
private List<String> mixins;
|
||||
private Map<String, List<String>> attributes;
|
||||
private Map<String, String> options;
|
||||
|
||||
/** Constructor for creating project import configuration */
|
||||
public NewProjectConfigImpl(String name,
|
||||
String path,
|
||||
String description,
|
||||
String type,
|
||||
SourceStorage sourceStorage) {
|
||||
this(name, path, description, type, sourceStorage, null, null, null);
|
||||
}
|
||||
|
||||
/** Constructor for creating project generator configuration */
|
||||
public NewProjectConfigImpl(String name,
|
||||
String path,
|
||||
String description,
|
||||
String type,
|
||||
Map<String, List<String>> attributes,
|
||||
Map<String, String> options) {
|
||||
this(name, path, description, type, null, null, attributes, options);
|
||||
}
|
||||
|
||||
/** Constructor for creating configuration from project template descriptor */
|
||||
public NewProjectConfigImpl(ProjectTemplateDescriptor descriptor) {
|
||||
this(descriptor.getName(),
|
||||
descriptor.getPath(),
|
||||
descriptor.getDescription(),
|
||||
descriptor.getProjectType(),
|
||||
descriptor.getSource(),
|
||||
descriptor.getMixins(),
|
||||
descriptor.getAttributes(),
|
||||
descriptor.getOptions());
|
||||
}
|
||||
|
||||
/** Constructor for creating configuration from DTO object */
|
||||
public NewProjectConfigImpl(NewProjectConfigDto dto) {
|
||||
this(dto.getName(),
|
||||
dto.getPath(),
|
||||
dto.getDescription(),
|
||||
dto.getType(),
|
||||
dto.getSource(),
|
||||
dto.getMixins(),
|
||||
dto.getAttributes(),
|
||||
dto.getOptions());
|
||||
}
|
||||
|
||||
public NewProjectConfigImpl(String name,
|
||||
String path,
|
||||
String description,
|
||||
String type,
|
||||
SourceStorage sourceStorage,
|
||||
List<String> mixins,
|
||||
Map<String, List<String>> attributes,
|
||||
Map<String, String> options) {
|
||||
this.name = name;
|
||||
this.path = path;
|
||||
this.description = description;
|
||||
this.type = type;
|
||||
this.sourceStorage = sourceStorage;
|
||||
this.mixins = mixins;
|
||||
this.attributes = attributes != null ? attributes : new HashMap<String, List<String>>();
|
||||
this.options = options != null ? options : new HashMap<String, String>();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setName(String name) {
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getPath() {
|
||||
return path;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setPath(String path) {
|
||||
this.path = path;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getDescription() {
|
||||
return description;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setDescription(String description) {
|
||||
this.description = description;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getType() {
|
||||
return type;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setType(String type) {
|
||||
this.type = type;
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<String> getMixins() {
|
||||
return mixins != null ? mixins : new ArrayList<String>();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setMixins(List<String> mixins) {
|
||||
this.mixins = mixins;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, List<String>> getAttributes() {
|
||||
return attributes != null ? attributes : new HashMap<String, List<String>>();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setAttributes(Map<String, List<String>> attributes) {
|
||||
this.attributes = attributes;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, String> getOptions() {
|
||||
return options != null ? options : new HashMap<String, String>();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setOptions(Map<String, String> options) {
|
||||
this.options = options;
|
||||
}
|
||||
|
||||
@Override
|
||||
public SourceStorage getSource() {
|
||||
return sourceStorage;
|
||||
}
|
||||
}
|
||||
|
|
@ -14,6 +14,7 @@ import org.eclipse.che.api.project.shared.dto.ItemReference;
|
|||
import org.eclipse.che.api.project.shared.dto.SourceEstimation;
|
||||
import org.eclipse.che.api.project.shared.dto.TreeElement;
|
||||
import org.eclipse.che.api.promises.client.Promise;
|
||||
import org.eclipse.che.api.workspace.shared.dto.NewProjectConfigDto;
|
||||
import org.eclipse.che.api.workspace.shared.dto.ProjectConfigDto;
|
||||
import org.eclipse.che.api.workspace.shared.dto.SourceStorageDto;
|
||||
import org.eclipse.che.ide.resource.Path;
|
||||
|
|
@ -92,6 +93,24 @@ public interface ProjectServiceClient {
|
|||
*/
|
||||
Promise<ProjectConfigDto> createProject(ProjectConfigDto configuration, Map<String, String> options);
|
||||
|
||||
/**
|
||||
* Create batch of projects according to their configurations.
|
||||
* <p/>
|
||||
* Notes: a project will be created by importing when project configuration contains {@link SourceStorageDto}
|
||||
* object, otherwise this one will be created corresponding its {@link NewProjectConfigDto}:
|
||||
* <li> - {@link NewProjectConfigDto} object contains only one mandatory {@link NewProjectConfigDto#setPath(String)} field.
|
||||
* In this case Project will be created as project of "blank" type </li>
|
||||
* <li> - a project will be created as project of "blank" type when declared primary project type is not registered, </li>
|
||||
* <li> - a project will be created without mixin project type when declared mixin project type is not registered</li>
|
||||
* <li> - for creating a project by generator {@link NewProjectConfigDto#getOptions()} should be specified.</li>
|
||||
*
|
||||
* @param configurations
|
||||
* the list of configurations to creating projects
|
||||
* @return {@link Promise} with the list of {@link ProjectConfigDto}
|
||||
* @see ProjectConfigDto
|
||||
*/
|
||||
Promise<List<ProjectConfigDto>> createBatchProjects(List<NewProjectConfigDto> configurations);
|
||||
|
||||
/**
|
||||
* Returns the item description by given {@code path}.
|
||||
*
|
||||
|
|
|
|||
|
|
@ -26,6 +26,7 @@ import org.eclipse.che.api.promises.client.Promise;
|
|||
import org.eclipse.che.api.promises.client.PromiseError;
|
||||
import org.eclipse.che.api.promises.client.callback.AsyncPromiseHelper;
|
||||
import org.eclipse.che.api.promises.client.callback.PromiseHelper;
|
||||
import org.eclipse.che.api.workspace.shared.dto.NewProjectConfigDto;
|
||||
import org.eclipse.che.api.workspace.shared.dto.ProjectConfigDto;
|
||||
import org.eclipse.che.api.workspace.shared.dto.SourceStorageDto;
|
||||
import org.eclipse.che.ide.MimeType;
|
||||
|
|
@ -65,7 +66,8 @@ import static org.eclipse.che.ide.rest.HTTPHeader.CONTENT_TYPE;
|
|||
*/
|
||||
public class ProjectServiceClientImpl implements ProjectServiceClient {
|
||||
|
||||
private static final String PROJECT = "/project";
|
||||
private static final String PROJECT = "/project";
|
||||
private static final String BATCH_PROJECTS = "/batch";
|
||||
|
||||
private static final String ITEM = "/item";
|
||||
private static final String TREE = "/tree";
|
||||
|
|
@ -213,6 +215,16 @@ public class ProjectServiceClientImpl implements ProjectServiceClient {
|
|||
.send(unmarshaller.newUnmarshaller(ProjectConfigDto.class));
|
||||
}
|
||||
|
||||
@Override
|
||||
public Promise<List<ProjectConfigDto>> createBatchProjects(List<NewProjectConfigDto> configurations) {
|
||||
final String url = getBaseUrl() + BATCH_PROJECTS;
|
||||
final String loaderMessage = configurations.size() > 1 ? "Creating the batch of projects..." : "Creating project...";
|
||||
return reqFactory.createPostRequest(url, configurations)
|
||||
.header(ACCEPT, MimeType.APPLICATION_JSON)
|
||||
.loader(loaderFactory.newLoader(loaderMessage))
|
||||
.send(unmarshaller.newListUnmarshaller(ProjectConfigDto.class));
|
||||
}
|
||||
|
||||
/** {@inheritDoc} */
|
||||
@Override
|
||||
public Promise<ItemReference> createFile(Path path, String content) {
|
||||
|
|
|
|||
|
|
@ -16,7 +16,7 @@ import javax.validation.constraints.NotNull;
|
|||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Registry for {@link org.eclipse.che.api.project.templates.shared.dto.ProjectTemplateDescriptor}s.
|
||||
* Registry for {@link ProjectTemplateDescriptor}s.
|
||||
*
|
||||
* @author Artem Zatsarynnyi
|
||||
*/
|
||||
|
|
|
|||
|
|
@ -99,7 +99,7 @@ public class ProjectWizard extends AbstractWizard<MutableProjectConfig> {
|
|||
});
|
||||
} else if (mode == IMPORT) {
|
||||
appContext.getWorkspaceRoot()
|
||||
.importProject()
|
||||
.newProject()
|
||||
.withBody(dataObject)
|
||||
.send()
|
||||
.thenPromise(new Function<Project, Promise<Project>>() {
|
||||
|
|
|
|||
|
|
@ -13,9 +13,13 @@ package org.eclipse.che.ide.projecttype.wizard.categoriespage;
|
|||
import com.google.gwt.user.client.ui.AcceptsOneWidget;
|
||||
import com.google.inject.Inject;
|
||||
|
||||
import org.eclipse.che.api.core.model.project.NewProjectConfig;
|
||||
import org.eclipse.che.api.project.shared.dto.ProjectTypeDto;
|
||||
import org.eclipse.che.api.project.templates.shared.dto.ProjectTemplateDescriptor;
|
||||
import org.eclipse.che.api.workspace.shared.dto.NewProjectConfigDto;
|
||||
import org.eclipse.che.ide.api.app.AppContext;
|
||||
import org.eclipse.che.ide.api.project.MutableProjectConfig;
|
||||
import org.eclipse.che.ide.api.project.NewProjectConfigImpl;
|
||||
import org.eclipse.che.ide.api.project.type.ProjectTemplateRegistry;
|
||||
import org.eclipse.che.ide.api.project.type.ProjectTypeRegistry;
|
||||
import org.eclipse.che.ide.api.project.type.wizard.PreSelectedProjectTypeManager;
|
||||
|
|
@ -23,12 +27,12 @@ import org.eclipse.che.ide.api.project.type.wizard.ProjectWizardMode;
|
|||
import org.eclipse.che.ide.api.project.type.wizard.ProjectWizardRegistry;
|
||||
import org.eclipse.che.ide.api.resources.Resource;
|
||||
import org.eclipse.che.ide.api.wizard.AbstractWizardPage;
|
||||
import org.eclipse.che.ide.api.project.MutableProjectConfig;
|
||||
import org.eclipse.che.ide.resource.Path;
|
||||
import org.eclipse.che.ide.resources.selector.SelectPathPresenter;
|
||||
import org.eclipse.che.ide.resources.selector.SelectionPathHandler;
|
||||
import org.eclipse.che.ide.util.NameUtils;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
|
|
@ -162,13 +166,20 @@ public class CategoriesPagePresenter extends AbstractWizardPage<MutableProjectCo
|
|||
if (projectTemplateSelectionListener != null) {
|
||||
projectTemplateSelectionListener.onProjectTemplateSelected(templateDescriptor);
|
||||
}
|
||||
|
||||
updateProjectConfigs(dataObject.getPath(), selectedProjectTemplate);
|
||||
updateDelegate.updateControls();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void projectNameChanged(String name) {
|
||||
final String newProjectPath = originParent.append(name).toString();
|
||||
if (selectedProjectTemplate != null) {
|
||||
updateProjectConfigs(newProjectPath, selectedProjectTemplate);
|
||||
}
|
||||
|
||||
dataObject.setName(name);
|
||||
dataObject.setPath(originParent.append(name).toString());
|
||||
dataObject.setPath(newProjectPath);
|
||||
updateDelegate.updateControls();
|
||||
|
||||
if (NameUtils.checkProjectName(name)) {
|
||||
|
|
@ -211,6 +222,26 @@ public class CategoriesPagePresenter extends AbstractWizardPage<MutableProjectCo
|
|||
projectTemplateSelectionListener = listener;
|
||||
}
|
||||
|
||||
private void updateProjectConfigs(String newProjectPath, ProjectTemplateDescriptor projectTemplate) {
|
||||
final List<NewProjectConfigDto> configDtoList = projectTemplate.getProjects();
|
||||
if (newProjectPath.equals("/")) {
|
||||
return;
|
||||
}
|
||||
|
||||
final String templatePath = projectTemplate.getPath();
|
||||
final List<NewProjectConfig> updatedConfigs = new ArrayList<>(configDtoList.size());
|
||||
for (NewProjectConfigDto configDto : configDtoList) {
|
||||
final NewProjectConfig newConfig = new NewProjectConfigImpl(configDto);
|
||||
final String projectPath = configDto.getPath();
|
||||
if (projectPath.startsWith(templatePath)) {
|
||||
final String path = projectPath.replaceFirst(templatePath, newProjectPath);
|
||||
newConfig.setPath(path);
|
||||
}
|
||||
updatedConfigs.add(newConfig);
|
||||
}
|
||||
dataObject.setProjects(updatedConfigs);
|
||||
}
|
||||
|
||||
private void loadProjectTypesAndTemplates() {
|
||||
List<ProjectTypeDto> projectTypes = projectTypeRegistry.getProjectTypes();
|
||||
Map<String, Set<ProjectTypeDto>> typesByCategory = new HashMap<>();
|
||||
|
|
|
|||
|
|
@ -14,12 +14,14 @@ import com.google.inject.Inject;
|
|||
import com.google.inject.Provider;
|
||||
import com.google.inject.Singleton;
|
||||
|
||||
import org.eclipse.che.api.core.model.project.NewProjectConfig;
|
||||
import org.eclipse.che.api.project.shared.dto.AttributeDto;
|
||||
import org.eclipse.che.api.project.shared.dto.ProjectTypeDto;
|
||||
import org.eclipse.che.api.project.templates.shared.dto.ProjectTemplateDescriptor;
|
||||
import org.eclipse.che.commons.annotation.Nullable;
|
||||
import org.eclipse.che.ide.api.dialogs.DialogFactory;
|
||||
import org.eclipse.che.ide.api.project.MutableProjectConfig;
|
||||
import org.eclipse.che.ide.api.project.NewProjectConfigImpl;
|
||||
import org.eclipse.che.ide.api.project.type.wizard.ProjectWizardMode;
|
||||
import org.eclipse.che.ide.api.project.type.wizard.ProjectWizardRegistrar;
|
||||
import org.eclipse.che.ide.api.project.type.wizard.ProjectWizardRegistry;
|
||||
|
|
@ -181,7 +183,15 @@ public class ProjectWizardPresenter implements Wizard.UpdateDelegate,
|
|||
if (wizardMode == UPDATE) {
|
||||
newProject.setAttributes(prevData.getAttributes());
|
||||
} else {
|
||||
List<AttributeDto> attributes = projectType.getAttributes();
|
||||
final MutableProjectConfig.MutableSourceStorage sourceStorage = prevData.getSource();
|
||||
if (sourceStorage != null) { // some values should be cleared when user switch between categories
|
||||
sourceStorage.setLocation("");
|
||||
sourceStorage.setType("");
|
||||
sourceStorage.getParameters().clear();
|
||||
}
|
||||
prevData.getProjects().clear();
|
||||
|
||||
final List<AttributeDto> attributes = projectType.getAttributes();
|
||||
Map<String, List<String>> prevDataAttributes = prevData.getAttributes();
|
||||
Map<String, List<String>> newAttributes = new HashMap<>();
|
||||
for (AttributeDto attribute : attributes) {
|
||||
|
|
@ -203,8 +213,9 @@ public class ProjectWizardPresenter implements Wizard.UpdateDelegate,
|
|||
wizard.navigateToFirst();
|
||||
|
||||
// set dataObject's values from projectTemplate
|
||||
dataObject.setType(projectTemplate.getProjectType());
|
||||
dataObject.setSource(projectTemplate.getSource());
|
||||
final NewProjectConfig newProjectConfig = new NewProjectConfigImpl(projectTemplate);
|
||||
dataObject.setType(newProjectConfig.getType());
|
||||
dataObject.setSource(newProjectConfig.getSource());
|
||||
}
|
||||
|
||||
/** Creates or returns project wizard for the specified projectType with the given dataObject. */
|
||||
|
|
|
|||
|
|
@ -16,6 +16,7 @@ import com.google.inject.Inject;
|
|||
import com.google.inject.assistedinject.Assisted;
|
||||
import com.google.web.bindery.event.shared.EventBus;
|
||||
|
||||
import org.eclipse.che.api.core.model.project.NewProjectConfig;
|
||||
import org.eclipse.che.api.core.model.project.ProjectConfig;
|
||||
import org.eclipse.che.api.core.model.project.SourceStorage;
|
||||
import org.eclipse.che.api.core.rest.shared.dto.Link;
|
||||
|
|
@ -27,6 +28,7 @@ import org.eclipse.che.api.promises.client.FunctionException;
|
|||
import org.eclipse.che.api.promises.client.Promise;
|
||||
import org.eclipse.che.api.promises.client.PromiseProvider;
|
||||
import org.eclipse.che.api.promises.client.js.Promises;
|
||||
import org.eclipse.che.api.workspace.shared.dto.NewProjectConfigDto;
|
||||
import org.eclipse.che.api.workspace.shared.dto.ProjectConfigDto;
|
||||
import org.eclipse.che.api.workspace.shared.dto.ProjectProblemDto;
|
||||
import org.eclipse.che.api.workspace.shared.dto.SourceStorageDto;
|
||||
|
|
@ -56,6 +58,7 @@ import org.eclipse.che.ide.dto.DtoFactory;
|
|||
import org.eclipse.che.ide.resource.Path;
|
||||
import org.eclipse.che.ide.util.Arrays;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
|
@ -263,22 +266,22 @@ public final class ResourceManager {
|
|||
* @since 4.4.0
|
||||
*/
|
||||
protected Promise<Project> update(final Path path, final ProjectRequest request) {
|
||||
|
||||
final ProjectConfig projectConfig = request.getBody();
|
||||
final SourceStorage source = projectConfig.getSource();
|
||||
final SourceStorageDto sourceDto = dtoFactory.createDto(SourceStorageDto.class);
|
||||
|
||||
if (request.getBody().getSource() != null) {
|
||||
sourceDto.setLocation(request.getBody().getSource().getLocation());
|
||||
sourceDto.setType(request.getBody().getSource().getType());
|
||||
sourceDto.setParameters(request.getBody().getSource().getParameters());
|
||||
if (source != null) {
|
||||
sourceDto.setLocation(source.getLocation());
|
||||
sourceDto.setType(source.getType());
|
||||
sourceDto.setParameters(source.getParameters());
|
||||
}
|
||||
|
||||
final ProjectConfigDto dto = dtoFactory.createDto(ProjectConfigDto.class)
|
||||
.withName(request.getBody().getName())
|
||||
.withName(projectConfig.getName())
|
||||
.withPath(path.toString())
|
||||
.withDescription(request.getBody().getDescription())
|
||||
.withType(request.getBody().getType())
|
||||
.withMixins(request.getBody().getMixins())
|
||||
.withAttributes(request.getBody().getAttributes())
|
||||
.withDescription(projectConfig.getDescription())
|
||||
.withType(projectConfig.getType())
|
||||
.withMixins(projectConfig.getMixins())
|
||||
.withAttributes(projectConfig.getAttributes())
|
||||
.withSource(sourceDto);
|
||||
|
||||
return ps.updateProject(dto).thenPromise(new Function<ProjectConfigDto, Promise<Project>>() {
|
||||
|
|
@ -410,21 +413,9 @@ public final class ResourceManager {
|
|||
checkArgument(typeRegistry.getProjectType(createRequest.getBody().getType()) != null, "Invalid project type");
|
||||
|
||||
final Path path = Path.valueOf(createRequest.getBody().getPath());
|
||||
|
||||
return findResource(path, true).thenPromise(new Function<Optional<Resource>, Promise<Project>>() {
|
||||
@Override
|
||||
public Promise<Project> apply(Optional<Resource> resource) throws FunctionException {
|
||||
|
||||
final MutableProjectConfig projectConfig = (MutableProjectConfig)createRequest.getBody();
|
||||
final ProjectConfigDto dto = dtoFactory.createDto(ProjectConfigDto.class)
|
||||
.withName(projectConfig.getName())
|
||||
.withPath(path.toString())
|
||||
.withDescription(projectConfig.getDescription())
|
||||
.withType(projectConfig.getType())
|
||||
.withMixins(projectConfig.getMixins())
|
||||
.withAttributes(projectConfig.getAttributes());
|
||||
|
||||
|
||||
if (resource.isPresent()) {
|
||||
if (resource.get().isProject()) {
|
||||
throw new IllegalStateException("Project already exists");
|
||||
|
|
@ -435,22 +426,32 @@ public final class ResourceManager {
|
|||
return update(path, createRequest);
|
||||
}
|
||||
|
||||
return ps.createProject(dto, projectConfig.getOptions()).thenPromise(new Function<ProjectConfigDto, Promise<Project>>() {
|
||||
final MutableProjectConfig projectConfig = (MutableProjectConfig)createRequest.getBody();
|
||||
final List<NewProjectConfig> projectConfigList = projectConfig.getProjects();
|
||||
projectConfigList.add(asDto(projectConfig));
|
||||
final List<NewProjectConfigDto> configDtoList = asDto(projectConfigList);
|
||||
|
||||
return ps.createBatchProjects(configDtoList).thenPromise(new Function<List<ProjectConfigDto>, Promise<Project>>() {
|
||||
@Override
|
||||
public Promise<Project> apply(ProjectConfigDto config) throws FunctionException {
|
||||
final Project newResource = resourceFactory.newProjectImpl(config, ResourceManager.this);
|
||||
store.register(newResource);
|
||||
public Promise<Project> apply(final List<ProjectConfigDto> configList) throws FunctionException {
|
||||
|
||||
return ps.getProjects().then(new Function<List<ProjectConfigDto>, Project>() {
|
||||
@Override
|
||||
public Project apply(List<ProjectConfigDto> updatedConfiguration) throws FunctionException {
|
||||
|
||||
//cache new configs
|
||||
cachedConfigs = updatedConfiguration.toArray(new ProjectConfigDto[updatedConfiguration.size()]);
|
||||
|
||||
eventBus.fireEvent(new ResourceChangedEvent(new ResourceDeltaImpl(newResource, ADDED | DERIVED)));
|
||||
for (ProjectConfigDto projectConfigDto : configList) {
|
||||
if (projectConfigDto.getPath().equals(path.toString())) {
|
||||
final Project newResource = resourceFactory.newProjectImpl(projectConfigDto, ResourceManager.this);
|
||||
store.register(newResource);
|
||||
eventBus.fireEvent(new ResourceChangedEvent(new ResourceDeltaImpl(newResource, ADDED | DERIVED)));
|
||||
|
||||
return newResource;
|
||||
return newResource;
|
||||
}
|
||||
}
|
||||
|
||||
throw new IllegalStateException("Created project is not found");
|
||||
}
|
||||
});
|
||||
}
|
||||
|
|
@ -459,6 +460,46 @@ public final class ResourceManager {
|
|||
});
|
||||
}
|
||||
|
||||
private NewProjectConfigDto asDto(MutableProjectConfig config) {
|
||||
final SourceStorage source = config.getSource();
|
||||
final SourceStorageDto sourceStorageDto = dtoFactory.createDto(SourceStorageDto.class)
|
||||
.withType(source.getType())
|
||||
.withLocation(source.getLocation())
|
||||
.withParameters(source.getParameters());
|
||||
|
||||
return dtoFactory.createDto(NewProjectConfigDto.class)
|
||||
.withName(config.getName())
|
||||
.withPath(config.getPath())
|
||||
.withDescription(config.getDescription())
|
||||
.withSource(sourceStorageDto)
|
||||
.withType(config.getType())
|
||||
.withMixins(config.getMixins())
|
||||
.withAttributes(config.getAttributes())
|
||||
.withOptions(config.getOptions());
|
||||
}
|
||||
|
||||
private List<NewProjectConfigDto> asDto(List<NewProjectConfig> configList) {
|
||||
List<NewProjectConfigDto> result = new ArrayList<>(configList.size());
|
||||
for (NewProjectConfig config : configList) {
|
||||
final SourceStorage source = config.getSource();
|
||||
final SourceStorageDto sourceStorageDto = dtoFactory.createDto(SourceStorageDto.class)
|
||||
.withType(source.getType())
|
||||
.withLocation(source.getLocation())
|
||||
.withParameters(source.getParameters());
|
||||
|
||||
result.add(dtoFactory.createDto(NewProjectConfigDto.class)
|
||||
.withName(config.getName())
|
||||
.withPath(config.getPath())
|
||||
.withDescription(config.getDescription())
|
||||
.withSource(sourceStorageDto)
|
||||
.withType(config.getType())
|
||||
.withMixins(config.getMixins())
|
||||
.withAttributes(config.getAttributes())
|
||||
.withOptions(config.getOptions()));
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
protected Promise<Project> importProject(final Project.ProjectRequest importRequest) {
|
||||
checkArgument(checkProjectName(importRequest.getBody().getName()), "Invalid project name");
|
||||
checkNotNull(importRequest.getBody().getSource(), "Null source configuration occurred");
|
||||
|
|
|
|||
|
|
@ -139,7 +139,7 @@ public class ProjectWizardTest {
|
|||
public void shouldImportProjectSuccessfully() throws Exception {
|
||||
prepareWizard(IMPORT);
|
||||
|
||||
when(workspaceRoot.importProject()).thenReturn(createProjectRequest);
|
||||
when(workspaceRoot.newProject()).thenReturn(createProjectRequest);
|
||||
when(createProjectRequest.withBody(any(ProjectConfig.class))).thenReturn(createProjectRequest);
|
||||
when(createProjectRequest.send()).thenReturn(createProjectPromise);
|
||||
when(createProjectPromise.then(any(Operation.class))).thenReturn(createProjectPromise);
|
||||
|
|
@ -159,7 +159,7 @@ public class ProjectWizardTest {
|
|||
public void shouldFailOnImportProject() throws Exception {
|
||||
prepareWizard(IMPORT);
|
||||
|
||||
when(workspaceRoot.importProject()).thenReturn(createProjectRequest);
|
||||
when(workspaceRoot.newProject()).thenReturn(createProjectRequest);
|
||||
when(createProjectRequest.withBody(any(ProjectConfig.class))).thenReturn(createProjectRequest);
|
||||
when(createProjectRequest.send()).thenReturn(createProjectPromise);
|
||||
when(createProjectPromise.then(any(Operation.class))).thenReturn(createProjectPromise);
|
||||
|
|
|
|||
|
|
@ -16,7 +16,8 @@ import org.eclipse.che.api.core.ConflictException;
|
|||
import org.eclipse.che.api.core.ForbiddenException;
|
||||
import org.eclipse.che.api.core.NotFoundException;
|
||||
import org.eclipse.che.api.core.ServerException;
|
||||
import org.eclipse.che.api.project.server.NewProjectConfig;
|
||||
import org.eclipse.che.api.core.model.project.NewProjectConfig;
|
||||
import org.eclipse.che.api.project.server.NewProjectConfigImpl;
|
||||
import org.eclipse.che.api.project.server.ProjectManager;
|
||||
import org.eclipse.che.api.project.server.ProjectRegistry;
|
||||
import org.eclipse.che.api.project.server.RegisteredProject;
|
||||
|
|
@ -104,7 +105,7 @@ public class ClasspathUpdaterService {
|
|||
ServerException {
|
||||
RegisteredProject project = projectRegistry.getProject(projectPath);
|
||||
|
||||
NewProjectConfig projectConfig = new NewProjectConfig(projectPath,
|
||||
NewProjectConfig projectConfig = new NewProjectConfigImpl(projectPath,
|
||||
project.getName(),
|
||||
project.getType(),
|
||||
project.getSource());
|
||||
|
|
|
|||
|
|
@ -61,4 +61,10 @@ public interface MavenLocalizationConstant extends Messages {
|
|||
|
||||
@Key("window.loader.title")
|
||||
String windowLoaderTitle();
|
||||
|
||||
@Key("maven.page.estimate.errorMessage")
|
||||
String mavenPageEstimateErrorMessage();
|
||||
|
||||
@Key("maven.page.errorDialog.title")
|
||||
String mavenPageErrorDialogTitle();
|
||||
}
|
||||
|
|
|
|||
|
|
@ -27,6 +27,7 @@ import org.eclipse.che.ide.api.wizard.AbstractWizardPage;
|
|||
import org.eclipse.che.ide.util.loging.Log;
|
||||
import org.eclipse.che.plugin.maven.client.MavenArchetype;
|
||||
import org.eclipse.che.plugin.maven.client.MavenExtension;
|
||||
import org.eclipse.che.plugin.maven.client.MavenLocalizationConstant;
|
||||
|
||||
import javax.validation.constraints.NotNull;
|
||||
import java.util.Arrays;
|
||||
|
|
@ -62,18 +63,21 @@ import static org.eclipse.che.plugin.maven.shared.MavenAttributes.VERSION;
|
|||
*/
|
||||
public class MavenPagePresenter extends AbstractWizardPage<MutableProjectConfig> implements MavenPageView.ActionDelegate {
|
||||
|
||||
private final MavenPageView view;
|
||||
private final DialogFactory dialogFactory;
|
||||
private final AppContext appContext;
|
||||
private final MavenPageView view;
|
||||
private final DialogFactory dialogFactory;
|
||||
private final AppContext appContext;
|
||||
private final MavenLocalizationConstant localization;
|
||||
|
||||
@Inject
|
||||
public MavenPagePresenter(MavenPageView view,
|
||||
DialogFactory dialogFactory,
|
||||
AppContext appContext) {
|
||||
AppContext appContext,
|
||||
MavenLocalizationConstant localization) {
|
||||
super();
|
||||
this.view = view;
|
||||
this.dialogFactory = dialogFactory;
|
||||
this.appContext = appContext;
|
||||
this.localization = localization;
|
||||
view.setDelegate(this);
|
||||
}
|
||||
|
||||
|
|
@ -104,6 +108,13 @@ public class MavenPagePresenter extends AbstractWizardPage<MutableProjectConfig>
|
|||
container.get().estimate(MAVEN_ID).then(new Operation<SourceEstimation>() {
|
||||
@Override
|
||||
public void apply(SourceEstimation estimation) throws OperationException {
|
||||
if (!estimation.isMatched()) {
|
||||
final String resolution = estimation.getResolution();
|
||||
final String errorMessage = resolution.isEmpty() ? localization.mavenPageEstimateErrorMessage() : resolution;
|
||||
dialogFactory.createMessageDialog(localization.mavenPageErrorDialogTitle(), errorMessage, null).show();
|
||||
return;
|
||||
}
|
||||
|
||||
Map<String, List<String>> estimatedAttributes = estimation.getAttributes();
|
||||
List<String> artifactIdValues = estimatedAttributes.get(ARTIFACT_ID);
|
||||
if (artifactIdValues != null && !artifactIdValues.isEmpty()) {
|
||||
|
|
@ -136,7 +147,7 @@ public class MavenPagePresenter extends AbstractWizardPage<MutableProjectConfig>
|
|||
}).catchError(new Operation<PromiseError>() {
|
||||
@Override
|
||||
public void apply(PromiseError arg) throws OperationException {
|
||||
dialogFactory.createMessageDialog("Not valid Maven project", arg.getMessage(), null).show();
|
||||
dialogFactory.createMessageDialog(localization.mavenPageErrorDialogTitle(), arg.getMessage(), null).show();
|
||||
Log.error(MavenPagePresenter.class, arg);
|
||||
}
|
||||
});
|
||||
|
|
|
|||
|
|
@ -36,3 +36,6 @@ loader.action.name=Dependencies resolver
|
|||
loader.action.description=Maven Dependencies Resolver
|
||||
window.loader.title=Resolving dependencies
|
||||
|
||||
##### Wizard Maven Page #####
|
||||
maven.page.errorDialog.title=Not valid Maven project
|
||||
maven.page.estimate.errorMessage=Source code not matches Maven project type requirements
|
||||
|
|
|
|||
|
|
@ -22,6 +22,7 @@ import org.eclipse.che.ide.api.dialogs.DialogFactory;
|
|||
import org.eclipse.che.ide.api.dialogs.MessageDialog;
|
||||
import org.eclipse.che.ide.api.project.MutableProjectConfig;
|
||||
import org.eclipse.che.ide.api.resources.Container;
|
||||
import org.eclipse.che.plugin.maven.client.MavenLocalizationConstant;
|
||||
import org.eclipse.che.plugin.maven.shared.MavenAttributes;
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
|
|
@ -52,13 +53,15 @@ public class MavenPagePresenterTest {
|
|||
private final static String TEXT = "to be or not to be";
|
||||
|
||||
@Mock
|
||||
private MavenPageView view;
|
||||
private MavenPageView view;
|
||||
@Mock
|
||||
private EventBus eventBus;
|
||||
private EventBus eventBus;
|
||||
@Mock
|
||||
private DialogFactory dialogFactory;
|
||||
private DialogFactory dialogFactory;
|
||||
@Mock
|
||||
private AppContext appContext;
|
||||
private AppContext appContext;
|
||||
@Mock
|
||||
private MavenLocalizationConstant localization;
|
||||
|
||||
@InjectMocks
|
||||
private MavenPagePresenter mavenPagePresenter;
|
||||
|
|
@ -106,11 +109,13 @@ public class MavenPagePresenterTest {
|
|||
|
||||
@Test
|
||||
public void warningWindowShouldBeShowedIfProjectEstimationHasSomeError() throws Exception {
|
||||
final String dialogTitle = "Not valid Maven project";
|
||||
PromiseError promiseError = mock(PromiseError.class);
|
||||
MessageDialog messageDialog = mock(MessageDialog.class);
|
||||
context.put(WIZARD_MODE_KEY, UPDATE.toString());
|
||||
|
||||
when(promiseError.getMessage()).thenReturn(TEXT);
|
||||
when(localization.mavenPageErrorDialogTitle()).thenReturn(dialogTitle);
|
||||
when(dialogFactory.createMessageDialog(anyString(), anyString(), anyObject())).thenReturn(messageDialog);
|
||||
when(sourceEstimationPromise.then(Matchers.<Operation<SourceEstimation>>anyObject())).thenReturn(sourceEstimationPromise);
|
||||
when(sourceEstimationPromise.catchError(Matchers.<Operation<PromiseError>>anyObject())).thenReturn(sourceEstimationPromise);
|
||||
|
|
@ -124,7 +129,7 @@ public class MavenPagePresenterTest {
|
|||
containerArgumentErrorCapture.getValue().apply(promiseError);
|
||||
|
||||
verify(promiseError).getMessage();
|
||||
verify(dialogFactory).createMessageDialog("Not valid Maven project", TEXT, null);
|
||||
verify(dialogFactory).createMessageDialog(dialogTitle, TEXT, null);
|
||||
verify(messageDialog).show();
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -15,19 +15,20 @@ package org.eclipse.che.api.project.shared;
|
|||
*/
|
||||
public class Constants {
|
||||
|
||||
public static final String BLANK_ID = "blank";
|
||||
public static final String ZIP_IMPORTER_ID = "zip";
|
||||
public static final String VCS_PROVIDER_NAME = "vcs.provider.name";
|
||||
public static final String BLANK_ID = "blank";
|
||||
public static final String ZIP_IMPORTER_ID = "zip";
|
||||
public static final String VCS_PROVIDER_NAME = "vcs.provider.name";
|
||||
// rels for known project links
|
||||
public static final String LINK_REL_GET_PROJECTS = "get projects";
|
||||
public static final String LINK_REL_CREATE_PROJECT = "create project";
|
||||
public static final String LINK_REL_UPDATE_PROJECT = "update project";
|
||||
public static final String LINK_REL_EXPORT_ZIP = "zipball sources";
|
||||
public static final String LINK_REL_CHILDREN = "children";
|
||||
public static final String LINK_REL_TREE = "tree";
|
||||
public static final String LINK_REL_DELETE = "delete";
|
||||
public static final String LINK_REL_GET_CONTENT = "get content";
|
||||
public static final String LINK_REL_UPDATE_CONTENT = "update content";
|
||||
public static final String LINK_REL_GET_PROJECTS = "get projects";
|
||||
public static final String LINK_REL_CREATE_PROJECT = "create project";
|
||||
public static final String LINK_REL_CREATE_BATCH_PROJECTS = "create batch of projects";
|
||||
public static final String LINK_REL_UPDATE_PROJECT = "update project";
|
||||
public static final String LINK_REL_EXPORT_ZIP = "zipball sources";
|
||||
public static final String LINK_REL_CHILDREN = "children";
|
||||
public static final String LINK_REL_TREE = "tree";
|
||||
public static final String LINK_REL_DELETE = "delete";
|
||||
public static final String LINK_REL_GET_CONTENT = "get content";
|
||||
public static final String LINK_REL_UPDATE_CONTENT = "update content";
|
||||
|
||||
public static final String LINK_REL_PROJECT_TYPES = "project types";
|
||||
|
||||
|
|
|
|||
|
|
@ -24,7 +24,6 @@ import java.util.Map;
|
|||
@DTO
|
||||
public interface SourceEstimation {
|
||||
|
||||
|
||||
/** Gets unique id of type of project. */
|
||||
@ApiModelProperty(value = "type ID", position = 1)
|
||||
String getType();
|
||||
|
|
@ -44,4 +43,10 @@ public interface SourceEstimation {
|
|||
|
||||
SourceEstimation withMatched(boolean matched);
|
||||
|
||||
|
||||
/** Gets resolution - the reason that source code not matches project type requirements. */
|
||||
@ApiModelProperty(value = "Resolution", position = 4)
|
||||
String getResolution();
|
||||
|
||||
SourceEstimation withResolution(String resolution);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,118 +0,0 @@
|
|||
/*******************************************************************************
|
||||
* Copyright (c) 2012-2016 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.project.server;
|
||||
|
||||
import org.eclipse.che.api.core.model.project.ProjectConfig;
|
||||
import org.eclipse.che.api.core.model.project.SourceStorage;
|
||||
import org.eclipse.che.api.project.server.type.BaseProjectType;
|
||||
import org.eclipse.che.api.vfs.Path;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* @author gazarenkov
|
||||
*/
|
||||
public class NewProjectConfig implements ProjectConfig {
|
||||
|
||||
private final String path;
|
||||
private final String type;
|
||||
private final List<String> mixins;
|
||||
private final String name;
|
||||
private final String description;
|
||||
private final Map<String, List<String>> attributes;
|
||||
private final SourceStorage origin;
|
||||
|
||||
/**
|
||||
* Full qualified constructor
|
||||
*
|
||||
* @param path
|
||||
* @param type
|
||||
* @param mixins
|
||||
* @param name
|
||||
* @param description
|
||||
* @param attributes
|
||||
* @param origin
|
||||
*/
|
||||
public NewProjectConfig(String path,
|
||||
String type,
|
||||
List<String> mixins,
|
||||
String name,
|
||||
String description,
|
||||
Map<String, List<String>> attributes,
|
||||
SourceStorage origin) {
|
||||
this.path = path;
|
||||
this.type = (type == null) ? BaseProjectType.ID : type;
|
||||
this.mixins = (mixins == null) ? new ArrayList<>() : mixins;
|
||||
this.name = name;
|
||||
this.description = description;
|
||||
this.attributes = (attributes == null) ? new HashMap<>() : attributes;
|
||||
this.origin = origin;
|
||||
}
|
||||
|
||||
/**
|
||||
* Constructor for project import
|
||||
*
|
||||
* @param path
|
||||
* @param name
|
||||
* @param type
|
||||
* @param origin
|
||||
*/
|
||||
public NewProjectConfig(String path, String name, String type, SourceStorage origin) {
|
||||
this(path, type, null, name, null, null, origin);
|
||||
}
|
||||
|
||||
/**
|
||||
* Constructor for reinit
|
||||
*
|
||||
* @param path
|
||||
*/
|
||||
public NewProjectConfig(Path path) {
|
||||
this(path.toString(), null, null, path.getName(), null, null, null);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getPath() {
|
||||
return path;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getDescription() {
|
||||
return description;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getType() {
|
||||
return type;
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<String> getMixins() {
|
||||
return mixins;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, List<String>> getAttributes() {
|
||||
return attributes;
|
||||
}
|
||||
|
||||
@Override
|
||||
public SourceStorage getSource() {
|
||||
return origin;
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,178 @@
|
|||
/*******************************************************************************
|
||||
* Copyright (c) 2012-2016 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.project.server;
|
||||
|
||||
import org.eclipse.che.api.core.model.project.NewProjectConfig;
|
||||
import org.eclipse.che.api.core.model.project.SourceStorage;
|
||||
import org.eclipse.che.api.project.server.type.BaseProjectType;
|
||||
import org.eclipse.che.api.vfs.Path;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import static com.google.common.collect.Lists.newArrayList;
|
||||
import static com.google.common.collect.Maps.newHashMap;
|
||||
|
||||
/**
|
||||
* Implementation of {@link NewProjectConfig} for creating project
|
||||
*
|
||||
* @author gazarenkov
|
||||
*/
|
||||
public class NewProjectConfigImpl implements NewProjectConfig {
|
||||
|
||||
private String path;
|
||||
private String type;
|
||||
private List<String> mixins;
|
||||
private String name;
|
||||
private String description;
|
||||
private Map<String, List<String>> attributes;
|
||||
private Map<String, String> options;
|
||||
private SourceStorage origin;
|
||||
|
||||
/**
|
||||
* Full qualified constructor
|
||||
*
|
||||
* @param path
|
||||
* project path
|
||||
* @param type
|
||||
* project type
|
||||
* @param mixins
|
||||
* mixin project types
|
||||
* @param name
|
||||
* project name
|
||||
* @param description
|
||||
* project description
|
||||
* @param attributes
|
||||
* project attributes
|
||||
* @param options
|
||||
* options for generator for creating project
|
||||
* @param origin
|
||||
* source configuration
|
||||
*/
|
||||
public NewProjectConfigImpl(String path,
|
||||
String type,
|
||||
List<String> mixins,
|
||||
String name,
|
||||
String description,
|
||||
Map<String, List<String>> attributes,
|
||||
Map<String, String> options,
|
||||
SourceStorage origin) {
|
||||
this.path = path;
|
||||
this.type = (type == null) ? BaseProjectType.ID : type;
|
||||
this.mixins = (mixins == null) ? new ArrayList<>() : mixins;
|
||||
this.name = name;
|
||||
this.description = description;
|
||||
this.attributes = (attributes == null) ? newHashMap() : attributes;
|
||||
this.options = (options == null) ? newHashMap() : options;
|
||||
this.origin = origin;
|
||||
}
|
||||
|
||||
/**
|
||||
* Constructor for project import
|
||||
*
|
||||
* @param path
|
||||
* project path
|
||||
* @param name
|
||||
* project name
|
||||
* @param type
|
||||
* project type
|
||||
* @param origin
|
||||
* source configuration
|
||||
*/
|
||||
public NewProjectConfigImpl(String path, String name, String type, SourceStorage origin) {
|
||||
this(path, type, null, name, null, null, null, origin);
|
||||
}
|
||||
|
||||
/**
|
||||
* Constructor for reinit
|
||||
*
|
||||
* @param path
|
||||
*/
|
||||
public NewProjectConfigImpl(Path path) {
|
||||
this(path.toString(), null, null, path.getName(), null, null, null, null);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setName(String name) {
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getPath() {
|
||||
return path;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setPath(String path) {
|
||||
this.path = path;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getDescription() {
|
||||
return description;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setDescription(String description) {
|
||||
this.description = description;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getType() {
|
||||
return type;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setType(String type) {
|
||||
this.type = type;
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<String> getMixins() {
|
||||
return mixins != null ? mixins : newArrayList();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setMixins(List<String> mixins) {
|
||||
this.mixins = mixins;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, List<String>> getAttributes() {
|
||||
return attributes != null ? attributes : newHashMap();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setAttributes(Map<String, List<String>> attributes) {
|
||||
this.attributes = attributes;
|
||||
}
|
||||
|
||||
@Override
|
||||
public SourceStorage getSource() {
|
||||
return origin;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setOptions(Map<String, String> options) {
|
||||
this.options = options;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, String> getOptions() {
|
||||
return options != null ? options : newHashMap();
|
||||
}
|
||||
}
|
||||
|
|
@ -12,16 +12,19 @@ package org.eclipse.che.api.project.server;
|
|||
|
||||
import com.google.common.util.concurrent.ThreadFactoryBuilder;
|
||||
|
||||
import org.eclipse.che.api.core.BadRequestException;
|
||||
import org.eclipse.che.api.core.ConflictException;
|
||||
import org.eclipse.che.api.core.ForbiddenException;
|
||||
import org.eclipse.che.api.core.NotFoundException;
|
||||
import org.eclipse.che.api.core.ServerException;
|
||||
import org.eclipse.che.api.core.UnauthorizedException;
|
||||
import org.eclipse.che.api.core.model.project.NewProjectConfig;
|
||||
import org.eclipse.che.api.core.model.project.ProjectConfig;
|
||||
import org.eclipse.che.api.core.model.project.SourceStorage;
|
||||
import org.eclipse.che.api.core.model.project.type.ProjectType;
|
||||
import org.eclipse.che.api.core.notification.EventService;
|
||||
import org.eclipse.che.api.core.util.LineConsumerFactory;
|
||||
import org.eclipse.che.api.project.server.RegisteredProject.Problem;
|
||||
import org.eclipse.che.commons.lang.concurrent.LoggingUncaughtExceptionHandler;
|
||||
import org.eclipse.che.api.project.server.handlers.CreateProjectHandler;
|
||||
import org.eclipse.che.api.project.server.handlers.ProjectHandlerRegistry;
|
||||
|
|
@ -33,7 +36,6 @@ import org.eclipse.che.api.project.server.type.BaseProjectType;
|
|||
import org.eclipse.che.api.project.server.type.ProjectTypeDef;
|
||||
import org.eclipse.che.api.project.server.type.ProjectTypeRegistry;
|
||||
import org.eclipse.che.api.project.server.type.ProjectTypeResolution;
|
||||
import org.eclipse.che.api.project.server.type.ValueStorageException;
|
||||
import org.eclipse.che.api.project.shared.dto.event.FileWatcherEventType;
|
||||
import org.eclipse.che.api.vfs.Path;
|
||||
import org.eclipse.che.api.vfs.VirtualFile;
|
||||
|
|
@ -61,6 +63,10 @@ import java.util.List;
|
|||
import java.util.Map;
|
||||
import java.util.concurrent.ExecutorService;
|
||||
import java.util.concurrent.Executors;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
import static com.google.common.base.Strings.isNullOrEmpty;
|
||||
import static java.lang.String.format;
|
||||
|
||||
/**
|
||||
* Facade for all project related operations.
|
||||
|
|
@ -196,7 +202,7 @@ public final class ProjectManager {
|
|||
public RegisteredProject getProject(String projectPath) throws ServerException, NotFoundException {
|
||||
final RegisteredProject project = projectRegistry.getProject(projectPath);
|
||||
if (project == null) {
|
||||
throw new NotFoundException(String.format("Project '%s' doesn't exist.", projectPath));
|
||||
throw new NotFoundException(format("Project '%s' doesn't exist.", projectPath));
|
||||
}
|
||||
|
||||
return project;
|
||||
|
|
@ -229,67 +235,179 @@ public final class ProjectManager {
|
|||
throw new ConflictException("Path for new project should be defined ");
|
||||
}
|
||||
|
||||
final String path = ProjectRegistry.absolutizePath(projectConfig.getPath());
|
||||
|
||||
if (projectConfig.getType() == null) {
|
||||
throw new ConflictException("Project Type is not defined " + path);
|
||||
throw new ConflictException("Project Type is not defined " + projectConfig.getPath());
|
||||
}
|
||||
|
||||
final String path = ProjectRegistry.absolutizePath(projectConfig.getPath());
|
||||
if (projectRegistry.getProject(path) != null) {
|
||||
throw new ConflictException("Project config already exists " + path);
|
||||
throw new ConflictException("Project config already exists for " + path);
|
||||
}
|
||||
|
||||
final CreateProjectHandler generator = handlers.getCreateProjectHandler(projectConfig.getType());
|
||||
FolderEntry projectFolder;
|
||||
if (generator != null) {
|
||||
Map<String, AttributeValue> valueMap = new HashMap<>();
|
||||
Map<String, List<String>> attributes = projectConfig.getAttributes();
|
||||
if (attributes != null) {
|
||||
for (Map.Entry<String, List<String>> entry : attributes.entrySet()) {
|
||||
valueMap.put(entry.getKey(), new AttributeValue(entry.getValue()));
|
||||
}
|
||||
}
|
||||
if (options == null) {
|
||||
options = new HashMap<>();
|
||||
}
|
||||
Path projectPath = Path.of(path);
|
||||
generator.onCreateProject(projectPath, valueMap, options);
|
||||
projectFolder = new FolderEntry(vfs.getRoot().getChild(projectPath), projectRegistry);
|
||||
} else {
|
||||
projectFolder = new FolderEntry(vfs.getRoot().createFolder(path), projectRegistry);
|
||||
}
|
||||
|
||||
final RegisteredProject project;
|
||||
try {
|
||||
project = projectRegistry.putProject(projectConfig, projectFolder, true, false);
|
||||
} catch (Exception e) {
|
||||
// rollback project folder
|
||||
|
||||
projectFolder.getVirtualFile().delete();
|
||||
throw e;
|
||||
}
|
||||
|
||||
// unlike imported it is not appropriate for newly created project to have problems
|
||||
if(!project.getProblems().isEmpty()) {
|
||||
|
||||
// rollback project folder
|
||||
projectFolder.getVirtualFile().delete();
|
||||
// remove project entry
|
||||
projectRegistry.removeProjects(projectConfig.getPath());
|
||||
throw new ServerException("Problems occured: " + project.getProblemsStr());
|
||||
}
|
||||
|
||||
|
||||
workspaceProjectsHolder.sync(projectRegistry);
|
||||
|
||||
projectRegistry.fireInitHandlers(project);
|
||||
|
||||
return project;
|
||||
return doCreateProject(projectConfig, options);
|
||||
} finally {
|
||||
projectTreeChangesDetector.resume();
|
||||
}
|
||||
}
|
||||
|
||||
/** Note: Use {@link ProjectTreeChangesDetector#suspend()} and {@link ProjectTreeChangesDetector#resume()} while creating a project */
|
||||
private RegisteredProject doCreateProject(ProjectConfig projectConfig, Map<String, String> options) throws ConflictException,
|
||||
ForbiddenException,
|
||||
ServerException,
|
||||
NotFoundException {
|
||||
final String path = ProjectRegistry.absolutizePath(projectConfig.getPath());
|
||||
final CreateProjectHandler generator = handlers.getCreateProjectHandler(projectConfig.getType());
|
||||
FolderEntry projectFolder;
|
||||
if (generator != null) {
|
||||
Map<String, AttributeValue> valueMap = new HashMap<>();
|
||||
Map<String, List<String>> attributes = projectConfig.getAttributes();
|
||||
if (attributes != null) {
|
||||
for (Map.Entry<String, List<String>> entry : attributes.entrySet()) {
|
||||
valueMap.put(entry.getKey(), new AttributeValue(entry.getValue()));
|
||||
}
|
||||
}
|
||||
if (options == null) {
|
||||
options = new HashMap<>();
|
||||
}
|
||||
Path projectPath = Path.of(path);
|
||||
generator.onCreateProject(projectPath, valueMap, options);
|
||||
projectFolder = new FolderEntry(vfs.getRoot().getChild(projectPath), projectRegistry);
|
||||
} else {
|
||||
projectFolder = new FolderEntry(vfs.getRoot().createFolder(path), projectRegistry);
|
||||
}
|
||||
|
||||
final RegisteredProject project = projectRegistry.putProject(projectConfig, projectFolder, true, false);
|
||||
workspaceProjectsHolder.sync(projectRegistry);
|
||||
projectRegistry.fireInitHandlers(project);
|
||||
|
||||
return project;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create batch of projects according to their configurations.
|
||||
* <p/>
|
||||
* Notes: - a project will be created by importing when project configuration contains {@link SourceStorage} object,
|
||||
* otherwise this one will be created corresponding its {@link NewProjectConfig}:
|
||||
* <li> - {@link NewProjectConfig} object contains only one mandatory {@link NewProjectConfig#setPath(String)} field.
|
||||
* In this case Project will be created as project of {@link BaseProjectType} type </li>
|
||||
* <li> - a project will be created as project of {@link BaseProjectType} type with {@link Problem#code} = 12
|
||||
* when declared primary project type is not registered, </li>
|
||||
* <li> - a project will be created with {@link Problem#code} = 12 and without mixin project type
|
||||
* when declared mixin project type is not registered</li>
|
||||
* <li> - for creating a project by generator {@link NewProjectConfig#getOptions()} should be specified.</li>
|
||||
*
|
||||
* @param projectConfigList
|
||||
* the list of configurations to create projects
|
||||
* @param rewrite
|
||||
* whether rewrite or not (throw exception otherwise) if such a project exists
|
||||
* @return the list of new projects
|
||||
* @throws BadRequestException
|
||||
* when {@link NewProjectConfig} object not contains mandatory {@link NewProjectConfig#setPath(String)} field.
|
||||
* @throws ConflictException
|
||||
* when the same path project exists and {@code rewrite} is {@code false}
|
||||
* @throws ForbiddenException
|
||||
* when trying to overwrite the project and this one contains at least one locked file
|
||||
* @throws NotFoundException
|
||||
* when parent folder does not exist
|
||||
* @throws UnauthorizedException
|
||||
* if user isn't authorized to access to location at importing source code
|
||||
* @throws ServerException
|
||||
* if other error occurs
|
||||
*/
|
||||
public List<RegisteredProject> createBatchProjects(List<? extends NewProjectConfig> projectConfigList, boolean rewrite)
|
||||
throws BadRequestException, ConflictException, ForbiddenException, NotFoundException, ServerException, UnauthorizedException,
|
||||
IOException {
|
||||
projectTreeChangesDetector.suspend();
|
||||
try {
|
||||
final List<RegisteredProject> projects = new ArrayList<>(projectConfigList.size());
|
||||
validateProjectConfigurations(projectConfigList, rewrite);
|
||||
|
||||
final List<NewProjectConfig> sortedConfigList = projectConfigList
|
||||
.stream()
|
||||
.sorted((config1, config2) -> config1.getPath().compareTo(config2.getPath()))
|
||||
.collect(Collectors.toList());
|
||||
|
||||
for (NewProjectConfig projectConfig : sortedConfigList) {
|
||||
RegisteredProject registeredProject;
|
||||
final String pathToProject = projectConfig.getPath();
|
||||
|
||||
//creating project(by config or by importing source code)
|
||||
try {
|
||||
final SourceStorage sourceStorage = projectConfig.getSource();
|
||||
if (sourceStorage != null && !isNullOrEmpty(sourceStorage.getLocation())) {
|
||||
doImportProject(pathToProject, sourceStorage, rewrite);
|
||||
} else if (!isVirtualFileExist(pathToProject)) {
|
||||
registeredProject = doCreateProject(projectConfig, projectConfig.getOptions());
|
||||
projects.add(registeredProject);
|
||||
continue;
|
||||
}
|
||||
} catch (Exception e) {
|
||||
if (!isVirtualFileExist(pathToProject)) {//project folder is absent
|
||||
rollbackCreatingBatchProjects(projects);
|
||||
throw e;
|
||||
}
|
||||
}
|
||||
|
||||
//update project
|
||||
if (isVirtualFileExist(pathToProject)) {
|
||||
try {
|
||||
registeredProject = updateProject(projectConfig);
|
||||
} catch (Exception e) {
|
||||
registeredProject = projectRegistry.putProject(projectConfig, asFolder(pathToProject), true, false);
|
||||
registeredProject.getProblems().add(new Problem(14, "The project is not updated, caused by " + e.getLocalizedMessage()));
|
||||
}
|
||||
} else {
|
||||
registeredProject = projectRegistry.putProject(projectConfig, null, true, false);
|
||||
}
|
||||
|
||||
projects.add(registeredProject);
|
||||
}
|
||||
|
||||
return projects;
|
||||
|
||||
} finally {
|
||||
projectTreeChangesDetector.resume();
|
||||
}
|
||||
}
|
||||
|
||||
private void rollbackCreatingBatchProjects(List<RegisteredProject> projects) {
|
||||
for (RegisteredProject project : projects) {
|
||||
try {
|
||||
final FolderEntry projectFolder = project.getBaseFolder();
|
||||
if (projectFolder != null) {
|
||||
projectFolder.getVirtualFile().delete();
|
||||
}
|
||||
projectRegistry.removeProjects(project.getPath());
|
||||
} catch (Exception e) {
|
||||
LOG.warn(e.getLocalizedMessage());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void validateProjectConfigurations(List<? extends NewProjectConfig> projectConfigList, boolean rewrite)
|
||||
throws NotFoundException, ServerException, ConflictException, ForbiddenException, BadRequestException {
|
||||
|
||||
for (NewProjectConfig projectConfig : projectConfigList) {
|
||||
final String pathToProject = projectConfig.getPath();
|
||||
if (isNullOrEmpty(pathToProject)) {
|
||||
throw new BadRequestException("Path for new project should be defined");
|
||||
}
|
||||
|
||||
final String path = ProjectRegistry.absolutizePath(pathToProject);
|
||||
final RegisteredProject registeredProject = projectRegistry.getProject(path);
|
||||
if (registeredProject != null && rewrite) {
|
||||
delete(path);
|
||||
} else if (registeredProject != null) {
|
||||
throw new ConflictException(format("Project config already exists for %s", path));
|
||||
}
|
||||
|
||||
final String projectTypeId = projectConfig.getType();
|
||||
if (isNullOrEmpty(projectTypeId)) {
|
||||
projectConfig.setType(BaseProjectType.ID);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Updating project means:
|
||||
* - getting the project (should exist)
|
||||
|
|
@ -311,31 +429,17 @@ public final class ProjectManager {
|
|||
ServerException,
|
||||
NotFoundException,
|
||||
ConflictException {
|
||||
String path = newConfig.getPath();
|
||||
|
||||
final String path = newConfig.getPath();
|
||||
if (path == null) {
|
||||
throw new ConflictException("Project path is not defined");
|
||||
}
|
||||
|
||||
final FolderEntry baseFolder = asFolder(path);
|
||||
|
||||
// If a project does not exist in the target path, create a new one
|
||||
if (baseFolder == null) {
|
||||
throw new NotFoundException(String.format("Folder '%s' doesn't exist.", path));
|
||||
throw new NotFoundException(format("Folder '%s' doesn't exist.", path));
|
||||
}
|
||||
|
||||
ProjectConfig oldConfig = projectRegistry.getProject(path);
|
||||
|
||||
final RegisteredProject project = projectRegistry.putProject(newConfig, baseFolder, true, false);
|
||||
|
||||
// unlike imported it is not appropriate for updated project to have problems
|
||||
if(!project.getProblems().isEmpty()) {
|
||||
|
||||
// rollback project folder
|
||||
projectRegistry.putProject(oldConfig, baseFolder, false, false);
|
||||
throw new ServerException("Problems occured: " + project.getProblemsStr());
|
||||
}
|
||||
|
||||
workspaceProjectsHolder.sync(projectRegistry);
|
||||
|
||||
projectRegistry.fireInitHandlers(project);
|
||||
|
|
@ -371,57 +475,67 @@ public final class ProjectManager {
|
|||
NotFoundException {
|
||||
projectTreeChangesDetector.suspend();
|
||||
try {
|
||||
final ProjectImporter importer = importers.getImporter(sourceStorage.getType());
|
||||
if (importer == null) {
|
||||
throw new NotFoundException(String.format("Unable import sources project from '%s'. Sources type '%s' is not supported.",
|
||||
sourceStorage.getLocation(), sourceStorage.getType()));
|
||||
}
|
||||
|
||||
// Preparing websocket output publisher to broadcast output of import process to the ide clients while importing
|
||||
final LineConsumerFactory outputOutputConsumerFactory =
|
||||
() -> new ProjectImportOutputWSLineConsumer(path, workspaceProjectsHolder.getWorkspaceId(), 300);
|
||||
|
||||
String normalizePath = (path.startsWith("/")) ? path : "/".concat(path);
|
||||
FolderEntry folder = asFolder(normalizePath);
|
||||
if (folder != null && !rewrite) {
|
||||
throw new ConflictException(String.format("Project %s already exists ", path));
|
||||
}
|
||||
|
||||
if (folder == null) {
|
||||
folder = getProjectsRoot().createFolder(normalizePath);
|
||||
}
|
||||
|
||||
try {
|
||||
importer.importSources(folder, sourceStorage, outputOutputConsumerFactory);
|
||||
} catch (final Exception e) {
|
||||
folder.remove();
|
||||
throw e;
|
||||
}
|
||||
|
||||
final String name = folder.getPath().getName();
|
||||
for (ProjectConfig project : workspaceProjectsHolder.getProjects()) {
|
||||
if (normalizePath.equals(project.getPath())) {
|
||||
// TODO Needed for factory project importing with keepDir. It needs to find more appropriate solution
|
||||
List<String> innerProjects = projectRegistry.getProjects(normalizePath);
|
||||
for (String innerProject : innerProjects) {
|
||||
RegisteredProject registeredProject = projectRegistry.getProject(innerProject);
|
||||
projectRegistry.putProject(registeredProject, asFolder(registeredProject.getPath()), true, false);
|
||||
}
|
||||
RegisteredProject rp = projectRegistry.putProject(project, folder, true, false);
|
||||
workspaceProjectsHolder.sync(projectRegistry);
|
||||
return rp;
|
||||
}
|
||||
}
|
||||
|
||||
RegisteredProject rp = projectRegistry
|
||||
.putProject(new NewProjectConfig(normalizePath, name, BaseProjectType.ID, sourceStorage), folder, true, false);
|
||||
workspaceProjectsHolder.sync(projectRegistry);
|
||||
return rp;
|
||||
return doImportProject(path, sourceStorage, rewrite);
|
||||
} finally {
|
||||
projectTreeChangesDetector.resume();
|
||||
}
|
||||
}
|
||||
|
||||
/** Note: Use {@link ProjectTreeChangesDetector#suspend()} and {@link ProjectTreeChangesDetector#resume()} while importing source code */
|
||||
private RegisteredProject doImportProject(String path, SourceStorage sourceStorage, boolean rewrite) throws ServerException,
|
||||
IOException,
|
||||
ForbiddenException,
|
||||
UnauthorizedException,
|
||||
ConflictException,
|
||||
NotFoundException {
|
||||
final ProjectImporter importer = importers.getImporter(sourceStorage.getType());
|
||||
if (importer == null) {
|
||||
throw new NotFoundException(format("Unable import sources project from '%s'. Sources type '%s' is not supported.",
|
||||
sourceStorage.getLocation(), sourceStorage.getType()));
|
||||
}
|
||||
|
||||
// Preparing websocket output publisher to broadcast output of import process to the ide clients while importing
|
||||
final LineConsumerFactory outputOutputConsumerFactory =
|
||||
() -> new ProjectImportOutputWSLineConsumer(path, workspaceProjectsHolder.getWorkspaceId(), 300);
|
||||
|
||||
String normalizePath = (path.startsWith("/")) ? path : "/".concat(path);
|
||||
FolderEntry folder = asFolder(normalizePath);
|
||||
if (folder != null && !rewrite) {
|
||||
throw new ConflictException(format("Project %s already exists ", path));
|
||||
}
|
||||
|
||||
if (folder == null) {
|
||||
folder = getProjectsRoot().createFolder(normalizePath);
|
||||
}
|
||||
|
||||
try {
|
||||
importer.importSources(folder, sourceStorage, outputOutputConsumerFactory);
|
||||
} catch (final Exception e) {
|
||||
folder.remove();
|
||||
throw e;
|
||||
}
|
||||
|
||||
final String name = folder.getPath().getName();
|
||||
for (ProjectConfig project : workspaceProjectsHolder.getProjects()) {
|
||||
if (normalizePath.equals(project.getPath())) {
|
||||
// TODO Needed for factory project importing with keepDir. It needs to find more appropriate solution
|
||||
List<String> innerProjects = projectRegistry.getProjects(normalizePath);
|
||||
for (String innerProject : innerProjects) {
|
||||
RegisteredProject registeredProject = projectRegistry.getProject(innerProject);
|
||||
projectRegistry.putProject(registeredProject, asFolder(registeredProject.getPath()), true, false);
|
||||
}
|
||||
RegisteredProject rp = projectRegistry.putProject(project, folder, true, false);
|
||||
workspaceProjectsHolder.sync(projectRegistry);
|
||||
return rp;
|
||||
}
|
||||
}
|
||||
|
||||
RegisteredProject rp = projectRegistry
|
||||
.putProject(new NewProjectConfigImpl(normalizePath, name, BaseProjectType.ID, sourceStorage), folder, true, false);
|
||||
workspaceProjectsHolder.sync(projectRegistry);
|
||||
return rp;
|
||||
}
|
||||
|
||||
/**
|
||||
* Estimates if the folder can be treated as a project of particular type
|
||||
*
|
||||
|
|
@ -431,11 +545,9 @@ public final class ProjectManager {
|
|||
* @return resolution object
|
||||
* @throws ServerException
|
||||
* @throws NotFoundException
|
||||
* @throws ValueStorageException
|
||||
*/
|
||||
public ProjectTypeResolution estimateProject(String path, String projectTypeId) throws ServerException,
|
||||
NotFoundException,
|
||||
ValueStorageException {
|
||||
NotFoundException {
|
||||
final ProjectTypeDef projectType = projectTypeRegistry.getProjectType(projectTypeId);
|
||||
if (projectType == null) {
|
||||
throw new NotFoundException("Project Type to estimate needed.");
|
||||
|
|
@ -468,13 +580,9 @@ public final class ProjectManager {
|
|||
continue;
|
||||
}
|
||||
|
||||
try {
|
||||
final ProjectTypeResolution resolution = estimateProject(path, type.getId());
|
||||
if (resolution.matched()) {
|
||||
resolutions.add(resolution);
|
||||
}
|
||||
} catch (ValueStorageException e) {
|
||||
LOG.warn(e.getLocalizedMessage(), e);
|
||||
final ProjectTypeResolution resolution = estimateProject(path, type.getId());
|
||||
if (resolution.matched()) {
|
||||
resolutions.add(resolution);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -606,13 +714,14 @@ public final class ProjectManager {
|
|||
|
||||
if (move.isProject()) {
|
||||
final RegisteredProject project = projectRegistry.getProject(itemPath);
|
||||
NewProjectConfig projectConfig = new NewProjectConfig(newItem.getPath().toString(),
|
||||
project.getType(),
|
||||
project.getMixins(),
|
||||
newName,
|
||||
project.getDescription(),
|
||||
project.getAttributes(),
|
||||
project.getSource());
|
||||
NewProjectConfig projectConfig = new NewProjectConfigImpl(newItem.getPath().toString(),
|
||||
project.getType(),
|
||||
project.getMixins(),
|
||||
newName,
|
||||
project.getDescription(),
|
||||
project.getAttributes(),
|
||||
null,
|
||||
project.getSource());
|
||||
|
||||
if (move instanceof FolderEntry) {
|
||||
projectRegistry.removeProjects(project.getPath());
|
||||
|
|
@ -623,6 +732,10 @@ public final class ProjectManager {
|
|||
return move;
|
||||
}
|
||||
|
||||
boolean isVirtualFileExist(String path) throws ServerException {
|
||||
return asVirtualFileEntry(path) != null;
|
||||
}
|
||||
|
||||
FolderEntry asFolder(String path) throws NotFoundException, ServerException {
|
||||
final VirtualFileEntry entry = asVirtualFileEntry(path);
|
||||
if (entry == null) {
|
||||
|
|
@ -630,13 +743,13 @@ public final class ProjectManager {
|
|||
}
|
||||
|
||||
if (!entry.isFolder()) {
|
||||
throw new NotFoundException(String.format("Item '%s' isn't a folder. ", path));
|
||||
throw new NotFoundException(format("Item '%s' isn't a folder. ", path));
|
||||
}
|
||||
|
||||
return (FolderEntry)entry;
|
||||
}
|
||||
|
||||
VirtualFileEntry asVirtualFileEntry(String path) throws NotFoundException, ServerException {
|
||||
VirtualFileEntry asVirtualFileEntry(String path) throws ServerException {
|
||||
final String apath = ProjectRegistry.absolutizePath(path);
|
||||
final FolderEntry root = getProjectsRoot();
|
||||
return root.getChild(apath);
|
||||
|
|
@ -649,7 +762,7 @@ public final class ProjectManager {
|
|||
}
|
||||
|
||||
if (!entry.isFile()) {
|
||||
throw new NotFoundException(String.format("Item '%s' isn't a file. ", path));
|
||||
throw new NotFoundException(format("Item '%s' isn't a file. ", path));
|
||||
}
|
||||
|
||||
return (FileEntry)entry;
|
||||
|
|
@ -676,7 +789,7 @@ public final class ProjectManager {
|
|||
}
|
||||
searcher.add(file);
|
||||
} catch (Exception e) {
|
||||
LOG.warn(String.format("Project: %s", project.getPath()), e.getMessage());
|
||||
LOG.warn(format("Project: %s", project.getPath()), e.getMessage());
|
||||
}
|
||||
});
|
||||
}
|
||||
|
|
|
|||
|
|
@ -14,6 +14,7 @@ import org.eclipse.che.api.core.ConflictException;
|
|||
import org.eclipse.che.api.core.ForbiddenException;
|
||||
import org.eclipse.che.api.core.NotFoundException;
|
||||
import org.eclipse.che.api.core.ServerException;
|
||||
import org.eclipse.che.api.core.model.project.NewProjectConfig;
|
||||
import org.eclipse.che.api.core.model.project.ProjectConfig;
|
||||
import org.eclipse.che.api.core.notification.EventService;
|
||||
import org.eclipse.che.api.project.server.handlers.ProjectHandlerRegistry;
|
||||
|
|
@ -181,15 +182,12 @@ public class ProjectRegistry {
|
|||
* whether this is automatically detected or explicitly defined project
|
||||
* @return project
|
||||
* @throws ServerException
|
||||
* @throws ConflictException
|
||||
* @throws NotFoundException
|
||||
* when path for project is undefined
|
||||
*/
|
||||
RegisteredProject putProject(ProjectConfig config,
|
||||
FolderEntry folder,
|
||||
boolean updated,
|
||||
boolean detected) throws ServerException,
|
||||
ConflictException,
|
||||
NotFoundException {
|
||||
boolean detected) throws ServerException {
|
||||
|
||||
final RegisteredProject project = new RegisteredProject(folder, config, updated, detected, this.projectTypeRegistry);
|
||||
projects.put(project.getPath(), project);
|
||||
|
|
@ -223,8 +221,7 @@ public class ProjectRegistry {
|
|||
* Attributes defined with particular Project Type
|
||||
* If incoming Project Type is primary and:
|
||||
* - If the folder located on projectPath is a Project, its Primary PT will be converted to incoming PT
|
||||
* - If the folder located on projectPath is NOT a Project the folder will be converted to "detected" Project
|
||||
* with incoming Primary PT
|
||||
* - If the folder located on projectPath is NOT a Project the folder will be converted to "detected" Project with incoming Primary PT
|
||||
* If incoming Project Type is mixin and:
|
||||
* - If the folder located on projectPath is a Project, this PT will be added (if not already there) to its Mixin PTs
|
||||
* - If the folder located on projectPath is NOT a Project - ConflictException will be thrown
|
||||
|
|
@ -268,7 +265,7 @@ public class ProjectRegistry {
|
|||
final String path = absolutizePath(projectPath);
|
||||
final String name = Path.of(projectPath).getName();
|
||||
|
||||
conf = new NewProjectConfig(path, type, newMixins, name, name, null, null);
|
||||
conf = new NewProjectConfigImpl(path, type, newMixins, name, name, null, null, null);
|
||||
|
||||
return putProject(conf, root.getChildFolder(path), true, true);
|
||||
}
|
||||
|
|
@ -283,12 +280,13 @@ public class ProjectRegistry {
|
|||
newType = type;
|
||||
}
|
||||
|
||||
conf = new NewProjectConfig(project.getPath(),
|
||||
conf = new NewProjectConfigImpl(project.getPath(),
|
||||
newType,
|
||||
newMixins,
|
||||
project.getName(),
|
||||
project.getDescription(),
|
||||
project.getAttributes(),
|
||||
null,
|
||||
project.getSource());
|
||||
|
||||
return putProject(conf, project.getBaseFolder(), true, project.isDetected());
|
||||
|
|
@ -339,12 +337,13 @@ public class ProjectRegistry {
|
|||
newType = BaseProjectType.ID;
|
||||
}
|
||||
|
||||
final NewProjectConfig conf = new NewProjectConfig(project.getPath(),
|
||||
final NewProjectConfig conf = new NewProjectConfigImpl(project.getPath(),
|
||||
newType,
|
||||
newMixins,
|
||||
project.getName(),
|
||||
project.getDescription(),
|
||||
project.getAttributes(),
|
||||
null,
|
||||
project.getSource());
|
||||
|
||||
return putProject(conf, project.getBaseFolder(), true, project.isDetected());
|
||||
|
|
@ -367,7 +366,7 @@ public class ProjectRegistry {
|
|||
putProject(null, folder, true, false);
|
||||
}
|
||||
}
|
||||
} catch (ServerException | ConflictException | NotFoundException e) {
|
||||
} catch (ServerException e) {
|
||||
LOG.warn(e.getLocalizedMessage());
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -43,6 +43,7 @@ import org.eclipse.che.api.vfs.search.QueryExpression;
|
|||
import org.eclipse.che.api.vfs.search.SearchResult;
|
||||
import org.eclipse.che.api.vfs.search.SearchResultEntry;
|
||||
import org.eclipse.che.api.vfs.search.Searcher;
|
||||
import org.eclipse.che.api.workspace.shared.dto.NewProjectConfigDto;
|
||||
import org.eclipse.che.api.workspace.shared.dto.ProjectConfigDto;
|
||||
import org.eclipse.che.api.workspace.shared.dto.SourceStorageDto;
|
||||
import org.eclipse.che.commons.env.EnvironmentContext;
|
||||
|
|
@ -90,6 +91,7 @@ import static javax.ws.rs.core.MediaType.APPLICATION_JSON;
|
|||
import static org.eclipse.che.api.core.util.LinksHelper.createLink;
|
||||
import static org.eclipse.che.api.project.server.DtoConverter.asDto;
|
||||
import static org.eclipse.che.api.project.shared.Constants.LINK_REL_CHILDREN;
|
||||
import static org.eclipse.che.api.project.shared.Constants.LINK_REL_CREATE_BATCH_PROJECTS;
|
||||
import static org.eclipse.che.api.project.shared.Constants.LINK_REL_CREATE_PROJECT;
|
||||
import static org.eclipse.che.api.project.shared.Constants.LINK_REL_DELETE;
|
||||
import static org.eclipse.che.api.project.shared.Constants.LINK_REL_GET_CONTENT;
|
||||
|
|
@ -206,6 +208,37 @@ public class ProjectService extends Service {
|
|||
return injectProjectLinks(configDto);
|
||||
}
|
||||
|
||||
@POST
|
||||
@Path("/batch")
|
||||
@Consumes(MediaType.APPLICATION_JSON)
|
||||
@Produces(MediaType.APPLICATION_JSON)
|
||||
@ApiOperation(value = "Creates batch of projects according to their configurations",
|
||||
notes = "A project will be created by importing when project configuration contains source object. " +
|
||||
"For creating a project by generator options should be specified.",
|
||||
response = ProjectConfigDto.class)
|
||||
@ApiResponses({@ApiResponse(code = 200, message = "OK"),
|
||||
@ApiResponse(code = 400, message = "Path for new project should be defined"),
|
||||
@ApiResponse(code = 403, message = "Operation is forbidden"),
|
||||
@ApiResponse(code = 409, message = "Project with specified name already exist in workspace"),
|
||||
@ApiResponse(code = 500, message = "Server error")})
|
||||
@GenerateLink(rel = LINK_REL_CREATE_BATCH_PROJECTS)
|
||||
public List<ProjectConfigDto> createBatchProjects(
|
||||
@Description("list of descriptors for projects") List<NewProjectConfigDto> projectConfigList,
|
||||
@ApiParam(value = "Force rewrite existing project", allowableValues = "true,false")
|
||||
@QueryParam("force") boolean rewrite)
|
||||
throws ConflictException, ForbiddenException, ServerException, NotFoundException, IOException, UnauthorizedException,
|
||||
BadRequestException {
|
||||
|
||||
List<ProjectConfigDto> result = new ArrayList<>(projectConfigList.size());
|
||||
for (RegisteredProject registeredProject : projectManager.createBatchProjects(projectConfigList, rewrite)) {
|
||||
ProjectConfigDto projectConfig = injectProjectLinks(asDto(registeredProject));
|
||||
result.add(projectConfig);
|
||||
|
||||
eventService.publish(new ProjectCreatedEvent(workspace, registeredProject.getPath()));
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
@PUT
|
||||
@Path("/{path:.*}")
|
||||
@Consumes(MediaType.APPLICATION_JSON)
|
||||
|
|
@ -271,6 +304,7 @@ public class ProjectService extends Service {
|
|||
return DtoFactory.newDto(SourceEstimation.class)
|
||||
.withType(projectType)
|
||||
.withMatched(resolution.matched())
|
||||
.withResolution(resolution.getResolution())
|
||||
.withAttributes(attributes);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -11,13 +11,10 @@
|
|||
package org.eclipse.che.api.project.server;
|
||||
|
||||
import org.eclipse.che.api.core.NotFoundException;
|
||||
import org.eclipse.che.api.core.ServerException;
|
||||
import org.eclipse.che.api.core.model.project.type.Attribute;
|
||||
import org.eclipse.che.api.project.server.RegisteredProject.Problem;
|
||||
import org.eclipse.che.api.project.server.type.ProjectTypeConstraintException;
|
||||
import org.eclipse.che.api.project.server.type.ProjectTypeDef;
|
||||
import org.eclipse.che.api.project.server.type.ProjectTypeRegistry;
|
||||
import org.eclipse.che.api.project.server.type.ValueStorageException;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
|
|
@ -26,6 +23,9 @@ import java.util.List;
|
|||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
import static com.google.common.collect.Lists.newArrayList;
|
||||
import static java.lang.String.format;
|
||||
|
||||
/**
|
||||
* @author gazarenkov
|
||||
*/
|
||||
|
|
@ -33,37 +33,40 @@ public class ProjectTypes {
|
|||
|
||||
private final String projectPath;
|
||||
private final ProjectTypeRegistry projectTypeRegistry;
|
||||
private ProjectTypeDef primary;
|
||||
private ProjectTypeDef primary;
|
||||
private final Map<String, ProjectTypeDef> mixins;
|
||||
private final Map<String, ProjectTypeDef> all;
|
||||
private final Map<String, Attribute> attributeDefs;
|
||||
private final List<Problem> problems;
|
||||
|
||||
ProjectTypes(String projectPath,
|
||||
String type,
|
||||
List<String> mixinTypes,
|
||||
ProjectTypeRegistry projectTypeRegistry,
|
||||
List<Problem> problems) throws ProjectTypeConstraintException, NotFoundException {
|
||||
String type,
|
||||
List<String> mixinTypes,
|
||||
ProjectTypeRegistry projectTypeRegistry,
|
||||
List<Problem> problems) {
|
||||
mixins = new HashMap<>();
|
||||
all = new HashMap<>();
|
||||
attributeDefs = new HashMap<>();
|
||||
this.problems = problems != null ? problems : newArrayList();
|
||||
|
||||
this.projectTypeRegistry = projectTypeRegistry;
|
||||
this.projectPath = projectPath;
|
||||
|
||||
ProjectTypeDef tmpPrimary;
|
||||
if (type == null) {
|
||||
problems.add(new Problem(12, "No primary type defined for " + projectPath + " Base Project Type assigned."));
|
||||
this.problems.add(new Problem(12, "No primary type defined for " + projectPath + " Base Project Type assigned."));
|
||||
tmpPrimary = ProjectTypeRegistry.BASE_TYPE;
|
||||
} else {
|
||||
try {
|
||||
tmpPrimary = projectTypeRegistry.getProjectType(type);
|
||||
} catch (NotFoundException e) {
|
||||
problems.add(new Problem(12, "Primary type " + type + " defined for " + projectPath + " is not registered. Base Project Type assigned."));
|
||||
this.problems.add(new Problem(12, "Primary type " + type + " defined for " + projectPath +
|
||||
" is not registered. Base Project Type assigned."));
|
||||
tmpPrimary = ProjectTypeRegistry.BASE_TYPE;
|
||||
}
|
||||
|
||||
if (!tmpPrimary.isPrimaryable()) {
|
||||
problems.add(new Problem(12, "Project type " + tmpPrimary.getId() + " is not allowable to be primary type. Base Project Type assigned."));
|
||||
this.problems.add(new Problem(12, "Project type " + tmpPrimary.getId() + " is not allowable to be primary type. Base Project Type assigned."));
|
||||
tmpPrimary = ProjectTypeRegistry.BASE_TYPE;
|
||||
}
|
||||
}
|
||||
|
|
@ -90,12 +93,12 @@ public class ProjectTypes {
|
|||
try {
|
||||
mixin = projectTypeRegistry.getProjectType(mixinFromConfig);
|
||||
} catch (NotFoundException e) {
|
||||
problems.add(new Problem(12, "Project type " + mixinFromConfig + " is not registered. Skipped."));
|
||||
this.problems.add(new Problem(12, "Project type " + mixinFromConfig + " is not registered. Skipped."));
|
||||
continue;
|
||||
}
|
||||
|
||||
if (!mixin.isMixable()) {
|
||||
problems.add(new Problem(12, "Project type " + mixin + " is not allowable to be mixin. It not mixable. Skipped."));
|
||||
this.problems.add(new Problem(12, "Project type " + mixin + " is not allowable to be mixin. It not mixable. Skipped."));
|
||||
continue;
|
||||
}
|
||||
|
||||
|
|
@ -105,14 +108,15 @@ public class ProjectTypes {
|
|||
|
||||
// detect duplicated attributes
|
||||
for (Attribute attr : mixin.getAttributes()) {
|
||||
if (attributeDefs.containsKey(attr.getName())) {
|
||||
|
||||
problems.add(new Problem(13, "Attribute name conflict. Duplicated attributes detected " + projectPath +
|
||||
" Attribute " + attr.getName() + " declared in " + mixin.getId() + " already declared in " +
|
||||
attributeDefs.get(attr.getName()).getProjectType()+" Skipped."));
|
||||
final String attrName = attr.getName();
|
||||
if (attributeDefs.containsKey(attrName)) {
|
||||
this.problems.add(new Problem(13,
|
||||
format("Attribute name conflict. Duplicated attributes detected for %s. " +
|
||||
"Attribute %s declared in %s already declared in %s. Skipped.",
|
||||
projectPath, attrName, mixin.getId(), attributeDefs.get(attrName).getProjectType())));
|
||||
continue;
|
||||
}
|
||||
attributeDefs.put(attr.getName(), attr);
|
||||
attributeDefs.put(attrName, attr);
|
||||
}
|
||||
|
||||
// Silently remove repeated items from mixins if any
|
||||
|
|
@ -147,22 +151,22 @@ public class ProjectTypes {
|
|||
void reset(Set<Attribute> attributesToDel) {
|
||||
|
||||
Set<String> ptsToDel = new HashSet<>();
|
||||
for(Attribute attr : attributesToDel) {
|
||||
for (Attribute attr : attributesToDel) {
|
||||
ptsToDel.add(attr.getProjectType());
|
||||
}
|
||||
|
||||
Set <String>attrNamesToDel = new HashSet<>();
|
||||
for(String pt : ptsToDel) {
|
||||
Set<String> attrNamesToDel = new HashSet<>();
|
||||
for (String pt : ptsToDel) {
|
||||
ProjectTypeDef typeDef = all.get(pt);
|
||||
for(Attribute attrDef: typeDef.getAttributes()) {
|
||||
for (Attribute attrDef : typeDef.getAttributes()) {
|
||||
attrNamesToDel.add(attrDef.getName());
|
||||
}
|
||||
}
|
||||
|
||||
// remove project types
|
||||
for(String typeId : ptsToDel) {
|
||||
for (String typeId : ptsToDel) {
|
||||
this.all.remove(typeId);
|
||||
if(this.primary.getId().equals(typeId)) {
|
||||
if (this.primary.getId().equals(typeId)) {
|
||||
this.primary = ProjectTypeRegistry.BASE_TYPE;
|
||||
this.all.put(ProjectTypeRegistry.BASE_TYPE.getId(), ProjectTypeRegistry.BASE_TYPE);
|
||||
} else {
|
||||
|
|
@ -171,30 +175,27 @@ public class ProjectTypes {
|
|||
}
|
||||
|
||||
// remove attributes
|
||||
for(String attr : attrNamesToDel) {
|
||||
for (String attr : attrNamesToDel) {
|
||||
this.attributeDefs.remove(attr);
|
||||
}
|
||||
}
|
||||
|
||||
void addTransient(FolderEntry projectFolder) throws ServerException,
|
||||
NotFoundException,
|
||||
ProjectTypeConstraintException,
|
||||
ValueStorageException {
|
||||
void addTransient(FolderEntry projectFolder) {
|
||||
for (ProjectTypeDef pt : projectTypeRegistry.getProjectTypes()) {
|
||||
// NOTE: Only mixable types allowed
|
||||
if (pt.isMixable() && !pt.isPersisted() && pt.resolveSources(projectFolder).matched()) {
|
||||
all.put(pt.getId(), pt);
|
||||
mixins.put(pt.getId(), pt);
|
||||
for (Attribute attr : pt.getAttributes()) {
|
||||
if (attributeDefs.containsKey(attr.getName())) {
|
||||
throw new ProjectTypeConstraintException(
|
||||
"Attribute name conflict. Duplicated attributes detected " + projectPath +
|
||||
" Attribute " + attr.getName() + " declared in " + pt.getId() + " already declared in " +
|
||||
attributeDefs.get(attr.getName()).getProjectType()
|
||||
);
|
||||
final String attrName = attr.getName();
|
||||
if (attributeDefs.containsKey(attrName)) {
|
||||
problems.add(new Problem(13,
|
||||
format("Attribute name conflict. Duplicated attributes detected for %s. " +
|
||||
"Attribute %s declared in %s already declared in %s. Skipped.",
|
||||
projectPath, attrName, pt.getId(), attributeDefs.get(attrName).getProjectType())));
|
||||
}
|
||||
|
||||
attributeDefs.put(attr.getName(), attr);
|
||||
attributeDefs.put(attrName, attr);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -10,14 +10,12 @@
|
|||
*******************************************************************************/
|
||||
package org.eclipse.che.api.project.server;
|
||||
|
||||
import org.eclipse.che.api.core.NotFoundException;
|
||||
import org.eclipse.che.api.core.ServerException;
|
||||
import org.eclipse.che.api.core.model.project.ProjectConfig;
|
||||
import org.eclipse.che.api.core.model.project.SourceStorage;
|
||||
import org.eclipse.che.api.core.model.project.type.Attribute;
|
||||
import org.eclipse.che.api.core.model.project.type.Value;
|
||||
import org.eclipse.che.api.project.server.type.AttributeValue;
|
||||
import org.eclipse.che.api.project.server.type.ProjectTypeConstraintException;
|
||||
import org.eclipse.che.api.project.server.type.ProjectTypeDef;
|
||||
import org.eclipse.che.api.project.server.type.ProjectTypeRegistry;
|
||||
import org.eclipse.che.api.project.server.type.ValueProvider;
|
||||
|
|
@ -27,12 +25,12 @@ import org.eclipse.che.api.vfs.Path;
|
|||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
import static java.lang.String.format;
|
||||
|
||||
/**
|
||||
* Internal Project implementation.
|
||||
* It is supposed that it is object always consistent.
|
||||
|
|
@ -63,15 +61,14 @@ public class RegisteredProject implements ProjectConfig {
|
|||
* if this project was detected, initialized when "parent" project initialized
|
||||
* @param projectTypeRegistry
|
||||
* project type registry
|
||||
* @throws ServerException
|
||||
* when path for project is undefined
|
||||
*/
|
||||
RegisteredProject(FolderEntry folder,
|
||||
ProjectConfig config,
|
||||
boolean updated,
|
||||
boolean detected,
|
||||
ProjectTypeRegistry projectTypeRegistry) throws NotFoundException,
|
||||
ProjectTypeConstraintException,
|
||||
ServerException,
|
||||
ValueStorageException {
|
||||
ProjectTypeRegistry projectTypeRegistry) throws ServerException {
|
||||
problems = new ArrayList<>();
|
||||
attributes = new HashMap<>();
|
||||
|
||||
|
|
@ -85,7 +82,7 @@ public class RegisteredProject implements ProjectConfig {
|
|||
}
|
||||
|
||||
this.folder = folder;
|
||||
this.config = (config == null) ? new NewProjectConfig(path) : config;
|
||||
this.config = config == null ? new NewProjectConfigImpl(path) : config;
|
||||
this.updated = updated;
|
||||
this.detected = detected;
|
||||
|
||||
|
|
@ -97,6 +94,7 @@ public class RegisteredProject implements ProjectConfig {
|
|||
problems.add(new Problem(11, "No project configured in workspace " + this.config.getPath()));
|
||||
}
|
||||
|
||||
|
||||
// 1. init project types
|
||||
this.types = new ProjectTypes(this.config.getPath(), this.config.getType(), this.config.getMixins(), projectTypeRegistry, problems);
|
||||
|
||||
|
|
@ -110,15 +108,9 @@ public class RegisteredProject implements ProjectConfig {
|
|||
|
||||
/**
|
||||
* Initialize project attributes.
|
||||
*
|
||||
* @throws ValueStorageException
|
||||
* @throws ProjectTypeConstraintException
|
||||
* @throws ServerException
|
||||
* @throws NotFoundException
|
||||
* Note: the problem with {@link Problem#code} = 13 will be added when a value for some attribute is not initialized
|
||||
*/
|
||||
private void initAttributes() throws ValueStorageException, ProjectTypeConstraintException, ServerException, NotFoundException {
|
||||
|
||||
Set<Attribute> invalidAttributes = new HashSet<>();
|
||||
private void initAttributes() {
|
||||
|
||||
// we take only defined attributes, others ignored
|
||||
for (Map.Entry<String, Attribute> entry : types.getAttributeDefs().entrySet()) {
|
||||
|
|
@ -140,12 +132,17 @@ public class RegisteredProject implements ProjectConfig {
|
|||
|
||||
if (folder != null) {
|
||||
|
||||
if (!valueProvider.isSettable() || value.isEmpty()) {
|
||||
// get provided value
|
||||
value = new AttributeValue(valueProvider.getValues(name));
|
||||
} else {
|
||||
// set provided (not empty) value
|
||||
valueProvider.setValues(name, value.getList());
|
||||
try {
|
||||
if (!valueProvider.isSettable() || value.isEmpty()) {
|
||||
// get provided value
|
||||
value = new AttributeValue(valueProvider.getValues(name));
|
||||
} else {
|
||||
// set provided (not empty) value
|
||||
valueProvider.setValues(name, value.getList());
|
||||
}
|
||||
} catch (ValueStorageException e) {
|
||||
this.problems.add(new Problem(13, format("Value for attribute %s is not initialized, caused by: %s",
|
||||
variable.getId(), e.getLocalizedMessage())));
|
||||
}
|
||||
|
||||
} else {
|
||||
|
|
@ -155,7 +152,6 @@ public class RegisteredProject implements ProjectConfig {
|
|||
|
||||
if (value.isEmpty() && variable.isRequired()) {
|
||||
this.problems.add(new Problem(13, "Value for required attribute is not initialized " + variable.getId()));
|
||||
invalidAttributes.add(variable);
|
||||
//throw new ProjectTypeConstraintException("Value for required attribute is not initialized " + variable.getId());
|
||||
}
|
||||
|
||||
|
|
@ -164,9 +160,6 @@ public class RegisteredProject implements ProjectConfig {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
types.reset(invalidAttributes);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
|||
|
|
@ -48,13 +48,14 @@ public abstract class WorkspaceProjectsSyncer {
|
|||
|
||||
if(!project.isSynced() && !project.isDetected()) {
|
||||
|
||||
final ProjectConfig config = new NewProjectConfig(project.getPath(),
|
||||
project.getType(),
|
||||
project.getMixins(),
|
||||
project.getName(),
|
||||
project.getDescription(),
|
||||
project.getPersistableAttributes(),
|
||||
project.getSource());
|
||||
final ProjectConfig config = new NewProjectConfigImpl(project.getPath(),
|
||||
project.getType(),
|
||||
project.getMixins(),
|
||||
project.getName(),
|
||||
project.getDescription(),
|
||||
project.getPersistableAttributes(),
|
||||
null,
|
||||
project.getSource());
|
||||
|
||||
boolean found = false;
|
||||
for(ProjectConfig r : remote) {
|
||||
|
|
|
|||
|
|
@ -20,6 +20,9 @@ import java.util.HashMap;
|
|||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import static com.google.common.collect.Maps.newHashMap;
|
||||
import static java.lang.String.format;
|
||||
|
||||
/**
|
||||
* @author gazarenkov
|
||||
*/
|
||||
|
|
@ -169,7 +172,7 @@ public abstract class ProjectTypeDef implements ProjectType {
|
|||
this.ancestors.add(ancestor);
|
||||
}
|
||||
|
||||
public ProjectTypeResolution resolveSources(FolderEntry projectFolder) throws ValueStorageException {
|
||||
public ProjectTypeResolution resolveSources(FolderEntry projectFolder) {
|
||||
Map<String, Value> matchAttrs = new HashMap<>();
|
||||
for (Map.Entry<String, Attribute> entry : attributes.entrySet()) {
|
||||
Attribute attr = entry.getValue();
|
||||
|
|
@ -178,11 +181,22 @@ public abstract class ProjectTypeDef implements ProjectType {
|
|||
Variable var = (Variable)attr;
|
||||
ValueProviderFactory factory = var.getValueProviderFactory();
|
||||
if (factory != null) {
|
||||
Value value = new AttributeValue(factory.newInstance(projectFolder).getValues(name));
|
||||
if (value.isEmpty()) {
|
||||
|
||||
Value value;
|
||||
String errorMessage = "";
|
||||
try {
|
||||
value = new AttributeValue(factory.newInstance(projectFolder).getValues(name));
|
||||
} catch (ValueStorageException e) {
|
||||
value = null;
|
||||
errorMessage = e.getLocalizedMessage();
|
||||
}
|
||||
|
||||
if (value == null || value.isEmpty()) {
|
||||
if (var.isRequired()) {
|
||||
// this PT is not match
|
||||
return new DefaultResolution(id, new HashMap<>(), false);
|
||||
errorMessage = errorMessage.isEmpty() ? format("Value for required attribute %s is not initialized", name)
|
||||
: errorMessage;
|
||||
return new DefaultResolution(id, errorMessage);
|
||||
}
|
||||
} else {
|
||||
// add one more matched attribute
|
||||
|
|
@ -204,6 +218,12 @@ public abstract class ProjectTypeDef implements ProjectType {
|
|||
this.match = match;
|
||||
}
|
||||
|
||||
/** Use this one when source code not matches project type requirements */
|
||||
public DefaultResolution(String type, String resolution) {
|
||||
super(type, newHashMap(), resolution);
|
||||
this.match = false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean matched() {
|
||||
return match;
|
||||
|
|
|
|||
|
|
@ -21,10 +21,16 @@ public abstract class ProjectTypeResolution {
|
|||
|
||||
private String type;
|
||||
private Map<String, Value> attributes;
|
||||
private String resolution;
|
||||
|
||||
public ProjectTypeResolution(String type, Map<String, Value> attributes) {
|
||||
this(type, attributes, "");
|
||||
}
|
||||
|
||||
public ProjectTypeResolution(String type, Map<String, Value> attributes, String resolution) {
|
||||
this.type = type;
|
||||
this.attributes = attributes;
|
||||
this.resolution = resolution;
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -34,6 +40,13 @@ public abstract class ProjectTypeResolution {
|
|||
return type;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the reason that current source code NOT matches project type requirements
|
||||
*/
|
||||
public String getResolution() {
|
||||
return resolution;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return true if current source code in generally matches project type requirements
|
||||
* by default (but not necessarily) it may check if there are all required provided attributes
|
||||
|
|
|
|||
|
|
@ -10,21 +10,25 @@
|
|||
*******************************************************************************/
|
||||
package org.eclipse.che.api.project.server;
|
||||
|
||||
import org.eclipse.che.api.core.BadRequestException;
|
||||
import org.eclipse.che.api.core.ConflictException;
|
||||
import org.eclipse.che.api.core.ForbiddenException;
|
||||
import org.eclipse.che.api.core.NotFoundException;
|
||||
import org.eclipse.che.api.core.ServerException;
|
||||
import org.eclipse.che.api.core.model.project.NewProjectConfig;
|
||||
import org.eclipse.che.api.core.model.project.ProjectConfig;
|
||||
import org.eclipse.che.api.core.model.project.SourceStorage;
|
||||
import org.eclipse.che.api.core.notification.EventSubscriber;
|
||||
import org.eclipse.che.api.core.util.LineConsumerFactory;
|
||||
import org.eclipse.che.api.core.util.ValueHolder;
|
||||
import org.eclipse.che.api.project.server.RegisteredProject.Problem;
|
||||
import org.eclipse.che.api.project.server.handlers.CreateProjectHandler;
|
||||
import org.eclipse.che.api.project.server.importer.ProjectImporter;
|
||||
import org.eclipse.che.api.project.server.type.AttributeValue;
|
||||
import org.eclipse.che.api.project.server.type.BaseProjectType;
|
||||
import org.eclipse.che.api.project.server.type.Variable;
|
||||
import org.eclipse.che.api.vfs.Path;
|
||||
import org.eclipse.che.api.workspace.shared.dto.NewProjectConfigDto;
|
||||
import org.eclipse.che.api.workspace.shared.dto.ProjectConfigDto;
|
||||
import org.eclipse.che.api.workspace.shared.dto.SourceStorageDto;
|
||||
import org.eclipse.che.dto.server.DtoFactory;
|
||||
|
|
@ -33,8 +37,10 @@ import org.junit.Test;
|
|||
|
||||
import java.io.ByteArrayInputStream;
|
||||
import java.io.ByteArrayOutputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
|
@ -43,6 +49,7 @@ import java.util.zip.ZipOutputStream;
|
|||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.junit.Assert.assertFalse;
|
||||
import static org.junit.Assert.assertNotEquals;
|
||||
import static org.junit.Assert.assertNotNull;
|
||||
import static org.junit.Assert.assertNull;
|
||||
import static org.junit.Assert.assertTrue;
|
||||
|
|
@ -52,7 +59,7 @@ import static org.junit.Assert.fail;
|
|||
* @author gazarenkov
|
||||
*/
|
||||
public class ProjectManagerWriteTest extends WsAgentTestBase {
|
||||
|
||||
private static final String FILE_CONTENT = "to be or not to be";
|
||||
|
||||
@Before
|
||||
public void setUp() throws Exception {
|
||||
|
|
@ -66,14 +73,412 @@ public class ProjectManagerWriteTest extends WsAgentTestBase {
|
|||
projectTypeRegistry.registerProjectType(new PTsettableVP());
|
||||
|
||||
projectHandlerRegistry.register(new SrcGenerator());
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCreateBatchProjectsByConfigs() throws Exception {
|
||||
final String projectPath1 = "/testProject1";
|
||||
final String projectPath2 = "/testProject2";
|
||||
|
||||
final NewProjectConfig config1 = createProjectConfigObject("testProject1", projectPath1, BaseProjectType.ID, null);
|
||||
final NewProjectConfig config2 = createProjectConfigObject("testProject2", projectPath2, BaseProjectType.ID, null);
|
||||
|
||||
final List<NewProjectConfig> configs = new ArrayList<>(2);
|
||||
configs.add(config1);
|
||||
configs.add(config2);
|
||||
|
||||
pm.createBatchProjects(configs, false);
|
||||
|
||||
checkProjectExist(projectPath1);
|
||||
checkProjectExist(projectPath2);
|
||||
assertEquals(2, projectRegistry.getProjects().size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCreateBatchProjectsByImportingSourceCode() throws Exception {
|
||||
final String projectPath1 = "/testProject1";
|
||||
final String projectPath2 = "/testProject2";
|
||||
final String importType1 = "importType1";
|
||||
final String importType2 = "importType2";
|
||||
|
||||
final String [] paths1 = {"folder1/", "folder1/file1.txt"};
|
||||
final List<String> children1 = new ArrayList<>(Arrays.asList(paths1));
|
||||
registerImporter(importType1, prepareZipArchiveBasedOn(children1));
|
||||
|
||||
final String [] paths2 = {"folder2/", "folder2/file2.txt"};
|
||||
final List<String> children2 = new ArrayList<>(Arrays.asList(paths2));
|
||||
registerImporter(importType2, prepareZipArchiveBasedOn(children2));
|
||||
|
||||
final SourceStorageDto source1 = DtoFactory.newDto(SourceStorageDto.class).withLocation("someLocation").withType(importType1);
|
||||
final NewProjectConfigDto config1 = createProjectConfigObject("testProject1", projectPath1, BaseProjectType.ID, source1);
|
||||
|
||||
final SourceStorageDto source2 = DtoFactory.newDto(SourceStorageDto.class).withLocation("someLocation").withType(importType2);
|
||||
final NewProjectConfigDto config2 = createProjectConfigObject("testProject2", projectPath2, BaseProjectType.ID, source2);
|
||||
|
||||
final List<NewProjectConfig> configs = new ArrayList<>(2);
|
||||
configs.add(config1);
|
||||
configs.add(config2);
|
||||
|
||||
pm.createBatchProjects(configs, false);
|
||||
|
||||
final RegisteredProject project1 = projectRegistry.getProject(projectPath1);
|
||||
final FolderEntry projectFolder1 = project1.getBaseFolder();
|
||||
checkProjectExist(projectPath1);
|
||||
checkChildrenFor(projectFolder1, children1);
|
||||
|
||||
final RegisteredProject project2 = projectRegistry.getProject(projectPath2);
|
||||
final FolderEntry projectFolder2 = project2.getBaseFolder();
|
||||
checkProjectExist(projectPath2);
|
||||
checkChildrenFor(projectFolder2, children2);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCreateProjectWhenSourceCodeIsNotReachable() throws Exception {
|
||||
final String projectPath = "/testProject";
|
||||
final SourceStorageDto source = DtoFactory.newDto(SourceStorageDto.class).withLocation("someLocation").withType("importType");
|
||||
final NewProjectConfigDto config = createProjectConfigObject("testProject1", projectPath, BaseProjectType.ID, source);
|
||||
|
||||
final List<NewProjectConfig> configs = new ArrayList<>(1);
|
||||
configs.add(config);
|
||||
|
||||
try {
|
||||
pm.createBatchProjects(configs, false);
|
||||
fail("Exception should be thrown when source code is not reachable");
|
||||
} catch (Exception e) {
|
||||
assertEquals(0, projectRegistry.getProjects().size());
|
||||
assertNull(projectRegistry.getProject(projectPath));
|
||||
assertNull(pm.getProjectsRoot().getChild(projectPath));
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void shouldRollbackCreatingBatchProjects() throws Exception {
|
||||
// we should rollback operation of creating batch projects when we have not source code for at least one project
|
||||
// For example: two projects were success created, but we could not get source code for third configuration
|
||||
// At this use case we should rollback the operation and clean up all created projects
|
||||
|
||||
final String projectPath1 = "/testProject1";
|
||||
final String projectPath2 = "/testProject2";
|
||||
final String projectPath3 = "/testProject3";
|
||||
final String importType1 = "importType1";
|
||||
final String importType2 = "importType2";
|
||||
|
||||
final String [] paths1 = {"folder1/", "folder1/file1.txt"};
|
||||
final List<String> children1 = new ArrayList<>(Arrays.asList(paths1));
|
||||
registerImporter(importType1, prepareZipArchiveBasedOn(children1));
|
||||
|
||||
final String [] paths2 = {"folder2/", "folder2/file2.txt"};
|
||||
final List<String> children2 = new ArrayList<>(Arrays.asList(paths2));
|
||||
registerImporter(importType2, prepareZipArchiveBasedOn(children2));
|
||||
|
||||
final SourceStorageDto source1 = DtoFactory.newDto(SourceStorageDto.class).withLocation("someLocation").withType(importType1);
|
||||
final NewProjectConfigDto config1 = createProjectConfigObject("testProject1", projectPath1, BaseProjectType.ID, source1);
|
||||
|
||||
final SourceStorageDto source2 = DtoFactory.newDto(SourceStorageDto.class).withLocation("someLocation").withType(importType2);
|
||||
final NewProjectConfigDto config2 = createProjectConfigObject("testProject2", projectPath2, BaseProjectType.ID, source2);
|
||||
|
||||
final SourceStorageDto source = DtoFactory.newDto(SourceStorageDto.class).withLocation("someLocation").withType("importType");
|
||||
final NewProjectConfigDto config3 = createProjectConfigObject("testProject3", projectPath3, BaseProjectType.ID, source);
|
||||
|
||||
final List<NewProjectConfig> configs = new ArrayList<>(2);
|
||||
configs.add(config1); //will be success created
|
||||
configs.add(config2); //will be success created
|
||||
configs.add(config3); //we be failed - we have not registered importer - source code will not be imported
|
||||
|
||||
try {
|
||||
pm.createBatchProjects(configs, false);
|
||||
fail("We should rollback operation of creating batch projects when we could not get source code for at least one project");
|
||||
} catch (Exception e) {
|
||||
assertEquals(0, projectRegistry.getProjects().size());
|
||||
|
||||
assertNull(projectRegistry.getProject(projectPath1));
|
||||
assertNull(pm.getProjectsRoot().getChild(projectPath1));
|
||||
|
||||
assertNull(projectRegistry.getProject(projectPath2));
|
||||
assertNull(pm.getProjectsRoot().getChild(projectPath2));
|
||||
|
||||
assertNull(projectRegistry.getProject(projectPath3));
|
||||
assertNull(pm.getProjectsRoot().getChild(projectPath3));
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCreateBatchProjectsWithInnerProject() throws Exception {
|
||||
final String rootProjectPath = "/testProject1";
|
||||
final String innerProjectPath = "/testProject1/innerProject";
|
||||
final String importType = "importType1";
|
||||
final String innerProjectType = "pt2";
|
||||
|
||||
Map<String, List<String>> attributes = new HashMap<>();
|
||||
attributes.put("pt2-var2", new AttributeValue("test").getList());
|
||||
|
||||
final String [] paths1 = {"folder1/", "folder1/file1.txt"};
|
||||
final String [] paths2 = {"innerProject/", "innerProject/folder2/", "innerProject/folder2/file2.txt"};
|
||||
final List<String> children1 = Arrays.asList(paths1);
|
||||
final List<String> children2 = Arrays.asList(paths2);
|
||||
final List<String> children = new ArrayList<>(children1);
|
||||
children.addAll(children2);
|
||||
registerImporter(importType, prepareZipArchiveBasedOn(children));
|
||||
|
||||
SourceStorageDto source = DtoFactory.newDto(SourceStorageDto.class).withLocation("someLocation").withType(importType);
|
||||
NewProjectConfigDto config1 = createProjectConfigObject("testProject1", rootProjectPath, BaseProjectType.ID, source);
|
||||
NewProjectConfigDto config2 = createProjectConfigObject("innerProject", innerProjectPath, innerProjectType, null);
|
||||
config2.setAttributes(attributes);
|
||||
|
||||
List<NewProjectConfig> configs = new ArrayList<>(2);
|
||||
configs.add(config1);
|
||||
configs.add(config2);
|
||||
|
||||
pm.createBatchProjects(configs, false);
|
||||
|
||||
RegisteredProject rootProject = projectRegistry.getProject(rootProjectPath);
|
||||
FolderEntry rootProjectFolder = rootProject.getBaseFolder();
|
||||
RegisteredProject innerProject = projectRegistry.getProject(innerProjectPath);
|
||||
FolderEntry innerProjectFolder = innerProject.getBaseFolder();
|
||||
|
||||
|
||||
assertNotNull(rootProject);
|
||||
assertTrue(rootProjectFolder.getVirtualFile().exists());
|
||||
assertEquals(rootProjectPath, rootProject.getPath());
|
||||
checkChildrenFor(rootProjectFolder, children1);
|
||||
|
||||
assertNotNull(innerProject);
|
||||
assertTrue(innerProjectFolder.getVirtualFile().exists());
|
||||
assertEquals(innerProjectPath, innerProject.getPath());
|
||||
assertEquals(innerProjectType, innerProject.getType());
|
||||
checkChildrenFor(rootProjectFolder, children2);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCreateBatchProjectsWithInnerProjectWhenInnerProjectContainsSource() throws Exception {
|
||||
final String rootProjectPath = "/rootProject";
|
||||
final String innerProjectPath = "/rootProject/innerProject";
|
||||
final String rootImportType = "rootImportType";
|
||||
final String innerImportType = "innerImportType";
|
||||
|
||||
final String innerProjectType = "pt2";
|
||||
|
||||
Map<String, List<String>> attributes = new HashMap<>();
|
||||
attributes.put("pt2-var2", new AttributeValue("test").getList());
|
||||
|
||||
final String [] paths1 = {"folder1/", "folder1/file1.txt"};
|
||||
final List<String> children1 = new ArrayList<>(Arrays.asList(paths1));
|
||||
registerImporter(rootImportType, prepareZipArchiveBasedOn(children1));
|
||||
|
||||
final String [] paths2 = {"folder2/", "folder2/file2.txt"};
|
||||
final List<String> children2 = new ArrayList<>(Arrays.asList(paths2));
|
||||
registerImporter(innerImportType, prepareZipArchiveBasedOn(children2));
|
||||
|
||||
final SourceStorageDto source1 = DtoFactory.newDto(SourceStorageDto.class).withLocation("someLocation").withType(rootImportType);
|
||||
final NewProjectConfigDto config1 = createProjectConfigObject("testProject1", rootProjectPath, BaseProjectType.ID, source1);
|
||||
|
||||
final SourceStorageDto source2 = DtoFactory.newDto(SourceStorageDto.class).withLocation("someLocation").withType(innerImportType);
|
||||
final NewProjectConfigDto config2 = createProjectConfigObject("testProject2", innerProjectPath, innerProjectType, source2);
|
||||
config2.setAttributes(attributes);
|
||||
|
||||
final List<NewProjectConfig> configs = new ArrayList<>(2);
|
||||
configs.add(config2);
|
||||
configs.add(config1);
|
||||
|
||||
pm.createBatchProjects(configs, false);
|
||||
|
||||
RegisteredProject rootProject = projectRegistry.getProject(rootProjectPath);
|
||||
FolderEntry rootProjectFolder = rootProject.getBaseFolder();
|
||||
checkProjectExist(rootProjectPath);
|
||||
checkChildrenFor(rootProjectFolder, children1);
|
||||
|
||||
RegisteredProject innerProject = projectRegistry.getProject(innerProjectPath);
|
||||
FolderEntry innerProjectFolder = innerProject.getBaseFolder();
|
||||
assertNotNull(innerProject);
|
||||
assertTrue(innerProjectFolder.getVirtualFile().exists());
|
||||
assertEquals(innerProjectPath, innerProject.getPath());
|
||||
assertEquals(innerProjectType, innerProject.getType());
|
||||
checkChildrenFor(innerProjectFolder, children2);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCreateBatchProjectsWithMixInnerProjects() throws Exception { // Projects should be sorted by path before creating
|
||||
final String [] paths = {"/1/z", "/2/z", "/1/d", "/2", "/1", "/1/a"};
|
||||
final List<String> projectsPaths = new ArrayList<>(Arrays.asList(paths));
|
||||
|
||||
final List<NewProjectConfig> configs = new ArrayList<>(projectsPaths.size());
|
||||
for (String path : projectsPaths) {
|
||||
configs.add(createProjectConfigObject(path.substring(path.length() - 1, path.length()), path, BaseProjectType.ID, null));
|
||||
}
|
||||
|
||||
pm.createBatchProjects(configs, false);
|
||||
|
||||
for (String path : projectsPaths) {
|
||||
checkProjectExist(path);
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCreateBatchProjectsWhenConfigContainsOnlyPath()
|
||||
throws Exception { // NewProjectConfig object contains only one mandatory Project Path field
|
||||
|
||||
final String projectPath1 = "/testProject1";
|
||||
final String projectPath2 = "/testProject2";
|
||||
|
||||
final NewProjectConfig config1 = createProjectConfigObject(null, projectPath1, null, null);
|
||||
final NewProjectConfig config2 = createProjectConfigObject(null, projectPath2, null, null);
|
||||
|
||||
final List<NewProjectConfig> configs = new ArrayList<>(2);
|
||||
configs.add(config1);
|
||||
configs.add(config2);
|
||||
|
||||
pm.createBatchProjects(configs, false);
|
||||
|
||||
checkProjectExist(projectPath1);
|
||||
checkProjectExist(projectPath2);
|
||||
assertEquals(2, projectRegistry.getProjects().size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void shouldThrowBadRequestExceptionAtCreatingBatchProjectsWhenConfigNotContainsPath()
|
||||
throws Exception { //Path is mandatory field for NewProjectConfig
|
||||
final SourceStorageDto source = DtoFactory.newDto(SourceStorageDto.class).withLocation("someLocation").withType("importType");
|
||||
final NewProjectConfig config = createProjectConfigObject("project", null, BaseProjectType.ID, source);
|
||||
|
||||
final List<NewProjectConfig> configs = new ArrayList<>(1);
|
||||
configs.add(config);
|
||||
|
||||
try {
|
||||
pm.createBatchProjects(configs, false);
|
||||
fail("BadRequestException should be thrown : path field is mandatory");
|
||||
} catch (BadRequestException e) {
|
||||
assertEquals(0, projectRegistry.getProjects().size());
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void shouldThrowConflictExceptionAtCreatingBatchProjectsWhenProjectWithPathAlreadyExist() throws Exception {
|
||||
final String path = "/somePath";
|
||||
final NewProjectConfig config = createProjectConfigObject("project", path, BaseProjectType.ID, null);
|
||||
|
||||
final List<NewProjectConfig> configs = new ArrayList<>(1);
|
||||
configs.add(config);
|
||||
|
||||
pm.createBatchProjects(configs, false);
|
||||
checkProjectExist(path);
|
||||
assertEquals(1, projectRegistry.getProjects().size());
|
||||
|
||||
try {
|
||||
pm.createBatchProjects(configs, false);
|
||||
fail("ConflictException should be thrown : Project config with the same path is already exists");
|
||||
} catch (ConflictException e) {
|
||||
assertEquals(1, projectRegistry.getProjects().size());
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void shouldCreateParentFolderAtCreatingProjectWhenParentDoesNotExist() throws Exception {
|
||||
final String nonExistentParentPath = "/rootProject";
|
||||
final String innerProjectPath = "/rootProject/innerProject";
|
||||
|
||||
final NewProjectConfig config = createProjectConfigObject(null, innerProjectPath, null, null);
|
||||
|
||||
final List<NewProjectConfig> configs = new ArrayList<>(2);
|
||||
configs.add(config);
|
||||
|
||||
pm.createBatchProjects(configs, false);
|
||||
|
||||
checkProjectExist(nonExistentParentPath);
|
||||
checkProjectExist(innerProjectPath);
|
||||
assertEquals(2, projectRegistry.getProjects().size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void shouldRewriteProjectAtCreatingBatchProjectsWhenProjectAlreadyExist() throws Exception {
|
||||
final String projectPath = "/testProject";
|
||||
final String importType1 = "importType1";
|
||||
final String importType2 = "importType2";
|
||||
|
||||
final String [] paths1 = {"folder1/", "folder1/file1.txt"};
|
||||
final List<String> children1 = new ArrayList<>(Arrays.asList(paths1));
|
||||
registerImporter(importType1, prepareZipArchiveBasedOn(children1));
|
||||
|
||||
final String [] paths2 = {"folder2/", "folder2/file2.txt"};
|
||||
final List<String> children2 = new ArrayList<>(Arrays.asList(paths2));
|
||||
registerImporter(importType2, prepareZipArchiveBasedOn(children2));
|
||||
|
||||
final SourceStorageDto source1 = DtoFactory.newDto(SourceStorageDto.class).withLocation("someLocation").withType(importType1);
|
||||
final NewProjectConfigDto config1 = createProjectConfigObject("testProject1", projectPath, "blank", source1);
|
||||
|
||||
final SourceStorageDto source2 = DtoFactory.newDto(SourceStorageDto.class).withLocation("someLocation").withType(importType2);
|
||||
final NewProjectConfigDto config2 = createProjectConfigObject("testProject2", projectPath, "blank", source2);
|
||||
|
||||
final List<NewProjectConfig> configs = new ArrayList<>(1);
|
||||
configs.add(config1);
|
||||
|
||||
pm.createBatchProjects(configs, false);
|
||||
|
||||
final FolderEntry projectFolder1 = projectRegistry.getProject(projectPath).getBaseFolder();
|
||||
checkProjectExist(projectPath);
|
||||
checkChildrenFor(projectFolder1, children1);
|
||||
assertEquals(1, projectRegistry.getProjects().size());
|
||||
|
||||
configs.clear();
|
||||
configs.add(config2);
|
||||
pm.createBatchProjects(configs, true);
|
||||
|
||||
final FolderEntry projectFolder2 = projectRegistry.getProject(projectPath).getBaseFolder();
|
||||
checkProjectExist(projectPath);
|
||||
checkChildrenFor(projectFolder2, children2);
|
||||
assertEquals(1, projectRegistry.getProjects().size());
|
||||
assertNull(projectFolder2.getChild("folder1/"));
|
||||
assertNull(projectFolder2.getChild("folder1/file1.txt"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void shouldSetBlankTypeAtCreatingBatchProjectsWhenConfigContainsUnregisteredProjectType()
|
||||
throws Exception {// If declared primary PT is not registered, project is created as Blank, with Problem 12
|
||||
|
||||
final String projectPath = "/testProject";
|
||||
final String projectType = "unregisteredProjectType";
|
||||
|
||||
final NewProjectConfig config = createProjectConfigObject("projectName", projectPath, projectType, null);
|
||||
|
||||
final List<NewProjectConfig> configs = new ArrayList<>(1);
|
||||
configs.add(config);
|
||||
|
||||
pm.createBatchProjects(configs, false);
|
||||
|
||||
final RegisteredProject project = projectRegistry.getProject(projectPath);
|
||||
final List<Problem> problems = project.getProblems();
|
||||
checkProjectExist(projectPath);
|
||||
assertNotEquals(projectType, project.getType());
|
||||
assertEquals(1, problems.size());
|
||||
assertEquals(12, problems.get(0).code);
|
||||
assertEquals(1, projectRegistry.getProjects().size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void shouldCreateBatchProjectsWithoutMixinPTWhenThisOneIsUnregistered()
|
||||
throws Exception {// If declared mixin PT is not registered, project is created w/o it, with Problem 12
|
||||
|
||||
final String projectPath = "/testProject";
|
||||
final String mixinPType = "unregistered";
|
||||
|
||||
final NewProjectConfig config = createProjectConfigObject("projectName", projectPath, BaseProjectType.ID, null);
|
||||
config.getMixins().add(mixinPType);
|
||||
|
||||
final List<NewProjectConfig> configs = new ArrayList<>(1);
|
||||
configs.add(config);
|
||||
|
||||
pm.createBatchProjects(configs, false);
|
||||
|
||||
final RegisteredProject project = projectRegistry.getProject(projectPath);
|
||||
final List<Problem> problems = project.getProblems();
|
||||
checkProjectExist(projectPath);
|
||||
assertEquals(1, problems.size());
|
||||
assertEquals(12, problems.get(0).code);
|
||||
assertTrue(project.getMixins().isEmpty());
|
||||
assertEquals(1, projectRegistry.getProjects().size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCreateProject() throws Exception {
|
||||
|
||||
|
||||
Map<String, List<String>> attrs = new HashMap<>();
|
||||
List<String> v = new ArrayList<>();
|
||||
v.add("meV");
|
||||
|
|
@ -95,74 +500,85 @@ public class ProjectManagerWriteTest extends WsAgentTestBase {
|
|||
assertEquals("/createProject", project.getPath());
|
||||
assertEquals(2, project.getAttributeEntries().size());
|
||||
assertEquals("meV", project.getAttributeEntries().get("var1").getString());
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCreateProjectInvalidAttribute() throws Exception {
|
||||
|
||||
ProjectConfig pc = new NewProjectConfig("/testCreateProjectInvalidAttributes", "pt2", null, "name", "descr", null, null);
|
||||
|
||||
try {
|
||||
pm.createProject(pc, null);
|
||||
fail("ProjectTypeConstraintException should be thrown : pt-var2 attribute is mandatory");
|
||||
} catch (ServerException e) {
|
||||
//
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public void testCreateProjectWithRequiredProvidedAttribute() throws Exception {
|
||||
|
||||
public void testCreateProjectWithInvalidAttribute() throws Exception {
|
||||
// SPECS:
|
||||
// If project type has provided required attributes,
|
||||
// respective CreateProjectHandler MUST be provided
|
||||
// Project will be created with problem code = 13(Value for required attribute is not initialized)
|
||||
// when required attribute is not initialized
|
||||
final String path = "/testCreateProjectInvalidAttributes";
|
||||
final String projectType = "pt2";
|
||||
final NewProjectConfig config = new NewProjectConfigImpl(path, projectType, null, "name", "descr", null, null, null);
|
||||
|
||||
Map<String, List<String>> attributes = new HashMap<>();
|
||||
pm.createProject(config, null);
|
||||
|
||||
RegisteredProject project = projectRegistry.getProject(path);
|
||||
assertNotNull(project);
|
||||
assertNotNull(pm.getProjectsRoot().getChild(path));
|
||||
assertEquals(projectType, project.getType());
|
||||
|
||||
List<Problem> problems = project.getProblems();
|
||||
assertNotNull(problems);
|
||||
assertFalse(problems.isEmpty());
|
||||
assertEquals(1, problems.size());
|
||||
assertEquals(13, problems.get(0).code);
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public void testCreateProjectWithRequiredProvidedAttributeWhenGivenProjectTypeHasGenerator() throws Exception {
|
||||
final String path = "/testCreateProjectWithRequiredProvidedAttribute";
|
||||
final String projectTypeId = "pt3";
|
||||
final Map<String, List<String>> attributes = new HashMap<>();
|
||||
attributes.put("pt2-var2", new AttributeValue("test").getList());
|
||||
ProjectConfig pc =
|
||||
new NewProjectConfig("/testCreateProjectWithRequiredProvidedAttribute", "pt3", null, "name", "descr", attributes, null);
|
||||
final ProjectConfig pc = new NewProjectConfigImpl(path, projectTypeId, null, "name", "descr", attributes, null, null);
|
||||
|
||||
pm.createProject(pc, null);
|
||||
|
||||
RegisteredProject project = projectRegistry.getProject("testCreateProjectWithRequiredProvidedAttribute");
|
||||
assertEquals("pt3", project.getType());
|
||||
final RegisteredProject project = projectRegistry.getProject(path);
|
||||
assertEquals(projectTypeId, project.getType());
|
||||
assertNotNull(project.getBaseFolder().getChild("file1"));
|
||||
assertEquals("pt2-provided1", project.getAttributes().get("pt2-provided1").get(0));
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testFailCreateProjectWithNoRequiredGenerator() throws Exception {
|
||||
|
||||
public void testCreateProjectWithRequiredProvidedAttributeWhenGivenProjectTypeHasNotGenerator() throws Exception {
|
||||
// SPECS:
|
||||
// If there are no respective CreateProjectHandler ServerException will be thrown
|
||||
// Project will be created with problem code = 13 (Value for required attribute is not initialized)
|
||||
// when project type has provided required attributes
|
||||
// but have not respective generator(CreateProjectHandler)
|
||||
|
||||
ProjectConfig pc = new NewProjectConfig("/testFailCreateProjectWithNoRequiredGenerator", "pt4", null, "name", "descr", null, null);
|
||||
|
||||
try {
|
||||
pm.createProject(pc, null);
|
||||
fail("ProjectTypeConstraintException: Value for required attribute is not initialized pt4:pt4-provided1");
|
||||
} catch (ServerException e) {
|
||||
}
|
||||
final String path = "/testCreateProjectWithRequiredProvidedAttribute";
|
||||
final String projectTypeId = "pt4";
|
||||
final ProjectConfig pc = new NewProjectConfigImpl(path, projectTypeId, null, "name", "descr", null, null, null);
|
||||
|
||||
pm.createProject(pc, null);
|
||||
|
||||
final RegisteredProject project = projectRegistry.getProject(path);
|
||||
final List<VirtualFileEntry> children = project.getBaseFolder().getChildren();
|
||||
final List<Problem> problems = project.getProblems();
|
||||
assertNotNull(project);
|
||||
assertNotNull(pm.getProjectsRoot().getChild(path));
|
||||
assertEquals(projectTypeId, project.getType());
|
||||
assertTrue(children.isEmpty());
|
||||
assertTrue(project.getAttributes().isEmpty());
|
||||
assertFalse(problems.isEmpty());
|
||||
assertEquals(1, problems.size());
|
||||
assertEquals(13, problems.get(0).code);
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public void testSamePathProjectCreateFailed() throws Exception {
|
||||
|
||||
// SPECS:
|
||||
// If there is a project with the same path ConflictException will be thrown on create project
|
||||
|
||||
ProjectConfig pc = new NewProjectConfig("/testSamePathProjectCreateFailed", "blank", null, "name", "descr", null, null);
|
||||
ProjectConfig pc = new NewProjectConfigImpl("/testSamePathProjectCreateFailed", "blank", null, "name", "descr", null, null, null);
|
||||
|
||||
pm.createProject(pc, null);
|
||||
|
||||
pc = new NewProjectConfig("/testSamePathProjectCreateFailed", "blank", null, "name", "descr", null, null);
|
||||
pc = new NewProjectConfigImpl("/testSamePathProjectCreateFailed", "blank", null, "name", "descr", null, null, null);
|
||||
|
||||
try {
|
||||
pm.createProject(pc, null);
|
||||
|
|
@ -171,94 +587,109 @@ public class ProjectManagerWriteTest extends WsAgentTestBase {
|
|||
}
|
||||
|
||||
assertNotNull(projectRegistry.getProject("/testSamePathProjectCreateFailed"));
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testInvalidPTProjectCreateFailed() throws Exception {
|
||||
// SPECS:
|
||||
// project will be created as project of "blank" type
|
||||
// with problem code 12(Primary type "someType" is not registered. Base Project Type assigned.)
|
||||
// when primary project type is not registered in PT registry
|
||||
final String path = "/testInvalidPTProjectCreateFailed";
|
||||
ProjectConfig pc = new NewProjectConfigImpl(path, "invalid", null, "name", "descr", null, null, null);
|
||||
|
||||
pm.createProject(pc, null);
|
||||
|
||||
RegisteredProject project = projectRegistry.getProject(path);
|
||||
assertNotNull(project);
|
||||
assertNotNull(pm.getProjectsRoot().getChild(path));
|
||||
assertEquals(BaseProjectType.ID, project.getType());
|
||||
|
||||
List<Problem> problems = project.getProblems();
|
||||
assertNotNull(problems);
|
||||
assertFalse(problems.isEmpty());
|
||||
assertEquals(1, problems.size());
|
||||
assertEquals(12, problems.get(0).code);
|
||||
|
||||
//clean up
|
||||
project.getBaseFolder().getVirtualFile().delete();
|
||||
projectRegistry.removeProjects(path);
|
||||
assertNull(projectRegistry.getProject(path));
|
||||
|
||||
|
||||
// SPECS:
|
||||
// If either primary or some mixin project type is not registered in PT registry
|
||||
// project creation failed with NotFoundException
|
||||
|
||||
ProjectConfig pc = new NewProjectConfig("/testInvalidPTProjectCreateFailed", "invalid", null, "name", "descr", null, null);
|
||||
|
||||
try {
|
||||
pm.createProject(pc, null);
|
||||
fail("NotFoundException: Project Type not found: invalid");
|
||||
} catch (ServerException e) {
|
||||
}
|
||||
|
||||
assertNull(projectRegistry.getProject("/testInvalidPTProjectCreateFailed"));
|
||||
assertNull(pm.getProjectsRoot().getChild("/testInvalidPTProjectCreateFailed"));
|
||||
//assertNull(projectRegistry.folder("/testInvalidPTProjectCreateFailed"));
|
||||
|
||||
// check mixin as well
|
||||
// project will be created without mixin project type and
|
||||
// with problem code 12(Project type "someType" is not registered. Skipped.)
|
||||
// when mixin project type is not registered in PT registry
|
||||
List<String> ms = new ArrayList<>();
|
||||
ms.add("invalid");
|
||||
|
||||
pc = new NewProjectConfig("/testInvalidPTProjectCreateFailed", "blank", ms, "name", "descr", null, null);
|
||||
|
||||
try {
|
||||
pm.createProject(pc, null);
|
||||
fail("NotFoundException: Project Type not found: invalid");
|
||||
} catch (ServerException e) {
|
||||
}
|
||||
pc = new NewProjectConfigImpl(path, "blank", ms, "name", "descr", null, null, null);
|
||||
pm.createProject(pc, null);
|
||||
|
||||
project = projectRegistry.getProject(path);
|
||||
assertNotNull(project);
|
||||
assertNotNull(pm.getProjectsRoot().getChild(path));
|
||||
assertTrue(project.getMixins().isEmpty());
|
||||
|
||||
problems = project.getProblems();
|
||||
assertNotNull(problems);
|
||||
assertFalse(problems.isEmpty());
|
||||
assertEquals(1, problems.size());
|
||||
assertEquals(12, problems.get(0).code);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testConflictAttributesProjectCreateFailed() throws Exception {
|
||||
|
||||
// SPECS:
|
||||
// If there are attributes with the same name in primary and mixin PT or between mixins
|
||||
// Project creation failed with ProjectTypeConstraintException
|
||||
// project will be created with problem code 13(Attribute name conflict)
|
||||
// when there are attributes with the same name in primary and mixin PT or between mixins
|
||||
|
||||
final String path = "/testConflictAttributesProjectCreateFailed";
|
||||
final String projectTypeId = "pt2";
|
||||
final String mixin = "m2";
|
||||
final List<String> ms = new ArrayList<>(1);
|
||||
ms.add(mixin);
|
||||
|
||||
List<String> ms = new ArrayList<>();
|
||||
ms.add("m2");
|
||||
ProjectConfig pc = new NewProjectConfigImpl(path, projectTypeId, ms, "name", "descr", null, null, null);
|
||||
pm.createProject(pc, null);
|
||||
|
||||
ProjectConfig pc = new NewProjectConfig("/testConflictAttributesProjectCreateFailed", "pt2", ms, "name", "descr", null, null);
|
||||
try {
|
||||
pm.createProject(pc, null);
|
||||
fail("ProjectTypeConstraintException: Attribute name conflict. Duplicated attributes detected /testConflictAttributesProjectCreateFailed Attribute pt2-const1 declared in m2 already declared in pt2");
|
||||
} catch (ServerException e) {
|
||||
}
|
||||
final RegisteredProject project = projectRegistry.getProject(path);
|
||||
assertNotNull(project);
|
||||
assertNotNull(pm.getProjectsRoot().getChild(path));
|
||||
|
||||
//assertNull(projectRegistry.folder("/testConflictAttributesProjectCreateFailed"));
|
||||
|
||||
assertNull(pm.getProjectsRoot().getChild("/testConflictAttributesProjectCreateFailed"));
|
||||
final List<String> mixins = project.getMixins();
|
||||
assertFalse(mixins.isEmpty());
|
||||
assertEquals(mixin, mixins.get(0));
|
||||
|
||||
final List<Problem> problems = project.getProblems();
|
||||
assertNotNull(problems);
|
||||
assertFalse(problems.isEmpty());
|
||||
assertEquals(13, problems.get(0).code);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testInvalidConfigProjectCreateFailed() throws Exception {
|
||||
|
||||
// SPECS:
|
||||
// If project path is not defined
|
||||
// Project creation failed with ConflictException
|
||||
|
||||
ProjectConfig pc = new NewProjectConfig(null, "pt2", null, "name", "descr", null, null);
|
||||
ProjectConfig pc = new NewProjectConfigImpl(null, "pt2", null, "name", "descr", null, null, null);
|
||||
|
||||
try {
|
||||
pm.createProject(pc, null);
|
||||
fail("ConflictException: Path for new project should be defined ");
|
||||
} catch (ConflictException e) {
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public void testCreateInnerProject() throws Exception {
|
||||
|
||||
|
||||
ProjectConfig pc = new NewProjectConfig("/testCreateInnerProject", BaseProjectType.ID, null, "name", "descr", null, null);
|
||||
ProjectConfig pc = new NewProjectConfigImpl("/testCreateInnerProject", BaseProjectType.ID, null, "name", "descr", null, null, null);
|
||||
pm.createProject(pc, null);
|
||||
|
||||
pc = new NewProjectConfig("/testCreateInnerProject/inner", BaseProjectType.ID, null, "name", "descr", null, null);
|
||||
pc = new NewProjectConfigImpl("/testCreateInnerProject/inner", BaseProjectType.ID, null, "name", "descr", null, null, null);
|
||||
pm.createProject(pc, null);
|
||||
|
||||
assertNotNull(projectRegistry.getProject("/testCreateInnerProject/inner"));
|
||||
|
|
@ -267,13 +698,12 @@ public class ProjectManagerWriteTest extends WsAgentTestBase {
|
|||
|
||||
// If there are no parent folder it will be created
|
||||
|
||||
pc = new NewProjectConfig("/nothing/inner", BaseProjectType.ID, null, "name", "descr", null, null);
|
||||
pc = new NewProjectConfigImpl("/nothing/inner", BaseProjectType.ID, null, "name", "descr", null, null, null);
|
||||
|
||||
pm.createProject(pc, null);
|
||||
assertNotNull(projectRegistry.getProject("/nothing/inner"));
|
||||
assertNotNull(projectRegistry.getProject("/nothing"));
|
||||
assertNotNull(pm.getProjectsRoot().getChildFolder("/nothing"));
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
|
@ -281,14 +711,14 @@ public class ProjectManagerWriteTest extends WsAgentTestBase {
|
|||
public void testUpdateProjectWithPersistedAttributes() throws Exception {
|
||||
Map<String, List<String>> attributes = new HashMap<>();
|
||||
|
||||
ProjectConfig pc = new NewProjectConfig("/testUpdateProject", BaseProjectType.ID, null, "name", "descr", null, null);
|
||||
ProjectConfig pc = new NewProjectConfigImpl("/testUpdateProject", BaseProjectType.ID, null, "name", "descr", null, null, null);
|
||||
RegisteredProject p = pm.createProject(pc, null);
|
||||
|
||||
assertEquals(BaseProjectType.ID, p.getType());
|
||||
assertEquals("name", p.getName());
|
||||
|
||||
attributes.put("pt2-var2", new AttributeValue("updated").getList());
|
||||
ProjectConfig pc1 = new NewProjectConfig("/testUpdateProject", "pt2", null, "updatedName", "descr", attributes, null);
|
||||
ProjectConfig pc1 = new NewProjectConfigImpl("/testUpdateProject", "pt2", null, "updatedName", "descr", attributes, null, null);
|
||||
|
||||
p = pm.updateProject(pc1);
|
||||
|
||||
|
|
@ -301,38 +731,30 @@ public class ProjectManagerWriteTest extends WsAgentTestBase {
|
|||
|
||||
@Test
|
||||
public void testUpdateProjectWithProvidedAttributes() throws Exception {
|
||||
// SPECS: Project should be updated with problem code = 13 when value for required attribute is not initialized
|
||||
|
||||
Map<String, List<String>> attributes = new HashMap<>();
|
||||
attributes.put("pt2-var2", new AttributeValue("test").getList());
|
||||
|
||||
ProjectConfig pc = new NewProjectConfig("/testUpdateProject", "pt2", null, "name", "descr", attributes, null);
|
||||
RegisteredProject p = pm.createProject(pc, null);
|
||||
ProjectConfig pc = new NewProjectConfigImpl("/testUpdateProject", "pt2", null, "name", "descr", attributes, null, null);
|
||||
pm.createProject(pc, null);
|
||||
|
||||
// SPECS:
|
||||
// If project type is updated with one required provided attributes
|
||||
// those attributes should be provided before update
|
||||
|
||||
pc = new NewProjectConfig("/testUpdateProject", "pt3", null, "updatedName", "descr", attributes, null);
|
||||
|
||||
try {
|
||||
pm.updateProject(pc);
|
||||
fail("ProjectTypeConstraintException: Value for required attribute is not initialized pt3:pt2-provided1 ");
|
||||
} catch (ServerException e) {
|
||||
}
|
||||
pc = new NewProjectConfigImpl("/testUpdateProject", "pt3", null, "updatedName", "descr", attributes, null, null);
|
||||
|
||||
|
||||
p.getBaseFolder().createFolder("file1");
|
||||
p = pm.updateProject(pc);
|
||||
assertEquals(new AttributeValue("pt2-provided1"), p.getAttributeEntries().get("pt2-provided1"));
|
||||
|
||||
RegisteredProject project = pm.updateProject(pc);
|
||||
|
||||
final List<Problem> problems = project.getProblems();
|
||||
assertNotNull(problems);
|
||||
assertFalse(problems.isEmpty());
|
||||
assertEquals(1, problems.size());
|
||||
assertEquals(13, problems.get(0).code);
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public void testUpdateProjectOnRawFolder() throws Exception {
|
||||
|
||||
ProjectConfig pc = new NewProjectConfig("/testUpdateProjectOnRawFolder", BaseProjectType.ID, null, "name", "descr", null, null);
|
||||
ProjectConfig pc = new NewProjectConfigImpl("/testUpdateProjectOnRawFolder", BaseProjectType.ID, null, "name", "descr", null, null, null);
|
||||
pm.createProject(pc, null);
|
||||
String folderPath = "/testUpdateProjectOnRawFolder/folder";
|
||||
pm.getProjectsRoot().createFolder(folderPath);
|
||||
|
|
@ -340,18 +762,15 @@ public class ProjectManagerWriteTest extends WsAgentTestBase {
|
|||
// SPECS:
|
||||
// If update is called on raw folder new project should be created
|
||||
|
||||
pc = new NewProjectConfig(folderPath, BaseProjectType.ID, null, "raw", "descr", null, null);
|
||||
pc = new NewProjectConfigImpl(folderPath, BaseProjectType.ID, null, "raw", "descr", null, null, null);
|
||||
pm.updateProject(pc);
|
||||
|
||||
assertEquals(BaseProjectType.ID, pm.getProject(folderPath).getType());
|
||||
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testInvalidUpdateConfig() throws Exception {
|
||||
|
||||
ProjectConfig pc = new NewProjectConfig(null, BaseProjectType.ID, null, "name", "descr", null, null);
|
||||
ProjectConfig pc = new NewProjectConfigImpl(null, BaseProjectType.ID, null, "name", "descr", null, null, null);
|
||||
|
||||
try {
|
||||
pm.updateProject(pc);
|
||||
|
|
@ -359,7 +778,7 @@ public class ProjectManagerWriteTest extends WsAgentTestBase {
|
|||
} catch (ConflictException e) {
|
||||
}
|
||||
|
||||
pc = new NewProjectConfig("/nothing", BaseProjectType.ID, null, "name", "descr", null, null);
|
||||
pc = new NewProjectConfigImpl("/nothing", BaseProjectType.ID, null, "name", "descr", null, null, null);
|
||||
try {
|
||||
pm.updateProject(pc);
|
||||
fail("NotFoundException: Project '/nothing' doesn't exist.");
|
||||
|
|
@ -371,9 +790,9 @@ public class ProjectManagerWriteTest extends WsAgentTestBase {
|
|||
@Test
|
||||
public void testDeleteProject() throws Exception {
|
||||
|
||||
ProjectConfig pc = new NewProjectConfig("/testDeleteProject", BaseProjectType.ID, null, "name", "descr", null, null);
|
||||
ProjectConfig pc = new NewProjectConfigImpl("/testDeleteProject", BaseProjectType.ID, null, "name", "descr", null, null, null);
|
||||
pm.createProject(pc, null);
|
||||
pc = new NewProjectConfig("/testDeleteProject/inner", BaseProjectType.ID, null, "name", "descr", null, null);
|
||||
pc = new NewProjectConfigImpl("/testDeleteProject/inner", BaseProjectType.ID, null, "name", "descr", null, null, null);
|
||||
pm.createProject(pc, null);
|
||||
|
||||
assertNotNull(projectRegistry.getProject("/testDeleteProject/inner"));
|
||||
|
|
@ -384,13 +803,11 @@ public class ProjectManagerWriteTest extends WsAgentTestBase {
|
|||
assertNull(projectRegistry.getProject("/testDeleteProject"));
|
||||
assertNull(pm.getProjectsRoot().getChild("/testDeleteProject/inner"));
|
||||
//assertNull(projectRegistry.folder("/testDeleteProject/inner"));
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testDeleteProjectEvent() throws Exception {
|
||||
|
||||
ProjectConfig pc = new NewProjectConfig("/testDeleteProject", BaseProjectType.ID, null, "name", "descr", null, null);
|
||||
ProjectConfig pc = new NewProjectConfigImpl("/testDeleteProject", BaseProjectType.ID, null, "name", "descr", null, null, null);
|
||||
pm.createProject(pc, null);
|
||||
|
||||
String[] deletedPath = new String[1];
|
||||
|
|
@ -401,13 +818,11 @@ public class ProjectManagerWriteTest extends WsAgentTestBase {
|
|||
pm.delete("/testDeleteProject");
|
||||
|
||||
assertEquals("/testDeleteProject", deletedPath[0]);
|
||||
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public void testImportProject() throws Exception {
|
||||
|
||||
ByteArrayOutputStream bout = new ByteArrayOutputStream();
|
||||
String fileContent = "to be or not to be";
|
||||
ZipOutputStream zipOut = new ZipOutputStream(bout);
|
||||
|
|
@ -433,7 +848,6 @@ public class ProjectManagerWriteTest extends WsAgentTestBase {
|
|||
|
||||
assertNotNull(project.getBaseFolder().getChild("file1"));
|
||||
assertEquals(fileContent, project.getBaseFolder().getChild("file1").getVirtualFile().getContentAsString());
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
|
|
@ -467,11 +881,11 @@ public class ProjectManagerWriteTest extends WsAgentTestBase {
|
|||
|
||||
@Test
|
||||
public void testProvidedAttributesNotSerialized() throws Exception {
|
||||
|
||||
Map<String, List<String>> attributes = new HashMap<>();
|
||||
attributes.put("pt2-var2", new AttributeValue("test2").getList());
|
||||
attributes.put("pt2-var1", new AttributeValue("test1").getList());
|
||||
ProjectConfig pc = new NewProjectConfig("/testProvidedAttributesNotSerialized", "pt3", null, "name", "descr", attributes, null);
|
||||
ProjectConfig pc =
|
||||
new NewProjectConfigImpl("/testProvidedAttributesNotSerialized", "pt3", null, "name", "descr", attributes, null, null);
|
||||
|
||||
pm.createProject(pc, null);
|
||||
|
||||
|
|
@ -493,10 +907,9 @@ public class ProjectManagerWriteTest extends WsAgentTestBase {
|
|||
|
||||
@Test
|
||||
public void testSettableValueProvider() throws Exception {
|
||||
|
||||
assertTrue(((Variable)projectTypeRegistry.getProjectType("settableVPPT").getAttribute("my")).isValueProvided());
|
||||
|
||||
ProjectConfig pc = new NewProjectConfig("/testSettableValueProvider", "settableVPPT", null, "", "", new HashMap<>(), null);
|
||||
ProjectConfig pc = new NewProjectConfigImpl("/testSettableValueProvider", "settableVPPT", null, "", "", new HashMap<>(), null, null);
|
||||
|
||||
pm.createProject(pc, null);
|
||||
|
||||
|
|
@ -507,18 +920,64 @@ public class ProjectManagerWriteTest extends WsAgentTestBase {
|
|||
|
||||
Map<String, List<String>> attributes = new HashMap<>();
|
||||
attributes.put("my", new AttributeValue("set").getList());
|
||||
pc = new NewProjectConfig("/testSettableValueProvider", "settableVPPT", null, "", "", attributes, null);
|
||||
pc = new NewProjectConfigImpl("/testSettableValueProvider", "settableVPPT", null, "", "", attributes, null, null);
|
||||
|
||||
pm.updateProject(pc);
|
||||
project = pm.getProject("/testSettableValueProvider");
|
||||
assertEquals("set", project.getAttributes().get("my").get(0));
|
||||
|
||||
}
|
||||
|
||||
/* ---------------------------------- */
|
||||
/* private */
|
||||
/* ---------------------------------- */
|
||||
|
||||
private void checkProjectExist(String projectPath) {
|
||||
RegisteredProject project = projectRegistry.getProject(projectPath);
|
||||
FolderEntry projectFolder = project.getBaseFolder();
|
||||
assertNotNull(project);
|
||||
assertTrue(projectFolder.getVirtualFile().exists());
|
||||
assertEquals(projectPath, project.getPath());
|
||||
assertEquals(BaseProjectType.ID, project.getType());
|
||||
}
|
||||
|
||||
private void checkChildrenFor(FolderEntry projectFolder, List<String> children) throws ServerException, ForbiddenException {
|
||||
for (String path : children) {
|
||||
assertNotNull(projectFolder.getChild(path));
|
||||
if (path.contains("file")) {
|
||||
String fileContent = projectFolder.getChild(path).getVirtualFile().getContentAsString();
|
||||
assertEquals(FILE_CONTENT, fileContent);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private InputStream prepareZipArchiveBasedOn(List<String> paths) throws IOException {
|
||||
ByteArrayOutputStream bout = new ByteArrayOutputStream();
|
||||
ZipOutputStream zipOut = new ZipOutputStream(bout);
|
||||
|
||||
for (String path : paths) {
|
||||
zipOut.putNextEntry(new ZipEntry(path));
|
||||
|
||||
if (path.contains("file")) {
|
||||
zipOut.write(FILE_CONTENT.getBytes());
|
||||
}
|
||||
}
|
||||
zipOut.close();
|
||||
return new ByteArrayInputStream(bout.toByteArray());
|
||||
}
|
||||
|
||||
private NewProjectConfigDto createProjectConfigObject(String projectName,
|
||||
String projectPath,
|
||||
String projectType,
|
||||
SourceStorageDto sourceStorage) {
|
||||
return DtoFactory.newDto(NewProjectConfigDto.class)
|
||||
.withPath(projectPath)
|
||||
.withName(projectName)
|
||||
.withType(projectType)
|
||||
.withDescription("description")
|
||||
.withSource(sourceStorage)
|
||||
.withAttributes(new HashMap<>());
|
||||
}
|
||||
|
||||
private void registerImporter(String importType, InputStream zip) throws Exception {
|
||||
final ValueHolder<FolderEntry> folderHolder = new ValueHolder<>();
|
||||
importerRegistry.register(new ProjectImporter() {
|
||||
|
|
@ -570,7 +1029,6 @@ public class ProjectManagerWriteTest extends WsAgentTestBase {
|
|||
throws ForbiddenException, ConflictException, ServerException {
|
||||
FolderEntry baseFolder = new FolderEntry(vfsProvider.getVirtualFileSystem().getRoot().createFolder(projectPath.toString()));
|
||||
baseFolder.createFolder("file1");
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
@ -578,5 +1036,4 @@ public class ProjectManagerWriteTest extends WsAgentTestBase {
|
|||
return "pt3";
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
|||
|
|
@ -10,6 +10,8 @@
|
|||
*******************************************************************************/
|
||||
package org.eclipse.che.api.project.server;
|
||||
|
||||
import com.google.common.io.ByteStreams;
|
||||
|
||||
import org.eclipse.che.api.core.ConflictException;
|
||||
import org.eclipse.che.api.core.ForbiddenException;
|
||||
import org.eclipse.che.api.core.NotFoundException;
|
||||
|
|
@ -29,6 +31,7 @@ import org.eclipse.che.api.project.server.handlers.ProjectHandlerRegistry;
|
|||
import org.eclipse.che.api.project.server.importer.ProjectImporter;
|
||||
import org.eclipse.che.api.project.server.importer.ProjectImporterRegistry;
|
||||
import org.eclipse.che.api.project.server.type.AttributeValue;
|
||||
import org.eclipse.che.api.project.server.type.ProjectTypeConstraintException;
|
||||
import org.eclipse.che.api.project.server.type.ProjectTypeDef;
|
||||
import org.eclipse.che.api.project.server.type.ProjectTypeRegistry;
|
||||
import org.eclipse.che.api.project.server.type.ReadonlyValueProvider;
|
||||
|
|
@ -52,7 +55,6 @@ import org.eclipse.che.api.workspace.shared.dto.ProjectConfigDto;
|
|||
import org.eclipse.che.api.workspace.shared.dto.SourceStorageDto;
|
||||
import org.eclipse.che.api.workspace.shared.dto.WorkspaceConfigDto;
|
||||
import org.eclipse.che.api.workspace.shared.dto.WorkspaceDto;
|
||||
import org.eclipse.che.commons.json.JsonHelper;
|
||||
import org.eclipse.che.commons.lang.IoUtil;
|
||||
import org.eclipse.che.commons.lang.ws.rs.ExtMediaType;
|
||||
import org.eclipse.che.commons.subject.SubjectImpl;
|
||||
|
|
@ -81,6 +83,7 @@ import javax.ws.rs.core.Application;
|
|||
import java.io.ByteArrayInputStream;
|
||||
import java.io.ByteArrayOutputStream;
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.net.URI;
|
||||
import java.nio.charset.Charset;
|
||||
|
|
@ -106,6 +109,7 @@ import java.util.stream.IntStream;
|
|||
import java.util.zip.ZipEntry;
|
||||
import java.util.zip.ZipOutputStream;
|
||||
|
||||
import static java.lang.String.format;
|
||||
import static java.util.Collections.singletonList;
|
||||
import static javax.ws.rs.HttpMethod.DELETE;
|
||||
import static javax.ws.rs.HttpMethod.GET;
|
||||
|
|
@ -115,6 +119,7 @@ import static javax.ws.rs.core.MediaType.APPLICATION_JSON;
|
|||
import static javax.ws.rs.core.MediaType.TEXT_PLAIN;
|
||||
import static org.eclipse.che.commons.lang.ws.rs.ExtMediaType.APPLICATION_ZIP;
|
||||
import static org.everrest.core.ApplicationContext.anApplicationContext;
|
||||
import static org.junit.Assert.assertFalse;
|
||||
import static org.junit.Assert.assertTrue;
|
||||
import static org.mockito.Matchers.any;
|
||||
import static org.mockito.Mockito.mock;
|
||||
|
|
@ -414,24 +419,9 @@ public class ProjectServiceTest {
|
|||
|
||||
@Test
|
||||
public void testCreateProject() throws Exception {
|
||||
|
||||
|
||||
|
||||
phRegistry.register(new CreateProjectHandler() {
|
||||
@Override
|
||||
public void onCreateProject(Path projectPath, Map<String, AttributeValue> attributes, Map<String, String> options)
|
||||
throws ForbiddenException, ConflictException, ServerException {
|
||||
FolderEntry projectFolder = new FolderEntry(vfsProvider.getVirtualFileSystem().getRoot().createFolder("new_project"));
|
||||
projectFolder.createFolder("a");
|
||||
projectFolder.createFolder("b");
|
||||
projectFolder.createFile("test.txt", "test".getBytes(Charset.defaultCharset()));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getProjectType() {
|
||||
return "testCreateProject";
|
||||
}
|
||||
});
|
||||
final String projectName = "new_project";
|
||||
final String projectType = "testCreateProject";
|
||||
phRegistry.register(createProjectHandlerFor(projectName, projectType));
|
||||
|
||||
Map<String, List<String>> headers = new HashMap<>();
|
||||
headers.put("Content-Type", singletonList(APPLICATION_JSON));
|
||||
|
|
@ -450,9 +440,9 @@ public class ProjectServiceTest {
|
|||
|
||||
final ProjectConfigDto newProjectConfig = DtoFactory.getInstance().createDto(ProjectConfigDto.class)
|
||||
.withPath("/new_project")
|
||||
.withName("new_project")
|
||||
.withName(projectName)
|
||||
.withDescription("new project")
|
||||
.withType("testCreateProject")
|
||||
.withType(projectType)
|
||||
.withAttributes(attributeValues)
|
||||
.withSource(DtoFactory.getInstance().createDto(SourceStorageDto.class));
|
||||
projects.add(newProjectConfig);
|
||||
|
|
@ -467,11 +457,11 @@ public class ProjectServiceTest {
|
|||
assertEquals(response.getStatus(), 200, "Error: " + response.getEntity());
|
||||
ProjectConfigDto result = (ProjectConfigDto)response.getEntity();
|
||||
assertNotNull(result);
|
||||
assertEquals(result.getName(), "new_project");
|
||||
assertEquals(result.getName(), projectName);
|
||||
assertEquals(result.getPath(), "/new_project");
|
||||
assertEquals(result.getDescription(), newProjectConfig.getDescription());
|
||||
assertEquals(result.getType(), newProjectConfig.getType());
|
||||
assertEquals(result.getType(), "testCreateProject");
|
||||
assertEquals(result.getType(), projectType);
|
||||
Map<String, List<String>> attributes = result.getAttributes();
|
||||
assertNotNull(attributes);
|
||||
assertEquals(attributes.size(), 1);
|
||||
|
|
@ -492,11 +482,63 @@ public class ProjectServiceTest {
|
|||
assertNotNull(project.getBaseFolder().getChild("a"));
|
||||
assertNotNull(project.getBaseFolder().getChild("b"));
|
||||
assertNotNull(project.getBaseFolder().getChild("test.txt"));
|
||||
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCreateBatchProjects() throws Exception {
|
||||
//prepare first project
|
||||
final String projectName1 = "testProject1";
|
||||
final String projectTypeId1 = "testProjectType1";
|
||||
final String projectPath1 = "/testProject1";
|
||||
|
||||
createTestProjectType(projectTypeId1);
|
||||
phRegistry.register(createProjectHandlerFor(projectName1, projectTypeId1));
|
||||
|
||||
//prepare inner project
|
||||
final String innerProjectName = "innerProject";
|
||||
final String innerProjectTypeId = "testProjectType2";
|
||||
final String innerProjectPath = "/testProject1/innerProject";
|
||||
|
||||
createTestProjectType(innerProjectTypeId);
|
||||
phRegistry.register(createProjectHandlerFor(innerProjectName, innerProjectTypeId));
|
||||
|
||||
//prepare project to import
|
||||
final String importProjectName = "testImportProject";
|
||||
final String importProjectTypeId = "testImportProjectType";
|
||||
final String importProjectPath = "/testImportProject";
|
||||
final String importType = "importType";
|
||||
final String [] paths = {"a", "b", "test.txt"};
|
||||
|
||||
final List<String> children = new ArrayList<>(Arrays.asList(paths));
|
||||
registerImporter(importType, prepareZipArchiveBasedOn(children));
|
||||
createTestProjectType(importProjectTypeId);
|
||||
|
||||
Map<String, List<String>> headers = new HashMap<>();
|
||||
headers.put("Content-Type", singletonList(APPLICATION_JSON));
|
||||
|
||||
try (InputStream content = getClass().getResourceAsStream("batchNewProjectConfigs.json")) {
|
||||
ContainerResponse response = launcher.service(POST,
|
||||
"http://localhost:8080/api/project/batch",
|
||||
"http://localhost:8080/api",
|
||||
headers,
|
||||
ByteStreams.toByteArray(content), null);
|
||||
|
||||
assertEquals(response.getStatus(), 200, "Error: " + response.getEntity());
|
||||
|
||||
final List<ProjectConfigDto> result = (List<ProjectConfigDto>)response.getEntity();
|
||||
assertNotNull(result);
|
||||
assertEquals(result.size(), 3);
|
||||
|
||||
final ProjectConfigDto importProjectConfig = result.get(0);
|
||||
checkProjectIsCreated(importProjectName, importProjectPath, importProjectTypeId, importProjectConfig);
|
||||
|
||||
final ProjectConfigDto config1 = result.get(1);
|
||||
checkProjectIsCreated(projectName1, projectPath1, projectTypeId1, config1);
|
||||
|
||||
final ProjectConfigDto innerProjectConfig = result.get(2);
|
||||
checkProjectIsCreated(innerProjectName, innerProjectPath, innerProjectTypeId, innerProjectConfig);
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testUpdateProject() throws Exception {
|
||||
|
|
@ -636,10 +678,9 @@ public class ProjectServiceTest {
|
|||
|
||||
ptRegistry.registerProjectType(pt);
|
||||
|
||||
ContainerResponse response =
|
||||
launcher.service(GET, String.format("http://localhost:8080/api/project/estimate/%s?type=%s",
|
||||
"testEstimateProjectGood", "testEstimateProjectPT"),
|
||||
"http://localhost:8080/api", null, null, null);
|
||||
ContainerResponse response = launcher.service(GET, format("http://localhost:8080/api/project/estimate/%s?type=%s",
|
||||
"testEstimateProjectGood", "testEstimateProjectPT"),
|
||||
"http://localhost:8080/api", null, null, null);
|
||||
assertEquals(response.getStatus(), 200, "Error: " + response.getEntity());
|
||||
//noinspection unchecked
|
||||
SourceEstimation result = (SourceEstimation)response.getEntity();
|
||||
|
|
@ -648,14 +689,15 @@ public class ProjectServiceTest {
|
|||
assertEquals(result.getAttributes().get("calculated_attribute").get(0), "checked");
|
||||
|
||||
// if project not matched
|
||||
response = launcher.service(GET, String.format("http://localhost:8080/api/project/estimate/%s?type=%s",
|
||||
"testEstimateProjectBad", "testEstimateProjectPT"),
|
||||
response = launcher.service(GET, format("http://localhost:8080/api/project/estimate/%s?type=%s",
|
||||
"testEstimateProjectBad", "testEstimateProjectPT"),
|
||||
"http://localhost:8080/api", null, null, null);
|
||||
|
||||
assertEquals(response.getStatus(), 409, "Error: " + response.getEntity());
|
||||
String msg = JsonHelper.parseJson(response.getEntity().toString()).getElement("message").getStringValue();
|
||||
assertEquals(errMessage, msg);
|
||||
|
||||
assertEquals(response.getStatus(), 200, "Error: " + response.getEntity());
|
||||
//noinspection unchecked
|
||||
result = (SourceEstimation)response.getEntity();
|
||||
assertFalse(result.isMatched());
|
||||
assertEquals(result.getAttributes().size(), 0);
|
||||
}
|
||||
|
||||
|
||||
|
|
@ -697,8 +739,8 @@ public class ProjectServiceTest {
|
|||
ptRegistry.registerProjectType(pt);
|
||||
|
||||
ContainerResponse response =
|
||||
launcher.service(GET, String.format("http://localhost:8080/api/project/resolve/%s",
|
||||
"testEstimateProjectGood"),
|
||||
launcher.service(GET, format("http://localhost:8080/api/project/resolve/%s",
|
||||
"testEstimateProjectGood"),
|
||||
"http://localhost:8080/api", null, null, null);
|
||||
assertEquals(response.getStatus(), 200, "Error: " + response.getEntity());
|
||||
List<SourceEstimation> result = (List<SourceEstimation>) response.getEntity();
|
||||
|
|
@ -746,7 +788,7 @@ public class ProjectServiceTest {
|
|||
" \"type\": \"%s\"\n" +
|
||||
"}";
|
||||
|
||||
byte[] b = String.format(json, importType).getBytes(Charset.defaultCharset());
|
||||
byte[] b = format(json, importType).getBytes(Charset.defaultCharset());
|
||||
ContainerResponse response = launcher.service(POST,
|
||||
"http://localhost:8080/api/project/import/new_project",
|
||||
"http://localhost:8080/api", headers, b, null);
|
||||
|
|
@ -878,7 +920,7 @@ public class ProjectServiceTest {
|
|||
public void testCreateFolderInRoot() throws Exception {
|
||||
String folder = "my_folder";
|
||||
ContainerResponse response = launcher.service(POST,
|
||||
String.format("http://localhost:8080/api/project/folder/%s", folder),
|
||||
format("http://localhost:8080/api/project/folder/%s", folder),
|
||||
"http://localhost:8080/api", null, null, null);
|
||||
assertEquals(response.getStatus(), 201, "Error: " + response.getEntity());
|
||||
ItemReference fileItem = (ItemReference)response.getEntity();
|
||||
|
|
@ -887,7 +929,7 @@ public class ProjectServiceTest {
|
|||
assertEquals(fileItem.getPath(), "/" + folder);
|
||||
validateFolderLinks(fileItem);
|
||||
assertEquals(response.getHttpHeaders().getFirst("Location"),
|
||||
URI.create(String.format("http://localhost:8080/api/project/children/%s", folder)));
|
||||
URI.create(format("http://localhost:8080/api/project/children/%s", folder)));
|
||||
}
|
||||
|
||||
@Test
|
||||
|
|
@ -1052,7 +1094,8 @@ public class ProjectServiceTest {
|
|||
String overwrittenContent = "that is the question";
|
||||
|
||||
((FolderEntry)myProject.getBaseFolder().getChild("a/b")).createFile(originFileName, originContent.getBytes(Charset.defaultCharset()));
|
||||
((FolderEntry)myProject.getBaseFolder().getChild("a/b/c")).createFile(destinationFileName, overwrittenContent.getBytes(Charset.defaultCharset()));
|
||||
((FolderEntry)myProject.getBaseFolder().getChild("a/b/c")).createFile(destinationFileName,
|
||||
overwrittenContent.getBytes(Charset.defaultCharset()));
|
||||
|
||||
Map<String, List<String>> headers = new HashMap<>();
|
||||
headers.put(CONTENT_TYPE, singletonList(APPLICATION_JSON));
|
||||
|
|
@ -1127,9 +1170,9 @@ public class ProjectServiceTest {
|
|||
assertEquals(response.getStatus(), 201, "Error: " + response.getEntity());
|
||||
assertEquals(response.getHttpHeaders().getFirst("Location"),
|
||||
URI.create(
|
||||
String.format("http://localhost:8080/api/project/children/my_project/a/b/c/%s", renamedFolder)));
|
||||
format("http://localhost:8080/api/project/children/my_project/a/b/c/%s", renamedFolder)));
|
||||
assertNotNull(myProject.getBaseFolder().getChild("a/b/test.txt"));
|
||||
assertNotNull(myProject.getBaseFolder().getChild(String.format("a/b/c/%s/test.txt", renamedFolder)));
|
||||
assertNotNull(myProject.getBaseFolder().getChild(format("a/b/c/%s/test.txt", renamedFolder)));
|
||||
}
|
||||
|
||||
@Test
|
||||
|
|
@ -1165,11 +1208,11 @@ public class ProjectServiceTest {
|
|||
assertEquals(response.getStatus(), 201, "Error: " + response.getEntity());
|
||||
assertEquals(response.getHttpHeaders().getFirst("Location"),
|
||||
URI.create(
|
||||
String.format("http://localhost:8080/api/project/children/my_project/a/b/c/%s", renamedFolder)));
|
||||
format("http://localhost:8080/api/project/children/my_project/a/b/c/%s", renamedFolder)));
|
||||
assertNotNull(myProject.getBaseFolder().getChild("a/b/test.txt"));
|
||||
assertNotNull(myProject.getBaseFolder().getChild(String.format("a/b/c/%s/test.txt", renamedFolder)));
|
||||
assertNotNull(myProject.getBaseFolder().getChild(format("a/b/c/%s/test.txt", renamedFolder)));
|
||||
assertEquals(myProject.getBaseFolder().getChild("a/b/test.txt").getName(),
|
||||
myProject.getBaseFolder().getChild(String.format("a/b/c/%s/%s", renamedFolder, originFileName)).getName());
|
||||
myProject.getBaseFolder().getChild(format("a/b/c/%s/%s", renamedFolder, originFileName)).getName());
|
||||
}
|
||||
|
||||
@Test
|
||||
|
|
@ -1210,8 +1253,8 @@ public class ProjectServiceTest {
|
|||
assertEquals(response.getStatus(), 201, "Error: " + response.getEntity());
|
||||
assertEquals(response.getHttpHeaders().getFirst("Location"),
|
||||
URI.create(
|
||||
String.format("http://localhost:8080/api/project/file/my_project/a/b/c/%s", destinationName)));
|
||||
VirtualFileEntry theTargetFile = myProject.getBaseFolder().getChild(String.format("a/b/c/%s", destinationName));
|
||||
format("http://localhost:8080/api/project/file/my_project/a/b/c/%s", destinationName)));
|
||||
VirtualFileEntry theTargetFile = myProject.getBaseFolder().getChild(format("a/b/c/%s", destinationName));
|
||||
assertNotNull(theTargetFile); // new
|
||||
}
|
||||
|
||||
|
|
@ -1238,8 +1281,8 @@ public class ProjectServiceTest {
|
|||
assertEquals(response.getStatus(), 201, "Error: " + response.getEntity());
|
||||
assertEquals(response.getHttpHeaders().getFirst("Location"),
|
||||
URI.create(
|
||||
String.format("http://localhost:8080/api/project/file/my_project/a/b/%s", destinationName)));
|
||||
VirtualFileEntry theTargetFile = myProject.getBaseFolder().getChild(String.format("a/b/%s", destinationName));
|
||||
format("http://localhost:8080/api/project/file/my_project/a/b/%s", destinationName)));
|
||||
VirtualFileEntry theTargetFile = myProject.getBaseFolder().getChild(format("a/b/%s", destinationName));
|
||||
assertNotNull(theTargetFile); // new
|
||||
}
|
||||
|
||||
|
|
@ -1333,8 +1376,8 @@ public class ProjectServiceTest {
|
|||
assertEquals(response.getStatus(), 201, "Error: " + response.getEntity());
|
||||
assertEquals(response.getHttpHeaders().getFirst("Location"),
|
||||
URI.create(
|
||||
String.format("http://localhost:8080/api/project/children/my_project/a/b/c/%s", renamedFolder)));
|
||||
assertNotNull(myProject.getBaseFolder().getChild(String.format("a/b/c/%s/test.txt", renamedFolder)));
|
||||
format("http://localhost:8080/api/project/children/my_project/a/b/c/%s", renamedFolder)));
|
||||
assertNotNull(myProject.getBaseFolder().getChild(format("a/b/c/%s/test.txt", renamedFolder)));
|
||||
}
|
||||
|
||||
@Test
|
||||
|
|
@ -1360,8 +1403,8 @@ public class ProjectServiceTest {
|
|||
assertEquals(response.getStatus(), 201, "Error: " + response.getEntity());
|
||||
assertEquals(response.getHttpHeaders().getFirst("Location"),
|
||||
URI.create(
|
||||
String.format("http://localhost:8080/api/project/children/my_project/a/%s", renamedFolder)));
|
||||
assertNotNull(myProject.getBaseFolder().getChild(String.format("a/%s/test.txt", renamedFolder)));
|
||||
format("http://localhost:8080/api/project/children/my_project/a/%s", renamedFolder)));
|
||||
assertNotNull(myProject.getBaseFolder().getChild(format("a/%s/test.txt", renamedFolder)));
|
||||
}
|
||||
|
||||
@Test
|
||||
|
|
@ -1397,8 +1440,8 @@ public class ProjectServiceTest {
|
|||
assertEquals(response.getStatus(), 201, "Error: " + response.getEntity());
|
||||
assertEquals(response.getHttpHeaders().getFirst("Location"),
|
||||
URI.create(
|
||||
String.format("http://localhost:8080/api/project/children/my_project/a/b/c/%s", renamedFolder)));
|
||||
assertNotNull(myProject.getBaseFolder().getChild(String.format("a/b/c/%s/test.txt", renamedFolder)));
|
||||
format("http://localhost:8080/api/project/children/my_project/a/b/c/%s", renamedFolder)));
|
||||
assertNotNull(myProject.getBaseFolder().getChild(format("a/b/c/%s/test.txt", renamedFolder)));
|
||||
}
|
||||
|
||||
@Test
|
||||
|
|
@ -1416,7 +1459,7 @@ public class ProjectServiceTest {
|
|||
Map<String, List<String>> headers = new HashMap<>();
|
||||
headers.put(CONTENT_TYPE, singletonList(ExtMediaType.APPLICATION_ZIP));
|
||||
ContainerResponse response = launcher.service(POST,
|
||||
String.format("http://localhost:8080/api/project/import/my_project/a/b"),
|
||||
format("http://localhost:8080/api/project/import/my_project/a/b"),
|
||||
"http://localhost:8080/api", headers, zip, null);
|
||||
assertEquals(response.getStatus(), 201, "Error: " + response.getEntity());
|
||||
assertEquals(response.getHttpHeaders().getFirst("Location"),
|
||||
|
|
@ -1520,8 +1563,8 @@ public class ProjectServiceTest {
|
|||
@Test
|
||||
public void testGetMissingItem() throws Exception {
|
||||
ContainerResponse response = launcher.service(GET,
|
||||
"http://localhost:8080/api/project/item/some_missing_project/a/b",
|
||||
"http://localhost:8080/api", null, null, null);
|
||||
"http://localhost:8080/api/project/item/some_missing_project/a/b",
|
||||
"http://localhost:8080/api", null, null, null);
|
||||
assertEquals(response.getStatus(), 404, "Error: " + response.getEntity());
|
||||
}
|
||||
|
||||
|
|
@ -1731,8 +1774,10 @@ public class ProjectServiceTest {
|
|||
"to" + URL_ENCODED_SPACE +
|
||||
"be" + URL_ENCODED_QUOTES;
|
||||
RegisteredProject myProject = pm.getProject("my_project");
|
||||
myProject.getBaseFolder().createFolder("x/y").createFile("containsSearchText.txt", "To be or not to be that is the question".getBytes(Charset.defaultCharset()));
|
||||
myProject.getBaseFolder().createFolder("a/b").createFile("test.txt", "Pay attention! To be or to be that is the question".getBytes(Charset.defaultCharset()));
|
||||
myProject.getBaseFolder().createFolder("x/y").createFile("containsSearchText.txt", "To be or not to be that is the question".getBytes(
|
||||
Charset.defaultCharset()));
|
||||
myProject.getBaseFolder().createFolder("a/b").createFile("test.txt", "Pay attention! To be or to be that is the question".getBytes(
|
||||
Charset.defaultCharset()));
|
||||
myProject.getBaseFolder().createFolder("c").createFile("_test", "Pay attention! To be or to not be that is the question".getBytes(Charset.defaultCharset()));
|
||||
|
||||
ContainerResponse response =
|
||||
|
|
@ -1755,11 +1800,14 @@ public class ProjectServiceTest {
|
|||
"the" + URL_ENCODED_QUOTES + URL_ENCODED_SPACE + AND_OPERATOR + URL_ENCODED_SPACE +
|
||||
"question" + URL_ENCODED_ASTERISK;
|
||||
RegisteredProject myProject = pm.getProject("my_project");
|
||||
myProject.getBaseFolder().createFolder("x/y").createFile("containsSearchText.txt", "To be or not to be that is the question".getBytes(Charset.defaultCharset()));
|
||||
myProject.getBaseFolder().createFolder("x/y").createFile("containsSearchText.txt", "To be or not to be that is the question".getBytes(
|
||||
Charset.defaultCharset()));
|
||||
myProject.getBaseFolder().createFolder("a/b")
|
||||
.createFile("containsSearchTextAlso.txt", "Pay attention! To be or not to be that is the questionS".getBytes(Charset.defaultCharset()));
|
||||
.createFile("containsSearchTextAlso.txt",
|
||||
"Pay attention! To be or not to be that is the questionS".getBytes(Charset.defaultCharset()));
|
||||
myProject.getBaseFolder().createFolder("c")
|
||||
.createFile("notContainsSearchText", "Pay attention! To be or to not be that is the questEon".getBytes(Charset.defaultCharset()));
|
||||
.createFile("notContainsSearchText",
|
||||
"Pay attention! To be or to not be that is the questEon".getBytes(Charset.defaultCharset()));
|
||||
|
||||
ContainerResponse response =
|
||||
launcher.service(GET,"http://localhost:8080/api/project/search/my_project" + queryToSearch,
|
||||
|
|
@ -1780,7 +1828,8 @@ public class ProjectServiceTest {
|
|||
String queryToSearch = "?text=" +
|
||||
"question" + URL_ENCODED_ASTERISK;
|
||||
RegisteredProject myProject = pm.getProject("my_project");
|
||||
myProject.getBaseFolder().createFolder("x/y").createFile("containsSearchText.txt", "To be or not to be that is the question".getBytes(Charset.defaultCharset()));
|
||||
myProject.getBaseFolder().createFolder("x/y").createFile("containsSearchText.txt", "To be or not to be that is the question".getBytes(
|
||||
Charset.defaultCharset()));
|
||||
myProject.getBaseFolder().createFolder("a/b")
|
||||
.createFile("containsSearchTextAlso.txt", "Pay attention! To be or not to be that is the questionS".getBytes(Charset.defaultCharset()));
|
||||
myProject.getBaseFolder().createFolder("c")
|
||||
|
|
@ -1806,10 +1855,12 @@ public class ProjectServiceTest {
|
|||
"question" + URL_ENCODED_SPACE + NOT_OPERATOR + URL_ENCODED_SPACE + URL_ENCODED_QUOTES +
|
||||
"attention!" + URL_ENCODED_QUOTES;
|
||||
RegisteredProject myProject = pm.getProject("my_project");
|
||||
myProject.getBaseFolder().createFolder("x/y").createFile("containsSearchText.txt", "To be or not to be that is the question".getBytes(Charset.defaultCharset()));
|
||||
myProject.getBaseFolder().createFolder("x/y").createFile("containsSearchText.txt", "To be or not to be that is the question".getBytes(
|
||||
Charset.defaultCharset()));
|
||||
myProject.getBaseFolder().createFolder("b")
|
||||
.createFile("notContainsSearchText", "Pay attention! To be or not to be that is the question".getBytes(Charset.defaultCharset()));
|
||||
myProject.getBaseFolder().createFolder("c").createFile("alsoNotContainsSearchText", "To be or to not be that is the ...".getBytes(Charset.defaultCharset()));
|
||||
myProject.getBaseFolder().createFolder("c").createFile("alsoNotContainsSearchText",
|
||||
"To be or to not be that is the ...".getBytes(Charset.defaultCharset()));
|
||||
|
||||
ContainerResponse response =
|
||||
launcher.service(GET, "http://localhost:8080/api/project/search/my_project" + queryToSearch,
|
||||
|
|
@ -1838,7 +1889,8 @@ public class ProjectServiceTest {
|
|||
URL_ENCODED_BACKSLASH + ':' + "projectName=test";
|
||||
RegisteredProject myProject = pm.getProject("my_project");
|
||||
myProject.getBaseFolder().createFolder("x/y")
|
||||
.createFile("test.txt", "http://localhost:8080/ide/dev6?action=createProject:projectName=test".getBytes(Charset.defaultCharset()));
|
||||
.createFile("test.txt",
|
||||
"http://localhost:8080/ide/dev6?action=createProject:projectName=test".getBytes(Charset.defaultCharset()));
|
||||
|
||||
ContainerResponse response = launcher.service(GET, "http://localhost:8080/api/project/search/my_project" + queryToSearch,
|
||||
"http://localhost:8080/api", null, null, null);
|
||||
|
|
@ -1864,11 +1916,11 @@ public class ProjectServiceTest {
|
|||
assertEquals(response.getStatus(), 200, "Error: " + response.getEntity());
|
||||
List<ItemReference> result = (List<ItemReference>)response.getEntity();
|
||||
assertEquals(result.size(), 2);
|
||||
assertEqualsNoOrder(new Object[] {
|
||||
assertEqualsNoOrder(new Object[]{
|
||||
result.get(0).getPath(),
|
||||
result.get(1).getPath()
|
||||
},
|
||||
new Object[] {
|
||||
new Object[]{
|
||||
"/my_project/a/b/test.txt",
|
||||
"/my_project/x/y/test.txt"
|
||||
});
|
||||
|
|
@ -1895,12 +1947,12 @@ public class ProjectServiceTest {
|
|||
Link link = item.getLink("delete");
|
||||
assertNotNull(link);
|
||||
assertEquals(link.getMethod(), DELETE);
|
||||
assertEquals(link.getHref(), "http://localhost:8080/api/project" + item.getPath());
|
||||
assertEquals(link.getHref(), "http://localhost:8080/api/project" + item.getPath());
|
||||
link = item.getLink("update content");
|
||||
assertNotNull(link);
|
||||
assertEquals(link.getMethod(), PUT);
|
||||
assertEquals(link.getConsumes(), "*/*");
|
||||
assertEquals(link.getHref(), "http://localhost:8080/api/project" + "/file" + item.getPath());
|
||||
assertEquals(link.getHref(), "http://localhost:8080/api/project" + "/file" + item.getPath());
|
||||
}
|
||||
|
||||
private void validateFolderLinks(ItemReference item) {
|
||||
|
|
@ -1974,6 +2026,77 @@ public class ProjectServiceTest {
|
|||
}
|
||||
}
|
||||
|
||||
private InputStream prepareZipArchiveBasedOn(List<String> paths) throws IOException {
|
||||
ByteArrayOutputStream bout = new ByteArrayOutputStream();
|
||||
ZipOutputStream zipOut = new ZipOutputStream(bout);
|
||||
|
||||
for (String path : paths) {
|
||||
zipOut.putNextEntry(new ZipEntry(path));
|
||||
}
|
||||
zipOut.close();
|
||||
return new ByteArrayInputStream(bout.toByteArray());
|
||||
}
|
||||
|
||||
private void checkProjectIsCreated(String expectedName, String expectedPath, String expectedType, ProjectConfigDto actualConfig)
|
||||
throws ServerException, NotFoundException {
|
||||
final String projectDescription = "someDescription";
|
||||
assertEquals(actualConfig.getName(), expectedName);
|
||||
assertEquals(actualConfig.getPath(), expectedPath);
|
||||
assertEquals(actualConfig.getDescription(), projectDescription);
|
||||
assertEquals(actualConfig.getType(), expectedType);
|
||||
|
||||
final String expectedAttribute = "new_test_attribute";
|
||||
final String expectedAttributeValue = "some_attribute_value";
|
||||
final Map<String, List<String>> attributes = actualConfig.getAttributes();
|
||||
assertNotNull(attributes);
|
||||
assertEquals(attributes.size(), 1);
|
||||
assertEquals(attributes.get(expectedAttribute), singletonList(expectedAttributeValue));
|
||||
|
||||
validateProjectLinks(actualConfig);
|
||||
|
||||
RegisteredProject project = pm.getProject(expectedPath);
|
||||
assertNotNull(project);
|
||||
assertEquals(project.getDescription(), projectDescription);
|
||||
assertEquals(project.getProjectType().getId(), expectedType);
|
||||
String attributeVal = project.getAttributeEntries().get(expectedAttribute).getString();
|
||||
assertNotNull(attributeVal);
|
||||
assertEquals(attributeVal, expectedAttributeValue);
|
||||
|
||||
assertNotNull(project.getBaseFolder().getChild("a"));
|
||||
assertNotNull(project.getBaseFolder().getChild("b"));
|
||||
assertNotNull(project.getBaseFolder().getChild("test.txt"));
|
||||
}
|
||||
|
||||
private void createTestProjectType(final String projectTypeId) throws ProjectTypeConstraintException {
|
||||
final ProjectTypeDef pt = new ProjectTypeDef(projectTypeId, "my project type", true, false) {
|
||||
{
|
||||
addConstantDefinition("new_test_attribute", "attr description", "some_attribute_value");
|
||||
}
|
||||
};
|
||||
ptRegistry.registerProjectType(pt);
|
||||
}
|
||||
|
||||
private CreateProjectHandler createProjectHandlerFor(final String projectName, final String projectTypeId) {
|
||||
return new CreateProjectHandler() {
|
||||
@Override
|
||||
public void onCreateProject(Path projectPath, Map<String, AttributeValue> attributes, Map<String, String> options)
|
||||
throws ForbiddenException, ConflictException, ServerException {
|
||||
final String pathToProject = projectPath.toString();
|
||||
final String pathToParent = pathToProject.substring(0, pathToProject.lastIndexOf("/"));
|
||||
final FolderEntry projectFolder = new FolderEntry(
|
||||
vfsProvider.getVirtualFileSystem().getRoot().getChild(Path.of(pathToParent)).createFolder(projectName));
|
||||
projectFolder.createFolder("a");
|
||||
projectFolder.createFolder("b");
|
||||
projectFolder.createFile("test.txt", "test".getBytes(Charset.defaultCharset()));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getProjectType() {
|
||||
return projectTypeId;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
private class LocalProjectType extends ProjectTypeDef {
|
||||
private LocalProjectType(String typeId, String typeName) {
|
||||
super(typeId, typeName, true, false);
|
||||
|
|
|
|||
|
|
@ -10,15 +10,11 @@
|
|||
*******************************************************************************/
|
||||
package org.eclipse.che.api.project.server;
|
||||
|
||||
import org.eclipse.che.api.core.ConflictException;
|
||||
import org.eclipse.che.api.core.ForbiddenException;
|
||||
import org.eclipse.che.api.core.ServerException;
|
||||
import org.eclipse.che.api.core.model.project.ProjectConfig;
|
||||
import org.eclipse.che.api.core.notification.EventService;
|
||||
import org.eclipse.che.api.project.server.handlers.CreateProjectHandler;
|
||||
import org.eclipse.che.api.project.server.handlers.ProjectHandlerRegistry;
|
||||
import org.eclipse.che.api.project.server.importer.ProjectImporterRegistry;
|
||||
import org.eclipse.che.api.project.server.type.AttributeValue;
|
||||
import org.eclipse.che.api.project.server.type.ProjectTypeDef;
|
||||
import org.eclipse.che.api.project.server.type.ProjectTypeRegistry;
|
||||
import org.eclipse.che.api.project.server.type.ReadonlyValueProvider;
|
||||
|
|
@ -26,7 +22,6 @@ import org.eclipse.che.api.project.server.type.SettableValueProvider;
|
|||
import org.eclipse.che.api.project.server.type.ValueProvider;
|
||||
import org.eclipse.che.api.project.server.type.ValueProviderFactory;
|
||||
import org.eclipse.che.api.project.server.type.ValueStorageException;
|
||||
import org.eclipse.che.api.vfs.Path;
|
||||
import org.eclipse.che.api.vfs.impl.file.DefaultFileWatcherNotificationHandler;
|
||||
import org.eclipse.che.api.vfs.impl.file.FileTreeWatcher;
|
||||
import org.eclipse.che.api.vfs.impl.file.FileWatcherNotificationHandler;
|
||||
|
|
|
|||
|
|
@ -0,0 +1,68 @@
|
|||
[
|
||||
{
|
||||
"name": "innerProject",
|
||||
"displayName": "innerProject",
|
||||
"path": "/testProject1/innerProject",
|
||||
"description": "someDescription",
|
||||
"type": "testProjectType2",
|
||||
"mixins": [],
|
||||
"attributes": {
|
||||
"new_test_attribute": [
|
||||
"some_attribute_value"
|
||||
]
|
||||
},
|
||||
"modules": [],
|
||||
"problems": [],
|
||||
"source": {
|
||||
"type": "",
|
||||
"location": "",
|
||||
"parameters": {}
|
||||
},
|
||||
"commands": [],
|
||||
"links": []
|
||||
},
|
||||
{
|
||||
"name": "testProject1",
|
||||
"displayName": "testProject1",
|
||||
"path": "/testProject1",
|
||||
"description": "someDescription",
|
||||
"type": "testProjectType1",
|
||||
"mixins": [],
|
||||
"attributes": {
|
||||
"new_test_attribute": [
|
||||
"some_attribute_value"
|
||||
]
|
||||
},
|
||||
"modules": [],
|
||||
"problems": [],
|
||||
"source": {
|
||||
"type": "",
|
||||
"location": "",
|
||||
"parameters": {}
|
||||
},
|
||||
"commands": [],
|
||||
"links": []
|
||||
},
|
||||
{
|
||||
"name": "testImportProject",
|
||||
"displayName": "testImportProject",
|
||||
"path": "/testImportProject",
|
||||
"description": "someDescription",
|
||||
"type": "testImportProjectType",
|
||||
"mixins": [],
|
||||
"attributes": {
|
||||
"new_test_attribute": [
|
||||
"some_attribute_value"
|
||||
]
|
||||
},
|
||||
"modules": [],
|
||||
"problems": [],
|
||||
"source": {
|
||||
"type": "importType",
|
||||
"location": "someLocation",
|
||||
"parameters": {}
|
||||
},
|
||||
"commands": [],
|
||||
"links": []
|
||||
}
|
||||
]
|
||||
|
|
@ -12,7 +12,7 @@ package org.eclipse.che.api.project.templates.shared.dto;
|
|||
|
||||
import org.eclipse.che.api.core.rest.shared.dto.Link;
|
||||
import org.eclipse.che.api.machine.shared.dto.CommandDto;
|
||||
import org.eclipse.che.api.workspace.shared.dto.ProjectConfigDto;
|
||||
import org.eclipse.che.api.workspace.shared.dto.NewProjectConfigDto;
|
||||
import org.eclipse.che.api.workspace.shared.dto.ProjectProblemDto;
|
||||
import org.eclipse.che.api.workspace.shared.dto.SourceStorageDto;
|
||||
import org.eclipse.che.dto.shared.DTO;
|
||||
|
|
@ -110,4 +110,16 @@ public interface ProjectTemplateDescriptor {
|
|||
void setTags(List<String> tags);
|
||||
|
||||
ProjectTemplateDescriptor withTags(List<String> tags);
|
||||
|
||||
List<NewProjectConfigDto> getProjects();
|
||||
|
||||
void setProjects(List<NewProjectConfigDto> projects);
|
||||
|
||||
ProjectTemplateDescriptor withProjects(List<NewProjectConfigDto> projects);
|
||||
|
||||
Map<String, String> getOptions();
|
||||
|
||||
void setOptions(Map<String, String> options);
|
||||
|
||||
ProjectTemplateDescriptor withOptions(Map<String, String> options);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,65 @@
|
|||
/*******************************************************************************
|
||||
* Copyright (c) 2012-2016 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.workspace.shared.dto;
|
||||
|
||||
import org.eclipse.che.api.core.factory.FactoryParameter;
|
||||
import org.eclipse.che.api.core.model.project.NewProjectConfig;
|
||||
import org.eclipse.che.api.core.rest.shared.dto.Link;
|
||||
import org.eclipse.che.dto.shared.DTO;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import static org.eclipse.che.api.core.factory.FactoryParameter.Obligation.OPTIONAL;
|
||||
|
||||
/**
|
||||
* Data transfer object (DTO) for creating of project.
|
||||
*
|
||||
* @author Roman Nikitenko
|
||||
*/
|
||||
@DTO
|
||||
public interface NewProjectConfigDto extends ProjectConfigDto, NewProjectConfig {
|
||||
@Override
|
||||
@FactoryParameter(obligation = OPTIONAL)
|
||||
String getName();
|
||||
|
||||
@Override
|
||||
@FactoryParameter(obligation = OPTIONAL)
|
||||
String getType();
|
||||
|
||||
@Override
|
||||
@FactoryParameter(obligation = OPTIONAL)
|
||||
SourceStorageDto getSource();
|
||||
|
||||
@Override
|
||||
@FactoryParameter(obligation = OPTIONAL)
|
||||
Map<String, String> getOptions();
|
||||
|
||||
NewProjectConfigDto withName(String name);
|
||||
|
||||
NewProjectConfigDto withPath(String path);
|
||||
|
||||
NewProjectConfigDto withDescription(String description);
|
||||
|
||||
NewProjectConfigDto withType(String type);
|
||||
|
||||
NewProjectConfigDto withMixins(List<String> mixins);
|
||||
|
||||
NewProjectConfigDto withAttributes(Map<String, List<String>> attributes);
|
||||
|
||||
NewProjectConfigDto withSource(SourceStorageDto source);
|
||||
|
||||
NewProjectConfigDto withLinks(List<Link> links);
|
||||
|
||||
NewProjectConfigDto withProblems(List<ProjectProblemDto> problems);
|
||||
|
||||
NewProjectConfigDto withOptions(Map<String, String> options);
|
||||
}
|
||||
Loading…
Reference in New Issue