]> git.datanom.net - omvzfs.git/blob - gui/rpc/zfs.inc
Add option to set mountpoint when creating pool.
[omvzfs.git] / gui / rpc / zfs.inc
1 <?php
2
3 require_once("openmediavault/object.inc");
4 require_once("openmediavault/config.inc");
5 require_once("openmediavault/error.inc");
6 require_once("openmediavault/util.inc");
7 require_once("openmediavault/rpcservice.inc");
8 require_once("openmediavault/notify.inc");
9 require_once("zfs/Utils.php");
10 require_once("zfs/Dataset.php");
11 require_once("zfs/Snapshot.php");
12 require_once("zfs/Zvol.php");
13 require_once("zfs/Zpool.php");
14 require_once("zfs/NotifyListener.php");
15
16 class OMVRpcServiceZFS extends OMVRpcServiceAbstract {
17 public function getName() {
18 return "ZFS"; // RPC Service name. Same as in .js files
19 }
20
21 /* Initialize the RPC service. Different methods of the RPC service are declared here*/
22 public function initialize() {
23 $this->registerMethod("addPool");
24 $this->registerMethod("getObjectTree");
25 $this->registermethod("passParam");
26 $this->registermethod("addObject");
27 $this->registermethod("deleteObject");
28 $this->registermethod("getProperties");
29 $this->registermethod("setProperties");
30 $this->registermethod("inherit");
31 $this->registermethod("getSharedParams");
32 $this->registermethod("createShare");
33 }
34
35 public function addPool($params, $context) {
36 $this->validateMethodContext($context, array("role" => OMV_ROLE_ADMINISTRATOR));
37 switch ($params['pooltype']) {
38 case "basic":
39 $pooltype = OMVModuleZFSVdevType::OMVMODULEZFSPLAIN;
40 break;
41 case "mirror":
42 $pooltype = OMVModuleZFSVdevType::OMVMODULEZFSMIRROR;
43 break;
44 case "raidz1":
45 $pooltype = OMVModuleZFSVdevType::OMVMODULEZFSRAIDZ1;
46 break;
47 case "raidz2":
48 $pooltype = OMVModuleZFSVdevType::OMVMODULEZFSRAIDZ2;
49 break;
50 case "raidz3":
51 $pooltype = OMVModuleZFSVdevType::OMVMODULEZFSRAIDZ3;
52 break;
53 default:
54 throw new OMVModuleZFSException("Incorrect pool type specified");
55 break;
56 }
57 //Check for user supplied options
58 $opts = "";
59 if ($params['force']) {
60 $opts .= "-f ";
61 }
62 if (strlen($params['mountpoint']) > 0) {
63 $opts .= "-m " . $params['mountpoint'] . " ";
64 }
65
66 $disks = preg_split("/[,;]/", $params['devices']);
67 $vdev = new OMVModuleZFSVdev($params['name'], $pooltype, $disks);
68 $pool = new OMVModuleZFSZpool($vdev, $opts);
69 //Ugly fix to solve the problem of blkid not displaying info on newly created pools
70 $pool->export();
71 $pool->import($pool->getName());
72 }
73
74 public function getObjectTree($params, $context) {
75 $this->validateMethodContext($context, array("role" => OMV_ROLE_ADMINISTRATOR));
76 $objects = OMVModuleZFSUtil::getZFSFlatArray();
77 $new = array();
78 foreach ($objects as $a){
79 $new[$a['parentid']][] = $a;
80 }
81 $tree = OMVModuleZFSUtil::createTree($new, $new['root']);
82 OMVModuleZFSUtil::addMissingOMVMntEnt(); //Adds missing ZFS filesystems to the OMV core
83 return $tree;
84 }
85
86 public function passParam($params, $context) {
87 $this->validateMethodContext($context, array("role" => OMV_ROLE_ADMINISTRATOR));
88 //$msg = "Key=" . $params['key'] . ";Value=" . $params['value'] . ";";
89 //throw new OMVModuleZFSException($msg);
90 return array($params['key'] => $params['value']);
91 }
92
93 public function addObject($params, $context) {
94 $this->validateMethodContext($context, array("role" => OMV_ROLE_ADMINISTRATOR));
95 switch ($params['type']) {
96 case "filesystem":
97 $name = $params['path'] . "/" . $params['name'];
98 $tmp = new OMVModuleZFSDataset($name);
99 break;
100 case "snapshot":
101 $name = $params['path'] . "@" . $params['name'];
102 $tmp = new OMVModuleZFSSnapshot($name);
103 break;
104 case "volume":
105 $name = $params['path'] . "/" . $params['name'];
106 $tmp = new OMVModuleZFSZvol($name);
107 $tmp->create($params['size']);
108 break;
109 default:
110 throw new OMVModuleZFSException("Illegal type provided: " . $params['type']);
111 break;
112 }
113 }
114
115 public function deleteObject($params, $context) {
116 $this->validateMethodContext($context, array("role" => OMV_ROLE_ADMINISTRATOR));
117 switch ($params['type']) {
118 case "Filesystem":
119 case "Clone":
120 $name = $params['name'];
121 $tmp = new OMVModuleZFSDataset($name);
122 $tmp->destroy();
123 break;
124 case "Snapshot":
125 $name = $params['name'];
126 $tmp = new OMVModuleZFSSnapshot($name);
127 $tmp->destroy();
128 break;
129 case "Volume":
130 $name = $params['name'];
131 $tmp = new OMVModuleZFSZvol($name);
132 $tmp->destroy();
133 break;
134 case "Pool":
135 $name = $params['name'];
136 $tmp = new OMVModuleZFSZpool($name);
137 $tmp->destroy();
138 break;
139 default:
140 throw new OMVModuleZFSException("Illegal type provided: " . $params['type']);
141 break;
142 }
143 }
144
145 public function getProperties($params, $context) {
146 $this->validateMethodContext($context, array("role" => OMV_ROLE_ADMINISTRATOR));
147 $objects = array();
148 $name = $params['name'];
149 switch ($params['type']) {
150 case "Filesystem":
151 case "Clone":
152 $tmp = new OMVModuleZFSDataset($name);
153 break;
154 case "Snapshot":
155 $tmp = new OMVModuleZFSSnapshot($name);
156 break;
157 case "Volume":
158 $tmp = new OMVModuleZFSZvol($name);
159 break;
160 case "Pool":
161 $tmp = new OMVModuleZFSZpool($name);
162 break;
163 default:
164 throw new OMVModuleZFSException("Illegal type provided: " . $params['type']);
165 break;
166 }
167 $properties = $tmp->getProperties();
168 foreach ($properties as $propertyk => $propertyv) {
169 if (!(strcmp($propertyv['source'], "-") == 0)) {
170 $objects[] = array('property' => $propertyk,
171 'value' => $propertyv['value'],
172 'source' => $propertyv['source'],
173 'modified' => "false");
174 }
175 }
176 return $objects;
177 }
178
179 public function setProperties($params, $context) {
180 $this->validateMethodContext($context, array("role" => OMV_ROLE_ADMINISTRATOR));
181 $objects = array();
182 switch ($params['type']) {
183 case "Filesystem":
184 case "Clone":
185 $tmp = new OMVModuleZFSDataset($params['name']);
186 break;
187 case "Snapshot":
188 $tmp = new OMVModuleZFSSnapshot($params['name']);
189 break;
190 case "Volume":
191 $tmp = new OMVModuleZFSZvol($params['name']);
192 break;
193 case "Pool":
194 $tmp = new OMVModuleZFSZpool($params['name']);
195 break;
196 default:
197 throw new OMVModuleZFSException("Illegal type provided: " . $params['type']);
198 break;
199 }
200 foreach ($params['properties'] as $property) {
201 $objects[$property['property']] = $property['value'];
202 }
203 $tmp->setProperties($objects);
204 }
205
206 public function inherit($params, $context) {
207 $this->validateMethodContext($context, array("role" => OMV_ROLE_ADMINISTRATOR));
208 // Create a background process.
209 $bgStatusFilename = $this->createBgProcStatus();
210 $pid = $this->fork();
211 if($pid > 0) { // Parent process.
212 $this->initializeBgProcStatus($bgStatusFilename, $pid);
213 return $bgStatusFilename;
214 }
215 // Child process.
216 try {
217 $bgOutputFilename = $this->createBgProcOutput();
218 $this->updateBgProcStatus($bgStatusFilename, "outputfilename", $bgOutputFilename);
219 switch ($params['type']) {
220 case "Filesystem":
221 case "Clone":
222 $tmp = new OMVModuleZFSDataset($params['name']);
223 break;
224 case "Snapshot":
225 $tmp = new OMVModuleZFSSnapshot($params['name']);
226 break;
227 case "Volume":
228 $tmp = new OMVModuleZFSZvol($params['name']);
229 break;
230 case "Pool":
231 $tmp = new OMVModuleZFSZpool($params['name']);
232 break;
233 default:
234 throw new OMVModuleZFSException("Illegal type provided: " . $params['type']);
235 break;
236 }
237 $tmp->inherit($params['property']);
238 $this->finalizeBgProcStatus($bgStatusFilename, $output);
239 exit(0);
240 } catch(Exception $e) {
241 $this->finalizeBgProcStatus($bgStatusFilename, "", $e);
242 exit(1);
243 }
244 }
245
246 public function getSharedParams($params, $context) {
247 $this->validateMethodContext($context, array("role" => OMV_ROLE_ADMINISTRATOR));
248 $objects = array();
249 $ds = new OMVModuleZFSDataset($params['name']);
250 $mountpoint = $ds->getMountPoint();
251 return array(
252 "mountpoint" => $mountpoint,
253 "name" => $params['name'],
254 "type" => $params['type']);
255 }
256
257 public function createShare($params, $context) {
258 global $xmlConfig;
259 $this->validateMethodContext($context, array("role" => OMV_ROLE_ADMINISTRATOR));
260
261 //Get the UUID of the Pool
262 $pooluuid = OMVModuleZFSUtil::getUUIDbyName($params['name']);
263 preg_match('/^([A-Za-z0-9]+)\/?.*$/', $params['name'], $result);
264 $poolname = $result[1];
265 unset($result);
266
267 //Get the mntent object and fetch it's uuid.
268 $xpath = "//system/fstab/mntent[fsname=" . $pooluuid . "]";
269 $object = $xmlConfig->get($xpath);
270 $mntentref = $object['uuid'];
271
272 // Prepare the configuration object. Use the name of the shared
273 // folder as the relative directory name of the share.
274 switch ($params['type']) {
275 case "Filesystem":
276 $tmp = new OMVModuleZFSDataset($params['name']);
277 break;
278 case "Clone":
279 $tmp = new OMVModuleZFSDataset($params['name']);
280 break;
281 default:
282 throw new OMVModuleZFSException("Illegal type provided: " . $params['type']);
283 break;
284 }
285
286 $uuid = OMVUtil::uuid();
287 $pathName = $tmp->getMountPoint();
288 $subdirs = preg_split('/\//',$pathName);
289 $reldirpath = $subdirs[count($subdirs)-1];
290 $object = array(
291 "uuid" => $uuid,
292 "name" => $params['sharename'],
293 "comment" => $params['comment'],
294 "mntentref" => $mntentref,
295 "reldirpath" => $reldirpath
296 );
297
298 // Set the configuration object.
299 $success = FALSE;
300 // Check uniqueness. The share name must be global unique because
301 // the name is also used when exporting a shared folder via NFS for
302 // example.
303 $xpath = sprintf("//system/shares/sharedfolder[name='%s']",
304 $params['name']);
305 if(TRUE === $xmlConfig->exists($xpath)) {
306 throw new OMVException(OMVErrorMsg::E_CONFIG_OBJECT_UNIQUENESS,
307 gettext("A shared folder with the given name already exists"));
308 }
309
310 // Add empty list of privileges per default.
311 $object['privileges'] = array();
312
313 // Append object to configuration.
314 $success = $xmlConfig->set("//system/shares",
315 array("sharedfolder" => $object));
316 if(FALSE === $success) {
317 throw new OMVException(OMVErrorMsg::E_CONFIG_SET_OBJECT_FAILED);
318 }
319
320 // Append the file mode field to the notification object if set.
321 // Defaults to 775.
322 $object['mode'] = "775";
323 if(array_key_exists("mode", $params)) {
324 $object['mode'] = $params['mode'];
325 }
326
327 // Change group owner of directory to configured default group,
328 // e.g. 'users'.
329 if(FALSE === chgrp($pathName, $GLOBALS['OMV_USERMGMT_DEFAULT_GROUP'])) {
330 throw new OMVException(OMVErrorMsg::E_MISC_FAILURE,
331 sprintf("Failed to set file group to '%s' for '%s'",
332 $GLOBALS['OMV_USERMGMT_DEFAULT_GROUP'], $pathName));
333 }
334
335 // Set the setgid bit. Setting this permission means that all files
336 // created in the folder will inherit the group of the folder rather
337 // than the primary group of the user who creates the file.
338 $mode = fileperms($pathName) | 02000;
339 if(FALSE === chmod($pathName, $mode)) {
340 throw new OMVException(OMVErrorMsg::E_MISC_FAILURE,
341 sprintf("Failed to set file mode to '%o' for '%s'",
342 $mode, $pathName));
343 }
344
345 // Notify configuration changes.
346 $dispatcher = &OMVNotifyDispatcher::getInstance();
347 $dispatcher->notify(OMV_NOTIFY_CREATE,"org.openmediavault.system.shares.sharedfolder", $object);
348 // Return the configuration object.
349 return $object;
350 }
351
352 }
353
354 // Register the RPC service.
355 $rpcServiceMgr = &OMVRpcServiceMgr::getInstance(); // Get the "root" instance for the Services
356 $rpcServiceMgr->registerService(new OMVRpcServiceZFS()); // Register a new instance of the RPC service described above
357 ?>
358
This page took 0.148099 seconds and 6 git commands to generate.