Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Tiny MCE popups blank in Django admin

I have got tinyMCE working in the django admin, but all the popups are blank (eg. edit HTML, add image)

The paths to the popup html pages all exist in the right places

http://thatch.media/js/tiny_mce/themes/advanced/source_editor.htm?mce_rdomain=thatch

The permissions are set to 777 on the whole js folder

This is my Model

class Page(models.Model):
    title = models.CharField(max_length=200)
    ...

    class Admin:
        js = ('js/tiny_mce/tiny_mce.js', 'js/textareas.js')

Any Ideas?

like image 662
Cato Johnston Avatar asked Feb 21 '09 02:02

Cato Johnston


6 Answers

I ran into this problem too, using an Amazon S3 bucket to store static media including the TinyMCE javascript.

To be more explicit -- your static media must be on a subdomain of your primary site. So, if your site is running at foo.bar.com -- your static media must be on something like static.foo.bar.com -- note that static.bar.com and static-foo.bar.com will NOT be okay. (If your site is on bar.com then static.bar.com is fine.)

So, once you have your static media served out of a subdomain (for S3 see Amazon S3: Static Web Sites: Custom Domain or Subdomain which helped me) you then need to set the document.domain in javascript in two places:

1) In tiny_mce_popup.js

2) In tiny_mce.js before anything else, or, alternatively, in your main page's rendered HTML in a script tag somewhere before the tiny_mce.init() call occurs. (I found it more expedient to hack up tiny_mce.js and reupload it to S3, rather than mucking around with django-tinymce's widget rendering.)

You need to set document.domain to the domain of the MAIN SITE in both places: so, for a site at foo.bar.com with static media at static.foo.bar.com you will need to set document.domain = "foo.bar.com"

This should prevent any security exceptions in the browser, and everything will now work right.

like image 185
ejucovy Avatar answered Nov 13 '22 21:11

ejucovy


I ran into this problem with running my django App on Heroku and using Rackspace CDN. My static file settings were all set to use rackspace CDN to share files

  • the solution was to use normal static file serving for the specific tinymce files:

    class Media:
    js = [
        '/static/grappelli/tinymce/jscripts/tiny_mce/tiny_mce.js',
        '/static/grappelli/tinymce_setup/tinymce_setup.js',
    ]
    

In my url conf:

urlpatterns += patterns('',
    url(r'^static/(?P<path>.*)$', 'django.views.static.serve', {
        'document_root': settings.STATIC_ROOT,
    }),

)

The static.serve function allows you to serve static files outside of your standard static settings. You can change static in url conf to whatever you want.

like image 32
Hacking Life Avatar answered Nov 13 '22 21:11

Hacking Life


If this is the JQuery version of TinyMCE, and you're serving media (including the TinyMCE .js files) from another server to that on which Django is running, this might apply: your browser will prevent the TinyMCE script from accessing the Django admin URL from the domain from which TinyMCE is served. Safari's error console is the most explicit e.g.:

Unsafe JavaScript attempt to access frame with URL http://127.0.0.1/~whatever/django-templates/javascript/tiny_mce/jscripts/more stuffhere/anchor.htm
from frame with URL http://127.0.0.1:8000/admin/flatpages/flatpage/1/.
Domains, protocols and ports must match.

There is a setting in tiny_mce_popup.js file that states:

// Uncomment and change this document.domain value if you are loading the script cross subdomains
// document.domain = 'moxiecode.com';

but it didn't work for me. You could try breaking the rules and serve the TinyMCE scripts from the Django server, or add the scripts to your modified admin templates' HTML... but I'm sure there's a better solution. I ran out of patience trying, and although I'm sure it's been done, I can't find a solution for getting TinyMCE to work across domains.

However, because of the hideous HTML/inline CSS mangling users can produce with visual editors, other solutions might be better: Textile (Ruby's Redcloth gives visual feedback - perhaps there's a similar Python implementation based on PyTextile or Python-Textile??), or markItUp! (JQuery, so might present the same problem) which has a nice visual editing toolbar.

If you're doubting this move away from 'Word-like' editors, <- that link is a good article on the issue.

Postscript: there's a nice Javascript implementation of Markdown in WMD, that offers a TinyMCE-like toolbar, semantic-markup-style (wysiwym - 'what you see is what you mean') editor shortcuts. GitHub uses a related solution.

like image 6
Dave Everitt Avatar answered Nov 13 '22 22:11

Dave Everitt


I found that the best solution is to just serve tiny_mce media from project root or media dir by setting:

TINYMCE_JS_URL = '%stiny_mce/tiny_mce.js' % MEDIA_URL
like image 5
Adam Spence Avatar answered Nov 13 '22 23:11

Adam Spence


Check your MEDIA_URL in your settings file. If this is set to a non-relative path, i.e. http://site.com/media_url as Django recommends, tiny_mce will popup blank pages. Set this to a relative path and it should work.

See http://pageworthy.com/blog/2009/mar/09/tiny_mce-blank-popups/ for more details.

like image 3
user75977 Avatar answered Nov 13 '22 23:11

user75977


I've had the blank popup problem. In my case the problems was having them in another subdomain. Not sure it's your case.

I solved by editing tiny_mce_popup.js and adding

document.domain = window.location.hostname.replace('static.','');

Of course replace static with your subdomain to have the "domain.com" string

Then define again document.domain before attaching .tinymce(...) to your elements. Depending on where you are, you can use server side script for that, or the same code above. See wiki from website here http://tinymce.moxiecode.com/wiki.php/How-to_load_TinyMCE_crossdomain

like image 2
E Ciotti Avatar answered Nov 13 '22 22:11

E Ciotti