From 92c597ca1cd0d93df7246eb2f81f84bcb08673ce Mon Sep 17 00:00:00 2001 From: Elrond Date: Sat, 26 Jan 2013 00:12:18 +0100 Subject: Allow doc string extraction and use for pluginapi. Allow us to extract docstrings from our sources using the sphinx.ext.autodoc module. First use: Extract some of the docs for the pluginapi and provide it in a new "Plugin API" section. --- docs/source/pluginwriter/api.rst | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) create mode 100644 docs/source/pluginwriter/api.rst (limited to 'docs/source/pluginwriter') diff --git a/docs/source/pluginwriter/api.rst b/docs/source/pluginwriter/api.rst new file mode 100644 index 00000000..206c8b0b --- /dev/null +++ b/docs/source/pluginwriter/api.rst @@ -0,0 +1,23 @@ +.. MediaGoblin Documentation + + Written in 2013 by MediaGoblin contributors + + To the extent possible under law, the author(s) have dedicated all + copyright and related and neighboring rights to this software to + the public domain worldwide. This software is distributed without + any warranty. + + You should have received a copy of the CC0 Public Domain + Dedication along with this software. If not, see + . + + +========== +Plugin API +========== + +:mod:`pluginapi` Module +----------------------- + +.. automodule:: mediagoblin.tools.pluginapi + :members: get_config, register_routes, register_template_path -- cgit v1.2.3 From ae9f0aec381c7f04898f0dde3af322ec876b9651 Mon Sep 17 00:00:00 2001 From: Elrond Date: Sat, 26 Jan 2013 19:21:40 +0100 Subject: Docs: Add a database guide to the plugin docs. Plugin writers will often need to create new tables. So give them some hints, what they need to do and where they might find more info. --- docs/source/pluginwriter/database.rst | 111 ++++++++++++++++++++++++++++++++++ 1 file changed, 111 insertions(+) create mode 100644 docs/source/pluginwriter/database.rst (limited to 'docs/source/pluginwriter') diff --git a/docs/source/pluginwriter/database.rst b/docs/source/pluginwriter/database.rst new file mode 100644 index 00000000..58edf3a0 --- /dev/null +++ b/docs/source/pluginwriter/database.rst @@ -0,0 +1,111 @@ +.. MediaGoblin Documentation + + Written in 2013 by MediaGoblin contributors + + To the extent possible under law, the author(s) have dedicated all + copyright and related and neighboring rights to this software to + the public domain worldwide. This software is distributed without + any warranty. + + You should have received a copy of the CC0 Public Domain + Dedication along with this software. If not, see + . + + +======== +Database +======== + + +Accessing Existing Data +======================= + +If your plugin wants to access existing data, this is quite +straight forward. Just import the appropiate models and use +the full power of SQLAlchemy. Take a look at the (upcoming) +database section in the Developer's Chapter. + + +Creating new Tables +=================== + +If your plugin needs some new space to store data, you +should create a new table. Please do not modify core +tables. Not doing so might seem inefficient and possibly +is. It will help keep things sane and easier to upgrade +versions later. + +So if you create a new plugin and need new tables, create a +file named ``models.py`` in your plugin directory. You +might take a look at the core's db.models for some ideas. +Here's a simple one: + +.. code-block:: python + + from mediagoblin.db.base import Base + from sqlalchemy import Column, Integer, Unicode, ForeignKey + + class MediaSecurity(Base): + __tablename__ = "yourplugin__media_security" + + # The primary key *and* reference to the main media_entry + media_entry = Column(Integer, ForeignKey('core__media_entries.id'), + primary_key=True) + get_media_entry = relationship("MediaEntry", + backref=backref("security_rating", cascade="all, delete-orphan")) + + rating = Column(Unicode) + + MODELS = [MediaSecurity] + +That's it. + +Some notes: + +* Make sure all your ``__tablename__`` start with your + plugin's name so the tables of various plugins can't + conflict in the database. (Conflicts in python naming are + much easier to fix later). +* Try to get your database design as good as possible in + the first attempt. Changing the database design later, + when people already have data using the old design, is + possible (see next chapter), but it's not easy. + + +Changing the Database Schema Later +================================== + +If your plugin is in use and instances use it to store some +data, changing the database design is a tricky thing. + +1. Make up your mind how the new schema should look like. +2. Change ``models.py`` to contain the new schema. Keep a + copy of the old version around for your personal + reference later. +3. Now make up your mind (possibly using your old and new + ``models.py``) what steps in SQL are needed to convert + the old schema to the new one. + This is called a "migration". +4. Create a file ``migrations.py`` that will contain all + your migrations and add your new migration. + +Take a look at the core's ``db/migrations.py`` for some +good examples on what you might be able to do. Here's a +simple one to add one column: + +.. code-block:: python + + from mediagoblin.db.migration_tools import RegisterMigration, inspect_table + from sqlalchemy import MetaData, Column, Integer + + MIGRATIONS = {} + + @RegisterMigration(1, MIGRATIONS) + def add_license_preference(db): + metadata = MetaData(bind=db.bind) + + security_table = inspect_table(metadata, 'yourplugin__media_security') + + col = Column('security_level', Integer) + col.create(security_table) + db.commit() -- cgit v1.2.3 From 75621003af128969c322d11aff74ec0c425a9ff4 Mon Sep 17 00:00:00 2001 From: Christopher Allan Webber Date: Wed, 30 Jan 2013 13:27:40 -0600 Subject: Added register_template_hooks and get_hook_templates to the plugin api auto module documentation. --- docs/source/pluginwriter/api.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'docs/source/pluginwriter') diff --git a/docs/source/pluginwriter/api.rst b/docs/source/pluginwriter/api.rst index 206c8b0b..f700e161 100644 --- a/docs/source/pluginwriter/api.rst +++ b/docs/source/pluginwriter/api.rst @@ -20,4 +20,4 @@ Plugin API ----------------------- .. automodule:: mediagoblin.tools.pluginapi - :members: get_config, register_routes, register_template_path + :members: get_config, register_routes, register_template_path, register_template_hooks, get_hook_templates -- cgit v1.2.3 From cf41e7d7444fb9d19a777a4720d9b00684e6fe7b Mon Sep 17 00:00:00 2001 From: Elrond Date: Thu, 31 Jan 2013 20:57:03 +0100 Subject: Improve formatting for hook template docs. --- docs/source/pluginwriter/api.rst | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'docs/source/pluginwriter') diff --git a/docs/source/pluginwriter/api.rst b/docs/source/pluginwriter/api.rst index f700e161..42dc3a3d 100644 --- a/docs/source/pluginwriter/api.rst +++ b/docs/source/pluginwriter/api.rst @@ -20,4 +20,5 @@ Plugin API ----------------------- .. automodule:: mediagoblin.tools.pluginapi - :members: get_config, register_routes, register_template_path, register_template_hooks, get_hook_templates + :members: get_config, register_routes, register_template_path, + register_template_hooks, get_hook_templates -- cgit v1.2.3 From 36748921c27deb3f8c9d88f9b7a3c368a427d418 Mon Sep 17 00:00:00 2001 From: Christopher Allan Webber Date: Thu, 11 Apr 2013 16:57:11 -0500 Subject: adding callable_runone and callable_runall to the docs --- docs/source/pluginwriter/api.rst | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'docs/source/pluginwriter') diff --git a/docs/source/pluginwriter/api.rst b/docs/source/pluginwriter/api.rst index 42dc3a3d..44ffd6e8 100644 --- a/docs/source/pluginwriter/api.rst +++ b/docs/source/pluginwriter/api.rst @@ -21,4 +21,5 @@ Plugin API .. automodule:: mediagoblin.tools.pluginapi :members: get_config, register_routes, register_template_path, - register_template_hooks, get_hook_templates + register_template_hooks, get_hook_templates, + callable_runone, callable_runall -- cgit v1.2.3 From 4d0191dcb8b43f82bfacc77ed8c92d0d3c573d8a Mon Sep 17 00:00:00 2001 From: Christopher Allan Webber Date: Fri, 19 Apr 2013 13:22:03 -0500 Subject: A warning about the plugin API being unstable. --- docs/source/pluginwriter/api.rst | 9 +++++++++ 1 file changed, 9 insertions(+) (limited to 'docs/source/pluginwriter') diff --git a/docs/source/pluginwriter/api.rst b/docs/source/pluginwriter/api.rst index 44ffd6e8..85870d28 100644 --- a/docs/source/pluginwriter/api.rst +++ b/docs/source/pluginwriter/api.rst @@ -16,6 +16,15 @@ Plugin API ========== +This documents the general plugin API. + +Please note, at this point OUR PLUGIN HOOKS MAY AND WILL CHANGE. +Authors are encouraged to develop plugins and work with the +MediaGoblin community to keep them up to date, but this API will be a +moving target for a few releases. + +Please check the release notes for updates! + :mod:`pluginapi` Module ----------------------- -- cgit v1.2.3 From 51d5d3aa20b5f2d7dbe9c88e7d8c21db7ea172d1 Mon Sep 17 00:00:00 2001 From: Christopher Allan Webber Date: Fri, 19 Apr 2013 16:29:03 -0500 Subject: changing the things to document in api.rst --- docs/source/pluginwriter/api.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'docs/source/pluginwriter') diff --git a/docs/source/pluginwriter/api.rst b/docs/source/pluginwriter/api.rst index 85870d28..3a75d455 100644 --- a/docs/source/pluginwriter/api.rst +++ b/docs/source/pluginwriter/api.rst @@ -31,4 +31,4 @@ Please check the release notes for updates! .. automodule:: mediagoblin.tools.pluginapi :members: get_config, register_routes, register_template_path, register_template_hooks, get_hook_templates, - callable_runone, callable_runall + hook_handle, hook_runall, hook_transform, -- cgit v1.2.3 From b835e15319882477e71c7b03db2c1565dd674a96 Mon Sep 17 00:00:00 2001 From: Elrond Date: Tue, 30 Apr 2013 00:24:45 +0200 Subject: Add warning about crypt/itsdangeroussecret.bin. You should not leak that file, really. --- docs/source/pluginwriter/api.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'docs/source/pluginwriter') diff --git a/docs/source/pluginwriter/api.rst b/docs/source/pluginwriter/api.rst index 3a75d455..6323f713 100644 --- a/docs/source/pluginwriter/api.rst +++ b/docs/source/pluginwriter/api.rst @@ -31,4 +31,4 @@ Please check the release notes for updates! .. automodule:: mediagoblin.tools.pluginapi :members: get_config, register_routes, register_template_path, register_template_hooks, get_hook_templates, - hook_handle, hook_runall, hook_transform, + hook_handle, hook_runall, hook_transform -- cgit v1.2.3 From f65bf8983611b18ec3a6a042404c50b8558529df Mon Sep 17 00:00:00 2001 From: Christopher Allan Webber Date: Wed, 8 May 2013 10:57:23 -0500 Subject: Documenting plugin configuration This commit sponsored by David Krupicz. Thanks, David! --- docs/source/pluginwriter/api.rst | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) (limited to 'docs/source/pluginwriter') diff --git a/docs/source/pluginwriter/api.rst b/docs/source/pluginwriter/api.rst index 6323f713..df933511 100644 --- a/docs/source/pluginwriter/api.rst +++ b/docs/source/pluginwriter/api.rst @@ -32,3 +32,19 @@ Please check the release notes for updates! :members: get_config, register_routes, register_template_path, register_template_hooks, get_hook_templates, hook_handle, hook_runall, hook_transform + +Configuration +------------- + +Your plugin may define its own configuration defaults. + +Simply add to the directory of your plugin a config_spec.ini file. An +example might look like:: + + [plugin_spec] + some_string = string(default="blork") + some_int = integer(default=50) + +This means that when people enable your plugin in their config you'll +be able to provide defaults as well as type validation. + -- cgit v1.2.3 From b312d2cd83dbbfb32adc30c5eb3a9a4cc6ae9295 Mon Sep 17 00:00:00 2001 From: Christopher Allan Webber Date: Tue, 14 May 2013 16:09:55 -0500 Subject: Added documentation on view specific hooks This commit sponsored by Matthew Woodward. Thank you! --- docs/source/pluginwriter/api.rst | 62 ++++++++++++++++++++++++++++++++++++++++ 1 file changed, 62 insertions(+) (limited to 'docs/source/pluginwriter') diff --git a/docs/source/pluginwriter/api.rst b/docs/source/pluginwriter/api.rst index df933511..0d5c82d8 100644 --- a/docs/source/pluginwriter/api.rst +++ b/docs/source/pluginwriter/api.rst @@ -48,3 +48,65 @@ example might look like:: This means that when people enable your plugin in their config you'll be able to provide defaults as well as type validation. + +Context Hooks +------------- + +View specific hooks ++++++++++++++++++++ + +You can hook up to almost any template called by any specific view +fairly easily. As long as the view directly or indirectly uses the +method ``render_to_response`` you can access the context via a hook +that has a key in the format of the tuple:: + + (view_symbolic_name, view_template_path) + +Where the "view symbolic name" is the same parameter used in +``request.urlgen()`` to look up the test. So say we're wanting to add +something to the context of the user's homepage. We look in +mediagoblin/user_pages/routing.py and see:: + + add_route('mediagoblin.user_pages.user_home', + '/u//', + 'mediagoblin.user_pages.views:user_home') + +Aha! That means that the name is ``mediagoblin.user_pages.user_home``. +Okay, so then we look at the view at the +``mediagoblin.user_pages.views:user_home`` method:: + + @uses_pagination + def user_home(request, page): + # [...] whole bunch of stuff here + return render_to_response( + request, + 'mediagoblin/user_pages/user.html', + {'user': user, + 'user_gallery_url': user_gallery_url, + 'media_entries': media_entries, + 'pagination': pagination}) + +Nice! So the template appears to be +``mediagoblin/user_pages/user.html``. Cool, that means that the key +is:: + + ("mediagoblin.user_pages.views:user_home", + "mediagoblin/user_pages/user.html") + +The context hook uses ``hook_transform()`` so that means that if we're +hooking into it, our hook will both accept one argument, ``context``, +and should return that modified object, like so:: + + def add_to_user_home_context(context): + context['foo'] = 'bar' + return context + + hooks = { + ("mediagoblin.user_pages.views:user_home", + "mediagoblin/user_pages/user.html"): add_to_user_home_context} + + +Global context hook ++++++++++++++++++++ + + -- cgit v1.2.3 From 1344c561a0da28290bab860e7e628998463fca15 Mon Sep 17 00:00:00 2001 From: Christopher Allan Webber Date: Wed, 15 May 2013 10:37:41 -0500 Subject: Adding global context hooks & fixing method names->symbolic view names in docs This commit sponsored by Sheila Miguez. Thanks Sheila! --- docs/source/pluginwriter/api.rst | 21 ++++++++++++++++++--- 1 file changed, 18 insertions(+), 3 deletions(-) (limited to 'docs/source/pluginwriter') diff --git a/docs/source/pluginwriter/api.rst b/docs/source/pluginwriter/api.rst index 0d5c82d8..b411fa4d 100644 --- a/docs/source/pluginwriter/api.rst +++ b/docs/source/pluginwriter/api.rst @@ -73,7 +73,7 @@ mediagoblin/user_pages/routing.py and see:: Aha! That means that the name is ``mediagoblin.user_pages.user_home``. Okay, so then we look at the view at the -``mediagoblin.user_pages.views:user_home`` method:: +``mediagoblin.user_pages.user_home`` method:: @uses_pagination def user_home(request, page): @@ -90,7 +90,7 @@ Nice! So the template appears to be ``mediagoblin/user_pages/user.html``. Cool, that means that the key is:: - ("mediagoblin.user_pages.views:user_home", + ("mediagoblin.user_pages.user_home", "mediagoblin/user_pages/user.html") The context hook uses ``hook_transform()`` so that means that if we're @@ -102,11 +102,26 @@ and should return that modified object, like so:: return context hooks = { - ("mediagoblin.user_pages.views:user_home", + ("mediagoblin.user_pages.user_home", "mediagoblin/user_pages/user.html"): add_to_user_home_context} Global context hook +++++++++++++++++++ +If you need to add something to the context of *every* view, it is not +hard; there are two hooks hook that also uses hook_transform (like the +above) but make available what you are providing to *every* view. +Note that there is a slight, but critical, difference between the two. + +The most general one is the ``'template_global_context'`` hook. This +one is run only once, and is read into the global context... all views +will get access to what are in this dict. + +The slightly more expensive but more powerful one is +``'template_context_prerender'``. This one is not added to the global +context... it is added to the actual context of each individual +template render right before it is run! Because of this you also can +do some powerful and crazy things, such as checking the request object +or other parts of the context before passing them on. -- cgit v1.2.3 From 0553976187a4ec870f944d2d4d17a4951075d2a8 Mon Sep 17 00:00:00 2001 From: Christopher Allan Webber Date: Wed, 15 May 2013 11:10:25 -0500 Subject: Hook->hooks since there's more than one of them :) --- docs/source/pluginwriter/api.rst | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'docs/source/pluginwriter') diff --git a/docs/source/pluginwriter/api.rst b/docs/source/pluginwriter/api.rst index b411fa4d..56aaac77 100644 --- a/docs/source/pluginwriter/api.rst +++ b/docs/source/pluginwriter/api.rst @@ -106,8 +106,8 @@ and should return that modified object, like so:: "mediagoblin/user_pages/user.html"): add_to_user_home_context} -Global context hook -+++++++++++++++++++ +Global context hooks +++++++++++++++++++++ If you need to add something to the context of *every* view, it is not hard; there are two hooks hook that also uses hook_transform (like the -- cgit v1.2.3 From 38ebd05d1a759c3a057ab041124c313cf5724dc4 Mon Sep 17 00:00:00 2001 From: Christopher Allan Webber Date: Wed, 15 May 2013 11:29:43 -0500 Subject: Simple tyop, view->test... I was writing too many tests at the time :) --- docs/source/pluginwriter/api.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'docs/source/pluginwriter') diff --git a/docs/source/pluginwriter/api.rst b/docs/source/pluginwriter/api.rst index 56aaac77..5e0568fd 100644 --- a/docs/source/pluginwriter/api.rst +++ b/docs/source/pluginwriter/api.rst @@ -63,7 +63,7 @@ that has a key in the format of the tuple:: (view_symbolic_name, view_template_path) Where the "view symbolic name" is the same parameter used in -``request.urlgen()`` to look up the test. So say we're wanting to add +``request.urlgen()`` to look up the view. So say we're wanting to add something to the context of the user's homepage. We look in mediagoblin/user_pages/routing.py and see:: -- cgit v1.2.3