CakePHP
  • Documentation
    • Book
    • API
    • Videos
    • Logos & Trademarks
  • Business Solutions
  • Swag
  • Road Trip
  • Team
  • Community
    • Community
    • Team
    • Issues (Github)
    • YouTube Channel
    • Get Involved
    • Bakery
    • Featured Resources
    • Newsletter
    • Certification
    • My CakePHP
    • CakeFest
    • Facebook
    • Twitter
    • Help & Support
    • Forum
    • Stack Overflow
    • IRC
    • Slack
    • Paid Support
CakePHP

C CakePHP 3.7 Red Velvet API

  • Overview
  • Tree
  • Deprecated
  • Version:
    • 3.7
      • 3.7
      • 3.6
      • 3.5
      • 3.4
      • 3.3
      • 3.2
      • 3.1
      • 3.0
      • 2.10
      • 2.9
      • 2.8
      • 2.7
      • 2.6
      • 2.5
      • 2.4
      • 2.3
      • 2.2
      • 2.1
      • 2.0
      • 1.3
      • 1.2

Namespaces

  • Cake
    • Auth
      • Storage
    • Cache
      • Engine
    • Collection
      • Iterator
    • Command
    • Console
      • Exception
    • Controller
      • Component
      • Exception
    • Core
      • Configure
        • Engine
      • Exception
      • Retry
    • Database
      • Driver
      • Exception
      • Expression
      • Schema
      • Statement
      • Type
    • Datasource
      • Exception
    • Error
      • Middleware
    • Event
      • Decorator
    • Filesystem
    • Form
    • Http
      • Client
        • Adapter
        • Auth
      • Cookie
      • Exception
      • Middleware
      • Session
    • I18n
      • Formatter
      • Middleware
      • Parser
    • Log
      • Engine
    • Mailer
      • Exception
      • Transport
    • Network
      • Exception
    • ORM
      • Association
      • Behavior
        • Translate
      • Exception
      • Locator
      • Rule
    • Routing
      • Exception
      • Filter
      • Middleware
      • Route
    • Shell
      • Helper
      • Task
    • TestSuite
      • Fixture
      • Stub
    • Utility
      • Exception
    • Validation
    • View
      • Exception
      • Form
      • Helper
      • Widget
  • None

Classes

  • AssetsTask
  • CommandTask
  • ExtractTask
  • LoadTask
  • UnloadTask
  1: <?php
  2: /**
  3:  * CakePHP(tm) : Rapid Development Framework (https://cakephp.org)
  4:  * Copyright (c) Cake Software Foundation, Inc. (https://cakefoundation.org)
  5:  *
  6:  * Licensed under The MIT License
  7:  * For full copyright and license information, please see the LICENSE.txt
  8:  * Redistributions of files must retain the above copyright notice.
  9:  *
 10:  * @copyright     Copyright (c) Cake Software Foundation, Inc. (https://cakefoundation.org)
 11:  * @link          https://cakephp.org CakePHP(tm) Project
 12:  * @since         3.0.0
 13:  * @license       https://opensource.org/licenses/mit-license.php MIT License
 14:  */
 15: namespace Cake\Shell\Task;
 16: 
 17: use Cake\Console\Shell;
 18: use Cake\Core\Plugin;
 19: use Cake\Filesystem\Folder;
 20: use Cake\Utility\Inflector;
 21: 
 22: /**
 23:  * Task for symlinking / copying plugin assets to app's webroot.
 24:  */
 25: class AssetsTask extends Shell
 26: {
 27: 
 28:     /**
 29:      * Attempt to symlink plugin assets to app's webroot. If symlinking fails it
 30:      * fallbacks to copying the assets. For vendor namespaced plugin, parent folder
 31:      * for vendor name are created if required.
 32:      *
 33:      * @param string|null $name Name of plugin for which to symlink assets.
 34:      *   If null all plugins will be processed.
 35:      * @return void
 36:      */
 37:     public function symlink($name = null)
 38:     {
 39:         $this->_process($this->_list($name));
 40:     }
 41: 
 42:     /**
 43:      * Copying plugin assets to app's webroot. For vendor namespaced plugin,
 44:      * parent folder for vendor name are created if required.
 45:      *
 46:      * @param string|null $name Name of plugin for which to symlink assets.
 47:      *   If null all plugins will be processed.
 48:      * @return void
 49:      */
 50:     public function copy($name = null)
 51:     {
 52:         $this->_process($this->_list($name), true, $this->param('overwrite'));
 53:     }
 54: 
 55:     /**
 56:      * Remove plugin assets from app's webroot.
 57:      *
 58:      * @param string|null $name Name of plugin for which to remove assets.
 59:      *   If null all plugins will be processed.
 60:      * @return void
 61:      * @since 3.5.12
 62:      */
 63:     public function remove($name = null)
 64:     {
 65:         $plugins = $this->_list($name);
 66: 
 67:         foreach ($plugins as $plugin => $config) {
 68:             $this->out();
 69:             $this->out('For plugin: ' . $plugin);
 70:             $this->hr();
 71: 
 72:             $this->_remove($config);
 73:         }
 74: 
 75:         $this->out();
 76:         $this->out('Done');
 77:     }
 78: 
 79:     /**
 80:      * Get list of plugins to process. Plugins without a webroot directory are skipped.
 81:      *
 82:      * @param string|null $name Name of plugin for which to symlink assets.
 83:      *   If null all plugins will be processed.
 84:      * @return array List of plugins with meta data.
 85:      */
 86:     protected function _list($name = null)
 87:     {
 88:         if ($name === null) {
 89:             $pluginsList = Plugin::loaded();
 90:         } else {
 91:             if (!Plugin::isLoaded($name)) {
 92:                 $this->err(sprintf('Plugin %s is not loaded.', $name));
 93: 
 94:                 return [];
 95:             }
 96:             $pluginsList = [$name];
 97:         }
 98: 
 99:         $plugins = [];
100: 
101:         foreach ($pluginsList as $plugin) {
102:             $path = Plugin::path($plugin) . 'webroot';
103:             if (!is_dir($path)) {
104:                 $this->verbose('', 1);
105:                 $this->verbose(
106:                     sprintf('Skipping plugin %s. It does not have webroot folder.', $plugin),
107:                     2
108:                 );
109:                 continue;
110:             }
111: 
112:             $link = Inflector::underscore($plugin);
113:             $dir = WWW_ROOT;
114:             $namespaced = false;
115:             if (strpos($link, '/') !== false) {
116:                 $namespaced = true;
117:                 $parts = explode('/', $link);
118:                 $link = array_pop($parts);
119:                 $dir = WWW_ROOT . implode(DIRECTORY_SEPARATOR, $parts) . DIRECTORY_SEPARATOR;
120:             }
121: 
122:             $plugins[$plugin] = [
123:                 'srcPath' => Plugin::path($plugin) . 'webroot',
124:                 'destDir' => $dir,
125:                 'link' => $link,
126:                 'namespaced' => $namespaced
127:             ];
128:         }
129: 
130:         return $plugins;
131:     }
132: 
133:     /**
134:      * Process plugins
135:      *
136:      * @param array $plugins List of plugins to process
137:      * @param bool $copy Force copy mode. Default false.
138:      * @param bool $overwrite Overwrite existing files.
139:      * @return void
140:      */
141:     protected function _process($plugins, $copy = false, $overwrite = false)
142:     {
143:         $overwrite = (bool)$this->param('overwrite');
144: 
145:         foreach ($plugins as $plugin => $config) {
146:             $this->out();
147:             $this->out('For plugin: ' . $plugin);
148:             $this->hr();
149: 
150:             if ($config['namespaced'] &&
151:                 !is_dir($config['destDir']) &&
152:                 !$this->_createDirectory($config['destDir'])
153:             ) {
154:                 continue;
155:             }
156: 
157:             $dest = $config['destDir'] . $config['link'];
158: 
159:             if (file_exists($dest)) {
160:                 if ($overwrite && !$this->_remove($config)) {
161:                     continue;
162:                 } elseif (!$overwrite) {
163:                     $this->verbose(
164:                         $dest . ' already exists',
165:                         1
166:                     );
167: 
168:                     continue;
169:                 }
170:             }
171: 
172:             if (!$copy) {
173:                 $result = $this->_createSymlink(
174:                     $config['srcPath'],
175:                     $dest
176:                 );
177:                 if ($result) {
178:                     continue;
179:                 }
180:             }
181: 
182:             $this->_copyDirectory(
183:                 $config['srcPath'],
184:                 $dest
185:             );
186:         }
187: 
188:         $this->out();
189:         $this->out('Done');
190:     }
191: 
192:     /**
193:      * Remove folder/symlink.
194:      *
195:      * @param array $config Plugin config.
196:      * @return bool
197:      */
198:     protected function _remove($config)
199:     {
200:         if ($config['namespaced'] && !is_dir($config['destDir'])) {
201:             $this->verbose(
202:                 $config['destDir'] . $config['link'] . ' does not exist',
203:                 1
204:             );
205: 
206:             return false;
207:         }
208: 
209:         $dest = $config['destDir'] . $config['link'];
210: 
211:         if (!file_exists($dest)) {
212:             $this->verbose(
213:                 $dest . ' does not exist',
214:                 1
215:             );
216: 
217:             return false;
218:         }
219: 
220:         if (is_link($dest)) {
221:             // @codingStandardsIgnoreLine
222:             if (@unlink($dest)) {
223:                 $this->out('Unlinked ' . $dest);
224: 
225:                 return true;
226:             } else {
227:                 $this->err('Failed to unlink  ' . $dest);
228: 
229:                 return false;
230:             }
231:         }
232: 
233:         $folder = new Folder($dest);
234:         if ($folder->delete()) {
235:             $this->out('Deleted ' . $dest);
236: 
237:             return true;
238:         } else {
239:             $this->err('Failed to delete ' . $dest);
240: 
241:             return false;
242:         }
243:     }
244: 
245:     /**
246:      * Create directory
247:      *
248:      * @param string $dir Directory name
249:      * @return bool
250:      */
251:     protected function _createDirectory($dir)
252:     {
253:         $old = umask(0);
254:         // @codingStandardsIgnoreStart
255:         $result = @mkdir($dir, 0755, true);
256:         // @codingStandardsIgnoreEnd
257:         umask($old);
258: 
259:         if ($result) {
260:             $this->out('Created directory ' . $dir);
261: 
262:             return true;
263:         }
264: 
265:         $this->err('Failed creating directory ' . $dir);
266: 
267:         return false;
268:     }
269: 
270:     /**
271:      * Create symlink
272:      *
273:      * @param string $target Target directory
274:      * @param string $link Link name
275:      * @return bool
276:      */
277:     protected function _createSymlink($target, $link)
278:     {
279:         // @codingStandardsIgnoreStart
280:         $result = @symlink($target, $link);
281:         // @codingStandardsIgnoreEnd
282: 
283:         if ($result) {
284:             $this->out('Created symlink ' . $link);
285: 
286:             return true;
287:         }
288: 
289:         return false;
290:     }
291: 
292:     /**
293:      * Copy directory
294:      *
295:      * @param string $source Source directory
296:      * @param string $destination Destination directory
297:      * @return bool
298:      */
299:     protected function _copyDirectory($source, $destination)
300:     {
301:         $folder = new Folder($source);
302:         if ($folder->copy(['to' => $destination])) {
303:             $this->out('Copied assets to directory ' . $destination);
304: 
305:             return true;
306:         }
307: 
308:         $this->err('Error copying assets to directory ' . $destination);
309: 
310:         return false;
311:     }
312: 
313:     /**
314:      * Gets the option parser instance and configures it.
315:      *
316:      * @return \Cake\Console\ConsoleOptionParser
317:      */
318:     public function getOptionParser()
319:     {
320:         $parser = parent::getOptionParser();
321: 
322:         $parser->addSubcommand('symlink', [
323:             'help' => 'Symlink (copy as fallback) plugin assets to app\'s webroot.'
324:         ])->addSubcommand('copy', [
325:             'help' => 'Copy plugin assets to app\'s webroot.'
326:         ])->addSubcommand('remove', [
327:             'help' => 'Remove plugin assets from app\'s webroot.'
328:         ])->addArgument('name', [
329:             'help' => 'A specific plugin you want to symlink assets for.',
330:             'optional' => true,
331:         ])->addOption('overwrite', [
332:             'help' => 'Overwrite existing symlink / folder / files.',
333:             'default' => false,
334:             'boolean' => true
335:         ]);
336: 
337:         return $parser;
338:     }
339: }
340: 
Follow @CakePHP
#IRC
OpenHub
Rackspace
  • Business Solutions
  • Showcase
  • Documentation
  • Book
  • API
  • Videos
  • Logos & Trademarks
  • Community
  • Team
  • Issues (Github)
  • YouTube Channel
  • Get Involved
  • Bakery
  • Featured Resources
  • Newsletter
  • Certification
  • My CakePHP
  • CakeFest
  • Facebook
  • Twitter
  • Help & Support
  • Forum
  • Stack Overflow
  • IRC
  • Slack
  • Paid Support

Generated using CakePHP API Docs