forked from rc/aircox
documentation
This commit is contained in:
parent
995efffc52
commit
54910f4df9
81
cms/README.md
Normal file
81
cms/README.md
Normal file
|
@ -0,0 +1,81 @@
|
|||
# Aircox.CMS
|
||||
Simple CMS generator used in Aircox. Main features includes:
|
||||
- website configuration and templating
|
||||
- articles and static pages
|
||||
- sections: embeddable views used to display related elements of an object
|
||||
- posts related to external models:
|
||||
- attributes binding, automatically updated
|
||||
- personalization of view rendering, using templates or sections
|
||||
- integrated admin interface if desired
|
||||
- list and detail views + routing
|
||||
- positioned menus using views
|
||||
- comment
|
||||
|
||||
We aims here to automatize most common tasks and to ease website
|
||||
configuration.
|
||||
|
||||
# Architecture
|
||||
A **Website** holds all required informations to run the server instance. It
|
||||
is used to register all kind of posts, routes to the views, menus, etc.
|
||||
|
||||
Basically, for each type of publication, the user declare the corresponding
|
||||
model, the routes, the sections used for rendering, and register them using
|
||||
website.register.
|
||||
|
||||
## Posts
|
||||
**Post** is the base model for a publication. **Article** is the provided model
|
||||
for articles and static pages.
|
||||
|
||||
**RelatedPost** is used to generate posts related to a model, the corresponding
|
||||
bindings and so on. The idea is that you declare your own models using it as
|
||||
parent, and give informations for bindings and so on. This is as simple as:
|
||||
|
||||
```python
|
||||
class MyModelPost(RelatedPost):
|
||||
class Relation:
|
||||
model = MyModel
|
||||
mapping = {
|
||||
'thread': 'parent_field_name',
|
||||
'title': 'name'
|
||||
}
|
||||
```
|
||||
|
||||
## Routes
|
||||
Routes are used to generate the URLs of the website. We provide some of the
|
||||
common routes: for the detail view of course, but also to select all posts or
|
||||
by thread, date, search, tags.
|
||||
|
||||
It is of course possible to create your own routes.
|
||||
|
||||
Routes are registered to a router (FIXME: it might be possible that we remove
|
||||
this later)
|
||||
|
||||
|
||||
## Section
|
||||
Sections are used to render part of a publication, for example to render a
|
||||
playlist related to the diffusion of a program.
|
||||
|
||||
If the rendering of a publication can vary depending the related element, in
|
||||
most of the cases when we render elements, we can find the same patterns: a
|
||||
picture, a text, a list of URLs/related posts/other items.
|
||||
|
||||
In order to avoid to much code writing and the multiplication of template
|
||||
files (e.g. one for each type of publication), we prefer to declare these
|
||||
sections and configure them. This reduce the work, keep design coherent,
|
||||
and reduce the risk of bugs and so on.
|
||||
|
||||
|
||||
## Website
|
||||
This class is used to create the website itself and regroup all the needed
|
||||
informations to make it beautiful. There are different steps to create the
|
||||
website, using instance of the Website class:
|
||||
|
||||
1. Create the Website instance with all basic information: name, tags,
|
||||
description, menus and so on.
|
||||
2. For each type of publication, register it using a Post model, a list of
|
||||
used sections, routes, and optional parameters. The given name is used
|
||||
for routing.
|
||||
3. Register website's URLs to Django.
|
||||
4. Change templates and css styles if needed.
|
||||
|
||||
|
|
@ -14,6 +14,10 @@ from taggit.managers import TaggableManager
|
|||
|
||||
|
||||
class Post (models.Model):
|
||||
"""
|
||||
Base model that can be used as is if wanted. Represent a generic
|
||||
publication on the website.
|
||||
"""
|
||||
thread_type = models.ForeignKey(
|
||||
ContentType,
|
||||
on_delete=models.SET_NULL,
|
||||
|
@ -64,6 +68,9 @@ class Post (models.Model):
|
|||
|
||||
|
||||
class Article (Post):
|
||||
"""
|
||||
Represent an article or a static page on the website.
|
||||
"""
|
||||
static_page = models.BooleanField(
|
||||
_('static page'),
|
||||
default = False,
|
||||
|
@ -141,12 +148,28 @@ class RelatedPostBase (models.base.ModelBase):
|
|||
|
||||
class RelatedPost (Post, metaclass = RelatedPostBase):
|
||||
"""
|
||||
Use this post to generate Posts that are related to an external model. An
|
||||
extra field "related" will be generated, and some bindings are possible to
|
||||
update te related object on save if desired;
|
||||
Post linked to an object of other model. This object is accessible through
|
||||
the field "related".
|
||||
|
||||
This is done through a class name Relation inside the declaration of the new
|
||||
model.
|
||||
It is possible to map attributes of the Post to the ones of the Related
|
||||
Object. It is also possible to automatically update post's thread based
|
||||
on the Related Object's parent if it is required.
|
||||
|
||||
Mapping can ensure that the Related Object will be updated when mapped
|
||||
fields of the Post are updated.
|
||||
|
||||
To configure the Related Post, you just need to create set attributes of
|
||||
the Relation sub-class.
|
||||
|
||||
```
|
||||
class MyModelPost(RelatedPost):
|
||||
class Relation:
|
||||
model = MyModel
|
||||
mapping = {
|
||||
'thread': 'parent_field_name',
|
||||
'title': 'name'
|
||||
}
|
||||
```
|
||||
"""
|
||||
related = None
|
||||
|
||||
|
@ -165,13 +188,11 @@ class RelatedPost (Post, metaclass = RelatedPostBase):
|
|||
If there is a post_attr "thread", the corresponding rel_attr is used
|
||||
to update the post thread to the correct Post model (in order to
|
||||
establish a parent-child relation between two models)
|
||||
* thread_model: generated by the metaclass that point to the
|
||||
RelatedModel class related to the model that is the parent of
|
||||
the current related one.
|
||||
* thread_model: generated by the metaclass, points to the RelatedPost
|
||||
model generated for the mapping.thread object.
|
||||
"""
|
||||
model = None
|
||||
mapping = None # values to map { post_attr: rel_attr }
|
||||
thread = None
|
||||
thread_model = None
|
||||
|
||||
def get_attribute (self, attr):
|
||||
|
|
|
@ -170,4 +170,5 @@ class SearchRoute (Route):
|
|||
qs.distinct()
|
||||
return qs
|
||||
|
||||
## TODO: by tag
|
||||
|
||||
|
|
|
@ -67,6 +67,11 @@ class Website:
|
|||
|
||||
def register (self, name, model, sections = None, routes = None,
|
||||
list_kwargs = {}, detail_kwargs = {}):
|
||||
"""
|
||||
Register a detail and list view for a given model, using
|
||||
routes. Just a wrapper around register_detail and
|
||||
register_list.
|
||||
"""
|
||||
if sections:
|
||||
self.register_detail(
|
||||
name, model,
|
||||
|
|
|
@ -36,7 +36,6 @@ class Actions:
|
|||
def skip (cl, monitor, controller, source):
|
||||
source.skip()
|
||||
|
||||
|
||||
class LiquidControl (View):
|
||||
template_name = 'aircox/liquidsoap/controller.html'
|
||||
|
||||
|
|
|
@ -744,7 +744,7 @@ class Log (models.Model):
|
|||
logger.info('log #%s: %s%s',
|
||||
str(self),
|
||||
self.comment or '',
|
||||
'\n - {}: #{}'.format(self.related_type, self.related_id)
|
||||
' -- {} #{}'.format(self.related_type, self.related_id)
|
||||
if self.related_object else ''
|
||||
)
|
||||
|
||||
|
|
Loading…
Reference in New Issue
Block a user