MediaWiki master
StreamFile.php
Go to the documentation of this file.
1<?php
2
24namespace MediaWiki\Output;
25
26use FileBackend;
28use InvalidArgumentException;
31use UploadBase;
32
38 private const UNKNOWN_CONTENT_TYPE = 'unknown/unknown';
39
52 public static function stream(
53 $fname,
54 $headers = [],
55 $sendErrors = true,
56 $optHeaders = [],
57 $flags = 0
58 ) {
59 if ( FileBackend::isStoragePath( $fname ) ) {
60 throw new InvalidArgumentException( __FUNCTION__ . " given storage path '$fname'." );
61 }
62
63 $streamer = new HTTPFileStreamer(
64 $fname,
65 [
66 'obResetFunc' => 'wfResetOutputBuffers',
67 'streamMimeFunc' => [ __CLASS__, 'contentTypeFromPath' ]
68 ]
69 );
70
71 return $streamer->stream( $headers, $sendErrors, $optHeaders, $flags );
72 }
73
81 public static function contentTypeFromPath( $filename, $safe = true ) {
82 // NOTE: TrivialMimeDetection is forced by ThumbnailEntryPoint. When this
83 // code is moved to a non-static method in a service object, we can no
84 // longer rely on that.
85 $trivialMimeDetection = MediaWikiServices::getInstance()->getMainConfig()
87
88 $ext = strrchr( $filename, '.' );
89 $ext = $ext ? strtolower( substr( $ext, 1 ) ) : '';
90
91 # trivial detection by file extension,
92 # used for thumbnails (thumb.php)
93 if ( $trivialMimeDetection ) {
94 switch ( $ext ) {
95 case 'gif':
96 return 'image/gif';
97 case 'png':
98 return 'image/png';
99 case 'jpg':
100 case 'jpeg':
101 return 'image/jpeg';
102 }
103
104 return self::UNKNOWN_CONTENT_TYPE;
105 }
106
107 $magic = MediaWikiServices::getInstance()->getMimeAnalyzer();
108 // Use the extension only, rather than magic numbers, to avoid opening
109 // up vulnerabilities due to uploads of files with allowed extensions
110 // but disallowed types.
111 $type = $magic->getMimeTypeFromExtensionOrNull( $ext );
112
117 if ( $safe ) {
118 $mainConfig = MediaWikiServices::getInstance()->getMainConfig();
119 $prohibitedFileExtensions = $mainConfig->get( MainConfigNames::ProhibitedFileExtensions );
120 $checkFileExtensions = $mainConfig->get( MainConfigNames::CheckFileExtensions );
121 $strictFileExtensions = $mainConfig->get( MainConfigNames::StrictFileExtensions );
122 $fileExtensions = $mainConfig->get( MainConfigNames::FileExtensions );
123 $verifyMimeType = $mainConfig->get( MainConfigNames::VerifyMimeType );
124 $mimeTypeExclusions = $mainConfig->get( MainConfigNames::MimeTypeExclusions );
125 [ , $extList ] = UploadBase::splitExtensions( $filename );
126 if ( UploadBase::checkFileExtensionList( $extList, $prohibitedFileExtensions ) ) {
127 return self::UNKNOWN_CONTENT_TYPE;
128 }
129 if (
130 $checkFileExtensions &&
131 $strictFileExtensions &&
132 !UploadBase::checkFileExtensionList( $extList, $fileExtensions )
133 ) {
134 return self::UNKNOWN_CONTENT_TYPE;
135 }
136 if ( $verifyMimeType && $type !== null && in_array( strtolower( $type ), $mimeTypeExclusions ) ) {
137 return self::UNKNOWN_CONTENT_TYPE;
138 }
139 }
140 return $type;
141 }
142}
143
145class_alias( StreamFile::class, 'StreamFile' );
Base class for all file backend classes (including multi-write backends).
static isStoragePath( $path)
Check if a given path is a "mwstore://" path.
Functions related to the output of file content.
A class containing constants representing the names of configuration variables.
const MimeTypeExclusions
Name constant for the MimeTypeExclusions setting, for use with Config::get()
const ProhibitedFileExtensions
Name constant for the ProhibitedFileExtensions setting, for use with Config::get()
const TrivialMimeDetection
Name constant for the TrivialMimeDetection setting, for use with Config::get()
const VerifyMimeType
Name constant for the VerifyMimeType setting, for use with Config::get()
const StrictFileExtensions
Name constant for the StrictFileExtensions setting, for use with Config::get()
const FileExtensions
Name constant for the FileExtensions setting, for use with Config::get()
const CheckFileExtensions
Name constant for the CheckFileExtensions setting, for use with Config::get()
Service locator for MediaWiki core services.
static getInstance()
Returns the global default instance of the top level service locator.
Functions related to the output of file content.
static contentTypeFromPath( $filename, $safe=true)
Determine the file type of a file based on the path.
static stream( $fname, $headers=[], $sendErrors=true, $optHeaders=[], $flags=0)
Stream a file to the browser, adding all the headings and fun stuff.
UploadBase and subclasses are the backend of MediaWiki's file uploads.
static splitExtensions( $filename)
Split a file into a base name and all dot-delimited 'extensions' on the end.
static checkFileExtensionList( $ext, $list)
Perform case-insensitive match against a list of file extensions.