Overview

Packages

  • ClipIt
    • clipit
      • api
    • urjc
      • backend
  • Elgg
    • Core
      • Access
      • Authentication
      • Cache
      • Caches
      • Core
      • DataMode
        • Site
      • DataModel
        • Annotations
        • Entities
        • Extender
        • File
        • Importable
        • Loggable
        • Notable
        • Object
        • User
      • DataStorage
      • Exception
      • Exceptions
        • Stub
      • FileStore
        • Disk
      • Groups
      • Helpers
      • HMAC
      • Memcache
      • Metadata
      • Navigation
      • ODD
      • Output
      • Plugins
        • Settings
      • Sessions
      • SocialModel
        • Friendable
        • Locatable
      • WebServicesAPI
      • Widgets
      • XML
      • XMLRPC
    • Exceptions
      • Stub
  • None
  • PHP

Classes

  • ElggFile
  • Overview
  • Package
  • Class
  • Tree
  1: <?php
  2: 
  3: /**
  4:  * This class represents a physical file.
  5:  *
  6:  * Create a new ElggFile object and specify a filename, and optionally a
  7:  * FileStore (if one isn't specified then the default is assumed.)
  8:  *
  9:  * Open the file using the appropriate mode, and you will be able to
 10:  * read and write to the file.
 11:  *
 12:  * Optionally, you can also call the file's save() method, this will
 13:  * turn the file into an entity in the system and permit you to do
 14:  * things like attach tags to the file etc. This is not done automatically
 15:  * since there are many occasions where you may want access to file data
 16:  * on datastores using the ElggFile interface but do not want to create
 17:  * an Entity reference to it in the system (temporary files for example).
 18:  *
 19:  * @class      ElggFile
 20:  * @package    Elgg.Core
 21:  * @subpackage DataModel.File
 22:  */
 23: class ElggFile extends ElggObject {
 24:     /** Filestore */
 25:     private $filestore;
 26: 
 27:     /** File handle used to identify this file in a filestore. Created by open. */
 28:     private $handle;
 29: 
 30:     /**
 31:      * Set subtype to 'file'.
 32:      *
 33:      * @return void
 34:      */
 35:     protected function initializeAttributes() {
 36:         parent::initializeAttributes();
 37: 
 38:         $this->attributes['subtype'] = "file";
 39:     }
 40: 
 41:     /**
 42:      * Loads an ElggFile entity.
 43:      *
 44:      * @param int $guid GUID of the ElggFile object
 45:      */
 46:     public function __construct($guid = null) {
 47:         parent::__construct($guid);
 48: 
 49:         // Set default filestore
 50:         $this->filestore = $this->getFilestore();
 51:     }
 52: 
 53:     /**
 54:      * Set the filename of this file.
 55:      *
 56:      * @param string $name The filename.
 57:      *
 58:      * @return void
 59:      */
 60:     public function setFilename($name) {
 61:         $this->filename = $name;
 62:     }
 63: 
 64:     /**
 65:      * Return the filename.
 66:      *
 67:      * @return string
 68:      */
 69:     public function getFilename() {
 70:         return $this->filename;
 71:     }
 72: 
 73:     /**
 74:      * Return the filename of this file as it is/will be stored on the
 75:      * filestore, which may be different to the filename.
 76:      *
 77:      * @return string
 78:      */
 79:     public function getFilenameOnFilestore() {
 80:         return $this->filestore->getFilenameOnFilestore($this);
 81:     }
 82: 
 83:     /**
 84:      * Return the size of the filestore associated with this file
 85:      *
 86:      * @param string $prefix         Storage prefix
 87:      * @param int    $container_guid The container GUID of the checked filestore
 88:      *
 89:      * @return int
 90:      */
 91:     public function getFilestoreSize($prefix = '', $container_guid = 0) {
 92:         if (!$container_guid) {
 93:             $container_guid = $this->container_guid;
 94:         }
 95:         $fs = $this->getFilestore();
 96:         // @todo add getSize() to ElggFilestore
 97:         return $fs->getSize($prefix, $container_guid);
 98:     }
 99: 
100:     /**
101:      * Get the mime type of the file.
102:      *
103:      * @return string
104:      */
105:     public function getMimeType() {
106:         if ($this->mimetype) {
107:             return $this->mimetype;
108:         }
109: 
110:         // @todo Guess mimetype if not here
111:     }
112: 
113:     /**
114:      * Set the mime type of the file.
115:      *
116:      * @param string $mimetype The mimetype
117:      *
118:      * @return bool
119:      */
120:     public function setMimeType($mimetype) {
121:         return $this->mimetype = $mimetype;
122:     }
123: 
124:     /**
125:      * Detects mime types based on filename or actual file.
126:      *
127:      * @param mixed $file    The full path of the file to check. For uploaded files, use tmp_name.
128:      * @param mixed $default A default. Useful to pass what the browser thinks it is.
129:      * @since 1.7.12
130:      *
131:      * @note If $file is provided, this may be called statically
132:      *
133:      * @return mixed Detected type on success, false on failure.
134:      */
135:     public function detectMimeType($file = null, $default = null) {
136:         if (!$file) {
137:             if (isset($this) && $this->filename) {
138:                 $file = $this->filename;
139:             } else {
140:                 return false;
141:             }
142:         }
143: 
144:         $mime = false;
145: 
146:         // for PHP5 folks.
147:         if (function_exists('finfo_file') && defined('FILEINFO_MIME_TYPE')) {
148:             $resource = finfo_open(FILEINFO_MIME_TYPE);
149:             if ($resource) {
150:                 $mime = finfo_file($resource, $file);
151:             }
152:         }
153: 
154:         // for everyone else.
155:         if (!$mime && function_exists('mime_content_type')) {
156:             $mime = mime_content_type($file);
157:         }
158: 
159:         // default
160:         if (!$mime) {
161:             return $default;
162:         }
163: 
164:         return $mime;
165:     }
166: 
167:     /**
168:      * Set the optional file description.
169:      *
170:      * @param string $description The description.
171:      *
172:      * @return bool
173:      */
174:     public function setDescription($description) {
175:         $this->description = $description;
176:     }
177: 
178:     /**
179:      * Open the file with the given mode
180:      *
181:      * @param string $mode Either read/write/append
182:      *
183:      * @return resource File handler
184:      *
185:      * @throws IOException|InvalidParameterException
186:      */
187:     public function open($mode) {
188:         if (!$this->getFilename()) {
189:             throw new IOException(elgg_echo('IOException:MissingFileName'));
190:         }
191: 
192:         // See if file has already been saved
193:         // seek on datastore, parameters and name?
194: 
195:         // Sanity check
196:         if (
197:             ($mode != "read") &&
198:             ($mode != "write") &&
199:             ($mode != "append")
200:         ) {
201:             $msg = elgg_echo('InvalidParameterException:UnrecognisedFileMode', array($mode));
202:             throw new InvalidParameterException($msg);
203:         }
204: 
205:         // Get the filestore
206:         $fs = $this->getFilestore();
207: 
208:         // Ensure that we save the file details to object store
209:         //$this->save();
210: 
211:         // Open the file handle
212:         $this->handle = $fs->open($this, $mode);
213: 
214:         return $this->handle;
215:     }
216: 
217:     /**
218:      * Write data.
219:      *
220:      * @param string $data The data
221:      *
222:      * @return bool
223:      */
224:     public function write($data) {
225:         $fs = $this->getFilestore();
226: 
227:         return $fs->write($this->handle, $data);
228:     }
229: 
230:     /**
231:      * Read data.
232:      *
233:      * @param int $length Amount to read.
234:      * @param int $offset The offset to start from.
235:      *
236:      * @return mixed Data or false
237:      */
238:     public function read($length, $offset = 0) {
239:         $fs = $this->getFilestore();
240: 
241:         return $fs->read($this->handle, $length, $offset);
242:     }
243: 
244:     /**
245:      * Gets the full contents of this file.
246:      *
247:      * @return mixed The file contents.
248:      */
249:     public function grabFile() {
250:         $fs = $this->getFilestore();
251:         return $fs->grabFile($this);
252:     }
253: 
254:     /**
255:      * Close the file and commit changes
256:      *
257:      * @return bool
258:      */
259:     public function close() {
260:         $fs = $this->getFilestore();
261: 
262:         if ($fs->close($this->handle)) {
263:             $this->handle = NULL;
264: 
265:             return true;
266:         }
267: 
268:         return false;
269:     }
270: 
271:     /**
272:      * Delete this file.
273:      *
274:      * @return bool
275:      */
276:     public function delete() {
277:         $fs = $this->getFilestore();
278:         
279:         $result = $fs->delete($this);
280:         
281:         if ($this->getGUID() && $result) {
282:             $result = parent::delete();
283:         }
284:         
285:         return $result;
286:     }
287: 
288:     /**
289:      * Seek a position in the file.
290:      *
291:      * @param int $position Position in bytes
292:      *
293:      * @return bool
294:      */
295:     public function seek($position) {
296:         $fs = $this->getFilestore();
297: 
298:         // @todo add seek() to ElggFilestore
299:         return $fs->seek($this->handle, $position);
300:     }
301: 
302:     /**
303:      * Return the current position of the file.
304:      *
305:      * @return int The file position
306:      */
307:     public function tell() {
308:         $fs = $this->getFilestore();
309: 
310:         return $fs->tell($this->handle);
311:     }
312: 
313:     /**
314:      * Return the size of the file in bytes.
315:      *
316:      * @return int
317:      */
318:     public function size() {
319:         return $this->filestore->getFileSize($this);
320:     }
321: 
322:     /**
323:      * Return a boolean value whether the file handle is at the end of the file
324:      *
325:      * @return bool
326:      */
327:     public function eof() {
328:         $fs = $this->getFilestore();
329: 
330:         return $fs->eof($this->handle);
331:     }
332: 
333:     /**
334:      * Returns if the file exists
335:      *
336:      * @return bool
337:      */
338:     public function exists() {
339:         $fs = $this->getFilestore();
340: 
341:         return $fs->exists($this);
342:     }
343: 
344:     /**
345:      * Set a filestore.
346:      *
347:      * @param ElggFilestore $filestore The file store.
348:      *
349:      * @return void
350:      */
351:     public function setFilestore(ElggFilestore $filestore) {
352:         $this->filestore = $filestore;
353:     }
354: 
355:     /**
356:      * Return a filestore suitable for saving this file.
357:      * This filestore is either a pre-registered filestore,
358:      * a filestore as recorded in metadata or the system default.
359:      *
360:      * @return ElggFilestore
361:      *
362:      * @throws ClassNotFoundException
363:      */
364:     protected function getFilestore() {
365:         // Short circuit if already set.
366:         if ($this->filestore) {
367:             return $this->filestore;
368:         }
369: 
370:         // ask for entity specific filestore
371:         // saved as filestore::className in metadata.
372:         // need to get all filestore::* metadata because the rest are "parameters" that
373:         // get passed to filestore::setParameters()
374:         if ($this->guid) {
375:             $options = array(
376:                 'guid' => $this->guid,
377:                 'where' => array("n.string LIKE 'filestore::%'"),
378:             );
379: 
380:             $mds = elgg_get_metadata($options);
381: 
382:             $parameters = array();
383:             foreach ($mds as $md) {
384:                 list($foo, $name) = explode("::", $md->name);
385:                 if ($name == 'filestore') {
386:                     $filestore = $md->value;
387:                 }
388:                 $parameters[$name] = $md->value;
389:             }
390:         }
391: 
392:         // need to check if filestore is set because this entity is loaded in save()
393:         // before the filestore metadata is saved.
394:         if (isset($filestore)) {
395:             if (!class_exists($filestore)) {
396:                 $msg = elgg_echo('ClassNotFoundException:NotFoundNotSavedWithFile',
397:                     array($filestore, $this->guid));
398:                 throw new ClassNotFoundException($msg);
399:             }
400: 
401:             $this->filestore = new $filestore();
402:             $this->filestore->setParameters($parameters);
403:             // @todo explain why $parameters will always be set here (PhpStorm complains)
404:         }
405: 
406:         // this means the entity hasn't been saved so fallback to default
407:         if (!$this->filestore) {
408:             $this->filestore = get_default_filestore();
409:         }
410: 
411:         return $this->filestore;
412:     }
413: 
414:     /**
415:      * Save the file
416:      *
417:      * Write the file's data to the filestore and save
418:      * the corresponding entity.
419:      *
420:      * @see ElggObject::save()
421:      *
422:      * @return bool
423:      */
424:     public function save() {
425:         if (!parent::save()) {
426:             return false;
427:         }
428: 
429:         // Save datastore metadata
430:         $params = $this->filestore->getParameters();
431:         foreach ($params as $k => $v) {
432:             $this->setMetaData("filestore::$k", $v);
433:         }
434: 
435:         // Now make a note of the filestore class
436:         $this->setMetaData("filestore::filestore", get_class($this->filestore));
437: 
438:         return true;
439:     }
440: }
441: 
API documentation generated by ApiGen 2.8.0