1 # -*- coding: iso-8859-1 -*- 2 """ 3 MoinMoin - CategoryMenu Macro 4 5 @copyright: 2008 by Paul Boddie <paul@boddie.org.uk> 6 @copyright: 2000-2004 Juergen Hermann <jh@web.de>, 7 2005-2008 MoinMoin:ThomasWaldmann. 8 @license: GNU GPL (v2 or later), see COPYING.txt for details. 9 """ 10 11 from MoinMoin.Page import Page 12 from MoinMoin import wikiutil, search, version 13 import re 14 15 category_regexp = None 16 17 Dependencies = ['pages'] 18 19 def isMoin15(): 20 return version.release.startswith("1.5.") 21 22 def getCategoryPattern(request): 23 global category_regexp 24 25 try: 26 return request.cfg.cache.page_category_regexact 27 except AttributeError: 28 29 # Use regular expression from MoinMoin 1.7.1 otherwise. 30 31 if category_regexp is None: 32 category_regexp = re.compile(u'^%s$' % ur'(?P<all>Category(?P<key>(?!Template)\S+))', re.UNICODE) 33 return category_regexp 34 35 def getCategories(request): 36 37 """ 38 From the AdvancedSearch macro, return a list of category page names using 39 the given 'request'. 40 """ 41 42 # This will return all pages with "Category" in the title. 43 44 cat_filter = getCategoryPattern(request).search 45 pagenames = request.rootpage.getPageList(filter=cat_filter) 46 pagenames.sort() 47 return pagenames 48 49 def getCategoryMapping(category_pagenames, request): 50 51 """ 52 For the given 'category_pagenames' return a list of tuples of the form 53 (category name, category page name) using the given 'request'. 54 """ 55 56 cat_pattern = getCategoryPattern(request) 57 mapping = [] 58 for pagename in category_pagenames: 59 name = cat_pattern.match(pagename).group("key") 60 if name != "Category": 61 mapping.append((name, pagename)) 62 mapping.sort() 63 return mapping 64 65 def getPages(pagename, request): 66 67 "Return the links minus category links for 'pagename' using the 'request'." 68 69 query = search.QueryParser().parse_query('"%s"' % pagename) 70 if isMoin15(): 71 results = search.searchPages(request, query) 72 results.sortByPagename() 73 else: 74 results = search.searchPages(request, query, "page_name") 75 76 cat_pattern = getCategoryPattern(request) 77 pages = [] 78 for page in results.hits: 79 if not cat_pattern.match(page.page_name): 80 pages.append(page) 81 return pages 82 83 def execute(macro, args): 84 request = macro.request 85 fmt = macro.formatter 86 page = fmt.page 87 88 # Interpret the arguments. 89 90 try: 91 selected_category_names = wikiutil.parse_quoted_separated(args, name_value=False) 92 except AttributeError: 93 selected_category_names = args.split(",") 94 95 selected_category_names = [arg for arg in selected_category_names if arg] 96 97 # Get the categories. 98 99 categories = getCategoryMapping(getCategories(request), request) 100 101 # Generate a menu with the categories, together with expanded submenus for 102 # the categories employed by the current page or as requested in the macro 103 # arguments. 104 105 output = [] 106 output.append(fmt.bullet_list(on=1, attr={"class" : "category-menu"})) 107 108 for category in categories: 109 category_name, category_pagename = category 110 111 pages_in_category = getPages(category_pagename, request) 112 pagenames_in_category = [p.page_name for p in pages_in_category] 113 114 # Generate the submenu where appropriate. 115 116 if selected_category_names and category_name in selected_category_names or \ 117 not selected_category_names and page.page_name in pagenames_in_category: 118 119 output.append(fmt.listitem(on=1, attr={"class" : "category-menu-item-selected"})) 120 output.append(fmt.text(category_name)) 121 122 output.append(fmt.bullet_list(on=1, attr={"class" : "category-submenu"})) 123 124 # Visit each page in the category. 125 126 for page_in_category in pages_in_category: 127 pagename = page_in_category.page_name 128 129 output.append(fmt.listitem(on=1)) 130 output.append(fmt.pagelink(on=1, pagename=pagename)) 131 output.append(fmt.text(pagename)) 132 output.append(fmt.pagelink(on=0, pagename=pagename)) 133 output.append(fmt.listitem(on=0)) 134 135 output.append(fmt.bullet_list(on=0)) 136 output.append(fmt.listitem(on=0)) 137 138 # Otherwise generate a simple link. 139 140 else: 141 output.append(fmt.listitem(on=1, attr={"class" : "category-menu-item"})) 142 output.append(fmt.pagelink(on=1, pagename=category_pagename)) 143 output.append(fmt.text(category_name)) 144 output.append(fmt.pagelink(on=0, pagename=category_pagename)) 145 output.append(fmt.listitem(on=0)) 146 147 output.append(fmt.bullet_list(on=0)) 148 149 return ''.join(output) 150 151 # vim: tabstop=4 expandtab shiftwidth=4