Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
1.2k views
in Technique[技术] by (71.8m points)

javascript - Sharing TinyMCE plugin across multiple applications

I'm using CakePHP 2.4.7 and the TinyMCE plugin from CakeDC.

I set up my CakePHP core along with the plugin in a shared location on my server so that multiple applications can access it. This keeps me from having to update multiple copies of TinyMCE. Everything was working well until I migrated to a new server and updated software.

The new server is running Apache 2.4 instead of 2.2 and using mod_ruid2 instead of suexec.

I now get this error when trying to load the editor:

Fatal Error (4): syntax error, unexpected T_CONSTANT_ENCAPSED_STRING in [/xyz/Plugin/TinyMCE/webroot/js/tiny_mce/tiny_mce.js, line 1]

How should I start debugging this?

Workaround Attempt

I tried adding a symlink from an application's webroot to TinyMCE's plugin webroot. This works in that it loads the js file and the editor, but then TinyMCE plugins are working on the wrong current directory and file management would not be separated.

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

The problem is the AssetDispatcher filter, it includes css and js files using PHPs include() statement, causing the files to be sent through the PHP parser, where it will stumble over the occurrences of <? in the TinyMCE script.

See https://github.com/.../2.4.7/lib/Cake/Routing/Filter/AssetDispatcher.php#L159-L160

A very annoying, and, since it's undocumented and non-optional, dangerous behavior if you ask me.

Custom asset dispatcher

In case you want to continue to use a plugin asset dispatcher, extend the built in one, and reimplement the AssetDispatcher::_deliverAsset() method with the include functionality removed. Of course this is kinda annoying, maintenance wise, but it's a pretty quick fix.

Something like:

// app/Routing/Filter/MyAssetDispatcher.php

App::uses('AssetDispatcher', 'Routing/Filter');

class MyAssetDispatcher extends AssetDispatcher {
    protected function _deliverAsset(CakeResponse $response, $assetFile, $ext) {
        // see the source of your CakePHP core for the
        // actual code that you'd need to reimpelment

        ob_start();
        $compressionEnabled = Configure::read('Asset.compress') && $response->compress();
        if ($response->type($ext) == $ext) {
            $contentType = 'application/octet-stream';
            $agent = env('HTTP_USER_AGENT');
            if (preg_match('%Opera(/| )([0-9].[0-9]{1,2})%', $agent) || preg_match('/MSIE ([0-9].[0-9]{1,2})/', $agent)) {
                $contentType = 'application/octetstream';
            }
            $response->type($contentType);
        }
        if (!$compressionEnabled) {
            $response->header('Content-Length', filesize($assetFile));
        }
        $response->cache(filemtime($assetFile));
        $response->send();
        ob_clean();


        // instead of the possible `include()` in the original
        // methods source, use `readfile()` only 
        readfile($assetFile);


        if ($compressionEnabled) {
            ob_end_flush();
        }
    }
}
// app/Config/bootstrap.php

Configure::write('Dispatcher.filters', array(
    'MyAssetDispatcher', // instead of AssetDispatcher
    // ...
));

See also http://book.cakephp.org/2.0/en/development/dispatch-filters.html

Don't just disable short open tags

I'm just guessig here, but the reason why it was working on your other server probably is that short open tags (ie <?) where disabled. However even if that is the problem on your new server, this isn't something you should rely on, the assets are still being served using include(), and you most probably don't want to check all your third party CSS/JS for possible PHP code injections on every update.


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...