Elgg  Version master
File.php
Go to the documentation of this file.
1 <?php
2 
3 namespace Elgg\FileService;
4 
8 
14 class File {
15 
16  const INLINE = 'inline';
17  const ATTACHMENT = 'attachment';
18 
22  private $file;
23 
27  private $expires;
28 
32  private $disposition;
33 
37  private $use_cookie = true;
38 
45  public function setFile(\ElggFile $file) {
46  $this->file = $file;
47  }
48 
54  public function getFile(): ?\ElggFile {
55  return $this->file;
56  }
57 
65  public function setExpires(string $expires = '+2 hours'): void {
66  $this->expires = strtotime($expires);
67  }
68 
77  public function setDisposition(string $disposition = self::ATTACHMENT): void {
78  if (!in_array($disposition, [self::ATTACHMENT, self::INLINE])) {
79  throw new DomainException("Disposition {$disposition} is not supported in " . __CLASS__);
80  }
81 
82  $this->disposition = $disposition;
83  }
84 
92  public function bindSession(bool $use_cookie = true): void {
93  $this->use_cookie = $use_cookie;
94  }
95 
101  public function getURL(): ?string {
102 
103  if (!$this->file->exists()) {
104  elgg_log('Unable to resolve resource URL for a file that does not exist on filestore');
105  return null;
106  }
107 
108  $relative_path = '';
109  $root_prefix = Paths::sanitize(_elgg_services()->config->dataroot);
110  $path = Paths::sanitize($this->file->getFilenameOnFilestore(), false);
111  if (str_starts_with($path, $root_prefix)) {
112  $relative_path = substr($path, strlen($root_prefix));
113  }
114 
115  if (!$relative_path) {
116  elgg_log('Unable to resolve relative path of the file on the filestore');
117  return null;
118  }
119 
120  if (preg_match('~[^a-zA-Z0-9_\./ ]~', $relative_path)) {
121  // Filenames may contain special characters that result in malformatted URLs
122  // and/or HMAC mismatches. We want to avoid that by encoding the path.
123  $relative_path = ':' . Base64Url::encode($relative_path);
124  }
125 
126  $data = [
127  'expires' => $this->expires ?? 0,
128  'last_updated' => filemtime($this->file->getFilenameOnFilestore()),
129  'disposition' => $this->disposition === self::INLINE ? 'i' : 'a',
130  'path' => $relative_path,
131  ];
132 
133  if ($this->use_cookie) {
134  $data['cookie'] = _elgg_services()->session->getID();
135  if (empty($data['cookie'])) {
136  return null;
137  }
138 
139  $data['use_cookie'] = 1;
140  } else {
141  $data['use_cookie'] = 0;
142  }
143 
144  ksort($data);
145  $mac = _elgg_services()->hmac->getHmac($data)->getToken();
146 
147  $url_segments = [
148  'serve-file',
149  "e{$data['expires']}",
150  "l{$data['last_updated']}",
151  "d{$data['disposition']}",
152  "c{$data['use_cookie']}",
153  $mac,
154  $relative_path,
155  ];
156 
157  return elgg_normalize_url(implode('/', $url_segments));
158  }
159 }
return[ 'admin/delete_admin_notices'=>['access'=> 'admin'], 'admin/menu/save'=>['access'=> 'admin'], 'admin/plugins/activate'=>['access'=> 'admin'], 'admin/plugins/activate_all'=>['access'=> 'admin'], 'admin/plugins/deactivate'=>['access'=> 'admin'], 'admin/plugins/deactivate_all'=>['access'=> 'admin'], 'admin/plugins/set_priority'=>['access'=> 'admin'], 'admin/security/security_txt'=>['access'=> 'admin'], 'admin/security/settings'=>['access'=> 'admin'], 'admin/security/regenerate_site_secret'=>['access'=> 'admin'], 'admin/site/cache/invalidate'=>['access'=> 'admin'], 'admin/site/flush_cache'=>['access'=> 'admin'], 'admin/site/icons'=>['access'=> 'admin'], 'admin/site/set_maintenance_mode'=>['access'=> 'admin'], 'admin/site/set_robots'=>['access'=> 'admin'], 'admin/site/theme'=>['access'=> 'admin'], 'admin/site/unlock_upgrade'=>['access'=> 'admin'], 'admin/site/settings'=>['access'=> 'admin'], 'admin/upgrade'=>['access'=> 'admin'], 'admin/upgrade/reset'=>['access'=> 'admin'], 'admin/user/ban'=>['access'=> 'admin'], 'admin/user/bulk/ban'=>['access'=> 'admin'], 'admin/user/bulk/delete'=>['access'=> 'admin'], 'admin/user/bulk/unban'=>['access'=> 'admin'], 'admin/user/bulk/validate'=>['access'=> 'admin'], 'admin/user/change_email'=>['access'=> 'admin'], 'admin/user/delete'=>['access'=> 'admin'], 'admin/user/login_as'=>['access'=> 'admin'], 'admin/user/logout_as'=>[], 'admin/user/makeadmin'=>['access'=> 'admin'], 'admin/user/resetpassword'=>['access'=> 'admin'], 'admin/user/removeadmin'=>['access'=> 'admin'], 'admin/user/unban'=>['access'=> 'admin'], 'admin/user/validate'=>['access'=> 'admin'], 'annotation/delete'=>[], 'avatar/upload'=>[], 'comment/save'=>[], 'diagnostics/download'=>['access'=> 'admin'], 'entity/chooserestoredestination'=>[], 'entity/delete'=>[], 'entity/mute'=>[], 'entity/restore'=>[], 'entity/subscribe'=>[], 'entity/trash'=>[], 'entity/unmute'=>[], 'entity/unsubscribe'=>[], 'login'=>['access'=> 'logged_out'], 'logout'=>[], 'notifications/mute'=>['access'=> 'public'], 'plugins/settings/remove'=>['access'=> 'admin'], 'plugins/settings/save'=>['access'=> 'admin'], 'plugins/usersettings/save'=>[], 'register'=>['access'=> 'logged_out', 'middleware'=>[\Elgg\Router\Middleware\RegistrationAllowedGatekeeper::class,],], 'river/delete'=>[], 'settings/notifications'=>[], 'settings/notifications/subscriptions'=>[], 'user/changepassword'=>['access'=> 'public'], 'user/requestnewpassword'=>['access'=> 'public'], 'useradd'=>['access'=> 'admin'], 'usersettings/save'=>[], 'widgets/add'=>[], 'widgets/delete'=>[], 'widgets/move'=>[], 'widgets/save'=>[],]
Definition: actions.php:73
if(! $entity instanceof \ElggUser) $data
Definition: attributes.php:13
Exception thrown if a value does not adhere to a defined valid data domain.
File service.
Definition: File.php:14
getFile()
Returns file object.
Definition: File.php:54
bindSession(bool $use_cookie=true)
Bind URL to current user session.
Definition: File.php:92
setDisposition(string $disposition=self::ATTACHMENT)
Sets content disposition.
Definition: File.php:77
getURL()
Returns publicly accessible URL.
Definition: File.php:101
setFile(\ElggFile $file)
Set file object.
Definition: File.php:45
setExpires(string $expires='+2 hours')
Sets URL expiration.
Definition: File.php:65
Find Elgg and project paths.
Definition: Paths.php:8
Encode and decode Base 64 URL.
Definition: Base64Url.php:10
elgg_log($message, $level=\Psr\Log\LogLevel::NOTICE)
Log a message.
Definition: elgglib.php:88
_elgg_services()
Get the global service provider.
Definition: elgglib.php:353
$mac
Definition: contents.php:14
$path
Definition: details.php:70
elgg_normalize_url(string $url)
Definition: output.php:163
if(parse_url(elgg_get_site_url(), PHP_URL_PATH) !=='/') if(file_exists(elgg_get_root_path() . 'robots.txt'))
Set robots.txt.
Definition: robots.php:10
$expires