trentrichardson / cakephp-shrink

Shrink is a CakePHP plugin to Compile, Combine, Compress js, css, less, sass, coffee assets
16 stars 9 forks source link

Error: Class 'Shrink\Lib\ShrinkCompiler\ShrinkCompiler' not found #7

Closed danielignatius closed 8 years ago

danielignatius commented 8 years ago

I've followed the instruction below,

bootstrap.php Plugin::load('Shrink',['autoload'=>true]);

AppController.php $helpers = array('Form','Html',Shrink.Shrink');

pp/plugin Shrink folder

but I not sure why am I getting a Error: Class 'Shrink\Lib\ShrinkCompiler\ShrinkCompiler' not found in File D:\home\site\wwwroot\plugins\Shrink\src\Lib\ShrinkType.php.

I've added the class _use Shrink\Lib\ShrinkCompiler\ShrinkCompiler; _ in ShrinkType.php. it still showing the error.

Any advise please?

trentrichardson commented 8 years ago

When including the file via the helper are you including the file extension? Also what is the file extension? On Jan 31, 2016 8:00 PM, "Daniel" notifications@github.com wrote:

I've followed the instruction below,

bootstrap.php Plugin::load('Shrink',['autoload'=>true]);

AppController.php $helpers = array('Form','Html',Shrink.Shrink');

pp/plugin Shrink folder

but I not sure why am I getting a Error: Class 'Shrink\Lib\ShrinkCompiler\ShrinkCompiler' not found in File D:\home\site\wwwroot\plugins\Shrink\src\Lib\ShrinkType.php.

I've added the class _use Shrink\Lib\ShrinkCompiler\ShrinkCompiler; _ in ShrinkType.php. it still showing the error.

Any advise please?

— Reply to this email directly or view it on GitHub https://github.com/trentrichardson/cakephp-shrink/issues/7.

danielignatius commented 8 years ago

Thanks Richardson for your quick reply. I would like to compress my all my css files into one css file. What am I missing still?

AppController.php public $helpers = ['Form','Html','Time','Shrink.Shrink'];

Layout $this->Shrink->css(['/css/uni-icons.css','/assets/css/style.css']); echo $this->Shrink->fetch('css');

trentrichardson commented 8 years ago

That looks correct.. are you using composer, and is it in composer.json? Maybe try composer update. On Jan 31, 2016 8:14 PM, "Daniel" notifications@github.com wrote:

Thanks Richardson for your quick reply. I would like to compress my all my css files into one css file. What am I missing still?

AppController.php public $helpers = ['Form','Html','Time','Shrink.Shrink'];

Layout $this->Shrink->css(['/css/uni-icons.css','/assets/css/style.css']); echo $this->Shrink->fetch('css');

— Reply to this email directly or view it on GitHub https://github.com/trentrichardson/cakephp-shrink/issues/7#issuecomment-177683877 .

trentrichardson commented 8 years ago

Looking back at the error it looks like it is searching the plug-ins directory for the code and not via composer. If you're familiar with composer try installing with it as it knows how to map out and lookup namespaces On Jan 31, 2016 8:14 PM, "Daniel" notifications@github.com wrote:

Thanks Richardson for your quick reply. I would like to compress my all my css files into one css file. What am I missing still?

AppController.php public $helpers = ['Form','Html','Time','Shrink.Shrink'];

Layout $this->Shrink->css(['/css/uni-icons.css','/assets/css/style.css']); echo $this->Shrink->fetch('css');

— Reply to this email directly or view it on GitHub https://github.com/trentrichardson/cakephp-shrink/issues/7#issuecomment-177683877 .

danielignatius commented 8 years ago

I've manually downloaded the plugin and place it in my plugin folder and set it as Plugin::load('Shrink',['autoload'=>true]); in the bootstrap.php file. I am not very familiar how to work with install a plugin using a composer. Therefore, I've manually added it into my application folder.

danielignatius commented 8 years ago

But I pretty sure that the plugins and the files is in the correct directory as required.

trentrichardson commented 8 years ago

Try this "Shrink/Shrink" to define the top level namespace in bootstrap.php:

http://book.cakephp.org/3.0/en/plugins.html#loading-a-plugin On Jan 31, 2016 8:28 PM, "Daniel" notifications@github.com wrote:

But I pretty sure that the plugins and the files is in the correct directory as required.

— Reply to this email directly or view it on GitHub https://github.com/trentrichardson/cakephp-shrink/issues/7#issuecomment-177690827 .

danielignatius commented 8 years ago

I've tried both namespace Shrink\Shrink; or use Shrink\Shrink; in bootstrap.php: Both doesn't work.

trentrichardson commented 8 years ago

Tried doing just this in bootstrap (note the forward slash, not backward slash)?

Plugin::load('Shrink/Shrink', ['autoload'=>true]);

Or have you tried:

Plugin::loadAll();

Sorry I'm sure you've already gone through a lot of this.. On Jan 31, 2016 8:37 PM, "Daniel" notifications@github.com wrote:

I've tried both namespace Shrink\Shrink; or use Shrink\Shrink; in bootstrap.php: Both doesn't work.

— Reply to this email directly or view it on GitHub https://github.com/trentrichardson/cakephp-shrink/issues/7#issuecomment-177692270 .

danielignatius commented 8 years ago

Plugin::load('Shrink/Shrink', ['autoload'=>true]); - WILL GIVE Make sure your plugin Shrink/Shrink is in the D:\home\site\wwwroot\plugins\ directory and was loaded. As the folder is called Shrink.

danielignatius commented 8 years ago

As for Plugin::loadAll(); it gives the below

Error: Shrink.ShrinkHelper could not be found.

Make sure your plugin was loaded from config\bootstrap.php and Composer is able to autoload its classes, see Loading a plugin and Plugins - autoloading plugin classes

trentrichardson commented 8 years ago

And you did rename the folder to "Shrink" inside the plugin folder? On Jan 31, 2016 9:04 PM, "Daniel" notifications@github.com wrote:

As for Plugin::loadAll(); it gives the below

Error: Shrink.ShrinkHelper could not be found.

Make sure your plugin was loaded from config\bootstrap.php and Composer is able to autoload its classes, see Loading a plugin and Plugins - autoloading plugin classes

— Reply to this email directly or view it on GitHub https://github.com/trentrichardson/cakephp-shrink/issues/7#issuecomment-177704507 .

danielignatius commented 8 years ago

Yes, the folder is called 'Shrink'. previously when i downloaded it was 'cakephp-shrink-master'

danielignatius commented 8 years ago

Should the folder called Shrink.Shrink? =/

trentrichardson commented 8 years ago

"Shrink" should be the correct folder name. Sorry I'm not at a computer to help debug... On Jan 31, 2016 9:24 PM, "Daniel" notifications@github.com wrote:

Should the folder called Shrink.Shrink?

— Reply to this email directly or view it on GitHub https://github.com/trentrichardson/cakephp-shrink/issues/7#issuecomment-177715632 .

danielignatius commented 8 years ago

That's okay. You've been helpful. :)

danielignatius commented 8 years ago

I've been trying solving this since last night.

I thought was a missing class and in the ShrinkType.php I have added use 'Shrink\Lib\ShrinkCompiler\ShrinkCompiler'; But it still not okay. =(

namespace Shrink\Lib;

use 'Shrink\Lib\ShrinkCompiler\ShrinkCompiler' ;

class ShrinkType{

/**
* Create a new instance of the requested Shrink Compiler class
* @param string $type - 'js', 'css', 'less'. This should be the input type
* @param array $settings - passthrough of complete settings from helper
* @return class - new instance of the requested type
*/
static function getCompiler($type, $settings){

    $class = __NAMESPACE__ . '\\ShrinkCompiler\\' .
        'ShrinkCompiler'. strtoupper(substr($type,0,1)).strtolower(substr($type,1));
    return new $class($settings);
}
trentrichardson commented 8 years ago

It may be tomorrow sometime, but when I get to my computer and can help debug it a little more.

I think it boils down to that Shrink namespace not being registered so that php knows where to find it. With cake 3 I've always used composer and I know it handles this automatically. The plugin may need to be tweaked for this.

And just for reference you are running php 5.4+? On Jan 31, 2016 9:34 PM, "Daniel" notifications@github.com wrote:

I've been trying solving this since last night.

I thought was a missing class and in the ShrinkType.php I have added use 'Shrink\Lib\ShrinkCompiler\ShrinkCompiler'; But it still not okay. =(

namespace Shrink\Lib;

use 'Shrink\Lib\ShrinkCompiler\ShrinkCompiler' ;

class ShrinkType{

/**

  • Create a new instance of the requested Shrink Compiler class
  • @param string $type - 'js', 'css', 'less'. This should be the input type
  • @param array $settings - passthrough of complete settings from helper
  • @return class - new instance of the requested type */ static function getCompiler($type, $settings){

    $class = NAMESPACE . '\ShrinkCompiler\' . 'ShrinkCompiler'. strtoupper(substr($type,0,1)).strtolower(substr($type,1)); return new $class($settings); }

— Reply to this email directly or view it on GitHub https://github.com/trentrichardson/cakephp-shrink/issues/7#issuecomment-177718593 .

danielignatius commented 8 years ago

Sure. Thanks so much. I am running php 5.6.7.

danielignatius commented 8 years ago

Hi Trent any lucks with the Shrink namespace? I really like to use your plugins. Thanks!

trentrichardson commented 8 years ago

I modified an existing cake app to manually place the plugin into the plugins folder. I didn't get your exact error but I did notice a similar error that a class was not found. I think this is because php can't find the "Shrink" namespace. I played around with it and found that if I simply change in composer.json from:

//...
    "autoload": {
        "psr-4": {
            "App\\": "src"
        }
    },
//...

to include an entry for Shrink like so:

//...
    "autoload": {
        "psr-4": {
            "App\\": "src",
            "Shrink\\": "./plugins/Shrink/src"
        }
    },
//...

and simply run composer update or composer dumpautoload that the error went away. My bootstrap had Plugin::load('Shrink'); and AppController.php included the helper with public $helpers = ['Shrink.Shrink'];.

Simply put, I think composer handles spl_autoload_register() which is what allows php to lookup namespaces in a customized way. When not using composer these namespaces don't get mapped and classes can't be found by namespaces.

I know its a small learning curve but I would highly recommend trying to transition to using Composer since CakePHP 3 is so tighly coupled to its new design. If nothing more than to install composer and run composer update to build the autoload. I can share with you my workflow since moving to cake 3 and composer if you like. Since making the switch I can honestly say I won't be going back as it was a huge improvement. It cleaned up my projects and made deployment and testing easier.

You may be able to simply download composer.phar into your project and run it like:

php composer.phar dumpautoload

Sorry I know thats a lot..

trentrichardson commented 8 years ago

Sorry, it also just dawned on me that the Shrink plugin itself requires composer to load it's dependencies like CSSMin.. I know that doesn't help matters much..

https://github.com/trentrichardson/cakephp-shrink/blob/master/composer.json

So it looks like the current state of Shrink does require composer to work properly..

danielignatius commented 8 years ago

Trust me, I am all willing to learn. I am really happy and appreciate if you can share your workflow with me. For instance, how do I add a plugin(like your plugin or some others) or even updating the latest CakePHP Core using composer. I find it hard to follow when the "baby steps" are missing from the book guide. So far, I learn a lot from you. I am using a Mac. First, I will download the composer.phar. And can you provide me with the list of command or workflow I need to do to download your plugin using composer. Really appreciate your help.

trentrichardson commented 8 years ago

I don't mind at all sharing my workflow. Send me your email and I will send it over to you. On Feb 1, 2016 10:44 PM, "Daniel" notifications@github.com wrote:

Trust me, I am all willing to learn. I am really happy and appreciate if you can share your workflow with me. For instance, how do I add a plugin(like your plugin or some others) or even updating the latest CakePHP Core using composer. I find it hard to follow when the "baby steps" are missing from the book guide. So far, I learn a lot from you. I am using a Mac. First, I will download the composer.phar. And can you provide me with the list of command or workflow I need to do to download your plugin using composer. Really appreciate your help.

— Reply to this email directly or view it on GitHub https://github.com/trentrichardson/cakephp-shrink/issues/7#issuecomment-178350488 .

danielignatius commented 8 years ago

Hey Trent, my email is danielignatius@me.com. Thanks! I really hope I get your plugin working!!

danielignatius commented 8 years ago

I've installed the composer.phar. on the root of my application. So is it true that for each app I need to install one composer.phar?

trentrichardson commented 8 years ago

Ideally you have a single composer that is system wide. I was more or less saying previously that you could download it into your project if you needed something very simple..

I'm going to send you an email with more info, and close this thread for now.

TempleCode commented 8 years ago

Hi, just bumped in the same error.

This is the steps I've followed:

1) updated my composer.json

"require": {
        //lot of requirements..
        "trentrichardson/cakephp-shrink": "~3.0"
    },

2) added this line in bootstrap.php Plugin::load('Shrink', ['ignoreMissing' => true, 'bootstrap' => true, 'routes' => true, 'autoload' => true]);

3) added this into AppView.php inside initialize func

$this->loadHelper('Shrink.Shrink', [
            'js'=>[
                    'path'=>'js/',        // folder to find src js files
                    'cachePath'=>'js/',   // folder to create cache files
                    'minifier'=>'jsmin'   // minifier to minify, false to leave as is
            ],
            'css'=>[
                    'path'=>'css/',       // folder to find src css files
                    'cachePath'=>'css/',  // folder to create cache files
                    'minifier'=>'cssmin', // minifier name to minify, false to leave as is
                    'charset'=>'utf-8'    // charset to use
            ],
            'url'=>'',                     // url without ending /, incase you access from another domain
            'prefix'=>'shrink_',           // prefix the beginning of cache files
            'debugLevel'=>1                // compared against Core.debug, eq will recompile, > will not minify
        ]);

4) Updated my layout with: <?= $this->Shrink->css($css_basic, true) ?>

Did I miss something?

TempleCode commented 8 years ago

Ok it was a little bubu about the plugin assets

in /vendor/trentrichardson/Shrink/src/Lib/Shrink.php on line 104 I changed the follow foreach:

foreach($files as $k=>$v){
    $tmpf = new File(preg_replace('/(\/+|\\+)/', DS, WWW_ROOT .DS. ($v[0]=='/'? '':$this->settings[$type]['path']) .DS. $v));
    $files[$k] = [
            'file'=>$tmpf,
            'rel_path'=>$v
        ];
    $srcMod = $tmpf->lastChange();
    if($srcMod > $maxAge){
        $maxAge = $srcMod;
    }
}

With this one:

foreach($files as $k=>$v){
    $webroot = WWW_ROOT;

    //Retrieve plugin
    list($plugin, $v) = pluginSplit($v);

    //Change webroot accordigly to plugin if present
    if(!is_null($plugin))
        $webroot = realpath(WWW_ROOT . '..' . DS . 'plugins' . DS . $plugin . DS . 'webroot');

    //Add realpath to aim a real directory
    $tmpf_path = realpath(preg_replace('/(\/+|\\+)/', DS, $webroot .DS. ($v[0]=='/'? '':$this->settings[$type]['path']) .DS. $v));

    $tmpf = new File($tmpf_path);
    $files[$k] = [
            'file'=>$tmpf,
            'rel_path'=>$v
        ];
    $srcMod = $tmpf->lastChange();
    if($srcMod > $maxAge){
        $maxAge = $srcMod;
    }
}

It should fix the problem when you want to shrink a file from a plugin and the file is not into the default folder (ex. folder assets on the same level of css and js folders).

So when you have a css/js list like the following Shrink could find the file correctly:

$css_basic = [
        $PLUGIN . '.' . '../assets/uniform/css/uniform.default.min.css',
        $PLUGIN . '.' . '../assets/bootstrap/css/bootstrap.min.css',
        //Lots of css files
    ];
echo $this->Shrink->css($css_basic, true);
trentrichardson commented 8 years ago

@EgoLord Thanks for posting your changes. You tracked it down and got it pretty close, but pluginSplit actually breaks it for regular files. That function is really just meant for splitting the plugin name and class name "Plugin.Class", and the asset path is more of a mixture of dot notation and file path when it comes to including plugin files.. odd, or maybe I'm going about it all wrong...?

https://github.com/cakephp/core/blob/master/functions.php#L89 http://book.cakephp.org/3.0/en/views/helpers/html.html#linking-to-css-files

So I went more on the route of checking for a dot notation, then check if that file exists as a plugin file. If not use it as a regular file. I also changed my tests around some to better check for this. Do you mind testing the updated code in the cakephp-v3.0 branch?

riddlemd commented 7 years ago

Still not fixed hu? I just ran into this same issue, it appears to be a bug in Cakephp3's File class' handling of extensions...

To work around it change line 128 in Shrink.php from $lang = $v['file']->ext(); to $lang = substr($v['file']->name, strrpos($v['file']->name, '.') + 1);

This is fixed in my branch: https://github.com/riddlemd/cakephp-shrink (as of this post this plugin has not been updated in 2 years, so he may not merge my changes back)

trentrichardson commented 7 years ago

Thanks @riddlemd. I applied this fix. Not sure if you were using master branch or cakephp-v3.0 branch, but beware there have been changes since 2 years ago.