| 1 |
# -*- coding: utf-8 -*- |
|---|
| 2 |
""" |
|---|
| 3 |
Wiki Macros for the plugin. |
|---|
| 4 |
|
|---|
| 5 |
License: BSD |
|---|
| 6 |
|
|---|
| 7 |
(c) 2007 ::: www.CodeResort.com - BV Network AS (simon-code@bvnetwork.no) |
|---|
| 8 |
""" |
|---|
| 9 |
|
|---|
| 10 |
from genshi.builder import tag |
|---|
| 11 |
|
|---|
| 12 |
from trac.core import TracError |
|---|
| 13 |
from trac.web.chrome import add_stylesheet, Chrome |
|---|
| 14 |
from trac.wiki.api import parse_args |
|---|
| 15 |
from trac.wiki.macros import WikiMacroBase |
|---|
| 16 |
|
|---|
| 17 |
from model import get_blog_posts, BlogPost |
|---|
| 18 |
from util import parse_period |
|---|
| 19 |
|
|---|
| 20 |
class BlogListMacro(WikiMacroBase): |
|---|
| 21 |
"""A macro to display list of posts and extracts outside (or inside) |
|---|
| 22 |
the Blog module - most commonly Wiki pages. |
|---|
| 23 |
|
|---|
| 24 |
All arguments are optional: |
|---|
| 25 |
{{{ |
|---|
| 26 |
[[BlogList]] |
|---|
| 27 |
}}} |
|---|
| 28 |
|
|---|
| 29 |
Available named arguments: |
|---|
| 30 |
* `recent=` - max. number of posts |
|---|
| 31 |
* `category=` - a category |
|---|
| 32 |
* `author=` - an author |
|---|
| 33 |
* `period=` - time period of the format YYYY/MM |
|---|
| 34 |
* `heading=` - a heading for the list |
|---|
| 35 |
* `format=` - type of display (see below for details) |
|---|
| 36 |
* `max_size=` - max. number of characters to render for each post |
|---|
| 37 |
|
|---|
| 38 |
Example showing some available named arguments: |
|---|
| 39 |
{{{ |
|---|
| 40 |
[[BlogList(recent=5, max_size=250, period=2007/12, author=osimons, format=float, heading=Some Trac Posts)]] |
|---|
| 41 |
}}} |
|---|
| 42 |
|
|---|
| 43 |
The arguments for criteria are 'AND'-based, so the above example will render |
|---|
| 44 |
at most 5 posts by 'osimons' in December 2007. |
|---|
| 45 |
|
|---|
| 46 |
There is no heading unless specified. |
|---|
| 47 |
|
|---|
| 48 |
Without restriction on recent number of posts, it will use the number currently |
|---|
| 49 |
active in the Blog module as default for 'float' and 'full' rendering, but for rendering |
|---|
| 50 |
of 'inline' list it will render all found as default unless restricted. Additionally for |
|---|
| 51 |
'float' and 'full' it will truncate content if it is larger than a max_size (if set). |
|---|
| 52 |
|
|---|
| 53 |
The `format=` keyword argument supports rendering these formats: |
|---|
| 54 |
||`format=inline`||Renders an unordered list in the normal text flow (default).|| |
|---|
| 55 |
||`format=float`||A floating box out on the side of the page with slightly more detail.|| |
|---|
| 56 |
||`format=full`||Full rendering like on period, category and author listings inside blog.|| |
|---|
| 57 |
|
|---|
| 58 |
The arguments can appear in any order. |
|---|
| 59 |
|
|---|
| 60 |
Posts are rendered sorted by newest first for all modes. |
|---|
| 61 |
""" |
|---|
| 62 |
|
|---|
| 63 |
def expand_macro(self, formatter, name, content): |
|---|
| 64 |
|
|---|
| 65 |
# Parse content for arguments |
|---|
| 66 |
args_list, args_dict = parse_args(content) |
|---|
| 67 |
from_dt, to_dt = parse_period(list(args_dict.get('period', '').split('/'))) |
|---|
| 68 |
category = args_dict.get('category', '') |
|---|
| 69 |
author = args_dict.get('author', '') |
|---|
| 70 |
recent = int(args_dict.get('recent', 0)) |
|---|
| 71 |
format = args_dict.get('format', 'inline').lower() |
|---|
| 72 |
heading = args_dict.get('heading', '') |
|---|
| 73 |
max_size = int(args_dict.get('max_size', 0)) |
|---|
| 74 |
|
|---|
| 75 |
# Get blog posts |
|---|
| 76 |
all_posts = get_blog_posts(self.env, author=author, category=category, |
|---|
| 77 |
from_dt=from_dt, to_dt=to_dt) |
|---|
| 78 |
|
|---|
| 79 |
# Trim posts against permissions and count |
|---|
| 80 |
post_list = [] |
|---|
| 81 |
post_instances = [] |
|---|
| 82 |
if format in ['float', 'full']: |
|---|
| 83 |
recent = recent or self.env.config.getint('fullblog', 'num_items_front') |
|---|
| 84 |
recent = recent or len(all_posts) |
|---|
| 85 |
count = 0 |
|---|
| 86 |
for post in all_posts: |
|---|
| 87 |
if count == recent: |
|---|
| 88 |
break |
|---|
| 89 |
bp = BlogPost(self.env, post[0]) |
|---|
| 90 |
if 'BLOG_VIEW' in formatter.req.perm(bp.resource): |
|---|
| 91 |
count += 1 |
|---|
| 92 |
post_instances.append(bp) |
|---|
| 93 |
post_list.append(post) |
|---|
| 94 |
|
|---|
| 95 |
# Rendering |
|---|
| 96 |
add_stylesheet(formatter.req, 'tracfullblog/css/fullblog.css') |
|---|
| 97 |
|
|---|
| 98 |
if format == 'inline': |
|---|
| 99 |
data = {'heading': heading, |
|---|
| 100 |
'posts': post_list, |
|---|
| 101 |
'execute_blog_macro': True} |
|---|
| 102 |
return Chrome(self.env).render_template(formatter.req, |
|---|
| 103 |
'fullblog_macro_monthlist.html', data=data, fragment=True) |
|---|
| 104 |
|
|---|
| 105 |
elif format == 'full': |
|---|
| 106 |
return self._render_full_format(formatter, post_list, |
|---|
| 107 |
post_instances, heading, max_size) |
|---|
| 108 |
|
|---|
| 109 |
elif format == 'float': |
|---|
| 110 |
# Essentially a 'full' list - just wrapped inside a new div |
|---|
| 111 |
return tag.div(self._render_full_format(formatter, post_list, |
|---|
| 112 |
post_instances, heading, max_size), |
|---|
| 113 |
class_="blogflash") |
|---|
| 114 |
|
|---|
| 115 |
else: |
|---|
| 116 |
raise TracError("Invalid 'format' argument used for macro %s." % name) |
|---|
| 117 |
|
|---|
| 118 |
def _render_full_format(self, formatter, post_list, post_instances, heading, |
|---|
| 119 |
max_size): |
|---|
| 120 |
""" Renters full blog posts. """ |
|---|
| 121 |
out = tag.div(class_="blog") |
|---|
| 122 |
out.append(tag.div(heading, class_="blog-list-title")) |
|---|
| 123 |
for post in post_instances: |
|---|
| 124 |
data = {'post': post, |
|---|
| 125 |
'list_mode': True, |
|---|
| 126 |
'execute_blog_macro': True} |
|---|
| 127 |
if max_size: |
|---|
| 128 |
data['blog_max_size'] = max_size |
|---|
| 129 |
out.append(Chrome(self.env).render_template(formatter.req, |
|---|
| 130 |
'fullblog_macro_post.html', data=data, fragment=True)) |
|---|
| 131 |
return out |
|---|