CHE-7010: Add volumes into machine model object

Signed-off-by: Oleksandr Garagatyi <ogaragat@redhat.com>
6.19.x
Oleksandr Garagatyi 2017-11-17 15:49:22 +02:00
parent 2598754ce6
commit ba7a1e2e51
24 changed files with 447 additions and 14 deletions

View File

@ -30,6 +30,7 @@
<class>org.eclipse.che.api.workspace.server.model.impl.ProjectConfigImpl$Attribute</class>
<class>org.eclipse.che.api.workspace.server.model.impl.SourceStorageImpl</class>
<class>org.eclipse.che.api.workspace.server.model.impl.ServerConfigImpl</class>
<class>org.eclipse.che.api.workspace.server.model.impl.VolumeImpl</class>
<class>org.eclipse.che.api.workspace.server.model.impl.stack.StackImpl</class>
<class>org.eclipse.che.api.workspace.server.model.impl.CommandImpl</class>

View File

@ -44,4 +44,7 @@ public interface MachineConfig {
/** Returns attributes of resources of machine. */
Map<String, String> getAttributes();
/** Returns volumes of machine */
Map<String, ? extends Volume> getVolumes();
}

View File

@ -0,0 +1,22 @@
/*
* Copyright (c) 2012-2017 Red Hat, Inc.
* 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:
* Red Hat, Inc. - initial API and implementation
*/
package org.eclipse.che.api.core.model.workspace.config;
/**
* Machine volume configuration.
*
* @author Alexander Garagatyi
*/
public interface Volume {
/** Mount path of the volume in the machine */
String getPath();
}

View File

@ -17,6 +17,7 @@ import java.util.Map;
import java.util.stream.Collectors;
import org.eclipse.che.api.core.model.workspace.config.MachineConfig;
import org.eclipse.che.api.core.model.workspace.config.ServerConfig;
import org.eclipse.che.api.core.model.workspace.config.Volume;
public class MachineConfigImpl implements MachineConfig {
@ -24,12 +25,14 @@ public class MachineConfigImpl implements MachineConfig {
private Map<String, String> env;
private Map<String, String> attributes;
private Map<String, ServerConfigImpl> servers;
private Map<String, VolumeImpl> volumes;
public MachineConfigImpl(
List<String> installers,
Map<String, ? extends ServerConfig> servers,
Map<String, String> env,
Map<String, String> attributes) {
Map<String, String> attributes,
Map<String, ? extends Volume> volumes) {
if (installers != null) {
this.installers = new ArrayList<>(installers);
}
@ -48,10 +51,23 @@ public class MachineConfigImpl implements MachineConfig {
if (attributes != null) {
this.attributes = new HashMap<>(attributes);
}
if (volumes != null) {
this.volumes =
volumes
.entrySet()
.stream()
.collect(
Collectors.toMap(Map.Entry::getKey, entry -> new VolumeImpl(entry.getValue())));
}
}
public MachineConfigImpl(MachineConfig machine) {
this(machine.getInstallers(), machine.getServers(), machine.getEnv(), machine.getAttributes());
this(
machine.getInstallers(),
machine.getServers(),
machine.getEnv(),
machine.getAttributes(),
machine.getVolumes());
}
@Override
@ -86,6 +102,14 @@ public class MachineConfigImpl implements MachineConfig {
return attributes;
}
@Override
public Map<String, VolumeImpl> getVolumes() {
if (volumes == null) {
volumes = new HashMap<>();
}
return volumes;
}
@Override
public boolean equals(Object obj) {
if (this == obj) {
@ -98,7 +122,8 @@ public class MachineConfigImpl implements MachineConfig {
return getInstallers().equals(that.getInstallers())
&& getEnv().equals(that.getEnv())
&& getAttributes().equals(that.getAttributes())
&& getServers().equals(that.getServers());
&& getServers().equals(that.getServers())
&& getVolumes().equals(that.getVolumes());
}
@Override
@ -108,6 +133,7 @@ public class MachineConfigImpl implements MachineConfig {
hash = 31 * hash + getEnv().hashCode();
hash = 31 * hash + getAttributes().hashCode();
hash = 31 * hash + getServers().hashCode();
hash = 31 * hash + getVolumes().hashCode();
return hash;
}
@ -122,6 +148,8 @@ public class MachineConfigImpl implements MachineConfig {
+ attributes
+ ", servers="
+ servers
+ ", volumes="
+ volumes
+ '}';
}
}

View File

@ -0,0 +1,56 @@
/*
* Copyright (c) 2012-2017 Red Hat, Inc.
* 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:
* Red Hat, Inc. - initial API and implementation
*/
package org.eclipse.che.ide.api.workspace.model;
import java.util.Objects;
import org.eclipse.che.api.core.model.workspace.config.Volume;
/** @author Alexander Garagatyi */
public class VolumeImpl implements Volume {
private final String path;
public VolumeImpl(String path) {
this.path = path;
}
public VolumeImpl(Volume value) {
path = value.getPath();
}
@Override
public String getPath() {
return path;
}
@Override
public boolean equals(Object obj) {
if (this == obj) {
return true;
}
if (!(obj instanceof VolumeImpl)) {
return false;
}
final VolumeImpl that = (VolumeImpl) obj;
return Objects.equals(path, that.path);
}
@Override
public int hashCode() {
int hash = 7;
hash = 31 * hash + Objects.hashCode(path);
return hash;
}
@Override
public String toString() {
return "VolumeImpl{" + "path='" + path + '\'' + '}';
}
}

View File

@ -29,6 +29,7 @@
<class>org.eclipse.che.api.workspace.server.model.impl.ProjectConfigImpl$Attribute</class>
<class>org.eclipse.che.api.workspace.server.model.impl.SourceStorageImpl</class>
<class>org.eclipse.che.api.workspace.server.model.impl.ServerConfigImpl</class>
<class>org.eclipse.che.api.workspace.server.model.impl.VolumeImpl</class>
<class>org.eclipse.che.api.workspace.server.model.impl.stack.StackImpl</class>
<class>org.eclipse.che.api.workspace.server.model.impl.CommandImpl</class>

View File

@ -30,6 +30,7 @@
<class>org.eclipse.che.api.workspace.server.model.impl.SourceStorageImpl</class>
<class>org.eclipse.che.api.workspace.server.model.impl.ServerConfigImpl</class>
<class>org.eclipse.che.api.workspace.server.model.impl.stack.StackImpl</class>
<class>org.eclipse.che.api.workspace.server.model.impl.VolumeImpl</class>
<class>org.eclipse.che.api.workspace.server.model.impl.CommandImpl</class>
<class>org.eclipse.che.workspace.infrastructure.docker.snapshot.MachineSourceImpl</class>

View File

@ -23,6 +23,7 @@ import org.eclipse.che.api.workspace.server.model.impl.ProjectConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.RecipeImpl;
import org.eclipse.che.api.workspace.server.model.impl.ServerConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.SourceStorageImpl;
import org.eclipse.che.api.workspace.server.model.impl.VolumeImpl;
import org.eclipse.che.api.workspace.server.model.impl.WorkspaceConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.WorkspaceImpl;
import org.eclipse.che.api.workspace.server.model.impl.stack.StackImpl;
@ -75,7 +76,8 @@ public class WorkspaceTckModule extends TckModule {
ServerConfigImpl.class,
StackImpl.class,
CommandImpl.class,
RecipeImpl.class)
RecipeImpl.class,
VolumeImpl.class)
.addEntityClass(
"org.eclipse.che.api.workspace.server.model.impl.ProjectConfigImpl$Attribute")
.setExceptionHandler(H2ExceptionHandler.class)

View File

@ -20,6 +20,7 @@ import org.eclipse.che.api.workspace.server.model.impl.ProjectConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.RecipeImpl;
import org.eclipse.che.api.workspace.server.model.impl.ServerConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.SourceStorageImpl;
import org.eclipse.che.api.workspace.server.model.impl.VolumeImpl;
import org.eclipse.che.api.workspace.server.model.impl.WorkspaceConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.WorkspaceImpl;
import org.eclipse.che.api.workspace.server.model.impl.stack.StackImpl;
@ -67,7 +68,8 @@ public class JpaTckModule extends TckModule {
ServerConfigImpl.class,
StackImpl.class,
CommandImpl.class,
RecipeImpl.class)
RecipeImpl.class,
VolumeImpl.class)
.addEntityClass(
"org.eclipse.che.api.workspace.server.model.impl.ProjectConfigImpl$Attribute")
.setExceptionHandler(H2ExceptionHandler.class)

View File

@ -29,6 +29,7 @@ import org.eclipse.che.api.workspace.server.model.impl.ProjectConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.RecipeImpl;
import org.eclipse.che.api.workspace.server.model.impl.ServerConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.SourceStorageImpl;
import org.eclipse.che.api.workspace.server.model.impl.VolumeImpl;
import org.eclipse.che.api.workspace.server.model.impl.WorkspaceConfigImpl;
import org.eclipse.che.commons.test.db.H2DBTestServer;
import org.eclipse.che.commons.test.db.H2JpaCleaner;
@ -75,7 +76,8 @@ public class FactoryTckModule extends TckModule {
MachineConfigImpl.class,
SourceStorageImpl.class,
ServerConfigImpl.class,
CommandImpl.class)
CommandImpl.class,
VolumeImpl.class)
.addEntityClass(
"org.eclipse.che.api.workspace.server.model.impl.ProjectConfigImpl$Attribute")
.setExceptionHandler(H2ExceptionHandler.class)

View File

@ -52,4 +52,12 @@ public interface MachineConfigDto extends MachineConfig {
void setAttributes(Map<String, String> attributes);
MachineConfigDto withAttributes(Map<String, String> attributes);
@Override
@FactoryParameter(obligation = OPTIONAL)
Map<String, VolumeDto> getVolumes();
void setVolumes(Map<String, VolumeDto> volumes);
MachineConfigDto withVolumes(Map<String, VolumeDto> volumes);
}

View File

@ -0,0 +1,25 @@
/*
* Copyright (c) 2012-2017 Red Hat, Inc.
* 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:
* Red Hat, Inc. - initial API and implementation
*/
package org.eclipse.che.api.workspace.shared.dto;
import org.eclipse.che.api.core.model.workspace.config.Volume;
import org.eclipse.che.dto.shared.DTO;
/** @author Alexander Garagatyi */
@DTO
public interface VolumeDto extends Volume {
@Override
String getPath();
void setPath(String path);
VolumeDto withPath(String path);
}

View File

@ -26,6 +26,7 @@ import org.eclipse.che.api.core.model.workspace.config.MachineConfig;
import org.eclipse.che.api.core.model.workspace.config.ProjectConfig;
import org.eclipse.che.api.core.model.workspace.config.ServerConfig;
import org.eclipse.che.api.core.model.workspace.config.SourceStorage;
import org.eclipse.che.api.core.model.workspace.config.Volume;
import org.eclipse.che.api.core.model.workspace.runtime.Machine;
import org.eclipse.che.api.core.model.workspace.runtime.RuntimeIdentity;
import org.eclipse.che.api.core.model.workspace.runtime.Server;
@ -41,6 +42,7 @@ import org.eclipse.che.api.workspace.shared.dto.RuntimeIdentityDto;
import org.eclipse.che.api.workspace.shared.dto.ServerConfigDto;
import org.eclipse.che.api.workspace.shared.dto.ServerDto;
import org.eclipse.che.api.workspace.shared.dto.SourceStorageDto;
import org.eclipse.che.api.workspace.shared.dto.VolumeDto;
import org.eclipse.che.api.workspace.shared.dto.WorkspaceConfigDto;
import org.eclipse.che.api.workspace.shared.dto.WorkspaceDto;
import org.eclipse.che.api.workspace.shared.dto.stack.StackComponentDto;
@ -204,6 +206,14 @@ public final class DtoConverter {
if (machine.getAttributes() != null) {
machineDto.setAttributes(machine.getAttributes());
}
if (machine.getVolumes() != null) {
machineDto.setVolumes(
machine
.getVolumes()
.entrySet()
.stream()
.collect(toMap(Map.Entry::getKey, entry -> asDto(entry.getValue()))));
}
return machineDto;
}
@ -254,5 +264,10 @@ public final class DtoConverter {
.withOwner(identity.getOwner());
}
/** Converts {@link Volume} to {@link VolumeDto}. */
public static VolumeDto asDto(Volume volume) {
return newDto(VolumeDto.class).withPath(volume.getPath());
}
private DtoConverter() {}
}

View File

@ -28,6 +28,7 @@ import org.eclipse.che.api.core.model.workspace.config.Command;
import org.eclipse.che.api.core.model.workspace.config.Environment;
import org.eclipse.che.api.core.model.workspace.config.MachineConfig;
import org.eclipse.che.api.core.model.workspace.config.Recipe;
import org.eclipse.che.api.core.model.workspace.config.Volume;
import org.eclipse.che.api.workspace.server.spi.InfrastructureException;
/**
@ -45,6 +46,9 @@ public class WorkspaceValidator {
private static final Pattern WS_NAME =
Pattern.compile("[a-zA-Z0-9][-_.a-zA-Z0-9]{1,98}[a-zA-Z0-9]");
private static final Pattern VOLUME_NAME = Pattern.compile("[a-z][a-z0-9]{1,18}");
private static final Pattern VOLUME_PATH = Pattern.compile("/.+");
private final WorkspaceRuntimes runtimes;
@Inject
@ -146,6 +150,27 @@ public class WorkspaceValidator {
memoryAttribute, MEMORY_LIMIT_ATTRIBUTE, name));
}
}
for (Entry<String, ? extends Volume> volumeEntry : machine.getVolumes().entrySet()) {
String volumeName = volumeEntry.getKey();
check(
VOLUME_NAME.matcher(volumeName).matches(),
"Volume name '%s' in machine '%s' is invalid",
volumeName,
name);
Volume volume = volumeEntry.getValue();
check(
volume != null && !isNullOrEmpty(volume.getPath()),
"Path of volume '%s' in machine '%s' is invalid. It should not be empty",
volumeName,
name);
check(
VOLUME_PATH.matcher(volume.getPath()).matches(),
"Path '%s' of volume '%s' in machine '%s' is invalid. It should be absolute",
volume.getPath(),
volumeName,
name);
}
}
/**

View File

@ -30,6 +30,7 @@ import javax.persistence.OneToMany;
import javax.persistence.Table;
import org.eclipse.che.api.core.model.workspace.config.MachineConfig;
import org.eclipse.che.api.core.model.workspace.config.ServerConfig;
import org.eclipse.che.api.core.model.workspace.config.Volume;
/** @author Alexander Garagatyi */
@Entity(name = "ExternalMachine")
@ -72,13 +73,19 @@ public class MachineConfigImpl implements MachineConfig {
@MapKeyColumn(name = "servers_key")
private Map<String, ServerConfigImpl> servers;
@OneToMany(cascade = CascadeType.ALL, orphanRemoval = true, fetch = FetchType.EAGER)
@JoinColumn(name = "machine_id")
@MapKeyColumn(name = "name")
private Map<String, VolumeImpl> volumes;
public MachineConfigImpl() {}
public MachineConfigImpl(
List<String> installers,
Map<String, ? extends ServerConfig> servers,
Map<String, String> env,
Map<String, String> attributes) {
Map<String, String> attributes,
Map<String, ? extends Volume> volumes) {
if (installers != null) {
this.installers = new ArrayList<>(installers);
}
@ -97,10 +104,23 @@ public class MachineConfigImpl implements MachineConfig {
if (attributes != null) {
this.attributes = new HashMap<>(attributes);
}
if (volumes != null) {
this.volumes =
volumes
.entrySet()
.stream()
.collect(
Collectors.toMap(Map.Entry::getKey, entry -> new VolumeImpl(entry.getValue())));
}
}
public MachineConfigImpl(MachineConfig machine) {
this(machine.getInstallers(), machine.getServers(), machine.getEnv(), machine.getAttributes());
this(
machine.getInstallers(),
machine.getServers(),
machine.getEnv(),
machine.getAttributes(),
machine.getVolumes());
}
@Override
@ -171,6 +191,23 @@ public class MachineConfigImpl implements MachineConfig {
return this;
}
@Override
public Map<String, VolumeImpl> getVolumes() {
if (volumes == null) {
volumes = new HashMap<>();
}
return volumes;
}
public void setVolumes(Map<String, VolumeImpl> volumes) {
this.volumes = volumes;
}
public MachineConfigImpl withVolumes(Map<String, VolumeImpl> volumes) {
this.volumes = volumes;
return this;
}
@Override
public boolean equals(Object obj) {
if (this == obj) {
@ -184,7 +221,8 @@ public class MachineConfigImpl implements MachineConfig {
&& getInstallers().equals(that.getInstallers())
&& getEnv().equals(that.getEnv())
&& getAttributes().equals(that.getAttributes())
&& getServers().equals(that.getServers());
&& getServers().equals(that.getServers())
&& getVolumes().equals(that.getVolumes());
}
@Override
@ -195,6 +233,7 @@ public class MachineConfigImpl implements MachineConfig {
hash = 31 * hash + getEnv().hashCode();
hash = 31 * hash + getAttributes().hashCode();
hash = 31 * hash + getServers().hashCode();
hash = 31 * hash + getVolumes().hashCode();
return hash;
}
@ -211,6 +250,8 @@ public class MachineConfigImpl implements MachineConfig {
+ attributes
+ ", servers="
+ servers
+ ", volumes="
+ volumes
+ '}';
}
}

View File

@ -0,0 +1,75 @@
/*
* Copyright (c) 2012-2017 Red Hat, Inc.
* 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:
* Red Hat, Inc. - initial API and implementation
*/
package org.eclipse.che.api.workspace.server.model.impl;
import java.util.Objects;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.Table;
import org.eclipse.che.api.core.model.workspace.config.Volume;
/** @author Alexander Garagatyi */
@Entity(name = "MachineVolume")
@Table(name = "machine_volume")
public class VolumeImpl implements Volume {
@Id
@GeneratedValue
@Column(name = "id")
private Long id;
@Column(name = "path")
private String path;
public VolumeImpl() {}
public VolumeImpl(Volume value) {
path = value.getPath();
}
@Override
public String getPath() {
return path;
}
public void setPath(String path) {
this.path = path;
}
public VolumeImpl withPath(String path) {
this.path = path;
return this;
}
@Override
public boolean equals(Object o) {
if (this == o) {
return true;
}
if (!(o instanceof VolumeImpl)) {
return false;
}
VolumeImpl volume = (VolumeImpl) o;
return Objects.equals(id, volume.id) && Objects.equals(getPath(), volume.getPath());
}
@Override
public int hashCode() {
return Objects.hash(id, getPath());
}
@Override
public String toString() {
return "VolumeImpl{" + "id=" + id + ", path='" + path + '\'' + '}';
}
}

View File

@ -558,7 +558,8 @@ public class WorkspaceManagerTest {
singletonList("org.eclipse.che.ws-agent"),
null,
singletonMap("CHE_ENV", "value"),
singletonMap(MEMORY_LIMIT_ATTRIBUTE, "10000"));
singletonMap(MEMORY_LIMIT_ATTRIBUTE, "10000"),
emptyMap());
EnvironmentImpl environment =
new EnvironmentImpl(
new RecipeImpl("type", "contentType", "content", null),

View File

@ -915,7 +915,8 @@ public class WorkspaceServiceTest {
singletonList("org.eclipse.che.ws-agent"),
null,
singletonMap("CHE_ENV", "value"),
singletonMap(MEMORY_LIMIT_ATTRIBUTE, "10000"));
singletonMap(MEMORY_LIMIT_ATTRIBUTE, "10000"),
emptyMap());
return DtoConverter.asDto(
new EnvironmentImpl(

View File

@ -27,6 +27,7 @@ import org.eclipse.che.api.workspace.shared.dto.EnvironmentDto;
import org.eclipse.che.api.workspace.shared.dto.MachineConfigDto;
import org.eclipse.che.api.workspace.shared.dto.RecipeDto;
import org.eclipse.che.api.workspace.shared.dto.ServerConfigDto;
import org.eclipse.che.api.workspace.shared.dto.VolumeDto;
import org.eclipse.che.api.workspace.shared.dto.WorkspaceConfigDto;
import org.mockito.InjectMocks;
import org.mockito.Mock;
@ -242,6 +243,89 @@ public class WorkspaceValidatorTest {
wsValidator.validateConfig(config);
}
@Test(
expectedExceptions = ValidationException.class,
expectedExceptionsMessageRegExp = "Volume name '.*' in machine '.*' is invalid",
dataProvider = "illegalVolumeNameProvider"
)
public void shouldFailValidationIfVolumeNameDoesNotMatchCriteria(String volumeName)
throws Exception {
final WorkspaceConfigDto config = createConfig();
EnvironmentDto env = config.getEnvironments().values().iterator().next();
MachineConfigDto machine = env.getMachines().values().iterator().next();
machine.getVolumes().put(volumeName, newDto(VolumeDto.class).withPath("/path"));
wsValidator.validateConfig(config);
}
@DataProvider(name = "illegalVolumeNameProvider")
public static Object[][] illegalVolumeNameProvider() {
return new Object[][] {
{"0volume"},
{"CAPITAL"},
{"veryveryveryveryveryveryverylongname"},
{"volume/name"},
{"volume_name"},
{"volume-name"}
};
}
@Test(
expectedExceptions = ValidationException.class,
expectedExceptionsMessageRegExp =
"Path of volume '.*' in machine '.*' is invalid. It should not be empty"
)
public void shouldFailValidationIfVolumeValueIsEmpty() throws Exception {
final WorkspaceConfigDto config = createConfig();
EnvironmentDto env = config.getEnvironments().values().iterator().next();
MachineConfigDto machine = env.getMachines().values().iterator().next();
machine.getVolumes().put("volume1", null);
wsValidator.validateConfig(config);
}
@Test(
expectedExceptions = ValidationException.class,
expectedExceptionsMessageRegExp =
"Path of volume '.*' in machine '.*' is invalid. It should not be empty"
)
public void shouldFailValidationIfVolumePathIsEmpty() throws Exception {
final WorkspaceConfigDto config = createConfig();
EnvironmentDto env = config.getEnvironments().values().iterator().next();
MachineConfigDto machine = env.getMachines().values().iterator().next();
machine.getVolumes().put("volume1", newDto(VolumeDto.class).withPath(""));
wsValidator.validateConfig(config);
}
@Test(
expectedExceptions = ValidationException.class,
expectedExceptionsMessageRegExp =
"Path of volume '.*' in machine '.*' is invalid. It should not be empty"
)
public void shouldFailValidationIfVolumePathIsNull() throws Exception {
final WorkspaceConfigDto config = createConfig();
EnvironmentDto env = config.getEnvironments().values().iterator().next();
MachineConfigDto machine = env.getMachines().values().iterator().next();
machine.getVolumes().put("volume1", newDto(VolumeDto.class).withPath(null));
wsValidator.validateConfig(config);
}
@Test(
expectedExceptions = ValidationException.class,
expectedExceptionsMessageRegExp =
"Path '.*' of volume '.*' in machine '.*' is invalid. It should be absolute"
)
public void shouldFailValidationIfVolumePathIsNotAbsolute() throws Exception {
final WorkspaceConfigDto config = createConfig();
EnvironmentDto env = config.getEnvironments().values().iterator().next();
MachineConfigDto machine = env.getMachines().values().iterator().next();
machine.getVolumes().put("volume1", newDto(VolumeDto.class).withPath("not/absolute/path"));
wsValidator.validateConfig(config);
}
private static WorkspaceConfigDto createConfig() {
final WorkspaceConfigDto workspaceConfigDto =
newDto(WorkspaceConfigDto.class).withName("ws-name").withDefaultEnv("dev-env");

View File

@ -20,6 +20,7 @@ import org.eclipse.che.api.workspace.server.model.impl.ProjectConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.RecipeImpl;
import org.eclipse.che.api.workspace.server.model.impl.ServerConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.SourceStorageImpl;
import org.eclipse.che.api.workspace.server.model.impl.VolumeImpl;
import org.eclipse.che.api.workspace.server.model.impl.WorkspaceConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.WorkspaceImpl;
import org.eclipse.che.api.workspace.server.model.impl.stack.StackImpl;
@ -61,7 +62,8 @@ public class WorkspaceTckModule extends TckModule {
ServerConfigImpl.class,
StackImpl.class,
CommandImpl.class,
RecipeImpl.class)
RecipeImpl.class,
VolumeImpl.class)
.addEntityClass(
"org.eclipse.che.api.workspace.server.model.impl.ProjectConfigImpl$Attribute")
.setExceptionHandler(H2ExceptionHandler.class)

View File

@ -46,6 +46,7 @@ import org.eclipse.che.api.workspace.server.model.impl.ProjectConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.RecipeImpl;
import org.eclipse.che.api.workspace.server.model.impl.ServerConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.SourceStorageImpl;
import org.eclipse.che.api.workspace.server.model.impl.VolumeImpl;
import org.eclipse.che.api.workspace.server.model.impl.WorkspaceConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.WorkspaceImpl;
import org.eclipse.che.api.workspace.server.spi.WorkspaceDao;
@ -554,6 +555,12 @@ public class WorkspaceDaoTest {
exMachine1.setInstallers(ImmutableList.of("agent5", "agent4"));
exMachine1.setAttributes(singletonMap("att1", "val"));
exMachine1.setEnv(ImmutableMap.of("CHE_ENV1", "value", "CHE_ENV2", "value"));
exMachine1.setVolumes(
ImmutableMap.of(
"vol1",
new VolumeImpl().withPath("/path/1"),
"vol2",
new VolumeImpl().withPath("/path/2")));
final MachineConfigImpl exMachine2 = new MachineConfigImpl();
final ServerConfigImpl serverConf3 = new ServerConfigImpl("2333", "https", "path3");
@ -562,6 +569,7 @@ public class WorkspaceDaoTest {
exMachine2.setInstallers(ImmutableList.of("agent2", "agent1"));
exMachine2.setAttributes(singletonMap("att1", "val"));
exMachine2.setEnv(singletonMap("CHE_ENV2", "value"));
exMachine2.setVolumes(ImmutableMap.of("vol2", new VolumeImpl().withPath("/path/2")));
final MachineConfigImpl exMachine3 = new MachineConfigImpl();
final ServerConfigImpl serverConf5 = new ServerConfigImpl("2333", "https", "path5");
@ -569,6 +577,7 @@ public class WorkspaceDaoTest {
exMachine3.setInstallers(ImmutableList.of("agent6", "agent2"));
exMachine3.setAttributes(singletonMap("att1", "val"));
exMachine3.setEnv(singletonMap("CHE_ENV3", "value"));
exMachine3.setVolumes(ImmutableMap.of("vol3", new VolumeImpl().withPath("/path/3")));
// Environments
final RecipeImpl recipe1 = new RecipeImpl();

View File

@ -0,0 +1,25 @@
--
-- Copyright (c) 2012-2017 Red Hat, Inc.
-- 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:
-- Red Hat, Inc. - initial API and implementation
--
-- Machine volumes configuration -----------------------------------------------
CREATE TABLE machine_volume (
id BIGINT NOT NULL,
name VARCHAR(255),
path VARCHAR(255) NOT NULL,
machine_id BIGINT,
PRIMARY KEY (id)
);
--constraints
ALTER TABLE machine_volume ADD CONSTRAINT fk_machine_volume_id FOREIGN KEY (machine_id) REFERENCES externalmachine (id);
--------------------------------------------------------------------------------
--indexes
CREATE INDEX index_machine_volume_machine_id ON machine_volume (machine_id);

View File

@ -71,6 +71,7 @@ import org.eclipse.che.api.workspace.server.model.impl.ProjectConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.RecipeImpl;
import org.eclipse.che.api.workspace.server.model.impl.ServerConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.SourceStorageImpl;
import org.eclipse.che.api.workspace.server.model.impl.VolumeImpl;
import org.eclipse.che.api.workspace.server.model.impl.WorkspaceConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.WorkspaceImpl;
import org.eclipse.che.api.workspace.server.model.impl.stack.StackImpl;
@ -160,7 +161,8 @@ public class CascadeRemovalTest {
StackImpl.class,
CommandImpl.class,
RecipeImpl.class,
SshPairImpl.class)
SshPairImpl.class,
VolumeImpl.class)
.addEntityClass(
"org.eclipse.che.api.workspace.server.model.impl.ProjectConfigImpl$Attribute")
.setExceptionHandler(H2ExceptionHandler.class)

View File

@ -50,6 +50,7 @@ import org.eclipse.che.api.workspace.server.model.impl.ProjectConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.RecipeImpl;
import org.eclipse.che.api.workspace.server.model.impl.ServerConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.SourceStorageImpl;
import org.eclipse.che.api.workspace.server.model.impl.VolumeImpl;
import org.eclipse.che.api.workspace.server.model.impl.WorkspaceConfigImpl;
import org.eclipse.che.api.workspace.server.model.impl.WorkspaceImpl;
import org.eclipse.che.api.workspace.server.model.impl.stack.StackImpl;
@ -116,7 +117,8 @@ public class PostgreSqlTckModule extends TckModule {
CommandImpl.class,
SshPairImpl.class,
InstallerImpl.class,
InstallerServerConfigImpl.class)
InstallerServerConfigImpl.class,
VolumeImpl.class)
.addEntityClass(
"org.eclipse.che.api.workspace.server.model.impl.ProjectConfigImpl$Attribute")
.build());