/vendor/devfactory/minify/src/Providers/BaseProvider.php
https://github.com/freescout-helpdesk/freescout · PHP · 360 lines · 207 code · 54 blank · 99 comment · 23 complexity · 71fca8b773e06beadcbbccecbd38fb78 MD5 · raw file
- <?php namespace Devfactory\Minify\Providers;
- use Devfactory\Minify\Exceptions\CannotRemoveFileException;
- use Devfactory\Minify\Exceptions\CannotSaveFileException;
- use Devfactory\Minify\Exceptions\DirNotExistException;
- use Devfactory\Minify\Exceptions\DirNotWritableException;
- use Devfactory\Minify\Exceptions\FileNotExistException;
- use Illuminate\Filesystem\Filesystem;
- use Countable;
- abstract class BaseProvider implements Countable
- {
- /**
- * @var string
- */
- protected $outputDir;
- /**
- * @var string
- */
- protected $appended = '';
- /**
- * @var string
- */
- protected $filename = '';
- /**
- * @var array
- */
- protected $files = array();
- /**
- * @var array
- */
- protected $headers = array();
- /**
- * @var string
- */
- private $publicPath;
- /**
- * @var Illuminate\Foundation\Filesystem
- */
- protected $file;
- /**
- * @var boolean
- */
- private $disable_mtime;
- /**
- * @var string
- */
- private $hash_salt;
- /**
- * @param null $publicPath
- */
- public function __construct($publicPath = null, $config = null, Filesystem $file = null)
- {
- $this->file = $file ?: new Filesystem;
- $this->publicPath = $publicPath ?: $_SERVER['DOCUMENT_ROOT'];
- $this->disable_mtime = $config['disable_mtime'] ?: false;
- $this->hash_salt = $config['hash_salt'] ?: '';
- $value = function($key)
- {
- return isset($_SERVER[$key]) ? $_SERVER[$key] : '';
- };
- $this->headers = array(
- 'User-Agent' => $value('HTTP_USER_AGENT'),
- 'Accept' => $value('HTTP_ACCEPT'),
- 'Accept-Language' => $value('HTTP_ACCEPT_LANGUAGE'),
- 'Accept-Encoding' => 'identity',
- 'Connection' => 'close',
- );
- }
- /**
- * @param $outputDir
- * @return bool
- */
- public function make($outputDir)
- {
- $this->outputDir = $this->publicPath . $outputDir;
- $this->checkDirectory();
- if ($this->checkExistingFiles())
- {
- return false;
- }
- $this->removeOldFiles();
- $this->appendFiles();
- return true;
- }
- /**
- * @param $file
- * @return void
- * @throws \Devfactory\Minify\Exceptions\FileNotExistException
- */
- public function add($file)
- {
- if (is_array($file))
- {
- foreach ($file as $value) $this->add($value);
- }
- else if ($this->checkExternalFile($file))
- {
- $this->files[] = $file;
- }
- else {
- $file = $this->publicPath . $file;
- if (!file_exists($file))
- {
- throw new FileNotExistException("File '{$file}' does not exist");
- }
- $this->files[] = $file;
- }
- }
- /**
- * @param $baseUrl
- * @param $attributes
- *
- * @return string
- */
- public function tags($baseUrl, $attributes)
- {
- $html = '';
- foreach($this->files as $file)
- {
- $file = $baseUrl . str_replace($this->publicPath, '', $file);
- $html .= $this->tag($file, $attributes);
- }
- return $html;
- }
- /**
- * @return int
- */
- public function count()
- {
- return count($this->files);
- }
- /**
- * @throws \Devfactory\Minify\Exceptions\FileNotExistException
- */
- protected function appendFiles()
- {
- foreach ($this->files as $file) {
- if ($this->checkExternalFile($file))
- {
- if (strpos($file, '//') === 0) $file = 'http:' . $file;
- $headers = $this->headers;
- foreach ($headers as $key => $value)
- {
- $headers[$key] = $key . ': ' . $value;
- }
- $context = stream_context_create(array('http' => array(
- 'ignore_errors' => true,
- 'header' => implode("\r\n", $headers),
- )));
- $http_response_header = array(false);
- $contents = file_get_contents($file, false, $context);
- if (strpos($http_response_header[0], '200') === false)
- {
- throw new FileNotExistException("File '{$file}' does not exist");
- }
- } else {
- $contents = file_get_contents($file);
- }
- $this->appended .= $contents . "\n";
- }
- }
- /**
- * @return bool
- */
- protected function checkExistingFiles()
- {
- $this->buildMinifiedFilename();
- return file_exists($this->outputDir . $this->filename);
- }
- /**
- * @throws \Devfactory\Minify\Exceptions\DirNotWritableException
- * @throws \Devfactory\Minify\Exceptions\DirNotExistException
- */
- protected function checkDirectory()
- {
- if (!file_exists($this->outputDir))
- {
- // Try to create the directory
- if (!$this->file->makeDirectory($this->outputDir, 0775, true)) {
- throw new DirNotExistException("Buildpath '{$this->outputDir}' does not exist");
- }
- }
- if (!is_writable($this->outputDir))
- {
- throw new DirNotWritableException("Buildpath '{$this->outputDir}' is not writable");
- }
- }
- /**
- * @param string $file
- * @return bool
- */
- protected function checkExternalFile($file)
- {
- return preg_match('/^(https?:)?\/\//', $file);
- }
- /**
- * @return string
- */
- protected function buildMinifiedFilename()
- {
- $this->filename = $this->getHashedFilename() . (($this->disable_mtime) ? '' : $this->countModificationTime()) . static::EXTENSION;
- }
- /**
- * Build an HTML attribute string from an array.
- *
- * @param array $attributes
- * @return string
- */
- protected function attributes($attributes)
- {
- $html = array();
- foreach ((array) $attributes as $key => $value)
- {
- $element = $this->attributeElement($key, $value);
- if ( ! is_null($element)) $html[] = $element;
- }
- $output = count($html) > 0 ? ' '.implode(' ', $html) : '';
- return trim($output);
- }
- /**
- * Build a single attribute element.
- *
- * @param string|integer $key
- * @param string|boolean $value
- * @return string|null
- */
- protected function attributeElement($key, $value)
- {
- if (is_numeric($key)) $key = $value;
- if(is_bool($value))
- return $key;
- if ( ! is_null($value))
- return $key.'="'.htmlentities($value, ENT_QUOTES, 'UTF-8', false).'"';
- return null;
- }
- /**
- * @return string
- */
- protected function getHashedFilename()
- {
- $publicPath = $this->publicPath;
- return md5(implode('-', array_map(function($file) use ($publicPath) { return str_replace($publicPath, '', $file); }, $this->files)) . $this->hash_salt);
- }
- /**
- * @return int
- */
- protected function countModificationTime()
- {
- $time = 0;
- foreach ($this->files as $file)
- {
- if ($this->checkExternalFile($file))
- {
- $userAgent = isset($this->headers['User-Agent']) ? $this->headers['User-Agent'] : '';
- $time += hexdec(substr(md5($file . $userAgent), 0, 8));
- }
- else {
- $time += filemtime($file);
- }
- }
- return $time;
- }
- /**
- * @throws \Devfactory\Minify\Exceptions\CannotRemoveFileException
- */
- protected function removeOldFiles()
- {
- $pattern = $this->outputDir . $this->getHashedFilename() . '*';
- $find = glob($pattern);
- if( is_array($find) && count($find) )
- {
- foreach ($find as $file)
- {
- if ( ! unlink($file) ) {
- throw new CannotRemoveFileException("File '{$file}' cannot be removed");
- }
- }
- }
- }
- /**
- * @param $minified
- * @return string
- * @throws \Devfactory\Minify\Exceptions\CannotSaveFileException
- */
- protected function put($minified)
- {
- if(file_put_contents($this->outputDir . $this->filename, $minified) === false)
- {
- throw new CannotSaveFileException("File '{$this->outputDir}{$this->filename}' cannot be saved");
- }
- return $this->filename;
- }
- /**
- * @return string
- */
- public function getAppended()
- {
- return $this->appended;
- }
- /**
- * @return string
- */
- public function getFilename()
- {
- return $this->filename;
- }
- }