summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorShireesh Anjal <shireesh@gluster.com>2011-03-23 19:24:44 +0530
committerShireesh Anjal <shireesh@gluster.com>2011-03-23 19:24:44 +0530
commit0766ea8fcf31990d07431521c7fc7db7e1acf762 (patch)
tree21274f8d8b96d3404609b215824e3d9a786b75f9
parente4868a85da0ef3db927314e4d724a305cfbda8ae (diff)
Create Volume
-rw-r--r--com.gluster.storage.management.client/src/com/gluster/storage/management/client/GlusterDataModelManager.java12
-rw-r--r--com.gluster.storage.management.client/src/com/gluster/storage/management/client/RunningTaskClient.java2
-rw-r--r--com.gluster.storage.management.client/src/com/gluster/storage/management/client/VolumesClient.java12
-rw-r--r--com.gluster.storage.management.core/src/com/gluster/storage/management/core/model/Cluster.java4
-rw-r--r--com.gluster.storage.management.core/src/com/gluster/storage/management/core/model/ClusterListener.java2
-rw-r--r--com.gluster.storage.management.core/src/com/gluster/storage/management/core/model/DefaultClusterListener.java4
-rw-r--r--com.gluster.storage.management.core/src/com/gluster/storage/management/core/utils/GlusterUtil.java64
-rw-r--r--com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/CreateVolumeDisksPage.java141
-rw-r--r--com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/CreateVolumePage1.java76
-rw-r--r--com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/CreateVolumeWizard.java24
-rw-r--r--com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/SelectDisksDialog.java22
-rw-r--r--com.gluster.storage.management.server/src/com/gluster/storage/management/server/resources/VolumesResource.java58
12 files changed, 330 insertions, 91 deletions
diff --git a/com.gluster.storage.management.client/src/com/gluster/storage/management/client/GlusterDataModelManager.java b/com.gluster.storage.management.client/src/com/gluster/storage/management/client/GlusterDataModelManager.java
index 01ba6468..4d594f36 100644
--- a/com.gluster.storage.management.client/src/com/gluster/storage/management/client/GlusterDataModelManager.java
+++ b/com.gluster.storage.management.client/src/com/gluster/storage/management/client/GlusterDataModelManager.java
@@ -135,13 +135,23 @@ public class GlusterDataModelManager {
}
}
- private Volume addVolume(List<Volume> volumes, String name, Cluster cluster, VOLUME_TYPE volumeType,
+ public Volume addVolume(List<Volume> volumes, String name, Cluster cluster, VOLUME_TYPE volumeType,
TRANSPORT_TYPE transportType, VOLUME_STATUS status) {
Volume volume = new Volume(name, cluster, volumeType, transportType, status);
volumes.add(volume);
return volume;
}
+
+ public void addVolume(Volume volume ) {
+ Cluster cluster = (Cluster)model.getChildren().get(0);
+ cluster.addVolume(volume);
+
+ for(ClusterListener listener : listeners) {
+ listener.volumeCreated(volume);
+ }
+ }
+
private void initializeVolumes(Cluster cluster) {
List<Volume> volumes = new ArrayList<Volume>();
diff --git a/com.gluster.storage.management.client/src/com/gluster/storage/management/client/RunningTaskClient.java b/com.gluster.storage.management.client/src/com/gluster/storage/management/client/RunningTaskClient.java
index d2305272..9309cdc8 100644
--- a/com.gluster.storage.management.client/src/com/gluster/storage/management/client/RunningTaskClient.java
+++ b/com.gluster.storage.management.client/src/com/gluster/storage/management/client/RunningTaskClient.java
@@ -8,7 +8,7 @@ import com.gluster.storage.management.core.model.RunningTask;
import com.gluster.storage.management.core.model.RunningTaskListResponse;
public class RunningTaskClient extends AbstractClient {
- private static final String RESOURCE_NAME = RESTConstants.PATH_PARAM_RUNNING_TASKS;
+ private static final String RESOURCE_NAME = RESTConstants.RESOURCE_PATH_RUNNING_TASKS;
public RunningTaskClient(String securityToken) {
super(securityToken);
diff --git a/com.gluster.storage.management.client/src/com/gluster/storage/management/client/VolumesClient.java b/com.gluster.storage.management.client/src/com/gluster/storage/management/client/VolumesClient.java
index f1abb5c1..03e83a31 100644
--- a/com.gluster.storage.management.client/src/com/gluster/storage/management/client/VolumesClient.java
+++ b/com.gluster.storage.management.client/src/com/gluster/storage/management/client/VolumesClient.java
@@ -32,7 +32,6 @@ import com.gluster.storage.management.core.model.Volume;
import com.sun.jersey.api.representation.Form;
public class VolumesClient extends AbstractClient {
- private static final String RESOURCE_NAME = "/cluster/volumes"; // TODO: move to common place
public VolumesClient(String securityToken) {
super(securityToken);
@@ -40,13 +39,17 @@ public class VolumesClient extends AbstractClient {
@Override
public String getResourceName() {
- return RESOURCE_NAME;
+ return RESTConstants.RESOURCE_PATH_VOLUMES;
}
@SuppressWarnings("unchecked")
public Status createVolume(Volume volume) {
- GenericResponse<String> response = (GenericResponse<String>) postObject(GenericResponse.class, volume);
- return response.getStatus();
+ GenericResponse<String> createVolumeResponse = (GenericResponse<String>) postObject(GenericResponse.class, volume);
+
+ if (!createVolumeResponse.getStatus().isSuccess()) {
+ return (Status) createVolumeResponse.getStatus();
+ }
+ return (Status) createVolumeResponse.getStatus();
}
private Status performOperation(String volumeName, String operation) {
@@ -64,6 +67,7 @@ public class VolumesClient extends AbstractClient {
return performOperation(volumeName, RESTConstants.FORM_PARAM_VALUE_STOP);
}
+
public static void main(String[] args) {
UsersClient usersClient = new UsersClient();
if (usersClient.authenticate("gluster", "gluster")) {
diff --git a/com.gluster.storage.management.core/src/com/gluster/storage/management/core/model/Cluster.java b/com.gluster.storage.management.core/src/com/gluster/storage/management/core/model/Cluster.java
index 79a2b80e..65d5ebea 100644
--- a/com.gluster.storage.management.core/src/com/gluster/storage/management/core/model/Cluster.java
+++ b/com.gluster.storage.management.core/src/com/gluster/storage/management/core/model/Cluster.java
@@ -75,6 +75,10 @@ public class Cluster extends Entity {
this.volumes = volumes;
children.add(new EntityGroup<Volume>("Volumes", Volume.class, this, volumes));
}
+
+ public void addVolume(Volume volume) {
+ this.volumes.add(volume);
+ }
public Cluster(String name, Entity parent) {
super(name, parent);
diff --git a/com.gluster.storage.management.core/src/com/gluster/storage/management/core/model/ClusterListener.java b/com.gluster.storage.management.core/src/com/gluster/storage/management/core/model/ClusterListener.java
index 85cdd872..ce2752a4 100644
--- a/com.gluster.storage.management.core/src/com/gluster/storage/management/core/model/ClusterListener.java
+++ b/com.gluster.storage.management.core/src/com/gluster/storage/management/core/model/ClusterListener.java
@@ -38,4 +38,6 @@ public interface ClusterListener {
public void volumeRemoved(Volume volume);
public void volumeChanged(Volume volume, Event event);
+
+ public void volumeCreated(Volume volume);
}
diff --git a/com.gluster.storage.management.core/src/com/gluster/storage/management/core/model/DefaultClusterListener.java b/com.gluster.storage.management.core/src/com/gluster/storage/management/core/model/DefaultClusterListener.java
index bf76de43..eb974fd9 100644
--- a/com.gluster.storage.management.core/src/com/gluster/storage/management/core/model/DefaultClusterListener.java
+++ b/com.gluster.storage.management.core/src/com/gluster/storage/management/core/model/DefaultClusterListener.java
@@ -55,4 +55,8 @@ public class DefaultClusterListener implements ClusterListener {
@Override
public void discoveredServerRemoved(Server server) {
}
+
+ @Override
+ public void volumeCreated(Volume volume) {
+ }
}
diff --git a/com.gluster.storage.management.core/src/com/gluster/storage/management/core/utils/GlusterUtil.java b/com.gluster.storage.management.core/src/com/gluster/storage/management/core/utils/GlusterUtil.java
index 81208eff..7e2cfc31 100644
--- a/com.gluster.storage.management.core/src/com/gluster/storage/management/core/utils/GlusterUtil.java
+++ b/com.gluster.storage.management.core/src/com/gluster/storage/management/core/utils/GlusterUtil.java
@@ -24,8 +24,12 @@ import java.util.ArrayList;
import java.util.List;
import com.gluster.storage.management.core.constants.CoreConstants;
+import com.gluster.storage.management.core.model.Disk;
import com.gluster.storage.management.core.model.GlusterServer;
import com.gluster.storage.management.core.model.GlusterServer.SERVER_STATUS;
+import com.gluster.storage.management.core.model.Volume;
+import com.gluster.storage.management.core.model.Volume.TRANSPORT_TYPE;
+import com.gluster.storage.management.core.model.Volume.VOLUME_TYPE;
/**
*
@@ -131,6 +135,7 @@ public class GlusterUtil {
return processUtil.executeCommand("gluster", "peer", "probe", serverName);
}
+
public ProcessResult startVolume(String volumeName) {
return processUtil.executeCommand("gluster", "volume", "start", volumeName);
}
@@ -139,6 +144,65 @@ public class GlusterUtil {
return processUtil.executeCommand("gluster", "--mode=script", "volume", "stop", volumeName);
}
+ public ProcessResult createVolume(Volume volume) {
+ int count=1; // replica or stripe count
+ String volumeType = null;
+ VOLUME_TYPE volType = volume.getVolumeType();
+ if(volType == VOLUME_TYPE.DISTRIBUTED_MIRROR) {
+ volumeType = "replica";
+ count = 2;
+ } else if(volType == VOLUME_TYPE.DISTRIBUTED_STRIPE) {
+ volumeType = "stripe";
+ count = 4;
+ }
+
+ String transportTypeStr = null;
+ TRANSPORT_TYPE transportType = volume.getTransportType();
+ transportTypeStr = (transportType == TRANSPORT_TYPE.ETHERNET) ? "tcp" : "rdma";
+
+ List<String> command = new ArrayList<String>();
+ command.add("gluster");
+ command.add("volume");
+ command.add("create");
+ command.add(volume.getName());
+ if(volumeType != null) {
+ command.add(volumeType);
+ command.add("" + count);
+ }
+ command.add("transport");
+ command.add(transportTypeStr);
+ for(Disk disk : volume.getDisks()) {
+ command.add(getBrickNotation(volume, disk));
+ }
+ return processUtil.executeCommand(command);
+ }
+
+ public ProcessResult setOption(List<String> command) {
+ return processUtil.executeCommand(command);
+ }
+
+ public ProcessResult setVolumeAccessControl(Volume volume) {
+ List<String> command = new ArrayList<String>();
+ command.add("gluster");
+ command.add("volume");
+ command.add("set");
+ command.add(volume.getName());
+ command.add("auth.allow");
+ command.add(volume.getAccessControlList());
+ return setOption(command);
+ }
+
+ /**
+ * @param disk
+ * @return
+ */
+ private String getBrickNotation(Volume vol, Disk disk) {
+ // TODO: Figure out an appropriate directory INSIDE the DISK having given NAME (e.g. sda, sdb, etc)
+ // String dirName = "/export/" + vol.getName() + "/" + disk.getName();
+ String dirName = "/export/" + vol.getName() ;
+ return disk.getServerName() + ":" + dirName;
+ }
+
public static void main(String args[]) {
List<String> names = new GlusterUtil().getGlusterServerNames();
System.out.println(names);
diff --git a/com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/CreateVolumeDisksPage.java b/com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/CreateVolumeDisksPage.java
index ce6df74c..80811226 100644
--- a/com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/CreateVolumeDisksPage.java
+++ b/com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/CreateVolumeDisksPage.java
@@ -18,6 +18,7 @@
*******************************************************************************/
package com.gluster.storage.management.gui.dialogs;
+import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
@@ -25,11 +26,14 @@ import org.eclipse.jface.viewers.ITableLabelProvider;
import org.eclipse.swt.SWT;
import org.eclipse.swt.events.KeyAdapter;
import org.eclipse.swt.events.KeyEvent;
+import org.eclipse.swt.events.SelectionAdapter;
+import org.eclipse.swt.events.SelectionEvent;
import org.eclipse.swt.layout.GridData;
import org.eclipse.swt.layout.GridLayout;
import org.eclipse.swt.widgets.Button;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Label;
+import org.eclipse.swt.widgets.TableItem;
import org.eclipse.swt.widgets.Text;
import com.gluster.storage.management.core.model.Disk;
@@ -54,13 +58,19 @@ public class CreateVolumeDisksPage extends Composite {
private GUIHelper guiHelper = GUIHelper.getInstance();
private CustomTableDualListComposite<Disk> dualTableViewer;
private Text filterText;
+ // This list keeps track of the order of the disks as user changes the same by clicking on up/down arrow buttons
+ private List<Disk> chosenDisks = new ArrayList<Disk>();
private IRemovableContentProvider<Disk> chosenDisksContentProvider;
- public CreateVolumeDisksPage(final Composite parent, int style, List<Disk> disks) {
+ private Button btnUp;
+
+ private Button btnDown;
+
+ public CreateVolumeDisksPage(final Composite parent, int style, List<Disk> allDisks, List<Disk> selectedDisks) {
super(parent, style);
- createPage(disks);
+ createPage(allDisks, selectedDisks);
parent.layout();
}
@@ -85,13 +95,22 @@ public class CreateVolumeDisksPage extends Composite {
};
}
- private void createPage(List<Disk> disks) {
+ private int indexOf(List<Disk> disks, Disk searchDisk) {
+ for(Disk disk : disks) {
+ if(disk.getQualifiedName().equals(searchDisk.getQualifiedName())) {
+ return disks.indexOf(disk);
+ }
+ }
+ return -1;
+ }
+
+ private void createPage(List<Disk> allDisks, List<Disk> selectedDisks) {
setupPageLayout();
filterText = guiHelper.createFilterText(this);
new Label(this, SWT.NONE);
- createDualTableViewer(disks);
+ createDualTableViewer(allDisks, selectedDisks);
createFilter(filterText, false); // attach filter text to the dual table viewer for auto-filtering
Composite buttonContainer = new Composite(this, SWT.NONE);
@@ -100,15 +119,64 @@ public class CreateVolumeDisksPage extends Composite {
buttonContainerData.minimumWidth = 40;
buttonContainer.setLayoutData(buttonContainerData);
- Button btnUp = new Button(buttonContainer, SWT.TOGGLE);
+ btnUp = new Button(buttonContainer, SWT.TOGGLE);
GridData btnUpData = new GridData(SWT.LEFT, SWT.BOTTOM, true, false);
btnUpData.minimumWidth = 30;
btnUp.setLayoutData(btnUpData);
btnUp.setImage(guiHelper.getImage(IImageKeys.ARROW_UP));
+ btnUp.addSelectionListener(new SelectionAdapter() {
+
+ @Override
+ public void widgetSelected(SelectionEvent e) {
+ chosenDisks = getChosenDisks();
+ List<Disk> selectedDisks = getSelectedChosenDisks();
+
+ chosenDisksContentProvider.removeElements(chosenDisks);
+ for(Disk disk : selectedDisks) {
+ int index = chosenDisks.indexOf(disk);
+ Disk diskAbove = chosenDisks.get(index - 1);
+ chosenDisks.set(index - 1, disk);
+ chosenDisks.set(index, diskAbove);
+ }
+ chosenDisksContentProvider.addElements(chosenDisks);
+ dualTableViewer.refreshChosenViewer();
+ updateButtons();
+ }
+ });
- Button btnDown = new Button(buttonContainer, SWT.TOGGLE);
+ btnDown = new Button(buttonContainer, SWT.TOGGLE);
btnDown.setLayoutData(new GridData(SWT.LEFT, SWT.TOP, true, false));
btnDown.setImage(guiHelper.getImage(IImageKeys.ARROW_DOWN));
+ btnDown.addSelectionListener(new SelectionAdapter() {
+
+ @Override
+ public void widgetSelected(SelectionEvent e) {
+
+ chosenDisks = getChosenDisks();
+ List<Disk> selectedDisks = getSelectedChosenDisks();
+
+ chosenDisksContentProvider.removeElements(chosenDisks);
+ for(Disk disk : selectedDisks) {
+ int index = chosenDisks.indexOf(disk);
+ Disk diskBelow = chosenDisks.get(index + 1);
+ chosenDisks.set(index + 1, disk);
+ chosenDisks.set(index, diskBelow);
+ }
+ chosenDisksContentProvider.addElements(chosenDisks);
+ dualTableViewer.refreshChosenViewer();
+ updateButtons();
+
+ }
+ });
+ }
+
+ private List<Disk> getSelectedChosenDisks() {
+ TableItem[] selectedItems = dualTableViewer.getChosenTable().getSelection();
+ List<Disk> selectedDisks = new ArrayList<Disk>();
+ for (TableItem item : selectedItems) {
+ selectedDisks.add((Disk)item.getData());
+ }
+ return selectedDisks;
}
private void createFilter(final Text filterText, boolean caseSensitive) {
@@ -141,7 +209,7 @@ public class CreateVolumeDisksPage extends Composite {
dualTableViewer.setChosenViewerFilter(filter);
}
- private void createDualTableViewer(List<Disk> disks) {
+ private void createDualTableViewer(List<Disk> allDisks, List<Disk> selectedDisks) {
TableColumnData[] columnData = createColumnData();
ITableLabelProvider diskLabelProvider = getDiskLabelProvider();
@@ -151,15 +219,57 @@ public class CreateVolumeDisksPage extends Composite {
dualTableViewer.setAvailableTableLinesVisible(false);
dualTableViewer.setAvailableTableHeaderVisible(true);
- dualTableViewer.setAvailableContentProvider(new RemovableContentProvider<Disk>());
+ dualTableViewer.setAvailableContentProvider(new RemovableContentProvider<Disk>(getAvailableDisks(allDisks,
+ selectedDisks)));
dualTableViewer.setAvailableLabelProvider(diskLabelProvider);
dualTableViewer.setChosenTableLinesVisible(true);
dualTableViewer.setChosenTableHeaderVisible(true);
- chosenDisksContentProvider = new RemovableContentProvider<Disk>(disks);
+ chosenDisksContentProvider = new RemovableContentProvider<Disk>(selectedDisks);
dualTableViewer.setChosenContentProvider(chosenDisksContentProvider);
dualTableViewer.setChosenLabelProvider(diskLabelProvider);
+
+ dualTableViewer.getChosenTable().addSelectionListener(new SelectionAdapter() {
+ /* (non-Javadoc)
+ * @see org.eclipse.swt.events.SelectionAdapter#widgetSelected(org.eclipse.swt.events.SelectionEvent)
+ */
+ @Override
+ public void widgetSelected(SelectionEvent e) {
+ updateButtons();
+ }
+ });
+ }
+
+ private void updateButtons() {
+ btnUp.setEnabled(true);
+ btnDown.setEnabled(true);
+ List<Disk> selectedChosenDisks = getSelectedChosenDisks();
+ List<Disk> chosenDisks = getChosenDisks();
+ for(Disk disk : selectedChosenDisks) {
+ int index = chosenDisks.indexOf(disk);
+ if(index == 0) {
+ btnUp.setEnabled(false);
+ }
+ if(index == chosenDisks.size() - 1) {
+ btnDown.setEnabled(false);
+ }
+ }
+ }
+
+ /**
+ * @param allDisks
+ * @param selectedDisks
+ * @return
+ */
+ private List<Disk> getAvailableDisks(List<Disk> allDisks, List<Disk> selectedDisks) {
+ List<Disk> availableDisks = new ArrayList<Disk>();
+ for (Disk disk : allDisks) {
+ if (!selectedDisks.contains(disk)) {
+ availableDisks.add(disk);
+ }
+ }
+ return availableDisks;
}
private TableColumnData[] createColumnData() {
@@ -182,11 +292,14 @@ public class CreateVolumeDisksPage extends Composite {
setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
}
- public List<Disk> getSelectedDisks() {
- // dualTableViewer.getChosenTable().getI
- Disk[] disks = (Disk[])chosenDisksContentProvider.getElements(dualTableViewer);
- if(disks != null) {
- return Arrays.asList(disks);
+ public List<Disk> getChosenDisks() {
+ Object[] disksArr = (Object[]) chosenDisksContentProvider.getElements(dualTableViewer);
+ if (disksArr != null) {
+ List<Disk> disks = new ArrayList<Disk>();
+ for (Object disk : disksArr) {
+ disks.add((Disk) disk);
+ }
+ return disks;
}
return null;
}
diff --git a/com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/CreateVolumePage1.java b/com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/CreateVolumePage1.java
index e47adcaf..50f5e013 100644
--- a/com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/CreateVolumePage1.java
+++ b/com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/CreateVolumePage1.java
@@ -29,6 +29,8 @@ import org.eclipse.jface.viewers.LabelProvider;
import org.eclipse.jface.window.Window;
import org.eclipse.jface.wizard.WizardPage;
import org.eclipse.swt.SWT;
+import org.eclipse.swt.events.ModifyEvent;
+import org.eclipse.swt.events.ModifyListener;
import org.eclipse.swt.layout.GridData;
import org.eclipse.swt.layout.GridLayout;
import org.eclipse.swt.widgets.Button;
@@ -40,6 +42,7 @@ import org.eclipse.swt.widgets.Link;
import org.eclipse.swt.widgets.Listener;
import org.eclipse.swt.widgets.Text;
+import com.gluster.storage.management.client.GlusterDataModelManager;
import com.gluster.storage.management.core.model.Disk;
import com.gluster.storage.management.core.model.Volume;
import com.gluster.storage.management.core.model.Volume.NAS_PROTOCOL;
@@ -52,8 +55,11 @@ public class CreateVolumePage1 extends WizardPage {
private ComboViewer typeComboViewer;
private Text txtAccessControl;
private Volume volume = new Volume();
- private List<Disk> disks;
+ private List<Disk> allDisks;
private Button btnNfs;
+ private Button btnStartVolume;
+ private Link linkCustomize;
+ private ValidationListener valListener = new ValidationListener();
/**
* Create the wizard.
@@ -62,13 +68,53 @@ public class CreateVolumePage1 extends WizardPage {
super(PAGE_NAME);
setTitle("Create Volume");
setDescription("Create a new Volume by choosing disks from the cluster servers and configuring the volume properties.");
+
+ // by default, we create volume with all available disks
+ allDisks = GlusterDataModelManager.getInstance().getReadyDisksOfAllServers();
+ volume.setDisks(allDisks);
}
+ private class ValidationListener implements ModifyListener {
+ /* (non-Javadoc)
+ * @see org.eclipse.swt.events.ModifyListener#modifyText(org.eclipse.swt.events.ModifyEvent)
+ */
+ @Override
+ public void modifyText(ModifyEvent e) {
+ String volumeName = txtName.getText().trim();
+ String accessControl = txtAccessControl.getText().trim();
+ String volumeNameToken = "^[a-zA-Z][a-zA-Z0-9\\-]*";
+
+
+ setErrorMessage(null);
+ setPageComplete(true);
+
+ if(volumeName.length() == 0) {
+ setPageComplete(false);
+ setErrorMessage("Please enter Volume Name");
+ }
+
+ if (!volumeName.matches(volumeNameToken)) {
+ setPageComplete(false);
+ setErrorMessage("Please enter valid Volume Name");
+ }
+
+ if(accessControl.length() == 0) {
+ setPageComplete(false);
+ setErrorMessage("Please enter Access Control");
+ }
+ // TODO: acl validation
+ // String[] aclList = accessControl.split(",");
+
+ }
+ }
+
/**
* Create contents of the wizard.
* @param parent
*/
public void createControl(Composite parent) {
+
+ setPageComplete(false);
Composite container = new Composite(parent, SWT.NULL);
setControl(container);
@@ -89,7 +135,8 @@ public class CreateVolumePage1 extends WizardPage {
txtName = new Text(container, SWT.BORDER);
GridData txtNameData = new GridData(SWT.LEFT, SWT.CENTER, true, false, 1, 1);
txtNameData.widthHint = 300;
- txtName.setLayoutData(txtNameData);
+ txtName.setLayoutData(txtNameData);
+ txtName.addModifyListener(valListener);
Label lblType = new Label(container, SWT.NONE);
lblType.setLayoutData(new GridData(SWT.RIGHT, SWT.CENTER, false, false, 1, 1));
@@ -120,19 +167,21 @@ public class CreateVolumePage1 extends WizardPage {
lblDisks.setLayoutData(new GridData(SWT.RIGHT, SWT.CENTER, false, false, 1, 1));
lblDisks.setText("Disks: ");
- Link linkCustomize = new Link(container, SWT.UNDERLINE_LINK);
- linkCustomize.setText("All Disks (<A>customize</A>)");
+ linkCustomize = new Link(container, SWT.UNDERLINE_LINK);
+ linkCustomize.setText("All Disk(s) (<a>customize</a>)");
linkCustomize.addListener (SWT.Selection, new Listener () {
public void handleEvent(Event event) {
- SelectDisksDialog dialog = new SelectDisksDialog(getShell());
+ SelectDisksDialog dialog = new SelectDisksDialog(getShell(), allDisks, volume.getDisks());
+
dialog.create();
if(dialog.open() == Window.OK) {
// user has customized disks. get them from the dialog box.
volume.setDisks(dialog.getSelectedDisks());
+ linkCustomize.setText("" + volume.getDisks().size() + " Disk(s) (<a>customize</a>)");
}
}
});
-
+
Label lblNasProtocol = new Label(container, SWT.RIGHT);
lblNasProtocol.setLayoutData(new GridData(SWT.RIGHT, SWT.CENTER, false, false, 1, 1));
lblNasProtocol.setText("NAS Protocol: ");
@@ -155,15 +204,24 @@ public class CreateVolumePage1 extends WizardPage {
txtAccessControl.setText("*");
GridData accessControlData = new GridData(SWT.LEFT, SWT.CENTER, true, false, 1, 1);
accessControlData.widthHint = 300;
- txtAccessControl.setLayoutData(accessControlData);
+ txtAccessControl.setLayoutData(accessControlData);
+ txtAccessControl.addModifyListener(valListener);
new Label(container, SWT.NONE);
Label lblAccessControlInfo = new Label(container, SWT.TOP);
lblAccessControlInfo.setLayoutData(new GridData(SWT.LEFT, SWT.TOP, false, false, 1, 1));
lblAccessControlInfo.setText("(Comma separated list of IP addresses)");
+
+ Label lblStartVolume = new Label(container, SWT.NONE);
+ lblStartVolume.setLayoutData(new GridData(SWT.RIGHT, SWT.CENTER, false, false, 1, 1));
+ lblStartVolume.setText("Start Volume: ");
+
+ btnStartVolume = new Button(container, SWT.CHECK);
+ btnStartVolume.setSelection(true);
}
public Volume getVolume() {
+
volume.setName(txtName.getText());
IStructuredSelection selection = (IStructuredSelection)typeComboViewer.getSelection();
@@ -180,4 +238,8 @@ public class CreateVolumePage1 extends WizardPage {
return volume;
}
+
+ public Boolean getStartVolumeRequest() {
+ return btnStartVolume.getSelection();
+ }
}
diff --git a/com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/CreateVolumeWizard.java b/com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/CreateVolumeWizard.java
index 7095caad..dfa5a97c 100644
--- a/com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/CreateVolumeWizard.java
+++ b/com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/CreateVolumeWizard.java
@@ -18,6 +18,9 @@
*******************************************************************************/
package com.gluster.storage.management.gui.dialogs;
+import java.util.HashSet;
+import java.util.Set;
+
import org.eclipse.jface.dialogs.MessageDialog;
import org.eclipse.jface.wizard.Wizard;
@@ -25,6 +28,7 @@ import com.gluster.storage.management.client.GlusterDataModelManager;
import com.gluster.storage.management.client.VolumesClient;
import com.gluster.storage.management.core.model.Status;
import com.gluster.storage.management.core.model.Volume;
+import com.gluster.storage.management.core.model.Volume.VOLUME_STATUS;
public class CreateVolumeWizard extends Wizard {
@@ -42,17 +46,25 @@ public class CreateVolumeWizard extends Wizard {
public boolean performFinish() {
CreateVolumePage1 page = (CreateVolumePage1) getPage(CreateVolumePage1.PAGE_NAME);
Volume newVol = page.getVolume();
-
GlusterDataModelManager modelManager = GlusterDataModelManager.getInstance();
VolumesClient volumesClient = new VolumesClient(modelManager.getSecurityToken());
Status status = volumesClient.createVolume(newVol);
+
if (status.isSuccess()) {
- new MessageDialog(getShell(), "Create Volume", null, "Volume created successfully!",
- MessageDialog.INFORMATION, new String[] { "OK" }, 0);
- // TODO: Update the model
+ newVol.setStatus(VOLUME_STATUS.OFFLINE);
+
+ if (page.getStartVolumeRequest()) {
+ Status volumeStartStatus = volumesClient.startVolume(newVol.getName());
+ if (volumeStartStatus.isSuccess()) {
+ newVol.setStatus(VOLUME_STATUS.ONLINE);
+ }
+ }
+
+ modelManager.addVolume(newVol);
+ MessageDialog.openInformation(getShell(), "Create Volume", "Volume created successfully and configuration added!");
} else {
- new MessageDialog(getShell(), "Create Volume", null, "Volume creation failed! [" + status.getCode() + "]["
- + status.getMessage() + "]", MessageDialog.INFORMATION, new String[] { "OK" }, 0);
+ MessageDialog.openError(getShell(), "Create Volume", "Volume creation failed! [" + status.getCode() + "]["
+ + status.getMessage() + "]");
}
return true;
diff --git a/com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/SelectDisksDialog.java b/com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/SelectDisksDialog.java
index b6d0a227..10a36fb0 100644
--- a/com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/SelectDisksDialog.java
+++ b/com.gluster.storage.management.gui/src/com/gluster/storage/management/gui/dialogs/SelectDisksDialog.java
@@ -22,6 +22,8 @@ import java.util.List;
import org.eclipse.jface.dialogs.Dialog;
import org.eclipse.jface.dialogs.IDialogConstants;
+import org.eclipse.jface.dialogs.MessageDialog;
+import org.eclipse.osgi.framework.internal.core.Msg;
import org.eclipse.swt.SWT;
import org.eclipse.swt.graphics.Point;
import org.eclipse.swt.layout.GridData;
@@ -32,19 +34,24 @@ import org.eclipse.swt.widgets.Shell;
import com.gluster.storage.management.client.GlusterDataModelManager;
import com.gluster.storage.management.core.model.Disk;
+import com.gluster.storage.management.core.model.Volume;
public class SelectDisksDialog extends Dialog {
private CreateVolumeDisksPage disksPage;
+ private List<Disk> allDisks;
+ private List<Disk> selectedDisks;
/**
* Create the dialog.
*
* @param parentShell
*/
- public SelectDisksDialog(Shell parentShell) {
+ public SelectDisksDialog(Shell parentShell, List<Disk> allDisks, List<Disk> selectedDisks) {
super(parentShell);
setShellStyle(getShellStyle() | SWT.RESIZE);
+ this.allDisks = allDisks;
+ this.selectedDisks = selectedDisks;
}
/**
@@ -61,8 +68,8 @@ public class SelectDisksDialog extends Dialog {
container.setLayoutData(containerLayoutData);
getShell().setText("Create Volume - Select Disks");
- disksPage = new CreateVolumeDisksPage(container, SWT.NONE, GlusterDataModelManager
- .getInstance().getReadyDisksOfAllServers());
+
+ disksPage = new CreateVolumeDisksPage(container, SWT.NONE, allDisks, selectedDisks);
return container;
}
@@ -93,11 +100,14 @@ public class SelectDisksDialog extends Dialog {
@Override
protected void okPressed() {
- // TODO Validations
- super.okPressed();
+ if (this.getSelectedDisks().size() == 0 ) {
+ MessageDialog.openError(getShell(), "Select Disk(s)", "Please select atlease one disk");
+ } else {
+ super.okPressed();
+ }
}
public List<Disk> getSelectedDisks() {
- return disksPage.getSelectedDisks();
+ return disksPage.getChosenDisks();
}
}
diff --git a/com.gluster.storage.management.server/src/com/gluster/storage/management/server/resources/VolumesResource.java b/com.gluster.storage.management.server/src/com/gluster/storage/management/server/resources/VolumesResource.java
index c4c374d6..35571d01 100644
--- a/com.gluster.storage.management.server/src/com/gluster/storage/management/server/resources/VolumesResource.java
+++ b/com.gluster.storage.management.server/src/com/gluster/storage/management/server/resources/VolumesResource.java
@@ -27,8 +27,6 @@ import static com.gluster.storage.management.core.constants.RESTConstants.PATH_P
import static com.gluster.storage.management.core.constants.RESTConstants.RESOURCE_PATH_VOLUMES;
import static com.gluster.storage.management.core.constants.RESTConstants.SUBRESOURCE_DEFAULT_OPTIONS;
-import java.util.ArrayList;
-import java.util.List;
import java.util.Map;
import javax.ws.rs.Consumes;
@@ -41,15 +39,11 @@ import javax.ws.rs.PathParam;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;
-import com.gluster.storage.management.core.model.Disk;
import com.gluster.storage.management.core.model.GenericResponse;
import com.gluster.storage.management.core.model.Status;
import com.gluster.storage.management.core.model.Volume;
-import com.gluster.storage.management.core.model.Volume.TRANSPORT_TYPE;
-import com.gluster.storage.management.core.model.Volume.VOLUME_TYPE;
import com.gluster.storage.management.core.utils.GlusterUtil;
import com.gluster.storage.management.core.utils.ProcessResult;
-import com.gluster.storage.management.core.utils.ProcessUtil;
import com.gluster.storage.management.server.constants.VolumeOptionsDefaults;
import com.sun.jersey.spi.resource.Singleton;
@@ -62,55 +56,15 @@ public class VolumesResource {
@Consumes(MediaType.TEXT_XML)
@Produces(MediaType.TEXT_XML)
public GenericResponse<String> createVolume(Volume volume) {
-
- int count = 1; // replica or stripe count
- String volumeType = null;
- VOLUME_TYPE volType = volume.getVolumeType();
- if (volType == VOLUME_TYPE.DISTRIBUTED_MIRROR) {
- volumeType = "replica";
- count = 2;
- } else if (volType == VOLUME_TYPE.DISTRIBUTED_STRIPE) {
- volumeType = "stripe";
- count = 4;
+ ProcessResult response = glusterUtil.createVolume(volume);
+ if (!response.isSuccess()) {
+ return new GenericResponse<String>(Status.STATUS_FAILURE, "Volume creation failed: ["
+ + response.getOutput() + "]");
}
- String transportTypeStr = null;
- TRANSPORT_TYPE transportType = volume.getTransportType();
- transportTypeStr = (transportType == TRANSPORT_TYPE.ETHERNET) ? "tcp" : "rdma";
-
- List<String> command = new ArrayList<String>();
- command.add("gluster");
- command.add("volume");
- command.add("create");
- command.add(volume.getName());
- if (volumeType != null) {
- command.add(volumeType);
- command.add("" + count);
- }
- command.add("transport");
- command.add(transportTypeStr);
-
- for (Disk disk : volume.getDisks()) {
- command.add(getBrickNotation(volume, disk));
- }
-
- ProcessResult result = new ProcessUtil().executeCommand(command);
-
- if (!result.isSuccess()) {
- return new GenericResponse<String>(Status.STATUS_FAILURE, "Volume creation failed: [" + result.getOutput()
- + "]");
- }
- return new GenericResponse<String>(Status.STATUS_SUCCESS, "Volume created successfully!");
- }
+ response = glusterUtil.setVolumeAccessControl(volume);
- /**
- * @param disk
- * @return
- */
- private String getBrickNotation(Volume vol, Disk disk) {
- // TODO: Figure out an appropriate directory INSIDE the DISK having given NAME (e.g. sda, sdb, etc)
- String dirName = "/export/" + vol.getName() + "/" + disk.getName();
- return disk.getServerName() + ":" + dirName;
+ return new GenericResponse<String>(Status.STATUS_SUCCESS, response.getOutput());
}
@PUT