1: <?php
2: /**
3: * Extension of the Horde_Share_Object class for handling Kolab share
4: * information.
5: *
6: * PHP version 5
7: *
8: * @category Horde
9: * @package Share
10: * @author Gunnar Wrobel <wrobel@pardus.de>
11: * @license http://www.horde.org/licenses/lgpl21 LGPL 2.1
12: * @link http://pear.horde.org/index.php?package=Share
13: */
14:
15: /**
16: * Extension of the Horde_Share_Object class for handling Kolab share
17: * information.
18: *
19: * Copyright 2004-2012 Horde LLC (http://www.horde.org/)
20: *
21: * See the enclosed file COPYING for license information (LGPL). If you
22: * did not receive this file, see http://www.horde.org/licenses/lgpl21.
23: *
24: * @category Horde
25: * @package Share
26: * @author Gunnar Wrobel <wrobel@pardus.de>
27: * @license http://www.horde.org/licenses/lgpl21 LGPL 2.1
28: * @link http://pear.horde.org/index.php?package=Share
29: */
30: class Horde_Share_Object_Kolab
31: extends Horde_Share_Object
32: implements Serializable, Horde_Perms_Permission_Kolab_Storage
33: {
34: /**
35: * Serializable version.
36: */
37: const VERSION = 2;
38:
39: /**
40: * The old share id.
41: *
42: * @var string
43: */
44: private $_old_id;
45:
46: /**
47: * The share id.
48: *
49: * @var string
50: */
51: private $_id;
52:
53: /**
54: * The Horde_Group driver
55: *
56: * @var Horde_Group_Base
57: */
58: private $_groups;
59:
60: /**
61: * The share attributes.
62: *
63: * @var array
64: */
65: protected $_data;
66:
67: /**
68: * The permission cache holds any permission changes that will be executed
69: * on saving.
70: *
71: * @var Horde_Perm_Permission_Kolab
72: */
73: private $_permission;
74:
75: /**
76: * Constructor.
77: *
78: * @param string $id The share id.
79: * @param Horde_Group_Base $groups The Horde_Group driver
80: * @param array $data The share data.
81: */
82: public function __construct($id, Horde_Group_Base $groups,
83: array $data = array())
84: {
85: $this->_old_id = $id;
86: $this->_id = $id;
87: $this->_groups = $groups;
88: $this->_data = $data;
89: }
90:
91: /**
92: * Serialize this object.
93: *
94: * @return string The serialized data.
95: */
96: public function serialize()
97: {
98: return serialize(array(
99: self::VERSION,
100: $this->_id,
101: $this->_data,
102: $this->_shareCallback
103: ));
104: }
105:
106: /**
107: * Unserialize object.
108: *
109: * @param <type> $data
110: */
111: public function unserialize($data)
112: {
113: $data = @unserialize($data);
114: if (!is_array($data) ||
115: !isset($data[0]) ||
116: ($data[0] != self::VERSION)) {
117: throw new Exception('Cache version change');
118: }
119:
120: $this->_id = $data[1];
121: $this->_data = $data[2];
122: if (empty($data[3])) {
123: throw new Exception('Missing callback for unserializing Horde_Share_Object');
124: }
125: $this->_shareCallback = $data[3];
126: $this->setShareOb(call_user_func($this->_shareCallback));
127: }
128:
129: /**
130: * Returns the ID of this share.
131: *
132: * @return string The share's ID.
133: */
134: public function getId()
135: {
136: if ($this->_id === null) {
137: throw new Horde_Share_Exception(
138: 'A new Kolab share requires a set("name", ...) and set("owner", ...) call before the ID is available.'
139: );
140: }
141: return $this->_id;
142: }
143:
144: /**
145: * Returns the permission ID of this share.
146: *
147: * @return string The share's permission ID.
148: */
149: public function getPermissionId()
150: {
151: if ($this->_id === null) {
152: /* We only get here if permissions are being set before the name has
153: * been set. For the Kolab permission instance it should not matter if the name is
154: * a random string. */
155: return md5(pack('I', mt_rand()));
156: }
157: return $this->_id;
158: }
159:
160: /**
161: * Returns the name of this share.
162: *
163: * @return string The share's name.
164: */
165: public function getName()
166: {
167: if (isset($this->_data['share_name'])) {
168: return $this->_data['share_name'];
169: } else {
170: return $this->getId();
171: }
172: }
173:
174: /**
175: * Returns the owner of this share.
176: *
177: * @return string The share's owner.
178: */
179: public function getOwner()
180: {
181: return $this->get('owner');
182: }
183:
184: /**
185: * Returns an attribute value from this object.
186: *
187: * @param string $attribute The attribute to return.
188: *
189: * @return mixed The value for $attribute.
190: */
191: public function get($attribute)
192: {
193: if (isset($this->_data[$attribute])) {
194: return $this->_data[$attribute];
195: }
196: }
197:
198: /**
199: * Sets an attribute value in this object.
200: *
201: * @param string $attribute The attribute to set.
202: * @param mixed $value The value for $attribute.
203: * @param boolean $update Update *only* this change immediately.
204: *
205: * @return NULL
206: */
207: public function set($attribute, $value, $update = false)
208: {
209: if (in_array($attribute, array('owner', 'name', 'prefix'))) {
210: $owner = $this->get('owner');
211: $name = $this->get('name');
212: $prefix = $this->get('prefix');
213: switch ($attribute) {
214: case 'name':
215: $name = $value;
216: break;
217: case 'owner':
218: $owner = $value;
219: break;
220: case 'prefix':
221: $prefix = $value;
222: break;
223: }
224: $subpath = $name;
225: $parent = $this->getParent();
226: if ($parent !== null) {
227: $subpath = $parent->get('subpath') . $parent->get('delimiter') .
228: $subpath;
229: }
230: $this->_data['folder'] = $this->getShareOb()->constructFolderName(
231: $owner, $subpath, $prefix
232: );
233: list($this->_data['prefix'], $this->_data['delimiter'], $this->_data['subpath']) = $this->getShareOb()->getFolderNameElements(
234: $this->_data['folder']
235: );
236: $this->_id = $this->getShareOb()->constructId(
237: $owner, $subpath, $this->_data['prefix']
238: );
239: }
240: $this->_data[$attribute] = $value;
241:
242: //@TODO: Not sure how to update a single attribute in kolab.
243: if ($update) {
244: $this->_save();
245: }
246: }
247:
248: /**
249: * Return a count of the number of children this share has
250: *
251: * @param string $user The user to use for checking perms
252: * @param integer $perm A Horde_Perms::* constant
253: * @param boolean $allLevels Count grandchildren or just children
254: *
255: * @return integer The number of child shares
256: */
257: public function countChildren($user, $perm = Horde_Perms::SHOW, $allLevels = true)
258: {
259: return $this->getShareOb()->countShares($user, $perm, null, $this, $allLevels);
260: }
261:
262: /**
263: * Get all children of this share.
264: *
265: * @param string $user The user to use for checking perms
266: * @param integer $perm Horde_Perms::* constant. If NULL will return
267: * all shares regardless of permissions.
268: * @param boolean $allLevels Return all levels.
269: *
270: * @return array An array of Horde_Share_Object objects
271: */
272: public function getChildren($user, $perm = Horde_Perms::SHOW, $allLevels = true)
273: {
274: return $this->getShareOb()->listShares(
275: $user, array('perm' => $perm,
276: 'direction' => 1,
277: 'parent' => $this,
278: 'all_levels' => $allLevels));
279: }
280:
281: /**
282: * Returns a child's direct parent.
283: *
284: * @return Horde_Share_Object|NULL The direct parent Horde_Share_Object or
285: * NULL in case the share has no parent.
286: */
287: public function getParent()
288: {
289: $parent_id = $this->get('parent');
290: if (!empty($parent_id)) {
291: try {
292: return $this->getShareOb()->getShareById($parent_id);
293: } catch (Horde_Exception_NotFound $e) {
294: return null;
295: }
296: }
297: return null;
298: }
299:
300: /**
301: * Get all of this share's parents.
302: *
303: * @return array() An array of Horde_Share_Objects
304: */
305: public function getParents()
306: {
307: $parents = array();
308: $share = $this->getParent();
309: while ($share instanceof Horde_Share_Object) {
310: $parents[] = $share;
311: $share = $share->getParent();
312: }
313:
314: return array_reverse($parents);
315: }
316:
317: /**
318: * Set the parent object for this share.
319: *
320: * @param mixed $parent A Horde_Share object or share id for the parent.
321: *
322: * @return NULL
323: */
324: public function setParent($parent)
325: {
326: if (!$parent instanceof Horde_Share_Object) {
327: $parent = $this->getShareOb()->getShareById($parent);
328: }
329: $this->_data['parent'] = $parent->getId();
330: $this->_data['prefix'] = $parent->get('prefix');
331: $this->set('owner', $parent->get('owner'));
332: }
333:
334: /**
335: * Saves the current attribute values.
336: */
337: protected function _save()
338: {
339: if (!isset($this->_data['share_name'])) {
340: $this->_data['share_name'] = $this->getName();
341: }
342: $this->getShareOb()->save($this->getId(), $this->_old_id, $this->_data);
343: $this->_old_id = $this->_id;
344: $this->getPermission()->save();
345: }
346:
347: /**
348: * Checks to see if a user has a given permission.
349: *
350: * @param string $userid The userid of the user.
351: * @param integer $permission A Horde_Perms::* constant to test for.
352: * @param string $creator The creator of the shared object.
353: *
354: * @return boolean Whether or not $userid has $permission.
355: */
356: public function hasPermission($userid, $permission, $creator = null)
357: {
358: if (empty($creator)) {
359: $creator = $this->getOwner();
360: }
361: return $this->getShareOb()->getPermsObject()->hasPermission($this->getPermission(), $userid, $permission, $creator);
362: }
363:
364: /**
365: * Returns the permissions from this storage object.
366: *
367: * @return Horde_Perms_Permission_Kolab The permissions on the share.
368: */
369: public function getPermission()
370: {
371: if ($this->_permission === null) {
372: $this->_permission = new Horde_Perms_Permission_Kolab($this, $this->_groups);
373: }
374: return $this->_permission;
375: }
376:
377: /**
378: * Sets the permissions on the share.
379: *
380: * @param Horde_Perms_Permission_Kolab $perms Permission object to folder on the
381: * object.
382: * @param boolean $update Save the updated information?
383: *
384: * @return NULL
385: */
386: public function setPermission($perms, $update = true)
387: {
388: if (!$perms instanceOf Horde_Perms_Permission_Kolab) {
389: $this->getPermission()->setData($perms->getData());
390: } else {
391: $this->_permission = $perms;
392: }
393: if ($update) {
394: $this->save();
395: }
396: }
397:
398: /**
399: * Retrieve the Kolab specific access rights for this share.
400: *
401: * @return An array of rights.
402: */
403: public function getAcl()
404: {
405: if ($this->_old_id === null) {
406: // The share has not been created yet.
407: return array(
408: $this->get('owner') => Horde_Perms_Permission_Kolab::ALL
409: );
410: }
411: return $this->getShareOb()->getAcl($this->_id);
412: }
413:
414: /**
415: * Set the Kolab specific access rights for this share.
416: *
417: * @param string $user The user to set the ACL for.
418: * @param string $acl The ACL.
419: *
420: * @return NULL
421: */
422: public function setAcl($user, $acl)
423: {
424: return $this->getShareOb()->setAcl($this->_id, $user, $acl);
425: }
426:
427: /**
428: * Delete Kolab specific access rights for this share.
429: *
430: * @param string $user The user to delete the ACL for.
431: *
432: * @return NULL
433: */
434: public function deleteAcl($user)
435: {
436: return $this->getShareOb()->deleteAcl($this->_id, $user);
437: }
438: }
439: