TYPO3 CMS  TYPO3_7-6
AbstractFile.php
Go to the documentation of this file.
1 <?php
3 
4 /*
5  * This file is part of the TYPO3 CMS project.
6  *
7  * It is free software; you can redistribute it and/or modify it under
8  * the terms of the GNU General Public License, either version 2
9  * of the License, or any later version.
10  *
11  * For the full copyright and license information, please read the
12  * LICENSE.txt file that was distributed with this source code.
13  *
14  * The TYPO3 project - inspiring people to share!
15  */
16 
18 
22 abstract class AbstractFile implements FileInterface
23 {
33  protected $properties;
34 
40  protected $storage = null;
41 
49  protected $identifier;
50 
56  protected $name;
57 
63  protected $deleted = false;
64 
68  const FILETYPE_UNKNOWN = 0;
69 
74  const FILETYPE_TEXT = 1;
75 
80  const FILETYPE_IMAGE = 2;
81 
86  const FILETYPE_AUDIO = 3;
87 
92  const FILETYPE_VIDEO = 4;
93 
99 
100  /******************
101  * VARIOUS FILE PROPERTY GETTERS
102  ******************/
109  public function hasProperty($key)
110  {
111  return array_key_exists($key, $this->properties);
112  }
113 
120  public function getProperty($key)
121  {
122  if ($this->hasProperty($key)) {
123  return $this->properties[$key];
124  } else {
125  return null;
126  }
127  }
128 
134  public function getProperties()
135  {
136  return $this->properties;
137  }
138 
144  public function getIdentifier()
145  {
146  return $this->identifier;
147  }
148 
154  public function getHashedIdentifier()
155  {
156  return $this->properties['identifier_hash'];
157  }
158 
164  public function getName()
165  {
166  // Do not check if file has been deleted because we might need the
167  // name for undeleting it.
168  return $this->name;
169  }
170 
176  public function getNameWithoutExtension()
177  {
178  return PathUtility::pathinfo($this->getName(), PATHINFO_FILENAME);
179  }
180 
187  public function getSize()
188  {
189  if ($this->deleted) {
190  throw new \RuntimeException('File has been deleted.', 1329821480);
191  }
192  if (empty($this->properties['size'])) {
193  $size = array_pop($this->getStorage()->getFileInfoByIdentifier($this->getIdentifier(), ['size']));
194  } else {
195  $size = $this->properties['size'];
196  }
197  return $size ? (int)$size : null;
198  }
199 
205  public function getUid()
206  {
207  return (int)$this->getProperty('uid');
208  }
209 
216  public function getSha1()
217  {
218  if ($this->deleted) {
219  throw new \RuntimeException('File has been deleted.', 1329821481);
220  }
221  return $this->getStorage()->hashFile($this, 'sha1');
222  }
223 
230  public function getCreationTime()
231  {
232  if ($this->deleted) {
233  throw new \RuntimeException('File has been deleted.', 1329821487);
234  }
235  return (int)$this->getProperty('creation_date');
236  }
237 
244  public function getModificationTime()
245  {
246  if ($this->deleted) {
247  throw new \RuntimeException('File has been deleted.', 1329821488);
248  }
249  return (int)$this->getProperty('modification_date');
250  }
251 
257  public function getExtension()
258  {
259  $pathinfo = PathUtility::pathinfo($this->getName());
260 
261  $extension = strtolower($pathinfo['extension']);
262 
263  return $extension;
264  }
265 
271  public function getMimeType()
272  {
273  return $this->properties['mime_type'] ?: array_pop($this->getStorage()->getFileInfoByIdentifier($this->getIdentifier(), ['mimetype']));
274  }
275 
289  public function getType()
290  {
291  // this basically extracts the mimetype and guess the filetype based
292  // on the first part of the mimetype works for 99% of all cases, and
293  // we don't need to make an SQL statement like EXT:media does currently
294  if (!$this->properties['type']) {
295  $mimeType = $this->getMimeType();
296  list($fileType) = explode('/', $mimeType);
297  switch (strtolower($fileType)) {
298  case 'text':
299  $this->properties['type'] = self::FILETYPE_TEXT;
300  break;
301  case 'image':
302  $this->properties['type'] = self::FILETYPE_IMAGE;
303  break;
304  case 'audio':
305  $this->properties['type'] = self::FILETYPE_AUDIO;
306  break;
307  case 'video':
308  $this->properties['type'] = self::FILETYPE_VIDEO;
309  break;
310  case 'application':
311 
312  case 'software':
313  $this->properties['type'] = self::FILETYPE_APPLICATION;
314  break;
315  default:
316  $this->properties['type'] = self::FILETYPE_UNKNOWN;
317  }
318  }
319  return (int)$this->properties['type'];
320  }
321 
322  /******************
323  * CONTENTS RELATED
324  ******************/
331  public function getContents()
332  {
333  if ($this->deleted) {
334  throw new \RuntimeException('File has been deleted.', 1329821479);
335  }
336  return $this->getStorage()->getFileContents($this);
337  }
338 
347  public function setContents($contents)
348  {
349  if ($this->deleted) {
350  throw new \RuntimeException('File has been deleted.', 1329821478);
351  }
352  $this->getStorage()->setFileContents($this, $contents);
353  return $this;
354  }
355 
356  /****************************************
357  * STORAGE AND MANAGEMENT RELATED METHDOS
358  ****************************************/
359 
366  public function getStorage()
367  {
368  if ($this->storage === null) {
369  throw new \RuntimeException('You\'re using fileObjects without a storage.', 1381570091);
370  }
371  return $this->storage;
372  }
373 
381  public function exists()
382  {
383  if ($this->deleted) {
384  return false;
385  }
386  return $this->storage->hasFile($this->getIdentifier());
387  }
388 
398  {
399  $this->storage = $storage;
400  $this->properties['storage'] = $storage->getUid();
401  return $this;
402  }
403 
411  public function setIdentifier($identifier)
412  {
413  $this->identifier = $identifier;
414  return $this;
415  }
416 
423  public function getCombinedIdentifier()
424  {
425  if (is_array($this->properties) && \TYPO3\CMS\Core\Utility\MathUtility::canBeInterpretedAsInteger($this->properties['storage'])) {
426  $combinedIdentifier = $this->properties['storage'] . ':' . $this->getIdentifier();
427  } else {
428  $combinedIdentifier = $this->getStorage()->getUid() . ':' . $this->getIdentifier();
429  }
430  return $combinedIdentifier;
431  }
432 
438  public function delete()
439  {
440  // The storage will mark this file as deleted
441  $wasDeleted = $this->getStorage()->deleteFile($this);
442 
443  // Unset all properties when deleting the file, as they will be stale anyway
444  // This needs to happen AFTER the storage deleted the file, because the storage
445  // emits a signal, which passes the file object to the slots, which may need
446  // all file properties of the deleted file.
447  $this->properties = [];
448 
449  return $wasDeleted;
450  }
451 
458  public function setDeleted()
459  {
460  $this->deleted = true;
461  }
462 
468  public function isDeleted()
469  {
470  return $this->deleted;
471  }
472 
481  public function rename($newName)
482  {
483  if ($this->deleted) {
484  throw new \RuntimeException('File has been deleted.', 1329821482);
485  }
486  return $this->getStorage()->renameFile($this, $newName);
487  }
488 
499  public function copyTo(Folder $targetFolder, $targetFileName = null, $conflictMode = DuplicationBehavior::RENAME)
500  {
501  if ($this->deleted) {
502  throw new \RuntimeException('File has been deleted.', 1329821483);
503  }
504  return $targetFolder->getStorage()->copyFile($this, $targetFolder, $targetFileName, $conflictMode);
505  }
506 
517  public function moveTo(Folder $targetFolder, $targetFileName = null, $conflictMode = DuplicationBehavior::RENAME)
518  {
519  if ($this->deleted) {
520  throw new \RuntimeException('File has been deleted.', 1329821484);
521  }
522  return $targetFolder->getStorage()->moveFile($this, $targetFolder, $targetFileName, $conflictMode);
523  }
524 
525  /*****************
526  * SPECIAL METHODS
527  *****************/
537  public function getPublicUrl($relativeToCurrentScript = false)
538  {
539  if ($this->deleted) {
540  return null;
541  } else {
542  return $this->getStorage()->getPublicUrl($this, $relativeToCurrentScript);
543  }
544  }
545 
556  public function getForLocalProcessing($writable = true)
557  {
558  if ($this->deleted) {
559  throw new \RuntimeException('File has been deleted.', 1329821486);
560  }
561  return $this->getStorage()->getFileForLocalProcessing($this, $writable);
562  }
563 
564  /***********************
565  * INDEX RELATED METHODS
566  ***********************/
574  abstract public function updateProperties(array $properties);
575 
581  public function getParentFolder()
582  {
583  return $this->getStorage()->getFolder($this->getStorage()->getFolderIdentifierFromFileIdentifier($this->getIdentifier()));
584  }
585 }
moveTo(Folder $targetFolder, $targetFileName=null, $conflictMode=DuplicationBehavior::RENAME)
copyTo(Folder $targetFolder, $targetFileName=null, $conflictMode=DuplicationBehavior::RENAME)
static pathinfo($path, $options=null)
setStorage(ResourceStorage $storage)
getPublicUrl($relativeToCurrentScript=false)