Plugins
Install the application from its GitHub repository using - this also places it in your virtualenv’s src
directory as a cloned Git repository:
You should end up with a folder structure similar to this:
env/
src/
django-polls/
polls/
__init__.py
admin.py
models.py
templates/
tests.py
urls.py
views.py
Let’s add it this application to our project. Add 'polls'
to the end of INSTALLED_APPS
in your project’s settings.py (see the note on The INSTALLED_APPS setting about ordering ).
Add the following line to urlpatterns
in the project’s urls.py
:
url(r'^polls/', include('polls.urls', namespace='polls')),
Make sure this line is included before the line for the django-cms urls:
django CMS’s URL pattern needs to be last, because it “swallows up” anything that hasn’t already been matched by a previous pattern.
Now run the application’s migrations using south
:
At this point you should be able to create polls and choices in the Django admin - localhost:8000/admin/ - and fill them in at /polls/
.
However, in pages of the polls application we only have minimal templates, and no navigation or styling. Let’s improve this by overriding the polls application’s base template.
add my_site/templates/polls/base.html
:
{% extends 'base.html' %}
{% block content %}
{% block polls_content %}
{% endblock %}
{% endblock %}
So now we have integrated the standard polls app in our project. But we’ve not done anything django CMS specific yet.
Creating a plugin
If you’ve played around with the CMS for a little, you’ve probably already encountered CMS Plugins. They are the objects you can place into placeholders on your pages through the frontend: “Text”, “Image” and so forth.
We’re now going to extend the django poll app so we can embed a poll easily into any CMS page. We’ll put this integration code in a separate package in our project.
This allows integrating 3rd party apps without having to fork them. It would also be possible to add this code directly into the django-polls app to make it integrate out of the box.
Create a new package at the project root called polls_plugin
:
So our workspace looks like this:
In your poll application’s models.py
add the following:
from django.db import models
from cms.models import CMSPlugin
from polls.models import Poll
class PollPlugin(CMSPlugin):
poll = models.ForeignKey(Poll)
def __unicode__(self):
return self.poll.question
Note
django CMS plugins inherit from cms.models.CMSPlugin
(or a subclass thereof) and not models.Model
.
For our poll plugin, we’re going to write the following plugin class:
from cms.plugin_base import CMSPluginBase
from django.utils.translation import ugettext as _
class CMSPollPlugin(CMSPluginBase):
model = PollPlugin # model where plugin data are saved
module = _("Polls")
name = _("Poll Plugin") # name of the plugin in the interface
render_template = "djangocms_polls/poll_plugin.html"
def render(self, context, instance, placeholder):
context.update({'instance': instance})
return context
plugin_pool.register_plugin(CMSPollPlugin) # register the plugin
Note
All plugin classes must inherit from and must register themselves with the cms.plugin_pool.plugin_pool
.
The convention for plugin naming is as follows:
- SomePlugin: the model class
- CMSSomePlugin: the plugin class
You don’t need to follow this, but it’s a sensible thing to do.
The render_template
attribute in the plugin class is required, and tells the plugin which render_template
to use when rendering.
In this case the template needs to be at polls_plugin/templates/djangocms_polls/poll_plugin.html
and should look something like this:
Now add polls_plugin
to INSTALLED_APPS
and create a database migration to add the plugin table (using South):
Finally, start the runserver and visit .
You can now drop the Poll Plugin
into any placeholder on any page, just as you would any other plugin.