slitaz-forge rev 64

Add bugs template and WSGI handler (may be buggy --> fallback to CGI or roundup-server)
author Christophe Lincoln <pankso@slitaz.org>
date Thu Apr 14 01:13:16 2011 +0200 (2011-04-14)
parents 3d1dfcfb56d9
children 988e0c3e8d34
files bugs/README bugs/roundup.wsgi bugs/server.ini bugs/templates/slitaz/TEMPLATE-INFO.txt bugs/templates/slitaz/detectors/messagesummary.py bugs/templates/slitaz/detectors/nosyreaction.py bugs/templates/slitaz/detectors/statusauditor.py bugs/templates/slitaz/detectors/userauditor.py bugs/templates/slitaz/extensions/README.txt bugs/templates/slitaz/html/_generic.404.html bugs/templates/slitaz/html/_generic.calendar.html bugs/templates/slitaz/html/_generic.collision.html bugs/templates/slitaz/html/_generic.help-empty.html bugs/templates/slitaz/html/_generic.help-list.html bugs/templates/slitaz/html/_generic.help-search.html bugs/templates/slitaz/html/_generic.help-submit.html bugs/templates/slitaz/html/_generic.help.html bugs/templates/slitaz/html/_generic.index.html bugs/templates/slitaz/html/_generic.item.html bugs/templates/slitaz/html/favicon.ico bugs/templates/slitaz/html/file.index.html bugs/templates/slitaz/html/file.item.html bugs/templates/slitaz/html/help.html bugs/templates/slitaz/html/help_controls.js bugs/templates/slitaz/html/home.classlist.html bugs/templates/slitaz/html/home.html bugs/templates/slitaz/html/issue.index.html bugs/templates/slitaz/html/issue.item.html bugs/templates/slitaz/html/issue.search.html bugs/templates/slitaz/html/keyword.item.html bugs/templates/slitaz/html/msg.index.html bugs/templates/slitaz/html/msg.item.html bugs/templates/slitaz/html/page.html bugs/templates/slitaz/html/query.edit.html bugs/templates/slitaz/html/query.item.html bugs/templates/slitaz/html/style.css bugs/templates/slitaz/html/user.forgotten.html bugs/templates/slitaz/html/user.help-search.html bugs/templates/slitaz/html/user.help.html bugs/templates/slitaz/html/user.index.html bugs/templates/slitaz/html/user.item.html bugs/templates/slitaz/html/user.register.html bugs/templates/slitaz/html/user.rego_progress.html bugs/templates/slitaz/html/user_utils.js bugs/templates/slitaz/initial_data.py bugs/templates/slitaz/schema.py
line diff
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/bugs/README	Thu Apr 14 01:13:16 2011 +0200
     1.3 @@ -0,0 +1,14 @@
     1.4 +
     1.5 +
     1.6 +http://bugs.slitaz.org/ runs a Roundup tracker powered by a WSGI handler
     1.7 +(much faster than standard CGI) and Lighttpd mod_proxy
     1.8 +
     1.9 +	* templates/   : Contain the SliTaz template used to install and initialize
    1.10 +	                 the tracker. It also have the xHTML files and CSS style.
    1.11 +	* roundup.wsgi : Is the WSGI handler (started at boot by the script
    1.12 +	                 /etc/init.d/local.sh)
    1.13 +	* server.ini   : Is a config that could be used with roundup-server
    1.14 +
    1.15 +The bugs tracker configuration file (config.ini) is not under Hg since
    1.16 +it have MySQL db login information and SMTP password.
    1.17 +
     2.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     2.2 +++ b/bugs/roundup.wsgi	Thu Apr 14 01:13:16 2011 +0200
     2.3 @@ -0,0 +1,11 @@
     2.4 +#!/usr/bin/python
     2.5 +
     2.6 +from wsgiref.simple_server import make_server
     2.7 +
     2.8 +# obtain the WSGI request dispatcher
     2.9 +from roundup.cgi.wsgi_handler import RequestDispatcher
    2.10 +tracker_home = '/home/slitaz/bugs'
    2.11 +app = RequestDispatcher(tracker_home)
    2.12 +
    2.13 +httpd = make_server('', 8917, app)
    2.14 +httpd.serve_forever()
     3.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     3.2 +++ b/bugs/server.ini	Thu Apr 14 01:13:16 2011 +0200
     3.3 @@ -0,0 +1,86 @@
     3.4 +# Roundup server configuration file
     3.5 +# Autogenerated at Wed Apr 13 00:31:14 2011
     3.6 +
     3.7 +[main]
     3.8 +
     3.9 +# Host name of the Roundup web server instance.
    3.10 +# If empty, listen on all network interfaces.
    3.11 +# Default: 
    3.12 +host = bugs.slitaz.org
    3.13 +
    3.14 +# Port to listen on.
    3.15 +# Default: 8080
    3.16 +port = 8917
    3.17 +
    3.18 +# Path to favicon.ico image file.  If unset, built-in favicon.ico is used.
    3.19 +# The path may be either absolute or relative
    3.20 +# to the directory containig this config file.
    3.21 +# Default: favicon.ico
    3.22 +favicon = favicon.ico
    3.23 +
    3.24 +# User ID as which the server will answer requests.
    3.25 +# In order to use this option, the server must be run initially as root.
    3.26 +# Availability: Unix.
    3.27 +# Default: 
    3.28 +user = www
    3.29 +
    3.30 +# Group ID as which the server will answer requests.
    3.31 +# In order to use this option, the server must be run initially as root.
    3.32 +# Availability: Unix.
    3.33 +# Default: 
    3.34 +group = www
    3.35 +
    3.36 +# don't fork (this overrides the pidfile mechanism)'
    3.37 +# Allowed values: yes, no
    3.38 +# Default: no
    3.39 +nodaemon = yes
    3.40 +
    3.41 +# Log client machine names instead of IP addresses (much slower)
    3.42 +# Allowed values: yes, no
    3.43 +# Default: no
    3.44 +log_hostnames = no
    3.45 +
    3.46 +# File to which the server records the process id of the daemon.
    3.47 +# If this option is not set, the server will run in foreground
    3.48 +# 
    3.49 +# The path may be either absolute or relative
    3.50 +# to the directory containig this config file.
    3.51 +# Default: 
    3.52 +pidfile = /var/run/roundup.pid
    3.53 +
    3.54 +# Log file path.  If unset, log to stderr.
    3.55 +# The path may be either absolute or relative
    3.56 +# to the directory containig this config file.
    3.57 +# Default: 
    3.58 +logfile = /var/log/roundup.log
    3.59 +
    3.60 +# Set processing of each request in separate subprocess.
    3.61 +# Allowed values: debug, none, thread, fork.
    3.62 +# Default: fork
    3.63 +multiprocess = fork
    3.64 +
    3.65 +# Tracker index template. If unset, built-in will be used.
    3.66 +# The path may be either absolute or relative
    3.67 +# to the directory containig this config file.
    3.68 +# Default: 
    3.69 +template = slitaz
    3.70 +
    3.71 +# Enable SSL support (requires pyopenssl)
    3.72 +# Allowed values: yes, no
    3.73 +# Default: no
    3.74 +ssl = no
    3.75 +
    3.76 +# PEM file used for SSL. A temporary self-signed certificate
    3.77 +# will be used if left blank.
    3.78 +# The path may be either absolute or relative
    3.79 +# to the directory containig this config file.
    3.80 +# Default: 
    3.81 +pem = 
    3.82 +
    3.83 +# Roundup trackers to serve.
    3.84 +# Each option in this section defines single Roundup tracker.
    3.85 +# Option name identifies the tracker and will appear in the URL.
    3.86 +# Option value is tracker home directory path.
    3.87 +# The path may be either absolute or relative
    3.88 +# to the directory containig this config file.
    3.89 +[trackers]
     4.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     4.2 +++ b/bugs/templates/slitaz/TEMPLATE-INFO.txt	Thu Apr 14 01:13:16 2011 +0200
     4.3 @@ -0,0 +1,5 @@
     4.4 +Name: slitaz
     4.5 +Description: This is a SliTaz GNU/Linux Roundup tracker template based on
     4.6 + the classic template provided by the Roundup.
     4.7 +Intended-for: All first-time Roundup users
     4.8 +Path: /home/slitaz/trackers/bugs
     5.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     5.2 +++ b/bugs/templates/slitaz/detectors/messagesummary.py	Thu Apr 14 01:13:16 2011 +0200
     5.3 @@ -0,0 +1,20 @@
     5.4 +#$Id: messagesummary.py,v 1.2 2007-04-03 06:47:21 a1s Exp $
     5.5 +
     5.6 +from roundup.mailgw import parseContent
     5.7 +
     5.8 +def summarygenerator(db, cl, nodeid, newvalues):
     5.9 +    ''' If the message doesn't have a summary, make one for it.
    5.10 +    '''
    5.11 +    if newvalues.has_key('summary') or not newvalues.has_key('content'):
    5.12 +        return
    5.13 +
    5.14 +    summary, content = parseContent(newvalues['content'], config=db.config)
    5.15 +    newvalues['summary'] = summary
    5.16 +
    5.17 +
    5.18 +def init(db):
    5.19 +    # fire before changes are made
    5.20 +    db.msg.audit('create', summarygenerator)
    5.21 +
    5.22 +# vim: set filetype=python ts=4 sw=4 et si
    5.23 +#SHA: 51433442433794dd7d80d65557aa21d59403d95a
     6.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     6.2 +++ b/bugs/templates/slitaz/detectors/nosyreaction.py	Thu Apr 14 01:13:16 2011 +0200
     6.3 @@ -0,0 +1,145 @@
     6.4 +#
     6.5 +# Copyright (c) 2001 Bizar Software Pty Ltd (http://www.bizarsoftware.com.au/)
     6.6 +# This module is free software, and you may redistribute it and/or modify
     6.7 +# under the same terms as Python, so long as this copyright message and
     6.8 +# disclaimer are retained in their original form.
     6.9 +#
    6.10 +# IN NO EVENT SHALL BIZAR SOFTWARE PTY LTD BE LIABLE TO ANY PARTY FOR
    6.11 +# DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING
    6.12 +# OUT OF THE USE OF THIS CODE, EVEN IF THE AUTHOR HAS BEEN ADVISED OF THE
    6.13 +# POSSIBILITY OF SUCH DAMAGE.
    6.14 +#
    6.15 +# BIZAR SOFTWARE PTY LTD SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
    6.16 +# BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
    6.17 +# FOR A PARTICULAR PURPOSE.  THE CODE PROVIDED HEREUNDER IS ON AN "AS IS"
    6.18 +# BASIS, AND THERE IS NO OBLIGATION WHATSOEVER TO PROVIDE MAINTENANCE,
    6.19 +# SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
    6.20 +# 
    6.21 +#$Id: nosyreaction.py,v 1.4 2005-04-04 08:47:14 richard Exp $
    6.22 +
    6.23 +# Python 2.3 ... 2.6 compatibility:
    6.24 +from roundup.anypy.sets_ import set
    6.25 +
    6.26 +from roundup import roundupdb, hyperdb
    6.27 +
    6.28 +def nosyreaction(db, cl, nodeid, oldvalues):
    6.29 +    ''' A standard detector is provided that watches for additions to the
    6.30 +        "messages" property.
    6.31 +        
    6.32 +        When a new message is added, the detector sends it to all the users on
    6.33 +        the "nosy" list for the issue that are not already on the "recipients"
    6.34 +        list of the message.
    6.35 +        
    6.36 +        Those users are then appended to the "recipients" property on the
    6.37 +        message, so multiple copies of a message are never sent to the same
    6.38 +        user.
    6.39 +        
    6.40 +        The journal recorded by the hyperdatabase on the "recipients" property
    6.41 +        then provides a log of when the message was sent to whom. 
    6.42 +    '''
    6.43 +    # send a copy of all new messages to the nosy list
    6.44 +    for msgid in determineNewMessages(cl, nodeid, oldvalues):
    6.45 +        try:
    6.46 +            cl.nosymessage(nodeid, msgid, oldvalues)
    6.47 +        except roundupdb.MessageSendError, message:
    6.48 +            raise roundupdb.DetectorError, message
    6.49 +
    6.50 +def determineNewMessages(cl, nodeid, oldvalues):
    6.51 +    ''' Figure a list of the messages that are being added to the given
    6.52 +        node in this transaction.
    6.53 +    '''
    6.54 +    messages = []
    6.55 +    if oldvalues is None:
    6.56 +        # the action was a create, so use all the messages in the create
    6.57 +        messages = cl.get(nodeid, 'messages')
    6.58 +    elif oldvalues.has_key('messages'):
    6.59 +        # the action was a set (so adding new messages to an existing issue)
    6.60 +        m = {}
    6.61 +        for msgid in oldvalues['messages']:
    6.62 +            m[msgid] = 1
    6.63 +        messages = []
    6.64 +        # figure which of the messages now on the issue weren't there before
    6.65 +        for msgid in cl.get(nodeid, 'messages'):
    6.66 +            if not m.has_key(msgid):
    6.67 +                messages.append(msgid)
    6.68 +    return messages
    6.69 +
    6.70 +def updatenosy(db, cl, nodeid, newvalues):
    6.71 +    '''Update the nosy list for changes to the assignedto
    6.72 +    '''
    6.73 +    # nodeid will be None if this is a new node
    6.74 +    current_nosy = set()
    6.75 +    if nodeid is None:
    6.76 +        ok = ('new', 'yes')
    6.77 +    else:
    6.78 +        ok = ('yes',)
    6.79 +        # old node, get the current values from the node if they haven't
    6.80 +        # changed
    6.81 +        if not newvalues.has_key('nosy'):
    6.82 +            nosy = cl.get(nodeid, 'nosy')
    6.83 +            for value in nosy:
    6.84 +                current_nosy.add(value)
    6.85 +
    6.86 +    # if the nosy list changed in this transaction, init from the new value
    6.87 +    if newvalues.has_key('nosy'):
    6.88 +        nosy = newvalues.get('nosy', [])
    6.89 +        for value in nosy:
    6.90 +            if not db.hasnode('user', value):
    6.91 +                continue
    6.92 +            current_nosy.add(value)
    6.93 +
    6.94 +    new_nosy = set(current_nosy)
    6.95 +
    6.96 +    # add assignedto(s) to the nosy list
    6.97 +    if newvalues.has_key('assignedto') and newvalues['assignedto'] is not None:
    6.98 +        propdef = cl.getprops()
    6.99 +        if isinstance(propdef['assignedto'], hyperdb.Link):
   6.100 +            assignedto_ids = [newvalues['assignedto']]
   6.101 +        elif isinstance(propdef['assignedto'], hyperdb.Multilink):
   6.102 +            assignedto_ids = newvalues['assignedto']
   6.103 +        for assignedto_id in assignedto_ids:
   6.104 +            new_nosy.add(assignedto_id)
   6.105 +
   6.106 +    # see if there's any new messages - if so, possibly add the author and
   6.107 +    # recipient to the nosy
   6.108 +    if newvalues.has_key('messages'):
   6.109 +        if nodeid is None:
   6.110 +            ok = ('new', 'yes')
   6.111 +            messages = newvalues['messages']
   6.112 +        else:
   6.113 +            ok = ('yes',)
   6.114 +            # figure which of the messages now on the issue weren't
   6.115 +            oldmessages = cl.get(nodeid, 'messages')
   6.116 +            messages = []
   6.117 +            for msgid in newvalues['messages']:
   6.118 +                if msgid not in oldmessages:
   6.119 +                    messages.append(msgid)
   6.120 +
   6.121 +        # configs for nosy modifications
   6.122 +        add_author = getattr(db.config, 'ADD_AUTHOR_TO_NOSY', 'new')
   6.123 +        add_recips = getattr(db.config, 'ADD_RECIPIENTS_TO_NOSY', 'new')
   6.124 +
   6.125 +        # now for each new message:
   6.126 +        msg = db.msg
   6.127 +        for msgid in messages:
   6.128 +            if add_author in ok:
   6.129 +                authid = msg.get(msgid, 'author')
   6.130 +                new_nosy.add(authid)
   6.131 +
   6.132 +            # add on the recipients of the message
   6.133 +            if add_recips in ok:
   6.134 +                for recipient in msg.get(msgid, 'recipients'):
   6.135 +                    new_nosy.add(recipient)
   6.136 +
   6.137 +    if current_nosy != new_nosy:
   6.138 +        # that's it, save off the new nosy list
   6.139 +        newvalues['nosy'] = list(new_nosy)
   6.140 +
   6.141 +def init(db):
   6.142 +    db.issue.react('create', nosyreaction)
   6.143 +    db.issue.react('set', nosyreaction)
   6.144 +    db.issue.audit('create', updatenosy)
   6.145 +    db.issue.audit('set', updatenosy)
   6.146 +
   6.147 +# vim: set filetype=python ts=4 sw=4 et si
   6.148 +#SHA: dc34be7cc4a4956a8b49b779a7462904a2edd00d
     7.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     7.2 +++ b/bugs/templates/slitaz/detectors/statusauditor.py	Thu Apr 14 01:13:16 2011 +0200
     7.3 @@ -0,0 +1,86 @@
     7.4 +# Copyright (c) 2002 ekit.com Inc (http://www.ekit-inc.com/)
     7.5 +#
     7.6 +# Permission is hereby granted, free of charge, to any person obtaining a copy
     7.7 +# of this software and associated documentation files (the "Software"), to deal
     7.8 +# in the Software without restriction, including without limitation the rights
     7.9 +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
    7.10 +# copies of the Software, and to permit persons to whom the Software is
    7.11 +# furnished to do so, subject to the following conditions:
    7.12 +#
    7.13 +#   The above copyright notice and this permission notice shall be included in
    7.14 +#   all copies or substantial portions of the Software.
    7.15 +#
    7.16 +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
    7.17 +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
    7.18 +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
    7.19 +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
    7.20 +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
    7.21 +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
    7.22 +# SOFTWARE.
    7.23 +#
    7.24 +#$Id: statusauditor.py,v 1.5 2004-03-27 00:01:48 richard Exp $
    7.25 +
    7.26 +def chatty(db, cl, nodeid, newvalues):
    7.27 +    ''' If the issue is currently 'unread', 'resolved', 'done-cbb' or None,
    7.28 +        then set it to 'chatting'
    7.29 +    '''
    7.30 +    # don't fire if there's no new message (ie. chat)
    7.31 +    if not newvalues.has_key('messages'):
    7.32 +        return
    7.33 +    if newvalues['messages'] == cl.get(nodeid, 'messages'):
    7.34 +        return
    7.35 +
    7.36 +    # get the chatting state ID
    7.37 +    try:
    7.38 +        chatting_id = db.status.lookup('chatting')
    7.39 +    except KeyError:
    7.40 +        # no chatting state, ignore all this stuff
    7.41 +        return
    7.42 +
    7.43 +    # get the current value
    7.44 +    current_status = cl.get(nodeid, 'status')
    7.45 +
    7.46 +    # see if there's an explicit change in this transaction
    7.47 +    if newvalues.has_key('status'):
    7.48 +        # yep, skip
    7.49 +        return
    7.50 +
    7.51 +    # determine the id of 'unread', 'resolved' and 'chatting'
    7.52 +    fromstates = []
    7.53 +    for state in 'unread resolved done-cbb'.split():
    7.54 +        try:
    7.55 +            fromstates.append(db.status.lookup(state))
    7.56 +        except KeyError:
    7.57 +            pass
    7.58 +
    7.59 +    # ok, there's no explicit change, so check if we are in a state that
    7.60 +    # should be changed
    7.61 +    if current_status in fromstates + [None]:
    7.62 +        # yep, we're now chatting
    7.63 +        newvalues['status'] = chatting_id
    7.64 +
    7.65 +
    7.66 +def presetunread(db, cl, nodeid, newvalues):
    7.67 +    ''' Make sure the status is set on new issues
    7.68 +    '''
    7.69 +    if newvalues.has_key('status') and newvalues['status']:
    7.70 +        return
    7.71 +
    7.72 +    # get the unread state ID
    7.73 +    try:
    7.74 +        unread_id = db.status.lookup('unread')
    7.75 +    except KeyError:
    7.76 +        # no unread state, ignore all this stuff
    7.77 +        return
    7.78 +
    7.79 +    # ok, do it
    7.80 +    newvalues['status'] = unread_id
    7.81 +
    7.82 +
    7.83 +def init(db):
    7.84 +    # fire before changes are made
    7.85 +    db.issue.audit('set', chatty)
    7.86 +    db.issue.audit('create', presetunread)
    7.87 +
    7.88 +# vim: set filetype=python ts=4 sw=4 et si
    7.89 +#SHA: 97f4de5b9d06b6be7ea73ba639a48141c80deaf9
     8.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     8.2 +++ b/bugs/templates/slitaz/detectors/userauditor.py	Thu Apr 14 01:13:16 2011 +0200
     8.3 @@ -0,0 +1,95 @@
     8.4 +# Copyright (c) 2003 Richard Jones (richard@mechanicalcat.net)
     8.5 +#
     8.6 +# Permission is hereby granted, free of charge, to any person obtaining a copy
     8.7 +# of this software and associated documentation files (the "Software"), to deal
     8.8 +# in the Software without restriction, including without limitation the rights
     8.9 +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
    8.10 +# copies of the Software, and to permit persons to whom the Software is
    8.11 +# furnished to do so, subject to the following conditions:
    8.12 +#
    8.13 +#   The above copyright notice and this permission notice shall be included in
    8.14 +#   all copies or substantial portions of the Software.
    8.15 +#
    8.16 +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
    8.17 +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
    8.18 +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
    8.19 +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
    8.20 +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
    8.21 +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
    8.22 +# SOFTWARE.
    8.23 +#
    8.24 +#$Id: userauditor.py,v 1.9 2007-09-12 21:11:13 jpend Exp $
    8.25 +
    8.26 +import re
    8.27 +
    8.28 +# regular expression thanks to: http://www.regular-expressions.info/email.html
    8.29 +# this is the "99.99% solution for syntax only".
    8.30 +email_regexp = (r"[a-z0-9!#$%&'*+/=?^_`{|}~-]+(?:\.[a-z0-9!#$%&'*+/=?^_`{|}~-]+)*", r"(localhost|(?:[a-z0-9](?:[a-z0-9-]*[a-z0-9])?\.)+[a-z0-9](?:[a-z0-9-]*[a-z0-9]))")
    8.31 +email_rfc = re.compile('^' + email_regexp[0] + '@' + email_regexp[1] + '$', re.IGNORECASE)
    8.32 +email_local = re.compile('^' + email_regexp[0] + '$', re.IGNORECASE)
    8.33 +
    8.34 +def valid_address(address):
    8.35 +    ''' If we see an @-symbol in the address then check against the full
    8.36 +        RFC syntax. Otherwise it is a local-only address so only check
    8.37 +        the local part of the RFC syntax.
    8.38 +    '''
    8.39 +    if '@' in address:
    8.40 +        return email_rfc.match(address)
    8.41 +    else:
    8.42 +        return email_local.match(address)
    8.43 +
    8.44 +def get_addresses(user):
    8.45 +    ''' iterate over all known addresses in a newvalues dict
    8.46 +        this takes of the address/alterate_addresses handling
    8.47 +    '''
    8.48 +    if user.has_key('address'):
    8.49 +        yield user['address']
    8.50 +    if user.get('alternate_addresses', None):
    8.51 +        for address in user['alternate_addresses'].split('\n'):
    8.52 +            yield address
    8.53 +
    8.54 +def audit_user_fields(db, cl, nodeid, newvalues):
    8.55 +    ''' Make sure user properties are valid.
    8.56 +
    8.57 +        - email address is syntactically valid
    8.58 +        - email address is unique
    8.59 +        - roles specified exist
    8.60 +        - timezone is valid
    8.61 +    '''
    8.62 +
    8.63 +    for address in get_addresses(newvalues):
    8.64 +        if not valid_address(address):
    8.65 +            raise ValueError, 'Email address syntax is invalid'
    8.66 +
    8.67 +        check_main = db.user.stringFind(address=address)
    8.68 +        # make sure none of the alts are owned by anyone other than us (x!=nodeid)
    8.69 +        check_alts = [x for x in db.user.filter(None, {'alternate_addresses' : address}) if x != nodeid]
    8.70 +        if check_main or check_alts:
    8.71 +            raise ValueError, 'Email address %s already in use' % address
    8.72 +
    8.73 +    for rolename in [r.lower().strip() for r in newvalues.get('roles', '').split(',')]:
    8.74 +            if rolename and not db.security.role.has_key(rolename):
    8.75 +                raise ValueError, 'Role "%s" does not exist'%rolename
    8.76 +
    8.77 +    tz = newvalues.get('timezone', None)
    8.78 +    if tz:
    8.79 +        # if they set a new timezone validate the timezone by attempting to
    8.80 +        # use it before we store it to the db.
    8.81 +        import roundup.date
    8.82 +        import datetime
    8.83 +        try:
    8.84 +            TZ = roundup.date.get_timezone(tz)
    8.85 +            dt = datetime.datetime.now()
    8.86 +            local = TZ.localize(dt).utctimetuple()
    8.87 +        except IOError:
    8.88 +            raise ValueError, 'Timezone "%s" does not exist' % tz
    8.89 +        except ValueError:
    8.90 +            raise ValueError, 'Timezone "%s" exceeds valid range [-23...23]' % tz
    8.91 +
    8.92 +def init(db):
    8.93 +    # fire before changes are made
    8.94 +    db.user.audit('set', audit_user_fields)
    8.95 +    db.user.audit('create', audit_user_fields)
    8.96 +
    8.97 +# vim: sts=4 sw=4 et si
    8.98 +#SHA: c7242008d09362eb32aa3933e334f6d5a2b09bb6
     9.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     9.2 +++ b/bugs/templates/slitaz/extensions/README.txt	Thu Apr 14 01:13:16 2011 +0200
     9.3 @@ -0,0 +1,6 @@
     9.4 +This directory is for tracker extensions:
     9.5 +
     9.6 +- CGI Actions
     9.7 +- Templating functions
     9.8 +
     9.9 +See the customisation doc for more information.
    10.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    10.2 +++ b/bugs/templates/slitaz/html/_generic.404.html	Thu Apr 14 01:13:16 2011 +0200
    10.3 @@ -0,0 +1,10 @@
    10.4 +<html>
    10.5 +<head>
    10.6 +<title>Item Not Found</title>
    10.7 +</head>
    10.8 +
    10.9 +<body>
   10.10 +There is no <span tal:content="context/_classname" /> with id <span tal:content="context/id"/>
   10.11 +</body>
   10.12 +</html>
   10.13 +<!-- SHA: 7c74a39904a98fd7aacba48daf5c6820da253ed2 -->
    11.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    11.2 +++ b/bugs/templates/slitaz/html/_generic.calendar.html	Thu Apr 14 01:13:16 2011 +0200
    11.3 @@ -0,0 +1,19 @@
    11.4 +<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
    11.5 +<html>
    11.6 + <head>
    11.7 +  <link rel="stylesheet" type="text/css" href="@@file/style.css" />
    11.8 +  <meta http-equiv="Content-Type" content="text/html; charset=utf-8;" />
    11.9 +  <title tal:content="string:Roundup Calendar"></title>
   11.10 +  <script language="Javascript"
   11.11 +          type="text/javascript"
   11.12 +          tal:content="structure string:
   11.13 +          // this is the name of the field in the original form that we're working on
   11.14 +          form  = window.opener.document.${request/form/form/value};
   11.15 +          field = '${request/form/property/value}';" >
   11.16 +  </script>
   11.17 + </head>
   11.18 + <body class="body"
   11.19 +       tal:content="structure python:utils.html_calendar(request)">
   11.20 + </body>
   11.21 +</html>
   11.22 +<!-- SHA: 3c1535fe01902cf3fa7115c982c45f7b0674b590 -->
    12.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    12.2 +++ b/bugs/templates/slitaz/html/_generic.collision.html	Thu Apr 14 01:13:16 2011 +0200
    12.3 @@ -0,0 +1,17 @@
    12.4 +<tal:block metal:use-macro="templates/page/macros/icing">
    12.5 +<title metal:fill-slot="head_title" i18n:translate=""
    12.6 + ><span tal:replace="python:context._classname.capitalize()"
    12.7 + i18n:name="class" /> Edit Collision - <span i18n:name="tracker"
    12.8 + tal:replace="config/TRACKER_NAME" /></title>
    12.9 +<tal:block metal:fill-slot="body_title" i18n:translate=""
   12.10 + ><span tal:replace="python:context._classname.capitalize()"
   12.11 + i18n:name="class" /> Edit Collision</tal:block>
   12.12 +
   12.13 +<td class="content" metal:fill-slot="content" i18n:translate="
   12.14 +  There has been a collision. Another user updated this node
   12.15 +  while you were editing. Please <a href='${context}'>reload</a>
   12.16 +  the node and review your edits.
   12.17 +"><span tal:replace="context/designator" i18n:name="context" />
   12.18 +</td>
   12.19 +</tal:block>
   12.20 +<!-- SHA: db15fb6c88215d4baf223910a6c9cd81c63dc994 -->
    13.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    13.2 +++ b/bugs/templates/slitaz/html/_generic.help-empty.html	Thu Apr 14 01:13:16 2011 +0200
    13.3 @@ -0,0 +1,9 @@
    13.4 +<html>
    13.5 +  <head>
    13.6 +    <title>Empty page (no search performed yet)</title>
    13.7 +  </head>
    13.8 +  <body>
    13.9 +    <p i18n:translate="">Please specify your search parameters!</p>
   13.10 +  </body>
   13.11 +</html>
   13.12 +<!-- SHA: 9a118377b03172347d95097ff75fca26a6dd3738 -->
    14.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    14.2 +++ b/bugs/templates/slitaz/html/_generic.help-list.html	Thu Apr 14 01:13:16 2011 +0200
    14.3 @@ -0,0 +1,84 @@
    14.4 +<!-- $Id: _generic.help-list.html,v 1.2 2008-03-01 08:18:07 richard Exp $ vim: sw=2 ts=8 et
    14.5 +--><html tal:define="vok context/is_view_ok">
    14.6 +  <head>
    14.7 +    <title>Search result for user helper</title>
    14.8 +    <link rel="stylesheet" type="text/css" href="@@file/style.css" />
    14.9 +    <script language="Javascript" type="text/javascript"
   14.10 +        tal:content="structure string:<!--
   14.11 +        // this is the name of the field in the original form that we're working on
   14.12 +        form  = parent.opener.document.${request/form/form/value};
   14.13 +        field  = '${request/form/property/value}';
   14.14 +    //-->"></script>
   14.15 +    <script src="@@file/help_controls.js" type="text/javascript"></script>
   14.16 +<script type="text/javascript"><!--
   14.17 +var text_field = parent.submit.document.frm_help.text_preview;
   14.18 +//--></script>
   14.19 +  </head>
   14.20 +  <body>
   14.21 +    <pre tal:content="request/env/QUERY_STRING" tal:condition=false />
   14.22 +
   14.23 +  <p tal:condition="not:vok" i18n:translate="">You are not
   14.24 +  allowed to view this page.</p>
   14.25 +
   14.26 +  <tal:if condition="context/is_view_ok">
   14.27 +  <tal:def define="batch request/batch;">
   14.28 +  <form name=dummyform>
   14.29 +    <table width="100%"
   14.30 +      tal:define="template string:help-list"
   14.31 +      metal:use-macro="templates/help/macros/batch_navi"
   14.32 +      >
   14.33 +      <tr class="navigation">
   14.34 +       <th>
   14.35 +        <a href="#">&lt;&lt; previous</a>
   14.36 +       </th>
   14.37 +       <th i18n:translate="">1..25 out of 50
   14.38 +       </th>
   14.39 +       <th>
   14.40 +        <a href="#">next &gt;&gt;</a>
   14.41 +       </th>
   14.42 +      </tr>
   14.43 +     </table>
   14.44 +
   14.45 +  <form name=dummyform>
   14.46 +  <table class="classhelp"
   14.47 +    tal:define="
   14.48 +       props python:request.form['properties'].value.split(',');
   14.49 +       legend templates/help/macros/legend;
   14.50 +    "><thead>
   14.51 +      <tr metal:use-macro="legend">
   14.52 +         <th>&nbsp;<b>x</b></th>
   14.53 +         <th tal:repeat="prop props" tal:content="prop" i18n:translate=""></th>
   14.54 +       </tr>
   14.55 +     </thead>
   14.56 +     <tfoot tal:condition=true>
   14.57 +       <tr metal:use-macro="legend" />
   14.58 +     </tfoot>
   14.59 +     <tbody>
   14.60 +       <tr tal:repeat="item batch">
   14.61 +         <tal:block tal:define="attr python:item[props[0]]" >
   14.62 +           <td>
   14.63 +             <input name="check"
   14.64 +             onclick="switch_val(text_field, this);" type="checkbox"
   14.65 +             tal:attributes="value attr; id string:id_$attr" />
   14.66 +             </td>
   14.67 +             <td tal:repeat="prop props">
   14.68 +                 <label class="classhelp-label"
   14.69 +                        tal:attributes="for string:id_$attr"
   14.70 +                        tal:content="python:item[prop]"></label>
   14.71 +             </td>
   14.72 +           </tal:block>
   14.73 +         </tr>
   14.74 +       </tbody>
   14.75 +     </table>
   14.76 +   </form>
   14.77 +     </tal:def>
   14.78 +     </tal:if>
   14.79 +     
   14.80 +     <pre tal:content=request tal:condition=false />
   14.81 +     <script type="text/javascript"><!--
   14.82 +       parent.submit.document.frm_help.cb_listpresent.checked=true;
   14.83 +       reviseList_framed(document.dummyform, text_field)
   14.84 +     //--></script>
   14.85 +  </body>
   14.86 +</html>
   14.87 +<!-- SHA: 9b8c6aade0245ba2f29505606f427948e3448d22 -->
    15.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    15.2 +++ b/bugs/templates/slitaz/html/_generic.help-search.html	Thu Apr 14 01:13:16 2011 +0200
    15.3 @@ -0,0 +1,14 @@
    15.4 +<html>
    15.5 +  <head>
    15.6 +    <title>Frame for search input fields</title>
    15.7 +  </head>
    15.8 +  <body>
    15.9 +    <p i18n:translate="">Generic template
   15.10 +    <span tal:replace="request/template" i18n:name="template">help-search</span>
   15.11 +    or version for class
   15.12 +    <span tal:replace="request/classname" i18n:name="classname">user</span>
   15.13 +    is not yet implemented</p>
   15.14 +  </body>
   15.15 +</html>
   15.16 +
   15.17 +<!-- SHA: b95a7bda7189c0747d2f4112d1d3d02808fd1753 -->
    16.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    16.2 +++ b/bugs/templates/slitaz/html/_generic.help-submit.html	Thu Apr 14 01:13:16 2011 +0200
    16.3 @@ -0,0 +1,74 @@
    16.4 +<html>
    16.5 +  <head>
    16.6 +      <link rel="stylesheet" type="text/css" href="@@file/style.css" />
    16.7 +      <meta http-equiv="Content-Type"
    16.8 +       tal:attributes="content string:text/html;; charset=${request/client/charset}" />
    16.9 +      <tal:block tal:condition="python:request.form.has_key('property')">
   16.10 +      <title>Generic submit page for framed helper windows</title>
   16.11 +      <script language="Javascript" type="text/javascript"
   16.12 +          tal:content="structure string:<!--
   16.13 +// this is the name of the field in the original form that we're working on
   16.14 +form  = parent.opener.document.${request/form/form/value};
   16.15 +callingform=form
   16.16 +field  = '${request/form/property/value}';
   16.17 +var listform = null
   16.18 +function listPresent() {
   16.19 +  return document.frm_help.cb_listpresent.checked
   16.20 +}
   16.21 +function getListForm() {
   16.22 +  if (listPresent()) {
   16.23 +    return parent.list.document.forms.dummyform
   16.24 +  } else {
   16.25 +    return null
   16.26 +  }
   16.27 +}
   16.28 +
   16.29 +
   16.30 +function checkListForm() {
   16.31 +  // global listform
   16.32 +  if (listform != null)
   16.33 +    if (parent.list.document.dummyform) {
   16.34 +      listform = parent.list.document.dummyform
   16.35 +      alert(listform)
   16.36 +    }
   16.37 +
   16.38 +  var bol= listform != null
   16.39 +  alert('checkListForm: bol='+bol)
   16.40 +  return bol
   16.41 +}
   16.42 +//-->">
   16.43 +      </script>
   16.44 +      <script src="@@file/help_controls.js" type="text/javascript"></script>
   16.45 +      </tal:block>
   16.46 +  </head>
   16.47 + <body class="body" onload="parent.focus();" id="submit">
   16.48 + <pre tal:content="request/env/QUERY_STRING" tal:condition=false />
   16.49 + <form name="frm_help"
   16.50 +       tal:define="batch request/batch;
   16.51 +       props python:request.form['properties'].value.split(',')"
   16.52 +       class="help-submit"
   16.53 +       id="classhelp-controls">
   16.54 +     <div style="width:100%;text-align:left;margin-bottom:0.2em">
   16.55 +       <input type="text" name="text_preview" size="24" class="preview"
   16.56 +       onchange="f=getListForm();if(f){ reviseList_framed(f, this)};"
   16.57 +       />
   16.58 +     </div>
   16.59 +     <input type=checkbox name="cb_listpresent" readonly="readonly" style="display:none">
   16.60 +     <input type="button" id="btn_cancel"
   16.61 +            value=" Cancel " onclick="parent.close();return false;"
   16.62 +            i18n:attributes="value" />
   16.63 +     <input type="reset" id="btn_reset"
   16.64 +     onclick="text_field.value=original_field;f=getListForm();if (f) {reviseList_framed(f, this)};return false"
   16.65 +            />
   16.66 +     <input type="submit" id="btn_apply" class="apply"
   16.67 +            value=" Apply " onclick="callingform[field].value=text_field.value; parent.close();"
   16.68 +            i18n:attributes="value" />
   16.69 + </form>
   16.70 + <script type="text/javascript"><!--
   16.71 +var text_field = document.frm_help.text_preview;
   16.72 +original_field=form[field].value;
   16.73 +text_field.value=original_field;
   16.74 +//--></script>
   16.75 + </body>
   16.76 +</html>
   16.77 +<!-- SHA: 1de39ac0d15dc59c64187b6c691d58ba20931372 -->
    17.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    17.2 +++ b/bugs/templates/slitaz/html/_generic.help.html	Thu Apr 14 01:13:16 2011 +0200
    17.3 @@ -0,0 +1,99 @@
    17.4 +<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
    17.5 +<html tal:define="property request/form/property/value" >
    17.6 +  <head>
    17.7 +      <link rel="stylesheet" type="text/css" href="@@file/style.css" />
    17.8 +      <meta http-equiv="Content-Type"
    17.9 +       tal:attributes="content string:text/html;; charset=${request/client/charset}" />
   17.10 +      <tal:block tal:condition="python:request.form.has_key('property')">
   17.11 +      <title i18n:translate=""><tal:x i18n:name="property"
   17.12 +       tal:content="property" i18n:translate="" /> help - <span i18n:name="tracker"
   17.13 +       tal:replace="config/TRACKER_NAME" /></title>
   17.14 +      <script language="Javascript" type="text/javascript"
   17.15 +          tal:content="structure string:
   17.16 +          // this is the name of the field in the original form that we're working on
   17.17 +          form  = window.opener.document.${request/form/form/value};
   17.18 +          field  = '${request/form/property/value}';">
   17.19 +      </script>
   17.20 +      <script src="@@file/help_controls.js" type="text/javascript"><!--
   17.21 +      //--></script>
   17.22 +      </tal:block>
   17.23 +  </head>
   17.24 + <body class="body" onload="resetList();">
   17.25 + <form name="frm_help" tal:attributes="action request/base"
   17.26 +       tal:define="batch request/batch;
   17.27 +                   props python:request.form['properties'].value.split(',')">
   17.28 +
   17.29 +     <div id="classhelp-controls">
   17.30 +       <!--input type="button" name="btn_clear"
   17.31 +              value="Clear" onClick="clearList()"/ -->
   17.32 +       <input type="text" name="text_preview" size="24" class="preview"
   17.33 +              onchange="reviseList(this.value);"/>
   17.34 +       <input type="button" name="btn_reset"
   17.35 +              value=" Cancel " onclick="resetList(); window.close();"
   17.36 +              i18n:attributes="value" />
   17.37 +       <input type="button" name="btn_apply" class="apply"
   17.38 +              value=" Apply " onclick="updateList(); window.close();"
   17.39 +              i18n:attributes="value" />
   17.40 +     </div>
   17.41 +     <table width="100%">
   17.42 +      <tr class="navigation">
   17.43 +       <th>
   17.44 +        <a tal:define="prev batch/previous" tal:condition="prev"
   17.45 +           tal:attributes="href python:request.indexargs_url(request.classname,
   17.46 +           {'@template':'help', 'property': request.form['property'].value,
   17.47 +            'properties': request.form['properties'].value,
   17.48 +            'form': request.form['form'].value,
   17.49 +            'type': request.form['type'].value,
   17.50 +            '@startwith':prev.first, '@pagesize':prev.size})"
   17.51 +           i18n:translate="" >&lt;&lt; previous</a>
   17.52 +        &nbsp;
   17.53 +       </th>
   17.54 +       <th i18n:translate=""><span tal:replace="batch/start" i18n:name="start"
   17.55 +        />..<span tal:replace="python: batch.start + batch.length -1" i18n:name="end"
   17.56 +        /> out of <span tal:replace="batch/sequence_length" i18n:name="total"
   17.57 +        />
   17.58 +       </th>
   17.59 +       <th>
   17.60 +        <a tal:define="next batch/next" tal:condition="next"
   17.61 +           tal:attributes="href python:request.indexargs_url(request.classname,
   17.62 +           {'@template':'help', 'property': request.form['property'].value,
   17.63 +            'properties': request.form['properties'].value,
   17.64 +            'form': request.form['form'].value,
   17.65 +            'type': request.form['type'].value,
   17.66 +            '@startwith':next.first, '@pagesize':next.size})"
   17.67 +           i18n:translate="" >next &gt;&gt;</a>
   17.68 +        &nbsp;
   17.69 +       </th>
   17.70 +      </tr>
   17.71 +     </table>
   17.72 +
   17.73 +     <table class="classhelp">
   17.74 +       <tr>
   17.75 +           <th>&nbsp;<b>x</b></th>
   17.76 +           <th tal:repeat="prop props" tal:content="prop" i18n:translate=""></th>
   17.77 +       </tr>
   17.78 +       <tr tal:repeat="item batch">
   17.79 +         <tal:block tal:define="attr python:item[props[0]]" >
   17.80 +           <td>
   17.81 +             <input name="check"
   17.82 +                 onclick="updatePreview();"
   17.83 +                 tal:attributes="type python:request.form['type'].value;
   17.84 +                                 value attr; id string:id_$attr" />
   17.85 +             </td>
   17.86 +             <td tal:repeat="prop props">
   17.87 +                 <label class="classhelp-label"
   17.88 +                        tal:attributes="for string:id_$attr"
   17.89 +                        tal:content="python:item[prop]"></label>
   17.90 +             </td>
   17.91 +           </tal:block>
   17.92 +       </tr>
   17.93 +       <tr>
   17.94 +           <th>&nbsp;<b>x</b></th>
   17.95 +           <th tal:repeat="prop props" tal:content="prop" i18n:translate=""></th>
   17.96 +       </tr>
   17.97 +     </table>
   17.98 +
   17.99 + </form>
  17.100 + </body>
  17.101 +</html>
  17.102 +<!-- SHA: 992685537210e03230c9cfc3d5a4060edb1f1536 -->
    18.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    18.2 +++ b/bugs/templates/slitaz/html/_generic.index.html	Thu Apr 14 01:13:16 2011 +0200
    18.3 @@ -0,0 +1,72 @@
    18.4 +<!-- dollarId: issue.index,v 1.2 2001/07/29 04:07:37 richard Exp dollar-->
    18.5 +
    18.6 +<tal:block metal:use-macro="templates/page/macros/icing">
    18.7 +<title metal:fill-slot="head_title" i18n:translate=""
    18.8 + ><span tal:replace="python:context._classname.capitalize()"
    18.9 + i18n:name="class" /> editing - <span i18n:name="tracker"
   18.10 + tal:replace="config/TRACKER_NAME" /></title>
   18.11 +<tal:block metal:fill-slot="body_title" i18n:translate=""
   18.12 + ><span tal:replace="python:context._classname.capitalize()"
   18.13 + i18n:name="class" /> editing</tal:block>
   18.14 +
   18.15 +<td class="content" metal:fill-slot="content">
   18.16 +
   18.17 +<span tal:condition="python:not (context.is_view_ok() or context.is_edit_ok()
   18.18 + or request.user.hasRole('Anonymous'))"
   18.19 + tal:omit-tag="python:1" i18n:translate=""
   18.20 +>You are not allowed to view this page.</span>
   18.21 +
   18.22 +<span tal:condition="python:not (context.is_view_ok() or context.is_edit_ok())
   18.23 + and request.user.hasRole('Anonymous')"
   18.24 + tal:omit-tag="python:1" i18n:translate=""
   18.25 +>Please login with your username and password.</span>
   18.26 +
   18.27 +<tal:block tal:condition="context/is_edit_ok">
   18.28 +<tal:block i18n:translate="">
   18.29 +<p class="form-help">
   18.30 + You may edit the contents of the
   18.31 + <span tal:replace="request/classname" i18n:name="classname"/>
   18.32 + class using this form. Commas, newlines and double quotes (") must be
   18.33 + handled delicately. You may include commas and newlines by enclosing the
   18.34 + values in double-quotes ("). Double quotes themselves must be quoted by
   18.35 + doubling ("").
   18.36 +</p>
   18.37 +
   18.38 +<p class="form-help">
   18.39 + Multilink properties have their multiple values colon (":") separated
   18.40 + (... ,"one:two:three", ...)
   18.41 +</p>
   18.42 +
   18.43 +<p class="form-help">
   18.44 + Remove entries by deleting their line. Add new entries by appending
   18.45 + them to the table - put an X in the id column. If you wish to restore a
   18.46 + removed item and you know its id then just put that id in the id column.
   18.47 +</p>
   18.48 +</tal:block>
   18.49 +<form onSubmit="return submit_once()" method="post"
   18.50 +      tal:attributes="action context/designator">
   18.51 +<textarea rows="15" style="width:90%" name="rows" tal:content="context/csv"></textarea>
   18.52 +<br>
   18.53 +<input type="hidden" name="@action" value="editCSV">
   18.54 +<input type="submit" value="Edit Items" i18n:attributes="value">
   18.55 +</form>
   18.56 +</tal:block>
   18.57 +
   18.58 +<table tal:condition="context/is_only_view_ok" width="100%" class="list">
   18.59 + <tr>
   18.60 +  <th tal:repeat="property context/propnames" tal:content="property">&nbsp;</th>
   18.61 + </tr>
   18.62 + <tal:block repeat="item context/list">
   18.63 + <tr tal:condition="item/is_view_ok"
   18.64 +     tal:attributes="class python:['normal', 'alt'][repeat['item'].index%6/3]">
   18.65 +  <td tal:repeat="property context/propnames"
   18.66 +   tal:content="python: item[property] or default"
   18.67 +  >&nbsp;</td>
   18.68 + </tr>
   18.69 + </tal:block>
   18.70 +</table>
   18.71 +
   18.72 +</td>
   18.73 +
   18.74 +</tal:block>
   18.75 +<!-- SHA: 0e2e831b8d3ec903798d21a7d1f96b3e07f740a1 -->
    19.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    19.2 +++ b/bugs/templates/slitaz/html/_generic.item.html	Thu Apr 14 01:13:16 2011 +0200
    19.3 @@ -0,0 +1,59 @@
    19.4 +<tal:block metal:use-macro="templates/page/macros/icing">
    19.5 +<title metal:fill-slot="head_title" i18n:translate=""
    19.6 + ><span tal:replace="python:context._classname.capitalize()"
    19.7 + i18n:name="class" /> editing - <span i18n:name="tracker"
    19.8 + tal:replace="config/TRACKER_NAME" /></title>
    19.9 +<tal:block metal:fill-slot="body_title" i18n:translate=""
   19.10 + ><span tal:replace="python:context._classname.capitalize()"
   19.11 + i18n:name="class" /> editing</tal:block>
   19.12 +
   19.13 +<td class="content" metal:fill-slot="content">
   19.14 +
   19.15 +<p tal:condition="python:not (context.is_view_ok()
   19.16 + or request.user.hasRole('Anonymous'))" i18n:translate="">
   19.17 + You are not allowed to view this page.</p>
   19.18 +
   19.19 +<p tal:condition="python:not context.is_view_ok()
   19.20 + and request.user.hasRole('Anonymous')" i18n:translate="">
   19.21 + Please login with your username and password.</p>
   19.22 +
   19.23 +<div tal:condition="context/is_view_ok">
   19.24 +
   19.25 +<form method="post" onSubmit="return submit_once()"
   19.26 +      enctype="multipart/form-data" tal:condition="context/is_view_ok"
   19.27 +      tal:attributes="action context/designator">
   19.28 +
   19.29 +<input type="hidden" name="@template" value="item">
   19.30 +
   19.31 +<table class="form">
   19.32 +
   19.33 +<tr tal:repeat="prop python:db[context._classname].properties()">
   19.34 + <tal:block tal:condition="python:prop._name not in ('id',
   19.35 +   'creator', 'creation', 'actor', 'activity')">
   19.36 +  <th tal:content="prop/_name"></th>
   19.37 +  <td tal:content="structure python:context[prop._name].field()"></td>
   19.38 + </tal:block>
   19.39 +</tr>
   19.40 +<tr>
   19.41 + <td>&nbsp;</td>
   19.42 + <td colspan=3 tal:content="structure context/submit">
   19.43 +  submit button will go here
   19.44 + </td>
   19.45 +</tr>
   19.46 +</table>
   19.47 +
   19.48 +</form>
   19.49 +
   19.50 +<tal:block tal:condition="context/id"
   19.51 +    tal:define="limit python:[10, None][request.form.has_key('show_all_history')]"
   19.52 +    tal:replace="structure python:context.history(limit=limit)" />
   19.53 +<p tal:condition="not:exists:request/form/show_all_history" i18n:translate="">Showing 10 items.
   19.54 +<a tal:attributes="href string:${context/_classname}${context/id}?show_all_history=yes">Show all history</a>
   19.55 +(warning: this could be VERY long)</p>
   19.56 +
   19.57 +</div>
   19.58 +
   19.59 +</td>
   19.60 +
   19.61 +</tal:block>
   19.62 +<!-- SHA: 78108e49cad0014d9861f955e51d19ecb02c6b64 -->
    20.1 Binary file bugs/templates/slitaz/html/favicon.ico has changed
    21.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    21.2 +++ b/bugs/templates/slitaz/html/file.index.html	Thu Apr 14 01:13:16 2011 +0200
    21.3 @@ -0,0 +1,32 @@
    21.4 +<!-- dollarId: file.index,v 1.4 2002/01/23 05:10:27 richard Exp dollar-->
    21.5 +<tal:block metal:use-macro="templates/page/macros/icing">
    21.6 +<title metal:fill-slot="head_title" i18n:translate=""
    21.7 + >List of files - <span tal:replace="config/TRACKER_NAME" i18n:name="tracker" /></title>
    21.8 +<span metal:fill-slot="body_title" tal:omit-tag="python:1"
    21.9 +  i18n:translate="">List of files</span>
   21.10 +<td class="content" metal:fill-slot="content">
   21.11 +
   21.12 +<table class="otherinfo" tal:define="batch request/batch">
   21.13 + <tr><th style="padding-right: 10" i18n:translate="">Download</th>
   21.14 +     <th style="padding-right: 10" i18n:translate="">Content Type</th>
   21.15 +     <th style="padding-right: 10" i18n:translate="">Uploaded By</th>
   21.16 +     <th style="padding-right: 10" i18n:translate="">Date</th>
   21.17 + </tr>
   21.18 + <tr tal:repeat="file batch" tal:attributes="class python:['normal', 'alt'][repeat['file'].index%6/3]">
   21.19 +  <td>
   21.20 +   <a tal:attributes="href string:file${file/id}/${file/name}"
   21.21 +      tal:content="file/name">dld link</a>
   21.22 +  </td>
   21.23 +  <td tal:content="file/type">content type</td>
   21.24 +  <td tal:content="file/creator">creator's name</td>
   21.25 +  <td tal:content="file/creation">creation date</td>
   21.26 + </tr>
   21.27 +
   21.28 + <metal:block use-macro="templates/issue.index/macros/batch-footer" />
   21.29 +
   21.30 +</table>
   21.31 +
   21.32 +</td>
   21.33 +
   21.34 +</tal:block>
   21.35 +<!-- SHA: f3a343f0682801cb8c47bd793d2d436fc7258d73 -->
    22.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    22.2 +++ b/bugs/templates/slitaz/html/file.item.html	Thu Apr 14 01:13:16 2011 +0200
    22.3 @@ -0,0 +1,54 @@
    22.4 +<tal:block metal:use-macro="templates/page/macros/icing">
    22.5 +<title metal:fill-slot="head_title" i18n:translate="">File display - <span
    22.6 + i18n:name="tracker" tal:replace="config/TRACKER_NAME" /></title>
    22.7 +<span metal:fill-slot="body_title" tal:omit-tag="python:1"
    22.8 + i18n:translate="">File display</span>
    22.9 +
   22.10 +<td class="content" metal:fill-slot="content">
   22.11 +
   22.12 +<p tal:condition="python:not (context.is_view_ok()
   22.13 + or request.user.hasRole('Anonymous'))" i18n:translate="">
   22.14 + You are not allowed to view this page.</p>
   22.15 +
   22.16 +<p tal:condition="python:not context.is_view_ok()
   22.17 + and request.user.hasRole('Anonymous')" i18n:translate="">
   22.18 + Please login with your username and password.</p>
   22.19 +
   22.20 +<form method="post" onSubmit="return submit_once()"
   22.21 +      enctype="multipart/form-data" tal:condition="context/is_view_ok"
   22.22 +      tal:attributes="action context/designator">
   22.23 +
   22.24 +<table class="form">
   22.25 + <tr>
   22.26 +  <th i18n:translate="">Name</th>
   22.27 +  <td tal:content="structure context/name/field"></td>
   22.28 + </tr>
   22.29 + <tr>
   22.30 +  <th i18n:translate="">Content Type</th>
   22.31 +  <td tal:content="structure context/type/field"></td>
   22.32 + </tr>
   22.33 +
   22.34 + <tr>
   22.35 +  <td>
   22.36 +   &nbsp;
   22.37 +   <input type="hidden" name="@template" value="item">
   22.38 +   <input type="hidden" name="@required" value="name,type">
   22.39 +   <input type="hidden" name="@multilink"
   22.40 +          tal:condition="python:request.form.has_key('@multilink')"
   22.41 +          tal:attributes="value request/form/@multilink/value">
   22.42 +  </td>
   22.43 +  <td tal:content="structure context/submit">submit button here</td>
   22.44 + </tr>
   22.45 +</table>
   22.46 +</form>
   22.47 +
   22.48 +<a tal:condition="python:context.id and context.is_view_ok()"
   22.49 + tal:attributes="href string:file${context/id}/${context/name}"
   22.50 + i18n:translate="">download</a>
   22.51 +
   22.52 +<tal:block tal:condition="context/id" tal:replace="structure context/history" />
   22.53 +
   22.54 +</td>
   22.55 +
   22.56 +</tal:block>
   22.57 +<!-- SHA: 9b0955c553e1df1d791dfc24530aeb945896cf46 -->
    23.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    23.2 +++ b/bugs/templates/slitaz/html/help.html	Thu Apr 14 01:13:16 2011 +0200
    23.3 @@ -0,0 +1,39 @@
    23.4 +<!--
    23.5 +Macros for framed help windows
    23.6 +-->
    23.7 +
    23.8 +<!-- legend for helper search results -->
    23.9 +<thead>
   23.10 +<tr metal:define-macro="legend">
   23.11 +  <th><b>x</b></th>
   23.12 +  <th tal:repeat="prop props" tal:content="prop" i18n:translate=""></th>
   23.13 +</tr>
   23.14 +</thead>
   23.15 +
   23.16 +<table width="100%"
   23.17 +  metal:define-macro="batch_navi"
   23.18 +  tal:define="prev batch/previous;
   23.19 +  next batch/next;
   23.20 +  "
   23.21 +  tal:condition="python:prev or next">
   23.22 +  <tr class="navigation">
   23.23 +   <th width="30%">
   23.24 +    <a tal:condition="prev"
   23.25 +       tal:attributes="href python:request.indexargs_url(request.classname, {'@template':'help-list', 'property': request.form['property'].value, 'properties': request.form['properties'].value, 'form': request.form['form'].value, '@startwith':prev.first, '@pagesize':prev.size})"
   23.26 +       i18n:translate="" >&lt;&lt; previous</a>
   23.27 +    &nbsp;
   23.28 +   </th>
   23.29 +   <th i18n:translate="" width="40%"><span tal:replace="batch/start" i18n:name="start"
   23.30 +    />..<span tal:replace="python: batch.start + batch.length -1" i18n:name="end"
   23.31 +    /> out of <span tal:replace="batch/sequence_length" i18n:name="total"
   23.32 +    />
   23.33 +   </th>
   23.34 +   <th width="30%">
   23.35 +    <a tal:condition="next"
   23.36 +       tal:attributes="href python:request.indexargs_url(request.classname, {'@template':'help-list', 'property': request.form['property'].value, 'properties': request.form['properties'].value, 'form': request.form['form'].value, '@startwith':next.first, '@pagesize':next.size})"
   23.37 +       i18n:translate="" >next &gt;&gt;</a>
   23.38 +    &nbsp;
   23.39 +   </th>
   23.40 +  </tr>
   23.41 + </table>
   23.42 +<!-- SHA: 5bb5e9db92d4dea06f6bd0224f34dce86020d4c2 -->
    24.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    24.2 +++ b/bugs/templates/slitaz/html/help_controls.js	Thu Apr 14 01:13:16 2011 +0200
    24.3 @@ -0,0 +1,324 @@
    24.4 +// initial values for either Nosy, Superseder, Keyword and Waiting On,
    24.5 +// depending on which has called
    24.6 +original_field = form[field].value;
    24.7 +
    24.8 +// Some browsers (ok, IE) don't define the "undefined" variable.
    24.9 +undefined = document.geez_IE_is_really_friggin_annoying;
   24.10 +
   24.11 +function trim(value) {
   24.12 +  var temp = value;
   24.13 +  var obj = /^(\s*)([\W\w]*)(\b\s*$)/;
   24.14 +  if (obj.test(temp)) { temp = temp.replace(obj, '$2'); }
   24.15 +  var obj = /  /g;
   24.16 +  while (temp.match(obj)) { temp = temp.replace(obj, " "); }
   24.17 +  return temp;
   24.18 +}
   24.19 +
   24.20 +function determineList() {
   24.21 +     // generate a comma-separated list of the checked items
   24.22 +     var list = new String('');
   24.23 +
   24.24 +     // either a checkbox object or an array of checkboxes
   24.25 +     var check = document.frm_help.check;
   24.26 +
   24.27 +     if ((check.length == undefined) && (check.checked != undefined)) {
   24.28 +         // only one checkbox on page
   24.29 +         if (check.checked) {
   24.30 +             list = check.value;
   24.31 +         }
   24.32 +     } else {
   24.33 +         // array of checkboxes
   24.34 +         for (box=0; box < check.length; box++) {
   24.35 +             if (check[box].checked) {
   24.36 +                 if (list.length == 0) {
   24.37 +                     separator = '';
   24.38 +                 }
   24.39 +                 else {
   24.40 +                     separator = ',';
   24.41 +                 }
   24.42 +                 // we used to use an Array and push / join, but IE5.0 sux
   24.43 +                 list = list + separator + check[box].value;
   24.44 +             }
   24.45 +         }
   24.46 +     }
   24.47 +     return list;
   24.48 +}
   24.49 +
   24.50 +/**
   24.51 + * update the field in the opening window;
   24.52 + * the text_field variable must be set in the calling page
   24.53 + */
   24.54 +function updateOpener() {
   24.55 +  // write back to opener window
   24.56 +  if (document.frm_help.check==undefined) { return; }
   24.57 +  form[field].value = text_field.value;
   24.58 +}
   24.59 +
   24.60 +function updateList() {
   24.61 +  // write back to opener window
   24.62 +  if (document.frm_help.check==undefined) { return; }
   24.63 +  form[field].value = determineList();
   24.64 +}
   24.65 +
   24.66 +function updatePreview() {
   24.67 +  // update the preview box
   24.68 +  if (document.frm_help.check==undefined) { return; }
   24.69 +  writePreview(determineList());
   24.70 +}
   24.71 +
   24.72 +function clearList() {
   24.73 +  // uncheck all checkboxes
   24.74 +  if (document.frm_help.check==undefined) { return; }
   24.75 +  for (box=0; box < document.frm_help.check.length; box++) {
   24.76 +      document.frm_help.check[box].checked = false;
   24.77 +  }
   24.78 +}
   24.79 +
   24.80 +function reviseList_framed(form, textfield) {
   24.81 +  // update the checkboxes based on the preview field
   24.82 +  // alert('reviseList_framed')
   24.83 +  // alert(form)
   24.84 +  if (form.check==undefined)
   24.85 +      return;
   24.86 +  // alert(textfield)
   24.87 +  var to_check;
   24.88 +  var list = textfield.value.split(",");
   24.89 +  if (form.check.length==undefined) {
   24.90 +      check = form.check;
   24.91 +      to_check = false;
   24.92 +      for (val in list) {
   24.93 +          if (check.value==trim(list[val])) {
   24.94 +              to_check = true;
   24.95 +              break;
   24.96 +          }
   24.97 +      }
   24.98 +      check.checked = to_check;
   24.99 +  } else {
  24.100 +    for (box=0; box < form.check.length; box++) {
  24.101 +      check = form.check[box];
  24.102 +      to_check = false;
  24.103 +      for (val in list) {
  24.104 +          if (check.value==trim(list[val])) {
  24.105 +              to_check = true;
  24.106 +              break;
  24.107 +          }
  24.108 +      }
  24.109 +      check.checked = to_check;
  24.110 +    }
  24.111 +  }
  24.112 +}
  24.113 +
  24.114 +function reviseList(vals) {
  24.115 +  // update the checkboxes based on the preview field
  24.116 +  if (document.frm_help.check==undefined) { return; }
  24.117 +  var to_check;
  24.118 +  var list = vals.split(",");
  24.119 +  if (document.frm_help.check.length==undefined) {
  24.120 +      check = document.frm_help.check;
  24.121 +      to_check = false;
  24.122 +      for (val in list) {
  24.123 +          if (check.value==trim(list[val])) {
  24.124 +              to_check = true;
  24.125 +              break;
  24.126 +          }
  24.127 +      }
  24.128 +      check.checked = to_check;
  24.129 +  } else {
  24.130 +    for (box=0; box < document.frm_help.check.length; box++) {
  24.131 +      check = document.frm_help.check[box];
  24.132 +      to_check = false;
  24.133 +      for (val in list) {
  24.134 +          if (check.value==trim(list[val])) {
  24.135 +              to_check = true;
  24.136 +              break;
  24.137 +          }
  24.138 +      }
  24.139 +      check.checked = to_check;
  24.140 +    }
  24.141 +  }
  24.142 +}
  24.143 +
  24.144 +function resetList() {
  24.145 +  // reset preview and check boxes to initial values
  24.146 +  if (document.frm_help.check==undefined) { return; }
  24.147 +  writePreview(original_field);
  24.148 +  reviseList(original_field);
  24.149 +}
  24.150 +
  24.151 +function writePreview(val) {
  24.152 +   // writes a value to the text_preview
  24.153 +   document.frm_help.text_preview.value = val;
  24.154 +}
  24.155 +
  24.156 +function focusField(name) {
  24.157 +    for(i=0; i < document.forms.length; ++i) {
  24.158 +      var obj = document.forms[i].elements[name];
  24.159 +      if (obj && obj.focus) {obj.focus();}
  24.160 +    }
  24.161 +}
  24.162 +
  24.163 +function selectField(name) {
  24.164 +    for(i=0; i < document.forms.length; ++i) {
  24.165 +      var obj = document.forms[i].elements[name];
  24.166 +      if (obj && obj.focus){obj.focus();}
  24.167 +      if (obj && obj.select){obj.select();}
  24.168 +    }
  24.169 +}
  24.170 +
  24.171 +function checkRequiredFields(fields)
  24.172 +{
  24.173 +    var bonk='';
  24.174 +    var res='';
  24.175 +    var argv = checkRequiredFields.arguments;
  24.176 +    var argc = argv.length;
  24.177 +    var input = '';
  24.178 +    var val='';
  24.179 +
  24.180 +    for (var i=0; i < argc; i++) {
  24.181 +        fi = argv[i];
  24.182 +        input = document.getElementById(fi);
  24.183 +        if (input) {
  24.184 +            val = input.value
  24.185 +            if (val == '' || val == '-1' || val == -1) {
  24.186 +                if (res == '') {
  24.187 +                    res = fi;
  24.188 +                    bonk = input;
  24.189 +                } else {
  24.190 +                    res += ', '+fi;
  24.191 +                }
  24.192 +            }
  24.193 +        } else {
  24.194 +            alert('Field with id='+fi+' not found!')
  24.195 +        }
  24.196 +    }
  24.197 +    if (res == '') {
  24.198 +        return submit_once();
  24.199 +    } else {
  24.200 +        alert('Missing value here ('+res+')!');
  24.201 +        if (window.event && window.event.returnvalue) {
  24.202 +            event.returnValue = 0;    // work-around for IE
  24.203 +        }
  24.204 +        bonk.focus();
  24.205 +        return false;
  24.206 +    }
  24.207 +}
  24.208 +
  24.209 +/**
  24.210 + * seeks the given value (2nd argument)
  24.211 + * in the value of the given input element (1st argument),
  24.212 + * which is considered a list of values, separated by commas
  24.213 + */
  24.214 +function has_value(input, val)
  24.215 +{
  24.216 +    var actval = input.value
  24.217 +    var arr = feld.value.split(',');
  24.218 +    var max = arr.length;
  24.219 +    for (i=0;i<max;i++) {
  24.220 +        if (trim(arr[i]) == val) {
  24.221 +            return true
  24.222 +        }
  24.223 +    }
  24.224 +    return false
  24.225 +}
  24.226 +
  24.227 +/**
  24.228 + * Switch Value:
  24.229 + * change the value of the given input field (might be of type text or hidden),
  24.230 + * adding or removing the value of the given checkbox field (might be a radio
  24.231 + * button as well)
  24.232 + *
  24.233 + * This function doesn't care whether or not the checkboxes of all values of
  24.234 + * interest are present; but of course it doesn't have total control of the
  24.235 + * text field.
  24.236 + */
  24.237 +function switch_val(text, check)
  24.238 +{
  24.239 +    var switched_val = check.value
  24.240 +    var arr = text.value.split(',')
  24.241 +    var max = arr.length
  24.242 +    if (check.checked) {
  24.243 +        for (i=0; i<max; i++) {
  24.244 +            if (trim(arr[i]) == switched_val) {
  24.245 +                return
  24.246 +            }
  24.247 +        }
  24.248 +	if (text.value)
  24.249 +            text.value = text.value+','+switched_val
  24.250 +	else
  24.251 +            text.value = switched_val
  24.252 +    } else {
  24.253 +        var neu = ''
  24.254 +	var changed = false
  24.255 +        for (i=0; i<max; i++) {
  24.256 +            if (trim(arr[i]) == switched_val) {
  24.257 +                changed=true
  24.258 +            } else {
  24.259 +                neu = neu+','+trim(arr[i])
  24.260 +            }
  24.261 +        }
  24.262 +        if (changed) {
  24.263 +            text.value = neu.substr(1)
  24.264 +        }
  24.265 +    }
  24.266 +}
  24.267 +
  24.268 +/**
  24.269 + * append the given value (2nd argument) to an input field
  24.270 + * (1st argument) which contains comma-separated values;
  24.271 + * see --> remove_val()
  24.272 + *
  24.273 + * This will work nicely even for batched lists
  24.274 + */
  24.275 +function append_val(name, val)
  24.276 +{
  24.277 +    var feld = document.itemSynopsis[name];
  24.278 +    var actval = feld.value;
  24.279 +    if (actval == '') {
  24.280 +        feld.value = val
  24.281 +    } else {
  24.282 +        var arr = feld.value.split(',');
  24.283 +        var max = arr.length;
  24.284 +        for (i=0;i<max;i++) {
  24.285 +            if (trim(arr[i]) == val) {
  24.286 +                return
  24.287 +            }
  24.288 +        }
  24.289 +        feld.value = actval+','+val
  24.290 +    }
  24.291 +}
  24.292 +
  24.293 +/**
  24.294 + * remove the given value (2nd argument) from the comma-separated values
  24.295 + * of the given input element (1st argument); see --> append_val()
  24.296 + */
  24.297 +function remove_val(name, val)
  24.298 +{
  24.299 +    var feld = document.itemSynopsis[name];
  24.300 +    var actval = feld.value;
  24.301 +    var changed=false;
  24.302 +    if (actval == '') {
  24.303 +	return
  24.304 +    } else {
  24.305 +        var arr = feld.value.split(',');
  24.306 +        var max = arr.length;
  24.307 +        var neu = ''
  24.308 +        for (i=0;i<max;i++) {
  24.309 +            if (trim(arr[i]) == val) {
  24.310 +                changed=true
  24.311 +            } else {
  24.312 +                neu = neu+','+trim(arr[i])
  24.313 +            }
  24.314 +        }
  24.315 +        if (changed) {
  24.316 +            feld.value = neu.substr(1)
  24.317 +        }
  24.318 +    }
  24.319 +}
  24.320 +
  24.321 +/**
  24.322 + * give the focus to the element given by id
  24.323 + */
  24.324 +function focus2id(name)
  24.325 +{
  24.326 +    document.getElementById(name).focus();
  24.327 +}
    25.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    25.2 +++ b/bugs/templates/slitaz/html/home.classlist.html	Thu Apr 14 01:13:16 2011 +0200
    25.3 @@ -0,0 +1,26 @@
    25.4 +<tal:block metal:use-macro="templates/page/macros/icing">
    25.5 +<title metal:fill-slot="head_title" i18n:translate="">List of classes - <span
    25.6 + i18n:name="tracker" tal:replace="config/TRACKER_NAME" /></title>
    25.7 +<span metal:fill-slot="body_title" tal:omit-tag="python:1"
    25.8 + i18n:translate="">List of classes</span>
    25.9 +<td class="content" metal:fill-slot="content">
   25.10 +<table class="classlist">
   25.11 +
   25.12 +<tal:block tal:repeat="cl db/classes">
   25.13 + <tr>
   25.14 +  <th class="header" colspan="2" align="left">
   25.15 +   <a tal:attributes="href string:${cl/classname}"
   25.16 +      tal:content="python:cl.classname.capitalize()">classname</a>
   25.17 +  </th>
   25.18 + </tr>
   25.19 + <tr tal:repeat="prop cl/properties">
   25.20 +  <th tal:content="prop/_name">name</th>
   25.21 +  <td tal:content="prop/_prop">type</td>
   25.22 + </tr>
   25.23 +</tal:block>
   25.24 +
   25.25 +</table>
   25.26 +</td>
   25.27 +
   25.28 +</tal:block>
   25.29 +<!-- SHA: e82456270ae1048cefdead99afda95578fff7b74 -->
    26.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    26.2 +++ b/bugs/templates/slitaz/html/home.html	Thu Apr 14 01:13:16 2011 +0200
    26.3 @@ -0,0 +1,11 @@
    26.4 +<!--
    26.5 + This is the default body that is displayed when people visit the
    26.6 + tracker. The tag below lists the currently open issues. You may
    26.7 + replace it with a greeting message, or a different list of issues or
    26.8 + whatever. It's a good idea to have the issues on the front page though
    26.9 +-->
   26.10 +<span tal:replace="structure python:db.issue.renderWith('index',
   26.11 +    sort=[('-', 'activity')], group=[('+', 'priority')], filter=['status'],
   26.12 +    columns=['id','activity','title','creator','assignedto', 'status'],
   26.13 +    filterspec={'status':['-1','1','2','3','4','5','6','7']})" />
   26.14 +<!-- SHA: c87a4e18d59a527331f1d367c0c6cc67ee123e63 -->
    27.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    27.2 +++ b/bugs/templates/slitaz/html/issue.index.html	Thu Apr 14 01:13:16 2011 +0200
    27.3 @@ -0,0 +1,167 @@
    27.4 +<!-- $Id: issue.index.html,v 1.29 2007-09-18 17:44:26 jpend Exp $ -->
    27.5 +<tal:block metal:use-macro="templates/page/macros/icing">
    27.6 +<title metal:fill-slot="head_title" >
    27.7 +  <span tal:omit-tag="true" i18n:translate="" >List of issues</span>
    27.8 +  <span tal:condition="request/dispname"
    27.9 +   tal:replace="python:' - %s '%request.dispname"
   27.10 +  /> - <span tal:replace="config/TRACKER_NAME" />
   27.11 +</title>
   27.12 +<span metal:fill-slot="body_title" tal:omit-tag="true">
   27.13 +  <span tal:omit-tag="true" i18n:translate="" >List of issues</span>
   27.14 +  <span tal:condition="request/dispname"
   27.15 +   tal:replace="python:' - %s' % request.dispname" />
   27.16 +</span>
   27.17 +<td class="content" metal:fill-slot="content">
   27.18 +
   27.19 +<p tal:condition="python:not (context.is_view_ok()
   27.20 + or request.user.hasRole('Anonymous'))" i18n:translate="">
   27.21 + You are not allowed to view this page.</p>
   27.22 +
   27.23 +<p tal:condition="python:not context.is_view_ok()
   27.24 + and request.user.hasRole('Anonymous')" i18n:translate="">
   27.25 + Please login with your username and password.</p>
   27.26 +
   27.27 +<tal:block tal:define="batch request/batch" tal:condition="context/is_view_ok">
   27.28 + <table class="list">
   27.29 +  <tr>
   27.30 +   <th tal:condition="request/show/priority" i18n:translate="">Priority</th>
   27.31 +   <th tal:condition="request/show/id" i18n:translate="">ID</th>
   27.32 +   <th tal:condition="request/show/creation" i18n:translate="">Creation</th>
   27.33 +   <th tal:condition="request/show/activity" i18n:translate="">Activity</th>
   27.34 +   <th tal:condition="request/show/actor" i18n:translate="">Actor</th>
   27.35 +   <th tal:condition="request/show/keyword" i18n:translate="">Keyword</th>
   27.36 +   <th tal:condition="request/show/title" i18n:translate="">Title</th>
   27.37 +   <th tal:condition="request/show/status" i18n:translate="">Status</th>
   27.38 +   <th tal:condition="request/show/creator" i18n:translate="">Creator</th>
   27.39 +   <!-- <th tal:condition="request/show/assignedto" i18n:translate="">Assigned&nbsp;To</th> -->
   27.40 +  </tr>
   27.41 + <tal:block tal:repeat="i batch" condition=true>
   27.42 +  <tr tal:define="group python:[r[1] for r in request.group]"
   27.43 +      tal:condition="python:group and batch.propchanged(*group)">
   27.44 +   <th tal:attributes="colspan python:len(request.columns)" class="group">
   27.45 +    <tal:block tal:repeat="g group">
   27.46 +     <tal:block i18n:translate="" tal:content="python:str(i[g]) or '(no %s set)'%g"/>
   27.47 +    </tal:block>
   27.48 +   </th>
   27.49 +  </tr>
   27.50 +
   27.51 +  <tr>
   27.52 +   <td tal:condition="request/show/priority"
   27.53 +       tal:content="python:i.priority.plain() or default">&nbsp;</td>
   27.54 +   <td tal:condition="request/show/id" tal:content="i/id">&nbsp;</td>
   27.55 +   <td class="date" tal:condition="request/show/creation"
   27.56 +       tal:content="i/creation/reldate">&nbsp;</td>
   27.57 +   <td class="date" tal:condition="request/show/activity"
   27.58 +       tal:content="i/activity/reldate">&nbsp;</td>
   27.59 +   <td class="date" tal:condition="request/show/actor"
   27.60 +       tal:content="python:i.actor.plain() or default">&nbsp;</td>
   27.61 +   <td tal:condition="request/show/keyword"
   27.62 +       tal:content="python:i.keyword.plain() or default">&nbsp;</td>
   27.63 +   <td tal:condition="request/show/title">
   27.64 +    <a tal:attributes="href string:issue${i/id}"
   27.65 +		tal:content="python:str(i.title.plain(hyperlink=0)) or '[no title]'">title</a>
   27.66 +   </td>
   27.67 +   <td tal:condition="request/show/status"
   27.68 +       i18n:translate=""
   27.69 +       tal:content="python:i.status.plain() or default">&nbsp;</td>
   27.70 +   <td tal:condition="request/show/creator"
   27.71 +       tal:content="python:i.creator.plain() or default">&nbsp;</td>
   27.72 +   <!-- <td tal:condition="request/show/assignedto"
   27.73 +       tal:content="python:i.assignedto.plain() or default">&nbsp;</td> -->
   27.74 +  </tr>
   27.75 +
   27.76 + </tal:block>
   27.77 +
   27.78 + <metal:index define-macro="batch-footer">
   27.79 + <tr tal:condition="batch">
   27.80 +  <th tal:attributes="colspan python:len(request.columns)">
   27.81 +   <table width="100%">
   27.82 +    <tr class="navigation">
   27.83 +     <th>
   27.84 +      <a tal:define="prev batch/previous" tal:condition="prev"
   27.85 +         tal:attributes="href python:request.indexargs_url(request.classname,
   27.86 +         {'@startwith':prev.first, '@pagesize':prev.size})"
   27.87 +         i18n:translate="">&lt;&lt; previous</a>
   27.88 +      &nbsp;
   27.89 +     </th>
   27.90 +     <th i18n:translate=""><span tal:replace="batch/start" i18n:name="start"
   27.91 +     />..<span tal:replace="python: batch.start + batch.length -1" i18n:name="end"
   27.92 +     /> out of <span tal:replace="batch/sequence_length" i18n:name="total"
   27.93 +     /></th>
   27.94 +     <th>
   27.95 +      <a tal:define="next batch/next" tal:condition="next"
   27.96 +         tal:attributes="href python:request.indexargs_url(request.classname,
   27.97 +         {'@startwith':next.first, '@pagesize':next.size})"
   27.98 +         i18n:translate="">next &gt;&gt;</a>
   27.99 +      &nbsp;
  27.100 +     </th>
  27.101 +    </tr>
  27.102 +   </table>
  27.103 +  </th>
  27.104 + </tr>
  27.105 + </metal:index>
  27.106 +</table>
  27.107 +
  27.108 +<a tal:attributes="href python:request.indexargs_url('issue',
  27.109 +            {'@action':'export_csv'})" i18n:translate="">Download as CSV</a>
  27.110 +
  27.111 +<form method="get" class="index-controls"
  27.112 +    tal:attributes="action request/classname">
  27.113 +
  27.114 + <table class="form" tal:define="n_sort python:2">
  27.115 +  <tal:block tal:repeat="n python:range(n_sort)" tal:condition="batch">
  27.116 +  <tr tal:define="key python:len(request.sort)>n and request.sort[n]">
  27.117 +   <th>
  27.118 +    <tal:block tal:condition="not:n" i18n:translate="">Sort on:</tal:block>
  27.119 +   </th>
  27.120 +   <td>
  27.121 +    <select tal:attributes="name python:'@sort%d'%n">
  27.122 +     <option value="" i18n:translate="">- nothing -</option>
  27.123 +     <option tal:repeat="col context/properties"
  27.124 +             tal:attributes="value col/_name;
  27.125 +                             selected python:key and col._name == key[1]"
  27.126 +             tal:content="col/_name"
  27.127 +             i18n:translate="">column</option>
  27.128 +    </select>
  27.129 +   </td>
  27.130 +   <th i18n:translate="">Descending:</th>
  27.131 +   <td><input type="checkbox" tal:attributes="name python:'@sortdir%d'%n;
  27.132 +              checked python:key and key[0] == '-'" />
  27.133 +   </td>
  27.134 +  </tr>
  27.135 +  </tal:block>
  27.136 +  <tal:block tal:repeat="n python:range(n_sort)" tal:condition="batch">
  27.137 +  <tr tal:define="key python:len(request.group)>n and request.group[n]">
  27.138 +   <th>
  27.139 +    <tal:block tal:condition="not:n" i18n:translate="">Group on:</tal:block>
  27.140 +   </th>
  27.141 +   <td>
  27.142 +    <select tal:attributes="name python:'@group%d'%n">
  27.143 +     <option value="" i18n:translate="">- nothing -</option>
  27.144 +     <option tal:repeat="col context/properties"
  27.145 +             tal:attributes="value col/_name;
  27.146 +                             selected python:key and col._name == key[1]"
  27.147 +             tal:content="col/_name"
  27.148 +             i18n:translate="">column</option>
  27.149 +    </select>
  27.150 +   </td>
  27.151 +   <th i18n:translate="">Descending:</th>
  27.152 +   <td><input type="checkbox" tal:attributes="name python:'@groupdir%d'%n;
  27.153 +              checked python:key and key[0] == '-'" />
  27.154 +   </td>
  27.155 +  </tr>
  27.156 +  </tal:block>
  27.157 +  <tr><td colspan="4">
  27.158 +              <input type="submit" value="Redisplay" i18n:attributes="value" />
  27.159 +              <tal:block tal:replace="structure
  27.160 +                python:request.indexargs_form(sort=0, group=0)" />
  27.161 +  </td></tr>
  27.162 + </table>
  27.163 +</form>
  27.164 +
  27.165 +</tal:block>
  27.166 +
  27.167 +</td>
  27.168 +</tal:block><tal:comment condition=false> vim: sw=1 ts=8 et si
  27.169 +</tal:comment>
  27.170 +<!-- SHA: 4600774f11f5947ff1f565e2fb8023125cf51fc2 -->
    28.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    28.2 +++ b/bugs/templates/slitaz/html/issue.item.html	Thu Apr 14 01:13:16 2011 +0200
    28.3 @@ -0,0 +1,198 @@
    28.4 +<!-- dollarId: issue.item,v 1.4 2001/08/03 01:19:43 richard Exp dollar-->
    28.5 +<tal:block metal:use-macro="templates/page/macros/icing">
    28.6 +<title metal:fill-slot="head_title">
    28.7 +<tal:block condition="context/id" i18n:translate=""
    28.8 + >Issue <tal:x tal:content="context/id" i18n:name="id"
    28.9 + />: <tal:x content="context/title" i18n:name="title"
   28.10 + /> - <tal:x content="config/TRACKER_NAME" i18n:name="tracker"
   28.11 +/></tal:block>
   28.12 +<tal:block condition="not:context/id" i18n:translate=""
   28.13 + >New Issue - <span tal:replace="config/TRACKER_NAME" i18n:name="tracker"
   28.14 +/></tal:block>
   28.15 +</title>
   28.16 +<tal:block metal:fill-slot="body_title">
   28.17 + <span tal:condition="python: not (context.id or context.is_edit_ok())"
   28.18 +  tal:omit-tag="python:1" i18n:translate="">New Issue</span>
   28.19 + <span tal:condition="python: not context.id and context.is_edit_ok()"
   28.20 +  tal:omit-tag="python:1" i18n:translate="">New Issue Editing</span>
   28.21 + <span tal:condition="python: context.id and not context.is_edit_ok()"
   28.22 +  tal:omit-tag="python:1" i18n:translate="">Issue<tal:x
   28.23 +  replace="context/id" i18n:name="id" /></span>
   28.24 + <span tal:condition="python: context.id and context.is_edit_ok()"
   28.25 +  tal:omit-tag="python:1" i18n:translate="">Issue<tal:x
   28.26 +  replace="context/id" i18n:name="id" /> Editing</span>
   28.27 +</tal:block>
   28.28 +
   28.29 +<td class="content" metal:fill-slot="content">
   28.30 +
   28.31 +<p tal:condition="python:not (context.is_view_ok()
   28.32 + or request.user.hasRole('Anonymous'))" i18n:translate="">
   28.33 + You are not allowed to view this page.</p>
   28.34 +
   28.35 +<p tal:condition="python:not context.is_view_ok()
   28.36 + and request.user.hasRole('Anonymous')" i18n:translate="">
   28.37 + Please login with your username and password.</p>
   28.38 +
   28.39 +<div tal:condition="context/is_view_ok">
   28.40 +
   28.41 +<form method="post" name="itemSynopsis"
   28.42 +      onSubmit="return submit_once()" enctype="multipart/form-data"
   28.43 +      tal:attributes="action context/designator">
   28.44 +
   28.45 +<table class="form">
   28.46 +<tr>
   28.47 + <th class="required" i18n:translate="">Title</th>
   28.48 + <td colspan=3 tal:content="structure python:context.title.field(size=60)">title</td>
   28.49 +</tr>
   28.50 +
   28.51 +<tr>
   28.52 + <th class="required" i18n:translate="">Priority</th>
   28.53 + <td tal:content="structure context/priority/menu">priority</td>
   28.54 + <th i18n:translate="">Status</th>
   28.55 + <td tal:content="structure context/status/menu">status</td>
   28.56 +</tr>
   28.57 +
   28.58 +<tr>
   28.59 + <th i18n:translate="">Superseder</th>
   28.60 + <td>
   28.61 +  <span tal:replace="structure python:context.superseder.field(showid=1, size=20)" />
   28.62 +  <span tal:condition="context/is_edit_ok" tal:replace="structure python:db.issue.classhelp('id,title', property='superseder')" />
   28.63 +  <span tal:condition="context/superseder">
   28.64 +   <br><span i18n:translate="">View:</span>
   28.65 +     <a tal:repeat="sup context/superseder"
   28.66 +        tal:content="python:sup['id'] + ', '*(not repeat['sup'].end)"
   28.67 +        tal:attributes="href string:issue${sup/id}"></a>
   28.68 +  </span>
   28.69 + </td>
   28.70 + <th i18n:translate="">Nosy List</th>
   28.71 + <td>
   28.72 +  <span tal:replace="structure context/nosy/field" />
   28.73 +  <span tal:condition="context/is_edit_ok" tal:replace="structure
   28.74 +python:db.user.classhelp('username,realname,address', property='nosy', width='600')" /><br>
   28.75 + </td>
   28.76 +</tr>
   28.77 +
   28.78 +<tr>
   28.79 + <th i18n:translate="">Assigned To</th>
   28.80 + <td tal:content="structure context/assignedto/menu">assignedto menu</td>
   28.81 + <th i18n:translate="">Keywords</th>
   28.82 + <td>
   28.83 +  <span tal:replace="structure context/keyword/field" />
   28.84 +  <span tal:condition="context/is_edit_ok" tal:replace="structure python:db.keyword.classhelp(property='keyword')" />
   28.85 + </td>
   28.86 +</tr>
   28.87 +
   28.88 +<tr tal:condition="context/is_edit_ok">
   28.89 + <th i18n:translate="">Change Note</th>
   28.90 + <td colspan=3>
   28.91 +  <textarea tal:content="request/form/@note/value | default"
   28.92 +            name="@note" wrap="hard" rows="5" cols="80"></textarea>
   28.93 + </td>
   28.94 +</tr>
   28.95 +
   28.96 +<tr tal:condition="context/is_edit_ok">
   28.97 + <th i18n:translate="">File</th>
   28.98 + <td colspan=3><input type="file" name="@file" size="40"></td>
   28.99 +</tr>
  28.100 +
  28.101 +<tr tal:condition="context/is_edit_ok">
  28.102 + <td>
  28.103 +  &nbsp;
  28.104 +  <input type="hidden" name="@template" value="item">
  28.105 +  <input type="hidden" name="@required" value="title,priority">
  28.106 + </td>
  28.107 + <td colspan=3>
  28.108 +  <span tal:replace="structure context/submit">submit button</span>
  28.109 +  <a tal:condition="context/id" tal:attributes="href context/copy_url"
  28.110 +   i18n:translate="">Make a copy</a>
  28.111 + </td>
  28.112 +</tr>
  28.113 +
  28.114 +</table>
  28.115 +</form>
  28.116 +
  28.117 +<tal:block tal:condition="not:context/id" i18n:translate="">
  28.118 +<table class="form">
  28.119 +<tr>
  28.120 + <td>Note:&nbsp;</td>
  28.121 + <th class="required">highlighted</th>
  28.122 + <td>&nbsp;fields are required.</td>
  28.123 +</tr>
  28.124 +</table>
  28.125 +</tal:block>
  28.126 +
  28.127 +<p tal:condition="context/id" i18n:translate="">
  28.128 + Created on <b tal:content="context/creation" i18n:name="creation" />
  28.129 + by <b tal:content="context/creator" i18n:name="creator" />,
  28.130 + last changed <b content="context/activity" i18n:name="activity" />
  28.131 + by <b tal:content="context/actor" i18n:name="actor" />.
  28.132 +</p>
  28.133 +
  28.134 +<table class="files" tal:condition="context/files">
  28.135 + <tr><th colspan="5" class="header" i18n:translate="">Files</th></tr>
  28.136 + <tr>
  28.137 +  <th i18n:translate="">File name</th>
  28.138 +  <th i18n:translate="">Uploaded</th>
  28.139 +  <th i18n:translate="">Type</th>
  28.140 +  <th i18n:translate="">Edit</th>
  28.141 +  <th i18n:translate="">Remove</th>
  28.142 + </tr>
  28.143 + <tr tal:repeat="file context/files">
  28.144 +  <td>
  28.145 +   <a tal:attributes="href file/download_url"
  28.146 +      tal:content="file/name">dld link</a>
  28.147 +  </td>
  28.148 +  <td>
  28.149 +   <span tal:content="file/creator">creator's name</span>,
  28.150 +   <span tal:content="file/creation">creation date</span>
  28.151 +  </td>
  28.152 +  <td tal:content="file/type" />
  28.153 +  <td><a tal:condition="file/is_edit_ok"
  28.154 +          tal:attributes="href string:file${file/id}">edit</a>
  28.155 +  </td>
  28.156 +  <td>
  28.157 +   <form style="padding:0" method="post" tal:condition="context/is_edit_ok"
  28.158 +         tal:attributes="action string:issue${context/id}">
  28.159 +    <input type="hidden" name="@remove@files" tal:attributes="value file/id">
  28.160 +    <input type="hidden" name="@action" value="edit">
  28.161 +    <input type="submit" value="remove" i18n:attributes="value">
  28.162 +   </form>
  28.163 +  </td>
  28.164 + </tr>
  28.165 +</table>
  28.166 +
  28.167 +<table class="messages" tal:condition="context/messages">
  28.168 + <tr><th colspan="4" class="header" i18n:translate="">Messages</th></tr>
  28.169 + <tal:block tal:repeat="msg context/messages/reverse">
  28.170 +  <tr>
  28.171 +   <th><a tal:attributes="href string:msg${msg/id}"
  28.172 +    i18n:translate="">msg<tal:x replace="msg/id" i18n:name="id" /> (view)</a></th>
  28.173 +   <th i18n:translate="">Author: <tal:x replace="msg/author"
  28.174 +       i18n:name="author" /></th>
  28.175 +   <th i18n:translate="">Date: <tal:x replace="msg/date"
  28.176 +       i18n:name="date" /></th>
  28.177 +   <th>
  28.178 +    <form style="padding:0" method="post" tal:condition="context/is_edit_ok"
  28.179 +          tal:attributes="action string:issue${context/id}">
  28.180 +     <input type="hidden" name="@remove@messages" tal:attributes="value msg/id">
  28.181 +     <input type="hidden" name="@action" value="edit">
  28.182 +     <input type="submit" value="remove" i18n:attributes="value">
  28.183 +    </form>
  28.184 +   </th>
  28.185 +  </tr>
  28.186 +  <tr>
  28.187 +   <td colspan="4" class="content">
  28.188 +    <pre tal:content="structure msg/content/hyperlinked">content</pre>
  28.189 +   </td>
  28.190 +  </tr>
  28.191 + </tal:block>
  28.192 +</table>
  28.193 +
  28.194 +<tal:block tal:condition="context/id" tal:replace="structure context/history" />
  28.195 +
  28.196 +</div>
  28.197 +
  28.198 +</td>
  28.199 +
  28.200 +</tal:block>
  28.201 +<!-- SHA: a242ab3ed5c6969916f3c42f80d487710f165fb8 -->
    29.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    29.2 +++ b/bugs/templates/slitaz/html/issue.search.html	Thu Apr 14 01:13:16 2011 +0200
    29.3 @@ -0,0 +1,235 @@
    29.4 +<tal:block metal:use-macro="templates/page/macros/icing">
    29.5 +<title metal:fill-slot="head_title" i18n:translate="">Issue searching - <span
    29.6 + i18n:name="tracker" tal:replace="config/TRACKER_NAME" /></title>
    29.7 +<span metal:fill-slot="body_title" tal:omit-tag="python:1"
    29.8 + i18n:translate="">Issue searching</span>
    29.9 +<td class="content" metal:fill-slot="content">
   29.10 +
   29.11 +<form method="get" name="itemSynopsis"
   29.12 +      tal:attributes="action request/classname">
   29.13 +      
   29.14 +<table class="form" tal:define="
   29.15 +   cols python:request.columns or 'id activity title status assignedto'.split();
   29.16 +   sort_on python:request.sort and request.sort[0] or nothing;
   29.17 +   sort_desc python:sort_on and sort_on[0] == '-';
   29.18 +   sort_on python:(sort_on and sort_on[1]) or 'activity';
   29.19 +   group_on python:request.group and request.group[0] or nothing;
   29.20 +   group_desc python:group_on and group_on[0] == '-';
   29.21 +   group_on python:(group_on and group_on[1]) or 'priority';
   29.22 +
   29.23 +   search_input templates/page/macros/search_input;
   29.24 +   search_date templates/page/macros/search_date;
   29.25 +   column_input templates/page/macros/column_input;
   29.26 +   sort_input templates/page/macros/sort_input;
   29.27 +   group_input templates/page/macros/group_input;
   29.28 +   search_select templates/page/macros/search_select;
   29.29 +   search_select_translated templates/page/macros/search_select_translated;
   29.30 +   search_multiselect templates/page/macros/search_multiselect;">
   29.31 +
   29.32 +<tr>
   29.33 + <th class="header">&nbsp;</th>
   29.34 + <th class="header" i18n:translate="">Filter on</th>
   29.35 + <th class="header" i18n:translate="">Display</th>
   29.36 + <th class="header" i18n:translate="">Sort on</th>
   29.37 + <th class="header" i18n:translate="">Group on</th>
   29.38 +</tr>
   29.39 +
   29.40 +<tr tal:define="name string:@search_text">
   29.41 +  <th i18n:translate="">All text*:</th>
   29.42 +  <td metal:use-macro="search_input"></td>
   29.43 +  <td>&nbsp;</td>
   29.44 +  <td>&nbsp;</td>
   29.45 +  <td>&nbsp;</td>
   29.46 +</tr>
   29.47 +
   29.48 +<tr tal:define="name string:title">
   29.49 +  <th i18n:translate="">Title:</th>
   29.50 +  <td metal:use-macro="search_input"></td>
   29.51 +  <td metal:use-macro="column_input"></td>
   29.52 +  <td metal:use-macro="sort_input"></td>
   29.53 +  <td>&nbsp;</td>
   29.54 +</tr>
   29.55 +
   29.56 +<tr tal:define="name string:keyword;
   29.57 +                db_klass string:keyword;
   29.58 +                db_content string:name;">
   29.59 +  <th i18n:translate="">Keyword:</th>
   29.60 +  <td metal:use-macro="search_select">
   29.61 +    <option metal:fill-slot="extra_options" value="-1" i18n:translate=""
   29.62 +            tal:attributes="selected python:value == '-1'">not selected</option>
   29.63 +  </td>
   29.64 +  <td metal:use-macro="column_input"></td>
   29.65 +  <td metal:use-macro="sort_input"></td>
   29.66 +  <td metal:use-macro="group_input"></td>
   29.67 +</tr>
   29.68 +
   29.69 +<tr tal:define="name string:id">
   29.70 +  <th i18n:translate="">ID:</th>
   29.71 +  <td metal:use-macro="search_input"></td>
   29.72 +  <td metal:use-macro="column_input"></td>
   29.73 +  <td metal:use-macro="sort_input"></td>
   29.74 +  <td>&nbsp;</td>
   29.75 +</tr>
   29.76 +
   29.77 +<tr tal:define="name string:creation">
   29.78 +  <th i18n:translate="">Creation Date:</th>
   29.79 +  <td metal:use-macro="search_date"></td>
   29.80 +  <td metal:use-macro="column_input"></td>
   29.81 +  <td metal:use-macro="sort_input"></td>
   29.82 +  <td metal:use-macro="group_input"></td>
   29.83 +</tr>
   29.84 +
   29.85 +<tr tal:define="name string:creator;
   29.86 +                db_klass string:user;
   29.87 +                db_content string:username;"
   29.88 +    tal:condition="db/user/is_view_ok">
   29.89 +  <th i18n:translate="">Creator:</th>
   29.90 +  <td metal:use-macro="search_select">
   29.91 +    <option metal:fill-slot="extra_options" i18n:translate=""
   29.92 +            tal:attributes="value request/user/id">created by me</option>
   29.93 +  </td>
   29.94 +  <td metal:use-macro="column_input"></td>
   29.95 +  <td metal:use-macro="sort_input"></td>
   29.96 +  <td metal:use-macro="group_input"></td>
   29.97 +</tr>
   29.98 +
   29.99 +<tr tal:define="name string:activity">
  29.100 +  <th i18n:translate="">Activity:</th>
  29.101 +  <td metal:use-macro="search_date"></td>
  29.102 +  <td metal:use-macro="column_input"></td>
  29.103 +  <td metal:use-macro="sort_input"></td>
  29.104 +  <td>&nbsp;</td>
  29.105 +</tr>
  29.106 +
  29.107 +<tr tal:define="name string:actor;
  29.108 +                db_klass string:user;
  29.109 +                db_content string:username;"
  29.110 +    tal:condition="db/user/is_view_ok">
  29.111 +  <th i18n:translate="">Actor:</th>
  29.112 +  <td metal:use-macro="search_select">
  29.113 +    <option metal:fill-slot="extra_options" i18n:translate=""
  29.114 +            tal:attributes="value request/user/id">done by me</option>
  29.115 +  </td>
  29.116 +  <td metal:use-macro="column_input"></td>
  29.117 +  <td metal:use-macro="sort_input"></td>
  29.118 +  <td>&nbsp;</td>
  29.119 +</tr>
  29.120 +
  29.121 +<tr tal:define="name string:priority;
  29.122 +                db_klass string:priority;
  29.123 +                db_content string:name;">
  29.124 +  <th i18n:translate="">Priority:</th>
  29.125 +  <td metal:use-macro="search_select_translated">
  29.126 +    <option metal:fill-slot="extra_options" value="-1" i18n:translate=""
  29.127 +            tal:attributes="selected python:value == '-1'">not selected</option>
  29.128 +  </td>
  29.129 +  <td metal:use-macro="column_input"></td>
  29.130 +  <td metal:use-macro="sort_input"></td>
  29.131 +  <td metal:use-macro="group_input"></td>
  29.132 +</tr>
  29.133 +
  29.134 +<tr tal:define="name string:status;
  29.135 +                db_klass string:status;
  29.136 +                db_content string:name;">
  29.137 +  <th i18n:translate="">Status:</th>
  29.138 +  <td metal:use-macro="search_select_translated">
  29.139 +    <tal:block metal:fill-slot="extra_options">
  29.140 +      <option value="-1,1,2,3,4,5,6,7" i18n:translate=""
  29.141 +              tal:attributes="selected python:value == '-1,1,2,3,4,5,6,7'">not resolved</option>
  29.142 +      <option value="-1" i18n:translate=""
  29.143 +              tal:attributes="selected python:value == '-1'">not selected</option>
  29.144 +    </tal:block>
  29.145 +  </td>
  29.146 +  <td metal:use-macro="column_input"></td>
  29.147 +  <td metal:use-macro="sort_input"></td>
  29.148 +  <td metal:use-macro="group_input"></td>
  29.149 +</tr>
  29.150 +
  29.151 +<tr tal:define="name string:assignedto;
  29.152 +                db_klass string:user;
  29.153 +                db_content string:username;"
  29.154 +    tal:condition="db/user/is_view_ok">
  29.155 +  <th i18n:translate="">Assigned to:</th>
  29.156 +  <td metal:use-macro="search_select">
  29.157 +    <tal:block metal:fill-slot="extra_options">
  29.158 +      <option tal:attributes="value request/user/id"
  29.159 +       i18n:translate="">assigned to me</option>
  29.160 +      <option value="-1" tal:attributes="selected python:value == '-1'"
  29.161 +       i18n:translate="">unassigned</option>
  29.162 +    </tal:block>
  29.163 +  </td>
  29.164 +  <td metal:use-macro="column_input"></td>
  29.165 +  <td metal:use-macro="sort_input"></td>
  29.166 +  <td metal:use-macro="group_input"></td>
  29.167 +</tr>
  29.168 +
  29.169 +<tr>
  29.170 + <th i18n:translate="">No Sort or group:</th>
  29.171 + <td>&nbsp;</td>
  29.172 + <td>&nbsp;</td>
  29.173 + <td><input type="radio" name="@sort" value=""></td>
  29.174 + <td><input type="radio" name="@group" value=""></td>
  29.175 +</tr>
  29.176 +
  29.177 +<tr>
  29.178 +<th i18n:translate="">Pagesize:</th>
  29.179 +<td><input name="@pagesize" size="3" value="50"
  29.180 +           tal:attributes="value request/form/@pagesize/value | default"></td>
  29.181 +</tr>
  29.182 +
  29.183 +<tr>
  29.184 +<th i18n:translate="">Start With:</th>
  29.185 +<td><input name="@startwith" size="3" value="0"
  29.186 +           tal:attributes="value request/form/@startwith/value | default"></td>
  29.187 +</tr>
  29.188 +
  29.189 +<tr>
  29.190 +<th i18n:translate="">Sort Descending:</th>
  29.191 +<td><input type="checkbox" name="@sortdir"
  29.192 +           tal:attributes="checked sort_desc">
  29.193 +</td>
  29.194 +</tr>
  29.195 +
  29.196 +<tr>
  29.197 +<th i18n:translate="">Group Descending:</th>
  29.198 +<td><input type="checkbox" name="@groupdir"
  29.199 +           tal:attributes="checked group_desc">
  29.200 +</td>
  29.201 +</tr>
  29.202 +
  29.203 +<tr tal:condition="python:request.user.hasPermission('Edit', 'query')">
  29.204 + <th i18n:translate="">Query name**:</th>
  29.205 + <td tal:define="value request/form/@queryname/value | nothing">
  29.206 +  <input name="@queryname" tal:attributes="value value">
  29.207 +  <input type="hidden" name="@old-queryname" tal:attributes="value value">
  29.208 + </td>
  29.209 +</tr>
  29.210 +
  29.211 +<tr>
  29.212 +  <td>
  29.213 +   &nbsp;
  29.214 +   <input type="hidden" name="@action" value="search">
  29.215 +  </td>
  29.216 +  <td><input type="submit" value="Search" i18n:attributes="value"></td>
  29.217 +</tr>
  29.218 +
  29.219 +<tr><td>&nbsp;</td>
  29.220 + <td colspan="4" class="help">
  29.221 +  <span i18n:translate="" tal:omit-tag="true">
  29.222 +   *: The "all text" field will look in message bodies and issue titles
  29.223 +  </span><br>
  29.224 +  <span tal:condition="python:request.user.hasPermission('Edit', 'query')"
  29.225 +   i18n:translate="" tal:omit-tag="true"
  29.226 +  >
  29.227 +   **: If you supply a name, the query will be saved off and available as a
  29.228 +       link in the sidebar
  29.229 +  </span>
  29.230 + </td>
  29.231 +</tr>
  29.232 +</table>
  29.233 +
  29.234 +</form>
  29.235 +</td>
  29.236 +
  29.237 +</tal:block>
  29.238 +<!-- SHA: fa3cf334a00d3f923b4b6c2489205c6c9b0dbd99 -->
    30.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    30.2 +++ b/bugs/templates/slitaz/html/keyword.item.html	Thu Apr 14 01:13:16 2011 +0200
    30.3 @@ -0,0 +1,56 @@
    30.4 +<!-- dollarId: keyword.item,v 1.3 2002/05/22 00:32:34 richard Exp dollar-->
    30.5 +<tal:block metal:use-macro="templates/page/macros/icing">
    30.6 +<title metal:fill-slot="head_title" i18n:translate="">Keyword editing - <span
    30.7 + i18n:name="tracker" tal:replace="config/TRACKER_NAME" /></title>
    30.8 +<span metal:fill-slot="body_title" tal:omit-tag="python:1"
    30.9 + i18n:translate="">Keyword editing</span>
   30.10 +<td class="content" metal:fill-slot="content">
   30.11 +
   30.12 +<table class="otherinfo" tal:define="keywords db/keyword/list"
   30.13 +       tal:condition="keywords">
   30.14 + <tr><th colspan="4" class="header" i18n:translate="">Existing Keywords</th></tr>
   30.15 + <tr tal:repeat="start python:range(0, len(keywords), 4)">
   30.16 +  <td width="25%" tal:define="batch python:utils.Batch(keywords, 4, start)"
   30.17 +      tal:repeat="keyword batch">
   30.18 +    <a tal:attributes="href string:keyword${keyword/id}"
   30.19 +       tal:content="keyword/name">keyword here</a>
   30.20 +  </td>
   30.21 + </tr>
   30.22 + <tr>
   30.23 +  <td colspan="4" style="border-top: 1px solid gray" i18n:translate="">
   30.24 +   To edit an existing keyword (for spelling or typing errors),
   30.25 +   click on its entry above.
   30.26 +  </td>
   30.27 + </tr>
   30.28 +</table>
   30.29 +
   30.30 +<p class="help" tal:condition="not:context/id" i18n:translate="">
   30.31 + To create a new keyword, enter it below and click "Submit New Entry".
   30.32 +</p>
   30.33 +
   30.34 +<form method="post" onSubmit="return submit_once()"
   30.35 +      enctype="multipart/form-data"
   30.36 +      tal:attributes="action context/designator">
   30.37 +
   30.38 + <table class="form">
   30.39 +  <tr>
   30.40 +   <th i18n:translate="">Keyword</th>
   30.41 +   <td tal:content="structure context/name/field">name</td>
   30.42 +  </tr>
   30.43 +
   30.44 +  <tr>
   30.45 +   <td>
   30.46 +    &nbsp;
   30.47 +    <input type="hidden" name="@required" value="name">
   30.48 +    <input type="hidden" name="@template" value="item">
   30.49 +   </td>
   30.50 +   <td colspan=3 tal:content="structure context/submit">
   30.51 +    submit button will go here
   30.52 +   </td>
   30.53 +  </tr>
   30.54 + </table>
   30.55 +</form>
   30.56 +</td>
   30.57 +
   30.58 +</tal:block>
   30.59 +<!-- SHA: 69377db97f924d320fdd672dd8363256ef6f2fbb -->
    31.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    31.2 +++ b/bugs/templates/slitaz/html/msg.index.html	Thu Apr 14 01:13:16 2011 +0200
    31.3 @@ -0,0 +1,26 @@
    31.4 +<tal:block metal:use-macro="templates/page/macros/icing">
    31.5 +<title metal:fill-slot="head_title" i18n:translate=""
    31.6 + >List of messages - <span tal:replace="config/TRACKER_NAME"
    31.7 + i18n:name="tracker"/></title>
    31.8 +<span metal:fill-slot="body_title" tal:omit-tag="python:1"
    31.9 + i18n:translate="">Message listing</span>
   31.10 +<td class="content" metal:fill-slot="content">
   31.11 +<table tal:define="batch request/batch" class="messages">
   31.12 + <tr><th colspan=2 class="header" i18n:translate="">Messages</th></tr>
   31.13 + <tal:block tal:repeat="msg batch">
   31.14 +  <tr>
   31.15 +   <th tal:content="string:Author: ${msg/author}">author</th>
   31.16 +   <th tal:content="string:Date: ${msg/date}">date</th>
   31.17 +  </tr>
   31.18 +  <tr>
   31.19 +   <td colspan="2"><pre tal:content="msg/content">content</pre></td>
   31.20 +  </tr>
   31.21 + </tal:block>
   31.22 +
   31.23 + <metal:block use-macro="templates/issue.index/macros/batch-footer" />
   31.24 +
   31.25 +</table>
   31.26 +</td>
   31.27 +
   31.28 +</tal:block>
   31.29 +<!-- SHA: 474d801a8005811ea3f2600ff719af95c6b798ce -->
    32.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    32.2 +++ b/bugs/templates/slitaz/html/msg.item.html	Thu Apr 14 01:13:16 2011 +0200
    32.3 @@ -0,0 +1,84 @@
    32.4 +<!-- dollarId: msg.item,v 1.3 2002/05/22 00:32:34 richard Exp dollar-->
    32.5 +<tal:block metal:use-macro="templates/page/macros/icing">
    32.6 +<title metal:fill-slot="head_title">
    32.7 +<tal:block condition="context/id" i18n:translate=""
    32.8 + >Message <span tal:replace="context/id" i18n:name="id"
    32.9 + /> - <span tal:replace="config/TRACKER_NAME" i18n:name="tracker"
   32.10 +/></tal:block>
   32.11 +<tal:block condition="not:context/id" i18n:translate=""
   32.12 + >New Message - <span tal:replace="config/TRACKER_NAME" i18n:name="tracker"
   32.13 +/></tal:block>
   32.14 +</title>
   32.15 +<tal:block metal:fill-slot="body_title">
   32.16 + <span tal:condition="python: not (context.id or context.is_edit_ok())"
   32.17 +  tal:omit-tag="python:1" i18n:translate="">New Message</span>
   32.18 + <span tal:condition="python: not context.id and context.is_edit_ok()"
   32.19 +  tal:omit-tag="python:1" i18n:translate="">New Message Editing</span>
   32.20 + <span tal:condition="python: context.id and not context.is_edit_ok()"
   32.21 +  tal:omit-tag="python:1" i18n:translate="">Message<tal:x
   32.22 +  replace="context/id" i18n:name="id" /></span>
   32.23 + <span tal:condition="python: context.id and context.is_edit_ok()"
   32.24 +  tal:omit-tag="python:1" i18n:translate="">Message<tal:x
   32.25 +  replace="context/id" i18n:name="id" /> Editing</span>
   32.26 +</tal:block>
   32.27 +<td class="content" metal:fill-slot="content">
   32.28 +
   32.29 +<p tal:condition="python:not (context.is_view_ok()
   32.30 + or request.user.hasRole('Anonymous'))" i18n:translate="">
   32.31 + You are not allowed to view this page.</p>
   32.32 +
   32.33 +<p tal:condition="python:not context.is_view_ok()
   32.34 + and request.user.hasRole('Anonymous')" i18n:translate="">
   32.35 + Please login with your username and password.</p>
   32.36 +
   32.37 +<div tal:condition="context/is_view_ok">
   32.38 +<table class="form">
   32.39 +
   32.40 +<tr>
   32.41 + <th i18n:translate="">Author</th>
   32.42 + <td tal:content="context/author"></td>
   32.43 +</tr>
   32.44 +
   32.45 +<tr>
   32.46 + <th i18n:translate="">Recipients</th>
   32.47 + <td tal:content="context/recipients"></td>
   32.48 +</tr>
   32.49 +
   32.50 +<tr>
   32.51 + <th i18n:translate="">Date</th>
   32.52 + <td tal:content="context/date"></td>
   32.53 +</tr>
   32.54 +</table>
   32.55 +
   32.56 +<table class="messages">
   32.57 + <tr><th colspan=2 class="header" i18n:translate="">Content</th></tr>
   32.58 + <tr>
   32.59 +  <td class="content" colspan=2><pre tal:content="structure context/content/hyperlinked"></pre></td>
   32.60 + </tr>
   32.61 +</table>
   32.62 +
   32.63 +<table class="files" tal:condition="context/files">
   32.64 + <tr><th colspan="2" class="header" i18n:translate="">Files</th></tr>
   32.65 + <tr>
   32.66 +  <th i18n:translate="">File name</th>
   32.67 +  <th i18n:translate="">Uploaded</th>
   32.68 + </tr>
   32.69 + <tr tal:repeat="file context/files">
   32.70 +  <td>
   32.71 +   <a tal:attributes="href string:file${file/id}/${file/name}"
   32.72 +      tal:content="file/name">dld link</a>
   32.73 +  </td>
   32.74 +  <td>
   32.75 +   <span tal:content="file/creator">creator's name</span>,
   32.76 +   <span tal:content="file/creation">creation date</span>
   32.77 +  </td>
   32.78 + </tr>
   32.79 +</table>
   32.80 +
   32.81 +<tal:block tal:replace="structure context/history" />
   32.82 +
   32.83 +</div>
   32.84 +</td>
   32.85 +
   32.86 +</tal:block>
   32.87 +<!-- SHA: e4a1c71477429a3750a6013098faa17f75d38f5d -->
    33.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    33.2 +++ b/bugs/templates/slitaz/html/page.html	Thu Apr 14 01:13:16 2011 +0200
    33.3 @@ -0,0 +1,396 @@
    33.4 +<!-- vim:sw=2 sts=2
    33.5 +--><tal:block metal:define-macro="icing"
    33.6 +><!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
    33.7 +	"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
    33.8 +<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
    33.9 +<head>
   33.10 +<title metal:define-slot="head_title">title goes here</title>
   33.11 +<link rel="stylesheet" type="text/css" href="@@file/style.css" />
   33.12 +<link rel="shortcut icon" href="@@file/favicon.ico" />
   33.13 +<meta http-equiv="Content-Type"
   33.14 + tal:attributes="content string:text/html;; charset=${request/client/charset}" />
   33.15 +<script tal:replace="structure request/base_javascript">
   33.16 +</script>
   33.17 +<metal:x define-slot="more-javascript" />
   33.18 +
   33.19 +</head>
   33.20 +<body>
   33.21 +
   33.22 +<!-- Header -->
   33.23 +<div id="header">
   33.24 +	<div id="logo"></div>
   33.25 +	<div id="network">
   33.26 +		<a href="http://www.slitaz.org/">
   33.27 +			<img src="http://tank.slitaz.org/images/network.png"
   33.28 +				alt="network.png" /></a>
   33.29 +		<a href="http://scn.slitaz.org/">Community</a>
   33.30 +		<a href="http://doc.slitaz.org/">Doc</a>
   33.31 +		<a href="http://forum.slitaz.org/">Forum</a>
   33.32 +		<a href="http://bugs.slitaz.org/">Bugs</a>
   33.33 +		<a href="http://hg.slitaz.org/">Hg</a>
   33.34 +	</div>
   33.35 +	<h1><a href="http://bugs.slitaz.org/">SliTaz Bugs</a></h1>
   33.36 +</div>
   33.37 +
   33.38 +<!-- Block -->
   33.39 +<div id="block">
   33.40 +	<!-- Navigation 
   33.41 +	<div id="block_nav" style="text-align: center; padding: 10px;">
   33.42 +		
   33.43 +	</div>-->
   33.44 +	<!-- Information/image -->
   33.45 +	<div id="block_info">
   33.46 +		<h4>SliTaz Bug Tracking System</h4>
   33.47 +		<p>
   33.48 +			Let track bugs, features requests and tasks in one easy to
   33.49 +			use and centralized place. 
   33.50 +		</p>
   33.51 +	</div>
   33.52 +</div>
   33.53 +
   33.54 +<table class="body"
   33.55 + tal:define="
   33.56 +kw_edit python:request.user.hasPermission('Edit', 'keyword');
   33.57 +kw_create python:request.user.hasPermission('Create', 'keyword');
   33.58 +kw_edit_link python:kw_edit and db.keyword.list();
   33.59 +columns string:id,activity,title,creator,status;
   33.60 +columns_showall string:id,activity,title,creator,assignedto,status;
   33.61 +status_notresolved string:-1,1,2,3,4,5,6,7;
   33.62 +"
   33.63 +>
   33.64 +
   33.65 +<tr>
   33.66 + <td class="page-header-left">&nbsp;</td>
   33.67 + <td class="page-header-top">
   33.68 +   <div id="searchbox">
   33.69 +     <form method="get" action="issue">
   33.70 +       <input type="hidden" name="@columns"
   33.71 +	      tal:attributes="value columns_showall"
   33.72 +	      value="id,activity,title,creator,assignedto,status" />
   33.73 +       <input type="hidden" name="@sort" value="activity" />
   33.74 +       <input type="hidden" name="@group" value="priority" />
   33.75 +       <input id="search-text" name="@search_text" size="10"
   33.76 +              tal:attributes="value request/search_text | default" />
   33.77 +       <input type="submit" id="submit" name="submit" value="Search"
   33.78 +              i18n:attributes="value" />
   33.79 +     </form>
   33.80 +   </div>
   33.81 +   <div id="body-title">
   33.82 +     <h2><span metal:define-slot="body_title">body title</span></h2>
   33.83 +   </div>
   33.84 + </td>
   33.85 +</tr>
   33.86 +
   33.87 +<tr>
   33.88 + <td rowspan="2" valign="top" class="sidebar">
   33.89 +  <p class="classblock"
   33.90 +     tal:condition="python:request.user.hasPermission('View', 'query')">
   33.91 +   <span i18n:translate=""
   33.92 +    ><b>Your Queries</b> (<a href="query?@template=edit">edit</a>)</span><br />
   33.93 +   <tal:block tal:repeat="qs request/user/queries">
   33.94 +    <a href="#" tal:attributes="href string:${qs/klass}?${qs/url}&@dispname=${qs/name}"
   33.95 +       tal:content="qs/name">link</a><br />
   33.96 +   </tal:block>
   33.97 +  </p>
   33.98 +
   33.99 +  <form method="post" tal:attributes="action request/base">
  33.100 +   <p class="classblock"
  33.101 +       tal:condition="python:request.user.hasPermission('View', 'issue')">
  33.102 +    <b i18n:translate="">Issues</b><br />
  33.103 +    <span tal:condition="python:request.user.hasPermission('Create', 'issue')">
  33.104 +      <a href="issue?@template=item" i18n:translate="">Create New</a><br />
  33.105 +    </span>
  33.106 +    <a href="#"
  33.107 +       tal:attributes="href python:request.indexargs_url('issue', {
  33.108 +      '@sort': '-activity',
  33.109 +      '@group': 'priority',
  33.110 +      '@filter': 'status,assignedto',
  33.111 +      '@columns': columns,
  33.112 +      '@search_text': '',
  33.113 +      'status': status_notresolved,
  33.114 +      'assignedto': '-1',
  33.115 +      '@dispname': i18n.gettext('Show Unassigned'),
  33.116 +     })"
  33.117 +       i18n:translate="">Show Unassigned</a><br />
  33.118 +    <a href="#"
  33.119 +       tal:attributes="href python:request.indexargs_url('issue', {
  33.120 +      '@sort': '-activity',
  33.121 +      '@group': 'priority',
  33.122 +      '@filter': 'status',
  33.123 +      '@columns': columns_showall,
  33.124 +      '@search_text': '',
  33.125 +      'status': status_notresolved,
  33.126 +      '@dispname': i18n.gettext('Show All'),
  33.127 +     })"
  33.128 +       i18n:translate="">Show All</a><br />
  33.129 +    <a href="issue?@template=search" i18n:translate="">Search</a><br />
  33.130 +    <input type="submit" class="form-small" value="Show issue:"
  33.131 +     i18n:attributes="value" /><input class="form-small" size="4"
  33.132 +     type="text" name="@number" />
  33.133 +    <input type="hidden" name="@type" value="issue" />
  33.134 +    <input type="hidden" name="@action" value="show" />
  33.135 +   </p>
  33.136 +  </form>
  33.137 +
  33.138 +  <p class="classblock"
  33.139 +     tal:condition="python:kw_edit or kw_create">
  33.140 +   <b i18n:translate="">Keywords</b><br />
  33.141 +   <span tal:condition="python:request.user.hasPermission('Create', 'keyword')">
  33.142 +    <a href="keyword?@template=item" i18n:translate="">Create New</a><br />
  33.143 +   </span>
  33.144 +   <span tal:condition="kw_edit_link">
  33.145 +    <a href="keyword?@template=item" i18n:translate="">Edit Existing</a><br />
  33.146 +   </span>
  33.147 +  </p>
  33.148 +
  33.149 +  <p class="classblock"
  33.150 +       tal:condition="python:request.user.hasPermission('View', 'user')">
  33.151 +   <b i18n:translate="">Administration</b><br />
  33.152 +   <span tal:condition="python:request.user.hasPermission('Edit', None)">
  33.153 +    <a href="home?@template=classlist" i18n:translate="">Class List</a><br />
  33.154 +   </span>
  33.155 +   <span tal:condition="python:request.user.hasPermission('View', 'user')
  33.156 +                            or request.user.hasPermission('Edit', 'user')">
  33.157 +    <a href="user"  i18n:translate="">User List</a><br />
  33.158 +   </span>
  33.159 +   <a tal:condition="python:request.user.hasPermission('Create', 'user')"
  33.160 +      href="user?@template=item" i18n:translate="">Add User</a>
  33.161 +  </p>
  33.162 +
  33.163 +  <form method="post" tal:condition="python:request.user.username=='anonymous'"
  33.164 +        tal:attributes="action request/base">
  33.165 +   <p class="userblock">
  33.166 +    <b i18n:translate="">Login</b><br />
  33.167 +    <input size="18" name="__login_name" /><br />
  33.168 +    <input size="18" type="password" name="__login_password" /><br />
  33.169 +    <input type="hidden" name="@action" value="Login" />
  33.170 +    <input type="checkbox" name="remember" id="remember" />
  33.171 +    <label for="remember" i18n:translate="">Remember me?</label><br />
  33.172 +    <input type="submit" value="Login" i18n:attributes="value" /><br />
  33.173 +    <input type="hidden" name="__came_from"
  33.174 +		tal:attributes="value string:${request/base}${request/env/PATH_INFO}" />
  33.175 +    <span tal:replace="structure request/indexargs_form" />
  33.176 +    <a href="user?@template=register"
  33.177 +       tal:condition="python:request.user.hasPermission('Register', 'user')"
  33.178 +     i18n:translate="">Register</a><br />
  33.179 +    <a href="user?@template=forgotten" i18n:translate="">Lost&nbsp;your&nbsp;login?</a><br />
  33.180 +   </p>
  33.181 +  </form>
  33.182 +
  33.183 +  <p class="userblock" tal:condition="python:request.user.username != 'anonymous'">
  33.184 +   <b i18n:translate="">Hello, <span i18n:name="user"
  33.185 +    tal:replace="python:request.user.username.plain(escape=1)">username</span></b><br />
  33.186 +    <a href="#"
  33.187 +       tal:attributes="href python:request.indexargs_url('issue', {
  33.188 +      '@sort': '-activity',
  33.189 +      '@group': 'priority',
  33.190 +      '@filter': 'status,assignedto',
  33.191 +      '@columns': 'id,activity,title,creator,status',
  33.192 +      '@search_text': '',
  33.193 +      'status': status_notresolved,
  33.194 +      'assignedto': request.user.id,
  33.195 +      '@dispname': i18n.gettext('Your Issues'),
  33.196 +     })"
  33.197 +    i18n:translate="">Your Issues</a><br />
  33.198 +   <a href="#" tal:attributes="href string:user${request/user/id}"
  33.199 +    i18n:translate="">Your Details</a><br />
  33.200 +   <a href="#" tal:attributes="href python:request.indexargs_url('',
  33.201 +       {'@action':'logout'})" i18n:translate="">Logout</a>
  33.202 +  </p>
  33.203 + </td>
  33.204 + <td>
  33.205 +  <p tal:condition="options/error_message | nothing" class="error-message"
  33.206 +     tal:repeat="m options/error_message" tal:content="structure m" />
  33.207 +  <p tal:condition="options/ok_message | nothing" class="ok-message">
  33.208 +    <span tal:repeat="m options/ok_message"
  33.209 +       tal:content="structure string:$m <br/ > " />
  33.210 +     <a class="form-small" tal:attributes="href request/current_url"
  33.211 +        i18n:translate="">clear this message</a>
  33.212 +  </p>
  33.213 + </td>
  33.214 +</tr>
  33.215 +<tr>
  33.216 + <td class="content" metal:define-slot="content">Page content goes here</td>
  33.217 +</tr>
  33.218 +
  33.219 +</table>
  33.220 +
  33.221 +<pre tal:condition="request/form/debug | nothing" tal:content="request">
  33.222 +</pre>
  33.223 +
  33.224 +<!-- Footer -->
  33.225 +<div id="footer">
  33.226 +	Copyright &copy; <span class="year"></span>
  33.227 +	<a href="http://www.slitaz.org/">SliTaz</a> - Network:
  33.228 +	<a href="http://scn.slitaz.org/">Community</a>
  33.229 +	<a href="http://doc.slitaz.org/">Doc</a>
  33.230 +	<a href="http://forum.slitaz.org/">Forum</a>
  33.231 +	<a href="http://pkgs.slitaz.org/">Packages</a>
  33.232 +	<a href="http://bugs.slitaz.org/">Bugs</a>
  33.233 +	<a href="http://hg.slitaz.org/">Hg</a>
  33.234 +	<p>
  33.235 +		SliTaz @
  33.236 +		<a href="http://twitter.com/slitaz">Twitter</a>
  33.237 +		<a href="http://www.facebook.com/slitaz">Facebook</a>
  33.238 +		<a href="http://distrowatch.com/slitaz">Distrowatch</a>
  33.239 +		<a href="http://en.wikipedia.org/wiki/SliTaz">Wikipedia</a>
  33.240 +		<a href="http://flattr.com/profile/slitaz">Flattr</a>
  33.241 +	</p>
  33.242 +</div>
  33.243 +
  33.244 +</body>
  33.245 +</html>
  33.246 +</tal:block>
  33.247 +
  33.248 +<!--
  33.249 +The following macros are intended to be used in search pages.
  33.250 +
  33.251 +The invoking context must define a "name" variable which names the
  33.252 +property being searched.
  33.253 +
  33.254 +See issue.search.html in the classic template for examples.
  33.255 +-->
  33.256 +
  33.257 +<!-- creates a th and a label: -->
  33.258 +<th metal:define-macro="th_label"
  33.259 +    tal:define="required required | python:[]"
  33.260 +    tal:attributes="class python:(name in required) and 'required' or nothing">
  33.261 +  <label tal:attributes="for name" tal:content="label" i18n:translate="">text</label>
  33.262 +	<metal:x define-slot="behind_the_label" />
  33.263 +</th>
  33.264 +
  33.265 +<td metal:define-macro="search_input">
  33.266 +  <input tal:attributes="value python:request.form.getvalue(name) or nothing;
  33.267 +                         name name;
  33.268 +                         id name" />
  33.269 +</td>
  33.270 +
  33.271 +<td metal:define-macro="search_date">
  33.272 +  <input tal:attributes="value python:request.form.getvalue(name) or nothing;
  33.273 +                         name name;
  33.274 +                         id name" />
  33.275 +  <a class="classhelp"
  33.276 +	 tal:attributes="href python:'''javascript:help_window('issue?@template=calendar&property=%s&form=itemSynopsis', 300, 200)'''%name">(cal)</a>
  33.277 +</td>
  33.278 +
  33.279 +<td metal:define-macro="search_popup">
  33.280 +  <!--
  33.281 +    context needs to specify the popup "columns" as a comma-separated
  33.282 +    string (eg. "id,title" or "id,name,description") as well as name
  33.283 +  -->
  33.284 +  <input tal:attributes="value python:request.form.getvalue(name) or nothing;
  33.285 +                         name name;
  33.286 +                         id name" />
  33.287 +  <span tal:replace="structure python:db[db_klass].classhelp(columns,
  33.288 +                                      property=name)" />
  33.289 +</td>
  33.290 +
  33.291 +<td metal:define-macro="search_select">
  33.292 +  <select tal:attributes="name name; id name"
  33.293 +          tal:define="value python:request.form.getvalue(name)">
  33.294 +    <option value="" i18n:translate="">don't care</option>
  33.295 +    <metal:slot define-slot="extra_options" />
  33.296 +    <option value="" i18n:translate="" disabled="disabled">------------</option>
  33.297 +    <option tal:repeat="s python:db[db_klass].list()"
  33.298 +            tal:attributes="value s/id; selected python:value == s.id"
  33.299 +            tal:content="python:s[db_content]"></option>
  33.300 +  </select>
  33.301 +</td>
  33.302 +
  33.303 +<!-- like search_select, but translates the further values.
  33.304 +Could extend it (METAL 1.1 attribute "extend-macro")
  33.305 +-->
  33.306 +<td metal:define-macro="search_select_translated">
  33.307 +  <select tal:attributes="name name; id name"
  33.308 +          tal:define="value python:request.form.getvalue(name)">
  33.309 +    <option value="" i18n:translate="">don't care</option>
  33.310 +    <metal:slot define-slot="extra_options" />
  33.311 +    <option value="" i18n:translate="" disabled="disabled">------------</option>
  33.312 +    <option tal:repeat="s python:db[db_klass].list()"
  33.313 +            tal:attributes="value s/id; selected python:value == s.id"
  33.314 +						tal:content="python:s[db_content]"
  33.315 +						i18n:translate=""></option>
  33.316 +  </select>
  33.317 +</td>
  33.318 +
  33.319 +<!-- currently, there is no convenient API to get a list of all roles -->
  33.320 +<td metal:define-macro="search_select_roles"
  33.321 +	  tal:define="onchange onchange | nothing">
  33.322 +  <select name=roles id=roles tal:attributes="onchange onchange">
  33.323 +    <option value="" i18n:translate="">don't care</option>
  33.324 +    <option value="" i18n:translate="" disabled="disabled">------------</option>
  33.325 +    <option value="User">User</option>
  33.326 +    <option value="Admin">Admin</option>
  33.327 +    <option value="Anonymous">Anonymous</option>
  33.328 +  </select>
  33.329 +</td>
  33.330 +
  33.331 +<td metal:define-macro="search_multiselect">
  33.332 +  <input tal:attributes="value python:request.form.getvalue(name) or nothing;
  33.333 +                         name name;
  33.334 +                         id name">
  33.335 +  <span tal:replace="structure python:db[db_klass].classhelp(db_content,
  33.336 +                                        property=name, width='600')" />
  33.337 +</td>
  33.338 +
  33.339 +<td metal:define-macro="search_checkboxes">
  33.340 + <ul class="search-checkboxes"
  33.341 +     tal:define="value python:request.form.getvalue(name);
  33.342 +                 values python:value and value.split(',') or []">
  33.343 + <li tal:repeat="s python:db[db_klass].list()">
  33.344 +  <input type="checkbox" tal:attributes="name name; id string:$name-${s/id};
  33.345 +    value s/id; checked python:s.id in values" />
  33.346 +  <label tal:attributes="for string:$name-${s/id}"
  33.347 +         tal:content="python:s[db_content]" />
  33.348 + </li>
  33.349 + <li metal:define-slot="no_value_item">
  33.350 +  <input type="checkbox" value="-1" tal:attributes="name name;
  33.351 +     id string:$name--1; checked python:value == '-1'" />
  33.352 +  <label tal:attributes="for string:$name--1" i18n:translate="">no value</label>
  33.353 + </li>
  33.354 + </ul>
  33.355 +</td>
  33.356 +
  33.357 +<td metal:define-macro="column_input">
  33.358 +  <input type="checkbox" name="@columns"
  33.359 +         tal:attributes="value name;
  33.360 +                         checked python:name in cols" />
  33.361 +</td>
  33.362 +
  33.363 +<td metal:define-macro="sort_input">
  33.364 +  <input type="radio" name="@sort"
  33.365 +         tal:attributes="value name;
  33.366 +                         checked python:name == sort_on"> /
  33.367 +</td>
  33.368 +
  33.369 +<td metal:define-macro="group_input">
  33.370 +  <input type="radio" name="@group"
  33.371 +         tal:attributes="value name;
  33.372 +                         checked python:name == group_on" />
  33.373 +</td>
  33.374 +
  33.375 +<!--
  33.376 +The following macros are intended for user editing.
  33.377 +
  33.378 +The invoking context must define a "name" variable which names the
  33.379 +property being searched; the "edit_ok" variable tells whether the
  33.380 +current user is allowed to edit.
  33.381 +
  33.382 +See user.item.html in the classic template for examples.
  33.383 +-->
  33.384 +<script metal:define-macro="user_utils" type="text/javascript" src="@@file/user_utils.js"></script>
  33.385 +
  33.386 +<!-- src: value will be re-used for other input fields -->
  33.387 +<input metal:define-macro="user_src_input"
  33.388 +    type="text" tal:attributes="onblur python:edit_ok and 'split_name(this)';
  33.389 +    id name; name name; value value; readonly not:edit_ok"
  33.390 +    value="heinz.kunz" />
  33.391 +<!-- normal: no re-using -->
  33.392 +<input metal:define-macro="user_normal_input" type="text"
  33.393 +    tal:attributes="id name; name name; value value; readonly not:edit_ok"
  33.394 +    value="heinz" />
  33.395 +<!-- password: type; no initial value -->
  33.396 +    <input metal:define-macro="user_pw_input" type="password"
  33.397 +    tal:attributes="id name; name name; readonly not:edit_ok" value="" />
  33.398 +    <input metal:define-macro="user_confirm_input" type="password"
  33.399 +    tal:attributes="id name; name string:@confirm@$name; readonly not:edit_ok" value="" />
    34.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    34.2 +++ b/bugs/templates/slitaz/html/query.edit.html	Thu Apr 14 01:13:16 2011 +0200
    34.3 @@ -0,0 +1,112 @@
    34.4 +<!-- dollarId: user.item,v 1.7 2002/08/16 04:29:04 richard Exp dollar-->
    34.5 +<tal:block metal:use-macro="templates/page/macros/icing">
    34.6 +<title metal:fill-slot="head_title" i18n:translate=""
    34.7 + >"Your Queries" Editing - <span tal:replace="config/TRACKER_NAME"
    34.8 + i18n:name="tracker" /></title>
    34.9 +<span metal:fill-slot="body_title" tal:omit-tag="python:1"
   34.10 + i18n:translate="">"Your Queries" Editing</span>
   34.11 +
   34.12 +<td class="content" metal:fill-slot="content">
   34.13 +
   34.14 +<span tal:condition="not:context/is_edit_ok"
   34.15 + i18n:translate="">You are not allowed to edit queries.</span>
   34.16 +
   34.17 +<script language="javascript">
   34.18 +// This exists solely because I can't figure how to get the & into an
   34.19 +// attributes TALES expression, and so it keeps getting quoted.
   34.20 +function retire(qid) {
   34.21 +    window.location = 'query'+qid+'?@action=retire&@template=edit';
   34.22 +}
   34.23 +</script>
   34.24 +
   34.25 +<form method="post" onSubmit="return submit_once()" action="query"
   34.26 +      enctype="multipart/form-data" tal:condition="context/is_edit_ok">
   34.27 +
   34.28 +<table class="list" width="100%"
   34.29 +       tal:define="uid request/user/id; mine request/user/queries">
   34.30 +
   34.31 +<tr><th i18n:translate="">Query</th>
   34.32 +    <th i18n:translate="">Include in "Your Queries"</th>
   34.33 +    <th i18n:translate="">Edit</th>
   34.34 +    <th i18n:translate="">Private to you?</th>
   34.35 +    <th>&nbsp;</th>
   34.36 +</tr>
   34.37 +
   34.38 +<tr tal:repeat="query mine">
   34.39 + <tal:block condition="query/is_retired">
   34.40 +
   34.41 + <td><a tal:attributes="href string:${query/klass}?${query/url}"
   34.42 +        tal:content="query/name">query</a></td>
   34.43 +
   34.44 + <td metal:define-macro="include">
   34.45 +  <select tal:condition="python:query.id not in mine"
   34.46 +          tal:attributes="name string:user${uid}@add@queries">
   34.47 +    <option value="" i18n:translate="">leave out</option>
   34.48 +    <option tal:attributes="value query/id" i18n:translate="">include</option>
   34.49 +  </select>
   34.50 +  <select tal:condition="python:query.id in mine"
   34.51 +          tal:attributes="name string:user${uid}@remove@queries">
   34.52 +    <option value="" i18n:translate="">leave in</option>
   34.53 +    <option tal:attributes="value query/id" i18n:translate="">remove</option>
   34.54 +  </select>
   34.55 + </td>
   34.56 +
   34.57 + <td colspan="3" i18n:translate="">[query is retired]</td>
   34.58 +
   34.59 + <!-- <td> maybe offer "restore" some day </td> -->
   34.60 + </tal:block>
   34.61 +</tr>
   34.62 +
   34.63 +<tr tal:repeat="query mine">
   34.64 + <tal:block condition="not:query/is_retired">
   34.65 + <td><a tal:attributes="href string:${query/klass}?${query/url}"
   34.66 +        tal:content="query/name">query</a></td>
   34.67 +
   34.68 + <td metal:use-macro="template/macros/include" />
   34.69 +
   34.70 + <td><a tal:attributes="href string:query${query/id}" i18n:translate="">edit</a></td>
   34.71 +
   34.72 + <td>
   34.73 +  <select tal:attributes="name string:query${query/id}@private_for">
   34.74 +   <option tal:attributes="selected python:query.private_for == uid;
   34.75 +           value uid" i18n:translate="">yes</option>
   34.76 +   <option tal:attributes="selected python:query.private_for == None"
   34.77 +           value="-1" i18n:translate="">no</option>
   34.78 +  </select>
   34.79 + </td>
   34.80 +
   34.81 + <td>
   34.82 +  <input type="button" value="Delete" i18n:attributes="value"
   34.83 +  tal:attributes="onClick python:'''retire('%s')'''%query.id">
   34.84 +  </td>
   34.85 +  </tal:block>
   34.86 +</tr>
   34.87 +
   34.88 +<tr tal:define="queries python:db.query.filter(filterspec={'private_for':None})"
   34.89 +     tal:repeat="query queries">
   34.90 + <tal:block condition="python: query.creator != uid">
   34.91 + <td><a tal:attributes="href string:${query/klass}?${query/url}"
   34.92 +        tal:content="query/name">query</a></td>
   34.93 +
   34.94 + <td metal:use-macro="template/macros/include" />
   34.95 +
   34.96 + <td colspan="3" tal:condition="query/is_edit_ok">
   34.97 +  <a tal:attributes="href string:query${query/id}" i18n:translate="">edit</a>
   34.98 + </td>
   34.99 + <td tal:condition="not:query/is_edit_ok" colspan="3"
  34.100 +    i18n:translate="">[not yours to edit]</td>
  34.101 + </tal:block>
  34.102 +</tr>
  34.103 +
  34.104 +<tr><td colspan="5">
  34.105 +   <input type="hidden" name="@action" value="edit">
  34.106 +   <input type="hidden" name="@template" value="edit">
  34.107 +   <input type="submit" value="Save Selection" i18n:attributes="value">
  34.108 +</td></tr>
  34.109 +
  34.110 +</table>
  34.111 +
  34.112 +</form>
  34.113 +</td>
  34.114 +</tal:block>
  34.115 +<!-- SHA: 381522a1ff6675e1da99ccc7c2b012e5e1e5f7b8 -->
    35.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    35.2 +++ b/bugs/templates/slitaz/html/query.item.html	Thu Apr 14 01:13:16 2011 +0200
    35.3 @@ -0,0 +1,4 @@
    35.4 +<!-- query.item -->
    35.5 +<span tal:replace="structure context/renderQueryForm" />
    35.6 +
    35.7 +<!-- SHA: 027820442d9341987bbb8b732cd6233aa1e56bed -->
    36.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    36.2 +++ b/bugs/templates/slitaz/html/style.css	Thu Apr 14 01:13:16 2011 +0200
    36.3 @@ -0,0 +1,630 @@
    36.4 +/*
    36.5 +	CSS style for SliTaz Network - (C) 2011 SliTaz GNU/Linux
    36.6 +*/
    36.7 +
    36.8 +html {
    36.9 +	min-height:  102%;
   36.10 +}
   36.11 +
   36.12 +body {
   36.13 +	background: #ffffff;
   36.14 +	color: black;
   36.15 +	font: 13px sans-serif, vernada, arial;
   36.16 +	margin: 0;
   36.17 +	min-width: 780px;
   36.18 +	height: 100%;
   36.19 +}
   36.20 +
   36.21 +a { text-decoration: underline; color: #215090; }
   36.22 +a:hover { text-decoration: none; color: blue; }
   36.23 +img { border: 0pt none; vertical-align: middle; }
   36.24 +h2 { color: #444; margin: 2px 0;}
   36.25 +h3 { color: #666; font-size: 140%; }
   36.26 +h4 { color: #888; font-size: 120%; }
   36.27 +
   36.28 +/* Header */
   36.29 +
   36.30 +#header { 
   36.31 +	height: 40px; 
   36.32 +	background: #351a0a;
   36.33 +}
   36.34 +
   36.35 +#header h1 {
   36.36 +	margin: 0;
   36.37 +	padding: 8px 0 0 42px;
   36.38 +	width: 250px;
   36.39 +}
   36.40 +
   36.41 +#header h1 a { 
   36.42 +	color: white; 
   36.43 +	text-decoration: none;
   36.44 +	font-size: 20px;
   36.45 +	font-style: italic;
   36.46 +}
   36.47 +
   36.48 +#header h1 a:hover, #network a:hover { 
   36.49 +	color: #d66018;
   36.50 +}
   36.51 +
   36.52 +/* Logo */
   36.53 +
   36.54 +#logo {
   36.55 +	background: url(http://tank.slitaz.org/images/logo.png) no-repeat left;
   36.56 +	position: absolute;
   36.57 +	float: left;
   36.58 +	left: 0px;
   36.59 +	top: 0px;
   36.60 +	width: 40px;
   36.61 +	height: 40px;
   36.62 +}
   36.63 +
   36.64 +/* SliTaz Network */
   36.65 +
   36.66 +#network { 
   36.67 +	float: right; 
   36.68 +	padding: 10px 5px 0; 
   36.69 +	font-size: 12px;
   36.70 +}
   36.71 +
   36.72 +#network a { padding: 0 6px; }
   36.73 +
   36.74 +/* Block */
   36.75 +
   36.76 +#block { 
   36.77 +	min-height: 104px; 
   36.78 +	background: #d66018; 
   36.79 +	padding: 26px 10% 0px;
   36.80 +	text-align: center;
   36.81 +	color: #333;
   36.82 +	border-bottom: 1px solid #f5f5f5;
   36.83 +}
   36.84 +
   36.85 +#block_info {
   36.86 +	text-align: justify; 
   36.87 +	width: 48%;
   36.88 +	padding: 10px 10px 0 0;
   36.89 +}
   36.90 +
   36.91 +#block a, #network a { 
   36.92 +	color: #fff; 
   36.93 +	font-weight: bold;
   36.94 +	text-decoration: none;
   36.95 +}
   36.96 +
   36.97 +#block h4 {
   36.98 +	color: #351a0a;
   36.99 +	margin: 0px;
  36.100 +	font-weight: bold;
  36.101 +	font-size: 110%;
  36.102 +}
  36.103 +
  36.104 +#block_info p { margin: 6px 0; padding: 0 12px 0 0; }
  36.105 +#block_info a { font-weight: normal; }
  36.106 +#block ul { list-style-type: square; }
  36.107 +#block a:hover { color: #351a0a; }
  36.108 +
  36.109 +/* Navigation */
  36.110 +
  36.111 +#block_nav {
  36.112 +	background: #cc5b17;
  36.113 +	padding: 10px 10px 40px;
  36.114 +	text-align: justify;
  36.115 +	width: 48%;
  36.116 +	float: right;
  36.117 +}
  36.118 +
  36.119 +#block_nav ul { 
  36.120 +	list-style-type: none; 
  36.121 +	margin: 6px 0; 
  36.122 +	padding: 0;
  36.123 +}
  36.124 +
  36.125 +#block_nav h4 img { 
  36.126 +	margin: 0 4px 0 0; 
  36.127 +	padding: 0;
  36.128 +}
  36.129 +
  36.130 +#searchbox input[type=submit] {
  36.131 +	padding: 4px;
  36.132 +	margin-left: -5px;
  36.133 +	background-color: #f1f1f1;
  36.134 +	border: 1px solid #ddd;
  36.135 +	cursor: pointer;
  36.136 +	color: #000;
  36.137 +	font-weight: bold;
  36.138 +	border-top-right-radius: 4px;
  36.139 +	border-bottom-right-radius: 4px;
  36.140 +	border-top-left-radius: 0px;
  36.141 +	border-bottom-left-radius: 0px;
  36.142 +}
  36.143 +
  36.144 +input#search-text {
  36.145 +	border: 1px solid #ddd;
  36.146 +	padding: 4px;
  36.147 +	height: 17px;
  36.148 +	margin: 0;
  36.149 +	width: 200px;
  36.150 +	border-top-left-radius: 4px;
  36.151 +	border-bottom-left-radius: 4px;
  36.152 +}
  36.153 +
  36.154 +input[type=submit] {
  36.155 +	padding: 2px;
  36.156 +	margin: 2px 0;
  36.157 +	background-color: #f1f1f1;
  36.158 +	border: 1px solid #ddd;
  36.159 +	cursor: pointer;
  36.160 +	color: #000;
  36.161 +}
  36.162 +
  36.163 +input[type=submit]:hover, #searchbox input[type=submit]:hover {
  36.164 +	background-color: #ddd;
  36.165 +	border: 1px solid #999;
  36.166 +}
  36.167 +
  36.168 +input[type=text] { height: 18px; margin: 4px 0; }
  36.169 +
  36.170 +
  36.171 +/* Round corner */
  36.172 +
  36.173 +input[type=submit], p.ok-message, p.error-message, table.form,
  36.174 +table.messages td {
  36.175 +	-moz-border-radius: 4px;
  36.176 +	-webkit-border-radius: 4px;
  36.177 +	border-radius: 4px;
  36.178 +}
  36.179 +
  36.180 +/* Footer */
  36.181 +
  36.182 +#footer {
  36.183 +	background: #f1f1f1;
  36.184 +	text-align: center;
  36.185 +	border-top: 1px solid #ddd;
  36.186 +	padding: 40px;
  36.187 +	color: #666;
  36.188 +	clear: both;
  36.189 +	margin-top: 160px;
  36.190 +	margin-bottom: -2%;
  36.191 +}
  36.192 +
  36.193 +#footer a { color: #666; padding: 0 2px; }
  36.194 +
  36.195 +.year:after {
  36.196 +	/* content: "2007-2011"; */
  36.197 +	content: "2011";
  36.198 +}
  36.199 +
  36.200 +/* Modified Roundup style */
  36.201 +
  36.202 +#searchbox {
  36.203 +	float: right;
  36.204 +}
  36.205 +
  36.206 +td.sidebar {
  36.207 +	white-space: nowrap;
  36.208 +	position: absolute;
  36.209 +	right: 10px;
  36.210 +	top: 230px;
  36.211 +	border-left: 1px solid #ddd;
  36.212 +	padding: 0 10px;
  36.213 +}
  36.214 +
  36.215 +td.sidebar a {
  36.216 +	text-decoration: none;
  36.217 +}
  36.218 +
  36.219 +td.page-header-left {
  36.220 +	padding: 5px;
  36.221 +}
  36.222 +
  36.223 +td.page-header-top {
  36.224 +	padding: 10px;
  36.225 +	position: absolute;
  36.226 +	left: 20px;
  36.227 +	right: 20px;
  36.228 +	width: auto;
  36.229 +}
  36.230 +
  36.231 +td.content {
  36.232 +	padding: 30px 220px 20px 30px;
  36.233 +	vertical-align: top;
  36.234 +	width: 100%;
  36.235 +}
  36.236 +
  36.237 +p.ok-message { color: #000; }
  36.238 +p.error-message { color: red; }
  36.239 +p.ok-message, p.error-message {
  36.240 +	background-color: #f8f8f8;
  36.241 +	padding: 5px;
  36.242 +	font-weight: bold;
  36.243 +	
  36.244 +	position: absolute;
  36.245 +	right: 10%;
  36.246 +	top: 70px;
  36.247 +	min-width: 220px;
  36.248 +}
  36.249 +
  36.250 +td.sidebar p.classblock {
  36.251 +	padding: 12px 5px 0;
  36.252 +	margin: 0;
  36.253 +}
  36.254 +
  36.255 +td.sidebar p.classblock:first-child { padding: 0px 5px 0; }
  36.256 +
  36.257 +td.sidebar p.userblock {
  36.258 +	padding: 12px 5px 0;
  36.259 +	margin: 0;
  36.260 +}
  36.261 +
  36.262 +table.form {
  36.263 +	margin: 0 0 10px;
  36.264 +	padding: 10px;
  36.265 +	border-spacing: 0;
  36.266 +	border-collapse: separate;
  36.267 +	background-color: #f8f8f8;
  36.268 +	border: 1px solid #ddd;
  36.269 +}
  36.270 +
  36.271 +.index-controls {
  36.272 +	margin: 20px 0;
  36.273 +}
  36.274 +
  36.275 +table.body {
  36.276 +  border: 0;
  36.277 +  padding: 0;
  36.278 +  border-spacing: 0;
  36.279 +  border-collapse: separate;
  36.280 +}
  36.281 +
  36.282 +/* don't display the sidebar when printing */
  36.283 +@media print {
  36.284 +    td.page-header-left {
  36.285 +        display: none;
  36.286 +    }
  36.287 +    td.sidebar {
  36.288 +        display: none;
  36.289 +    }
  36.290 +    .index-controls {
  36.291 +        display: none;
  36.292 +    }
  36.293 +    #searchbox {
  36.294 +        display: none;
  36.295 +    }
  36.296 +}
  36.297 +
  36.298 +form {
  36.299 +  margin: 0;
  36.300 +}
  36.301 +
  36.302 +textarea {
  36.303 +    font-family: monospace;
  36.304 +}
  36.305 +
  36.306 +.form-small {
  36.307 +  padding: 0;
  36.308 +  font-size: 75%;
  36.309 +}
  36.310 +
  36.311 +td.date, th.date { 
  36.312 +  white-space: nowrap;
  36.313 +  width: 130px;
  36.314 +}
  36.315 +
  36.316 +p.error-message a[href] {
  36.317 +  color: white;
  36.318 +  text-decoration: underline;
  36.319 +}
  36.320 +
  36.321 +/* style for search forms */
  36.322 +ul.search-checkboxes {
  36.323 +    display: inline;
  36.324 +    padding: 0;
  36.325 +    list-style: none;
  36.326 +}
  36.327 +ul.search-checkboxes > li {
  36.328 +    display: inline;
  36.329 +    padding-right: .5em;
  36.330 +}
  36.331 +
  36.332 +/* style for forms */
  36.333 +
  36.334 +table.form th {
  36.335 +	color: #555;
  36.336 +	text-align: right;
  36.337 +	vertical-align: top;
  36.338 +	font-weight: normal;
  36.339 +	white-space: nowrap;
  36.340 +	padding: 0 4px 0 0;
  36.341 +}
  36.342 +
  36.343 +table.form th.header {
  36.344 +  font-weight: bold;
  36.345 +  background-color: #f1f1f1;
  36.346 +  text-align: left;
  36.347 +}
  36.348 +
  36.349 +table.form th.required {
  36.350 +	font-weight: bold;
  36.351 +	color: #b20000;
  36.352 +}
  36.353 +
  36.354 +table.form td {
  36.355 +  color: #000;
  36.356 +  empty-cells: show;
  36.357 +  vertical-align: top;
  36.358 +}
  36.359 +
  36.360 +table.form td.optional {
  36.361 +  font-weight: bold;
  36.362 +  font-style: italic;
  36.363 +}
  36.364 +
  36.365 +table.form td.html {
  36.366 +  color: #000;
  36.367 +}
  36.368 +
  36.369 +/* style for lists */
  36.370 +table.list {
  36.371 +	border-spacing: 0 4px;
  36.372 +	border-collapse: separate;
  36.373 +	width: 100%;
  36.374 +}
  36.375 +
  36.376 +table.list th {
  36.377 +	padding: 0px;
  36.378 +	color: #888;
  36.379 +	background-color: #fff;
  36.380 +	vertical-align: top;
  36.381 +	empty-cells: show;
  36.382 +	text-align: left;
  36.383 +}
  36.384 +table.list th a[href]:hover { color: #333 }
  36.385 +table.list th a[href]:link { color: #333 }
  36.386 +table.list th a[href] { color: #333 }
  36.387 +table.list th.group {
  36.388 +	background-color: #f8f8f8;
  36.389 +	color: #666;
  36.390 +	text-align: left;
  36.391 +	padding: 4px;
  36.392 +	font-size: 120%;
  36.393 +	border: 1px solid #ddd;
  36.394 +	border-radius: 4px;
  36.395 +}
  36.396 +table.list th.group:first-letter {
  36.397 +	text-transform: uppercase;
  36.398 +}
  36.399 +
  36.400 +table.list td {
  36.401 +	padding: 2px;
  36.402 +	color: #000;
  36.403 +	vertical-align: top;
  36.404 +	empty-cells: show;
  36.405 +	/* border-bottom: 1px solid #ddd; */
  36.406 +}
  36.407 +
  36.408 +table.list tr.navigation th {
  36.409 +  width: 33%;
  36.410 +  border-style: hidden;
  36.411 +  text-align: center;
  36.412 +}
  36.413 +table.list tr.navigation td {
  36.414 +    border: none
  36.415 +}
  36.416 +table.list tr.navigation th:first-child {
  36.417 +  text-align: left;
  36.418 +}
  36.419 +table.list tr.navigation th:last-child {
  36.420 +  text-align: right;
  36.421 +}
  36.422 +
  36.423 +/* style for message displays */
  36.424 +table.messages {
  36.425 +  border-spacing: 0;
  36.426 +  border-collapse: separate;
  36.427 +  width: 100%;
  36.428 +}
  36.429 +
  36.430 +table.messages th.header {
  36.431 +	padding: 20px 0 4px;
  36.432 +	font-weight: bold;
  36.433 +	background-color: white;
  36.434 +	color: #666;
  36.435 +	font-size: 140%;
  36.436 +}
  36.437 +
  36.438 +table.messages th {
  36.439 +	font-weight: bold;
  36.440 +	color: black;
  36.441 +	text-align: left;
  36.442 +	padding: 10px 0 2px;
  36.443 +}
  36.444 +
  36.445 +table.messages th a {
  36.446 +	text-decoration: none;
  36.447 +}
  36.448 +
  36.449 +table.messages td {
  36.450 +	font-family: monospace;
  36.451 +	background-color: #f8f8f8;
  36.452 +	border: 1px solid #ddd; 
  36.453 +	color: black;
  36.454 +	empty-cells: show;
  36.455 +	vertical-align: top;
  36.456 +	padding: 4px 10px 5px 10px;
  36.457 +}
  36.458 +
  36.459 +/* style for file displays */
  36.460 +table.files {
  36.461 +  border-spacing: 0;
  36.462 +  border-collapse: separate;
  36.463 +  width: 100%;
  36.464 +}
  36.465 +
  36.466 +table.files th.header{
  36.467 +	padding: 10px 0;
  36.468 +	border-bottom: 0px solid gray;
  36.469 +	font-weight: bold;
  36.470 +	background-color: white;
  36.471 +	color: #666;
  36.472 +	font-size: 140%;
  36.473 +}
  36.474 +
  36.475 +table.files th {
  36.476 +  border-bottom: 1px solid #888;
  36.477 +  font-weight: bold;
  36.478 +  text-align: left;
  36.479 +  padding: 10px 0 2px;
  36.480 +}
  36.481 +
  36.482 +table.files td {
  36.483 +  font-family: monospace;
  36.484 +  empty-cells: show;
  36.485 +  padding-top: 5px;
  36.486 +}
  36.487 +
  36.488 +/* style for history displays */
  36.489 +table.history {
  36.490 +	border-spacing: 0;
  36.491 +	border-collapse: separate;
  36.492 +	width: 100%;
  36.493 +	margin: 0 0 40px;
  36.494 +}
  36.495 +
  36.496 +table.history th.header {
  36.497 +	padding: 20px 0 4px;
  36.498 +	border-bottom: 1px solid #fff;
  36.499 +	font-weight: bold;
  36.500 +	background-color: white;
  36.501 +	color: #666;
  36.502 +	font-size: 140%;
  36.503 +}
  36.504 +
  36.505 +table.history th {
  36.506 +  border-bottom: 1px solid #666;
  36.507 +  font-weight: bold;
  36.508 +  text-align: left;
  36.509 +  padding: 10px 0 2px;
  36.510 +}
  36.511 +
  36.512 +table.history td {
  36.513 +  vertical-align: top;
  36.514 +  empty-cells: show;
  36.515 +  padding-top: 5px;
  36.516 +}
  36.517 +
  36.518 +
  36.519 +/* style for class list */
  36.520 +table.classlist {
  36.521 +  border-spacing: 0;
  36.522 +  border-collapse: separate;
  36.523 +  width: 100%;
  36.524 +}
  36.525 +
  36.526 +table.classlist th.header{
  36.527 +  padding-top: 10px;
  36.528 +  border-bottom: 1px solid gray;
  36.529 +  font-weight: bold;
  36.530 +  background-color: white;
  36.531 +  color: #707040;
  36.532 +}
  36.533 +
  36.534 +table.classlist th {
  36.535 +  font-weight: bold;
  36.536 +  text-align: left;
  36.537 +}
  36.538 +
  36.539 +
  36.540 +/* style for class help display */
  36.541 +table.classhelp {      /* the table-layout: fixed;        */ 
  36.542 +  table-layout: fixed; /* compromises quality for speed   */
  36.543 +  overflow: hidden;
  36.544 +  font-size: .9em;
  36.545 +  padding-bottom: 3em;
  36.546 +}
  36.547 +
  36.548 +table.classhelp th {
  36.549 +  font-weight: normal;
  36.550 +  text-align: left;
  36.551 +  color: #444;
  36.552 +  background-color: #efefef;
  36.553 +  border-bottom: 1px solid #afafaf;
  36.554 +  border-top: 1px solid #afafaf;
  36.555 +  text-transform: uppercase;
  36.556 +  vertical-align: middle;
  36.557 +  line-height:1.5em;
  36.558 +}
  36.559 +
  36.560 +table.classhelp td {
  36.561 +  vertical-align: middle;
  36.562 +  padding-right: .2em;
  36.563 +  border-bottom: 1px solid #efefef;
  36.564 +  text-align: left;
  36.565 +  empty-cells: show;
  36.566 +  white-space: nowrap;
  36.567 +  vertical-align: middle;
  36.568 +}
  36.569 +
  36.570 +table.classhelp tr:hover {
  36.571 +  background-color: #eee;
  36.572 +}
  36.573 +
  36.574 +label.classhelp-label {
  36.575 +  cursor: pointer;
  36.576 +}
  36.577 +
  36.578 +#classhelp-controls {
  36.579 +  position: fixed;
  36.580 +  display: block;
  36.581 +  top: auto;
  36.582 +  right: 0;
  36.583 +  bottom: 0;
  36.584 +  left: 0;
  36.585 +  padding: .5em;
  36.586 +  border-top: 2px solid #444;
  36.587 +  background-color: #eee;
  36.588 +}
  36.589 +
  36.590 +#classhelp-controls input.apply {
  36.591 +  width: 7em;
  36.592 +  font-weight: bold;
  36.593 +  margin-right: 2em;
  36.594 +  margin-left: 2em;
  36.595 +}
  36.596 +
  36.597 +#classhelp-controls input.preview {
  36.598 +   margin-right: 3em;
  36.599 +   margin-left: 1em;
  36.600 +}
  36.601 +
  36.602 +/* style for "other" displays */
  36.603 +table.otherinfo {
  36.604 +  border-spacing: 0;
  36.605 +  border-collapse: separate;
  36.606 +  width: 100%;
  36.607 +}
  36.608 +
  36.609 +table.otherinfo th.header{
  36.610 +  padding-top: 10px;
  36.611 +  border-bottom: 1px solid gray;
  36.612 +  font-weight: bold;
  36.613 +  background-color: white;
  36.614 +  color: #707040;
  36.615 +}
  36.616 +
  36.617 +table.otherinfo th {
  36.618 +  border-bottom: 1px solid #afafaf;
  36.619 +  font-weight: bold;
  36.620 +  text-align: left;
  36.621 +}
  36.622 +
  36.623 +.calendar_display {
  36.624 +  text-align: center;
  36.625 +}
  36.626 +
  36.627 +.calendar_display td {
  36.628 +  padding: 1px 4px 1px 4px;
  36.629 +}
  36.630 +
  36.631 +.calendar_display .today {
  36.632 +  background-color: #afafaf;
  36.633 +}
    37.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    37.2 +++ b/bugs/templates/slitaz/html/user.forgotten.html	Thu Apr 14 01:13:16 2011 +0200
    37.3 @@ -0,0 +1,44 @@
    37.4 +<!-- dollarId: user.item,v 1.7 2002/08/16 04:29:04 richard Exp dollar-->
    37.5 +<tal:block metal:use-macro="templates/page/macros/icing">
    37.6 +<title metal:fill-slot="head_title" i18n:translate="">Password reset request - <span
    37.7 + i18n:name="tracker" tal:replace="config/TRACKER_NAME" /></title>
    37.8 +<span metal:fill-slot="body_title" tal:omit-tag="python:1"
    37.9 + i18n:translate="">Password reset request</span>
   37.10 +<td class="content" metal:fill-slot="content">
   37.11 +
   37.12 +<p i18n:translate="">You have two options if you have forgotten your password.
   37.13 +If you know the email address you registered with, enter it below.</p>
   37.14 +
   37.15 +<form method="post" onSubmit="return submit_once()"
   37.16 +      tal:attributes="action context/designator">
   37.17 +    <table class="form">
   37.18 +      <tr>
   37.19 +        <th i18n:translate="">Email Address:</th>
   37.20 +        <td><input name="address"></td>
   37.21 +      </tr>
   37.22 +      <tr>
   37.23 +        <td>&nbsp;</td>
   37.24 +        <td>
   37.25 +          <input type="hidden" name="@action" value="passrst">
   37.26 +          <input type="hidden" name="@template" value="forgotten">
   37.27 +          <input type="submit" value="Request password reset"
   37.28 +           i18n:attributes="value">
   37.29 +        </td>
   37.30 +      </tr>
   37.31 +</table>
   37.32 +
   37.33 +<p i18n:translate="">Or, if you know your username, then enter it below.</p>
   37.34 +
   37.35 +<table class="form">
   37.36 + <tr><th i18n:translate="">Username:</th> <td><input name="username"></td> </tr>
   37.37 + <tr><td></td><td><input type="submit" value="Request password reset"
   37.38 +   i18n:attributes="value"></td></tr>
   37.39 +</table>
   37.40 +</form>
   37.41 +
   37.42 +<p i18n:translate="">A confirmation email will be sent to you -
   37.43 +please follow the instructions within it to complete the reset process.</p>
   37.44 +</td>
   37.45 +
   37.46 +</tal:block>
   37.47 +<!-- SHA: 6fdb58c55fd854904ae98906d5935549a221fabf -->
    38.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    38.2 +++ b/bugs/templates/slitaz/html/user.help-search.html	Thu Apr 14 01:13:16 2011 +0200
    38.3 @@ -0,0 +1,86 @@
    38.4 +<html
    38.5 +  tal:define="form request/form/form/value;
    38.6 +  field request/form/property/value"
    38.7 +  >
    38.8 +  <head>
    38.9 +    <title>Search input for user helper</title>
   38.10 +    <script language="Javascript" type="text/javascript"
   38.11 +        tal:content="structure string:<!--
   38.12 +        // this is the name of the field in the original form that we're working on
   38.13 +        form  = parent.opener.document.${form};
   38.14 +        field  = '${field}';
   38.15 +        //-->">
   38.16 +    </script>
   38.17 +    <script type="text/javascript" src="@@file/help_controls.js"></script>
   38.18 +    <link rel="stylesheet" type="text/css" href="@@file/style.css" />
   38.19 +  </head>
   38.20 +  <body onload="parent.submit.url='...'"
   38.21 +    tal:define="
   38.22 +qs request/env/QUERY_STRING;
   38.23 +qs python:'&'.join([a for a in qs.split('&') if not a.startswith('@template=')])"
   38.24 +>
   38.25 +    <pre tal:content="request/env/QUERY_STRING" tal:condition=false />
   38.26 +    <form method="get" name="itemSynopsis"
   38.27 +      target="list"
   38.28 +      tal:attributes="action request/classname"
   38.29 +      tal:define="
   38.30 +      property request/form/property/value;
   38.31 +   cols python:request.columns or 'id username address realname roles'.split();
   38.32 +   sort_on request/sort | nothing;
   38.33 +   sort_desc python:sort_on and request.sort[0][0] == '-';
   38.34 +   sort_on python:sort_on and request.sort[0][1] or 'lastname';
   38.35 +
   38.36 +   search_input templates/page/macros/search_input;
   38.37 +   search_select templates/page/macros/search_select;
   38.38 +   search_select_roles templates/page/macros/search_select_roles;
   38.39 +   required python:[];
   38.40 +   th_label templates/page/macros/th_label;
   38.41 +   ">
   38.42 +   <input type="hidden" name="@template" value="help-list">
   38.43 +   <input type="hidden" name="property" value="" tal:attributes="value property">
   38.44 +   <input type="hidden" name="form" value="" tal:attributes="value request/form/form/value">
   38.45 +   <table>
   38.46 +<tr tal:define="name string:username; label string:Username:">
   38.47 +  <th metal:use-macro="th_label">Name</th>
   38.48 +  <td metal:use-macro="search_input"><input type=text></td>
   38.49 +</tr>
   38.50 +
   38.51 +<tr tal:define="name string:website; label string:Phone number">
   38.52 +  <th metal:use-macro="th_label">Phone</th>
   38.53 +  <td metal:use-macro="search_input"><input type=text></td>
   38.54 +</tr>
   38.55 +
   38.56 +<tr tal:define="name string:roles;
   38.57 +                onchange string:this.form.submit();
   38.58 +                label string:Roles:"
   38.59 +                >
   38.60 +  <th metal:use-macro="th_label">role</th>
   38.61 +  <td metal:use-macro="search_select_roles">
   38.62 +    <select>
   38.63 +      <option value="">jokester</option>
   38.64 +    </select>
   38.65 +  </td>
   38.66 +</tr>
   38.67 +
   38.68 +<tr>
   38.69 +  <td>&nbsp;</td>
   38.70 +  <td>
   38.71 +    <input type="hidden" name="@action" value="search">
   38.72 +    <input type="submit" value="Search" i18n:attributes="value">
   38.73 +    <input type="reset">
   38.74 +    <input type="hidden" value="username,realname,website,scnprofile,roles" name="properties">
   38.75 +    <input type="text" name="@pagesize" id="sp-pagesize" value="25" size="2">
   38.76 +    <label for="sp-pagesize" i18n:translate="">Pagesize</label>
   38.77 +  </td>
   38.78 +</tr>
   38.79 +
   38.80 +   </table>
   38.81 +
   38.82 +</form>
   38.83 +<pre tal:content="request" tal:condition=false />
   38.84 +<script type="text/javascript"><!--
   38.85 +  focus2id('username');
   38.86 +//--></script>
   38.87 +  </body>
   38.88 +</html>
   38.89 +<!-- SHA: df15cb20b84032f72d0530d0717382786668f6a0 -->
    39.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    39.2 +++ b/bugs/templates/slitaz/html/user.help.html	Thu Apr 14 01:13:16 2011 +0200
    39.3 @@ -0,0 +1,50 @@
    39.4 +<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
    39.5 +<html tal:define="property request/form/property/value;
    39.6 +qs request/env/QUERY_STRING;
    39.7 +qs python:'&'.join([a for a in qs.split('&') if not a.startswith('@template=')]);
    39.8 +form request/form/form/value;
    39.9 +field request/form/property/value">
   39.10 +  <head>
   39.11 +      <link rel="stylesheet" type="text/css" href="@@file/style.css" />
   39.12 +      <meta http-equiv="Content-Type"
   39.13 +       tal:attributes="content string:text/html;; charset=${request/client/charset}" />
   39.14 +      <tal:block tal:condition="python:request.form.has_key('property')">
   39.15 +      <title><tal:x i18n:translate=""><tal:x i18n:name="property"
   39.16 +       tal:content="property" i18n:translate="" /> help - <span i18n:name="tracker"
   39.17 +	       tal:replace="config/TRACKER_NAME" /></tal:x></title>
   39.18 +      <script language="Javascript" type="text/javascript"
   39.19 +	      tal:condition=false
   39.20 +          tal:content="structure string:<!--
   39.21 +          // this is the name of the field in the original form that we're working on
   39.22 +          form  = window.opener.document.${form};
   39.23 +          field  = '${field}';
   39.24 +          //-->">
   39.25 +      </script>
   39.26 +      <script src="@@file/help_controls.js"
   39.27 +     tal:condition=false type="text/javascript"><!--
   39.28 +      //--></script>
   39.29 +      </tal:block>
   39.30 +  </head>
   39.31 +<frameset rows="123,*,62">
   39.32 +  <frame src="#" tal:attributes="src string:?@template=help-search&${qs}" name="search">
   39.33 +  <!-- for search results: help-list -->
   39.34 +  <frame
   39.35 +  tal:attributes="src string:?@template=help-empty&${qs}"
   39.36 +  name="list">
   39.37 +  <frame
   39.38 +  tal:attributes="src string:?@template=help-submit&${qs}"
   39.39 +  name="submit">
   39.40 +  <!-- -->
   39.41 +</frameset>
   39.42 +<noframes>
   39.43 +  <body>
   39.44 +<p i18n:translate="">
   39.45 +Your browser is not capable of using frames; you should be redirected immediately,
   39.46 +or visit <a href="#" tal:attributes="href string:?${qs}&template=help-noframes"
   39.47 +i18n:name="link">this link</a>.
   39.48 +</p>
   39.49 +</body>
   39.50 +</noframes>
   39.51 +
   39.52 +</html>
   39.53 +<!-- SHA: d59dff4cb24ac0eee209b10c121299a203170227 -->
    40.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    40.2 +++ b/bugs/templates/slitaz/html/user.index.html	Thu Apr 14 01:13:16 2011 +0200
    40.3 @@ -0,0 +1,51 @@
    40.4 +<!-- dollarId: user.index,v 1.3 2002/07/09 05:29:51 richard Exp dollar-->
    40.5 +<tal:block metal:use-macro="templates/page/macros/icing">
    40.6 +<title metal:fill-slot="head_title" i18n:translate="">User listing - <span
    40.7 + i18n:name="tracker" tal:replace="config/TRACKER_NAME" /></title>
    40.8 +<span metal:fill-slot="body_title" tal:omit-tag="python:1"
    40.9 + i18n:translate="">User listing</span>
   40.10 +<td class="content" metal:fill-slot="content">
   40.11 +
   40.12 +<span tal:condition="python:not (context.is_view_ok()
   40.13 + or request.user.hasRole('Anonymous'))"
   40.14 + i18n:translate="">You are not allowed to view this page.</span>
   40.15 +
   40.16 +<span tal:condition="python:not context.is_view_ok()
   40.17 + and request.user.hasRole('Anonymous')"
   40.18 + i18n:translate="">Please login with your username and password.</span>
   40.19 +
   40.20 +<table width="100%" tal:condition="context/is_view_ok" class="list">
   40.21 +<tr>
   40.22 + <th i18n:translate="">Username</th>
   40.23 + <th i18n:translate="">Real name</th>
   40.24 + <th i18n:translate="">Email address</th>
   40.25 + <th i18n:translate="">Website</th>
   40.26 + <th tal:condition="context/is_edit_ok" i18n:translate="">Retire</th>
   40.27 +</tr>
   40.28 +<tal:block repeat="user context/list">
   40.29 +<tr tal:attributes="class python:['normal', 'alt'][repeat['user'].index%6/3]">
   40.30 + <td>
   40.31 +  <a tal:attributes="href string:user${user/id}"
   40.32 +     tal:content="user/username">username</a>
   40.33 + </td>
   40.34 + <td tal:content="python:user.realname.plain() or default">&nbsp;</td>
   40.35 + <td tal:content="python:user.address.email() or default">&nbsp;</td>
   40.36 + <td>
   40.37 +  <a tal:attributes="href python:user.website.plain() or default"
   40.38 +     tal:content="user/website">website</a>
   40.39 + </td>
   40.40 + <td tal:condition="context/is_retire_ok">
   40.41 +    <form style="padding:0" method="post"
   40.42 +          tal:attributes="action string:user${user/id}">
   40.43 +     <input type="hidden" name="@template" value="index">
   40.44 +     <input type="hidden" name="@action" value="retire">
   40.45 +     <input type="submit" value="retire" i18n:attributes="value">
   40.46 +    </form>
   40.47 + </td>
   40.48 +</tr>
   40.49 +</tal:block>
   40.50 +</table>
   40.51 +</td>
   40.52 +
   40.53 +</tal:block>
   40.54 +<!-- SHA: 6d282dc45e45caf1d19d8ded6c5c57554be9c1af -->
    41.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    41.2 +++ b/bugs/templates/slitaz/html/user.item.html	Thu Apr 14 01:13:16 2011 +0200
    41.3 @@ -0,0 +1,165 @@
    41.4 +<!-- dollarId: user.item,v 1.7 2002/08/16 04:29:04 richard Exp dollar-->
    41.5 +<tal:doc metal:use-macro="templates/page/macros/icing"
    41.6 +define="edit_ok context/is_edit_ok"
    41.7 +>
    41.8 +<title metal:fill-slot="head_title">
    41.9 +<tal:if condition="context/id" i18n:translate=""
   41.10 + >User <tal:x content="context/id" i18n:name="id"
   41.11 + />: <tal:x content="context/username" i18n:name="title"
   41.12 + /> - <tal:x content="config/TRACKER_NAME" i18n:name="tracker"
   41.13 +/></tal:if>
   41.14 +<tal:if condition="not:context/id" i18n:translate=""
   41.15 + >New User - <span tal:replace="config/TRACKER_NAME" i18n:name="tracker"
   41.16 +/></tal:if>
   41.17 +</title>
   41.18 +<metal:slot fill-slot="more-javascript">
   41.19 +<script metal:use-macro="templates/page/macros/user_utils"></script>
   41.20 +<script type="text/javascript" src="@@file/help_controls.js"></script>
   41.21 +</metal:slot>
   41.22 +<tal:block metal:fill-slot="body_title"
   41.23 +  define="edit_ok context/is_edit_ok">
   41.24 + <span tal:condition="python: not (context.id or edit_ok)"
   41.25 +  tal:omit-tag="python:1" i18n:translate="">New User</span>
   41.26 + <span tal:condition="python: not context.id and edit_ok"
   41.27 +  tal:omit-tag="python:1" i18n:translate="">New User Editing</span>
   41.28 + <span tal:condition="python: context.id and not edit_ok"
   41.29 +  tal:omit-tag="python:1" i18n:translate="">User<tal:x
   41.30 +  replace="context/id" i18n:name="id" /></span>
   41.31 + <span tal:condition="python: context.id and edit_ok"
   41.32 +  tal:omit-tag="python:1" i18n:translate="">User<tal:x
   41.33 +  replace="context/id" i18n:name="id" /> Editing</span>
   41.34 +</tal:block>
   41.35 +
   41.36 +<td class="content" metal:fill-slot="content">
   41.37 +
   41.38 +<p tal:condition="python:not (context.is_view_ok()
   41.39 + or request.user.hasRole('Anonymous'))" i18n:translate="">
   41.40 + You are not allowed to view this page.</p>
   41.41 +
   41.42 +<p tal:condition="python:not context.is_view_ok()
   41.43 + and request.user.hasRole('Anonymous')" i18n:translate="">
   41.44 + Please login with your username and password.</p>
   41.45 +
   41.46 +<div tal:condition="context/is_view_ok">
   41.47 +
   41.48 +<form method="post"
   41.49 +      name="itemSynopsis"
   41.50 +      tal:define="required python:'username address'.split()"
   41.51 +      enctype="multipart/form-data"
   41.52 +      tal:attributes="action context/designator;
   41.53 +      onSubmit python:'return checkRequiredFields(\'%s\')'%'\', \''.join(required);
   41.54 +      ">
   41.55 +<table class="form" tal:define="
   41.56 +  th_label templates/page/macros/th_label;
   41.57 +  src_input templates/page/macros/user_src_input;
   41.58 +  normal_input templates/page/macros/user_normal_input;
   41.59 +  pw_input templates/page/macros/user_pw_input;
   41.60 +  confirm_input templates/page/macros/user_confirm_input;
   41.61 +  edit_ok context/is_edit_ok;
   41.62 +  ">
   41.63 + <tr tal:define="name string:realname; label string:Name; value context/realname; edit_ok edit_ok">
   41.64 +  <th metal:use-macro="th_label">Name</th>
   41.65 +  <td><input name="realname" metal:use-macro="src_input"></td>
   41.66 + </tr>
   41.67 + <tr tal:define="name string:username; label string:Login Name; value context/username">
   41.68 +   <th metal:use-macro="th_label">Login Name</th>
   41.69 +   <td><input metal:use-macro="src_input"></td>
   41.70 + </tr>
   41.71 + <tal:if condition="edit_ok">
   41.72 + <tr tal:define="name string:password; label string:Login Password">
   41.73 +  <th metal:use-macro="th_label">Login Password</th>
   41.74 +  <td><input metal:use-macro="pw_input" type="password"></td>
   41.75 + </tr>
   41.76 + <tr tal:define="name string:password; label string:Confirm Password">
   41.77 +  <th metal:use-macro="th_label">Confirm Password</th>
   41.78 +  <td><input metal:use-macro="confirm_input" type="password"></td>
   41.79 + </tr>
   41.80 + </tal:if>
   41.81 + <tal:if condition="python:request.user.hasPermission('Web Roles')">
   41.82 + <tr tal:define="name string:roles; label string:Roles;">
   41.83 +  <th><label for="roles" i18n:translate="">Roles</label></th>
   41.84 +  <td tal:define="gips context/id">
   41.85 +    <tal:subif condition=gips define="value context/roles">
   41.86 +      <input metal:use-macro="normal_input">
   41.87 +    </tal:subif>
   41.88 +    <tal:subif condition="not:gips" define="value db/config/NEW_WEB_USER_ROLES">
   41.89 +      <input metal:use-macro="normal_input">
   41.90 +    </tal:subif>
   41.91 +   <tal:block i18n:translate="">(to give the user more than one role,
   41.92 +    enter a comma,separated,list)</tal:block>
   41.93 +  </td>
   41.94 + </tr>
   41.95 + </tal:if>
   41.96 +
   41.97 + <tr tal:define="name string:website; label string:Website; value context/website">
   41.98 +  <th metal:use-macro="th_label">Website</th>
   41.99 +  <td><input name="website" metal:use-macro="normal_input"></td>
  41.100 + </tr>
  41.101 +
  41.102 + <tr tal:condition="python:edit_ok or context.timezone"
  41.103 +     tal:define="name string:timezone; label string:Timezone; value context/timezone">
  41.104 +  <th metal:use-macro="th_label">Timezone</th>
  41.105 +  <td><input name="timezone" metal:use-macro="normal_input">
  41.106 +   <tal:block tal:condition="edit_ok" i18n:translate="">(this is a numeric hour offset, the default is
  41.107 +    <span tal:replace="db/config/DEFAULT_TIMEZONE" i18n:name="zone"
  41.108 +    />)</tal:block>
  41.109 +  </td>
  41.110 + </tr>
  41.111 +
  41.112 + <tr tal:define="name string:address; label string:E-mail address; value context/address">
  41.113 +  <th metal:use-macro="th_label">E-mail address</th>
  41.114 +  <td tal:define="mailto python:context.address.field(id='address');
  41.115 +	  mklink python:mailto and not edit_ok">
  41.116 +      <a href="mailto:calvin@the-z.org"
  41.117 +		  tal:attributes="href string:mailto:$value"
  41.118 +		  tal:content="value"
  41.119 +          tal:condition="python:mklink">calvin@the-z.org</a>
  41.120 +      <tal:if condition=edit_ok>
  41.121 +      <input metal:use-macro="src_input" value="calvin@the-z.org">
  41.122 +      </tal:if>
  41.123 +      &nbsp;
  41.124 +  </td>
  41.125 + </tr>
  41.126 +
  41.127 + <tr>
  41.128 +  <th><label for="alternate_addresses" i18n:translate="">Alternate E-mail addresses<br>One address per line</label></th>
  41.129 +  <td>
  41.130 +    <textarea rows=5 cols=40 tal:replace="structure context/alternate_addresses/multiline">nobody@nowhere.org
  41.131 +anybody@everywhere.net
  41.132 +(alternate_addresses)
  41.133 +    </textarea>
  41.134 +  </td>
  41.135 + </tr>
  41.136 +
  41.137 + <tr tal:condition="edit_ok">
  41.138 +  <td>
  41.139 +   &nbsp;
  41.140 +   <input type="hidden" name="@template" value="item">
  41.141 +   <input type="hidden" name="@required" value="username,address"
  41.142 +          tal:attributes="value python:','.join(required)">
  41.143 +  </td>
  41.144 +  <td><input type="submit" value="save" tal:replace="structure context/submit"><!--submit button here-->
  41.145 +    <input type=reset>
  41.146 +  </td>
  41.147 + </tr>
  41.148 +</table>
  41.149 +</form>
  41.150 +
  41.151 +<tal:block tal:condition="not:context/id" i18n:translate="">
  41.152 +<table class="form">
  41.153 +<tr>
  41.154 + <td>Note:&nbsp;</td>
  41.155 + <th class="required">highlighted</th>
  41.156 + <td>&nbsp;fields are required.</td>
  41.157 +</tr>
  41.158 +</table>
  41.159 +</tal:block>
  41.160 +
  41.161 +<tal:block tal:condition="context/id" tal:replace="structure context/history" />
  41.162 +
  41.163 +</div>
  41.164 +
  41.165 +</td>
  41.166 +
  41.167 +</tal:doc>
  41.168 +<!-- SHA: bfc3a0fd9a3a54b3b1d1d7bfeb43191237af5184 -->
    42.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    42.2 +++ b/bugs/templates/slitaz/html/user.register.html	Thu Apr 14 01:13:16 2011 +0200
    42.3 @@ -0,0 +1,78 @@
    42.4 +<!-- dollarId: user.item,v 1.7 2002/08/16 04:29:04 richard Exp dollar-->
    42.5 +<tal:block metal:use-macro="templates/page/macros/icing">
    42.6 +<title metal:fill-slot="head_title"
    42.7 + i18n:translate="">Registering with <span i18n:name="tracker"
    42.8 + tal:replace="db/config/TRACKER_NAME" /></title>
    42.9 +<span metal:fill-slot="body_title" tal:omit-tag="python:1"
   42.10 + i18n:translate="">Registering with <span i18n:name="tracker"
   42.11 + tal:replace="db/config/TRACKER_NAME" /></span>
   42.12 +<td class="content" metal:fill-slot="content">
   42.13 +
   42.14 +<form method="post" onSubmit="return submit_once()"
   42.15 +      enctype="multipart/form-data"
   42.16 +      tal:attributes="action context/designator">
   42.17 +
   42.18 +<table class="form">
   42.19 + <tr>
   42.20 +  <th i18n:translate="">Name</th>
   42.21 +  <td tal:content="structure context/realname/field">realname</td>
   42.22 + </tr>
   42.23 + <tr>
   42.24 +  <th class="required" i18n:translate="">Login Name</th>
   42.25 +  <td tal:content="structure context/username/field">username</td>
   42.26 + </tr>
   42.27 + <tr>
   42.28 +  <th class="required" i18n:translate="">Login Password</th>
   42.29 +  <td tal:content="structure context/password/field">password</td>
   42.30 + </tr>
   42.31 + <tr>
   42.32 +  <th class="required" i18n:translate="">Confirm Password</th>
   42.33 +  <td tal:content="structure context/password/confirm">password</td>
   42.34 + </tr>
   42.35 + <tr tal:condition="python:request.user.hasPermission('Web Roles')">
   42.36 +  <th i18n:translate="">Roles</th>
   42.37 +  <td tal:condition="exists:item"
   42.38 +      tal:content="structure context/roles/field">roles</td>
   42.39 +  <td tal:condition="not:exists:item">
   42.40 +   <input name="roles" tal:attributes="value db/config/NEW_WEB_USER_ROLES">
   42.41 +  </td>
   42.42 + </tr>
   42.43 + <tr>
   42.44 +  <th i18n:translate="">Website</th>
   42.45 +  <td tal:content="structure context/website/field">website</td>
   42.46 + </tr>
   42.47 + <tr>
   42.48 +  <th class="required" i18n:translate="">E-mail address</th>
   42.49 +  <td tal:content="structure context/address/field">address</td>
   42.50 + </tr>
   42.51 + <tr>
   42.52 +  <th i18n:translate="">Alternate E-mail addresses<br>One address per line</th>
   42.53 +  <td tal:content="structure context/alternate_addresses/multiline">alternate_addresses</td>
   42.54 + </tr>
   42.55 +
   42.56 + <tr>
   42.57 +  <td>&nbsp;</td>
   42.58 +  <td>
   42.59 +   <input type="hidden" name="@template" value="register">
   42.60 +   <input type="hidden" name="@required" value="username,password,address">
   42.61 +   <input type="hidden" name="@action" value="register">
   42.62 +   <input type="submit" name="submit" value="Register" i18n:attributes="value">
   42.63 +  </td>
   42.64 + </tr>
   42.65 +</table>
   42.66 +</form>
   42.67 +
   42.68 +<tal:block tal:condition="not:context/id" i18n:translate="">
   42.69 +<table class="form">
   42.70 +<tr>
   42.71 + <td>Note:&nbsp;</td>
   42.72 + <th class="required">highlighted</th>
   42.73 + <td>&nbsp;fields are required.</td>
   42.74 +</tr>
   42.75 +</table>
   42.76 +</tal:block>
   42.77 +
   42.78 +</td>
   42.79 +
   42.80 +</tal:block>
   42.81 +<!-- SHA: ed7a2465033194eb71fa79431b028150c23be650 -->
    43.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    43.2 +++ b/bugs/templates/slitaz/html/user.rego_progress.html	Thu Apr 14 01:13:16 2011 +0200
    43.3 @@ -0,0 +1,17 @@
    43.4 +<!-- dollarId: issue.index,v 1.2 2001/07/29 04:07:37 richard Exp dollar-->
    43.5 +<tal:block metal:use-macro="templates/page/macros/icing">
    43.6 +<title metal:fill-slot="head_title"
    43.7 + i18n:translate="">Registration in progress - <span i18n:name="tracker"
    43.8 + tal:replace="config/TRACKER_NAME" /></title>
    43.9 +<span metal:fill-slot="body_title" tal:omit-tag="python:1"
   43.10 + i18n:translate="">Registration in progress...</span>
   43.11 +<td class="content" metal:fill-slot="content">
   43.12 +
   43.13 +<p i18n:translate="">You will shortly receive an email
   43.14 +to confirm your registration. To complete the registration process,
   43.15 +visit the link indicated in the email.
   43.16 +</p>
   43.17 +
   43.18 +</td>
   43.19 +</tal:block>
   43.20 +<!-- SHA: c2f389db861a4e0d20b41e5ff88120270862f609 -->
    44.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    44.2 +++ b/bugs/templates/slitaz/html/user_utils.js	Thu Apr 14 01:13:16 2011 +0200
    44.3 @@ -0,0 +1,114 @@
    44.4 +// User Editing Utilities
    44.5 +
    44.6 +/**
    44.7 + * for new users:
    44.8 + * Depending on the input field which calls it, takes the value
    44.9 + * and dispatches it to certain other input fields:
   44.10 + *
   44.11 + * address
   44.12 + *  +-> username
   44.13 + *  |    `-> realname
   44.14 + *  `-> scnprofile
   44.15 + */
   44.16 +function split_name(that) {
   44.17 +    var raw = that.value
   44.18 +    var val = trim(raw)
   44.19 +    if (val == '') {
   44.20 +        return
   44.21 +    }
   44.22 +    var username=''
   44.23 +    var realname=''
   44.24 +    var address=''
   44.25 +    switch (that.name) {
   44.26 +        case 'address':
   44.27 +            address=val
   44.28 +            break
   44.29 +        case 'username':
   44.30 +            username=val
   44.31 +            break
   44.32 +        case 'realname':
   44.33 +            realname=val
   44.34 +            break
   44.35 +        case 'firstname':
   44.36 +        case 'lastname':
   44.37 +           return
   44.38 +        default:
   44.39 +            alert('Ooops - unknown name field '+that.name+'!')
   44.40 +            return
   44.41 +    }
   44.42 +    var the_form = that.form;
   44.43 +
   44.44 +    function field_empty(name) {
   44.45 +        return the_form[name].value == ''
   44.46 +    }
   44.47 +
   44.48 +    // no break statements - on purpose!
   44.49 +    switch (that.name) {
   44.50 +        case 'address':
   44.51 +            var split1 = address.split('@')
   44.52 +            if (field_empty('username')) {
   44.53 +                username = split1[0]
   44.54 +                the_form.username.value = username
   44.55 +            }
   44.56 +            if (field_empty('scnprofile')) {
   44.57 +                the_form.scnprofile.value = default_scnprofile(split1[1])
   44.58 +            }
   44.59 +        case 'username':
   44.60 +            if (field_empty('realname')) {
   44.61 +                realname = Cap(username.split('.').join(' '))
   44.62 +                the_form.realname.value = realname
   44.63 +            }
   44.64 +        case 'realname':
   44.65 +            if (field_empty('username')) {
   44.66 +                username = Cap(realname.replace(' ', '.'))
   44.67 +                the_form.username.value = username
   44.68 +            }
   44.69 +            if (the_form.firstname && the_form.lastname) {
   44.70 +                var split2 = realname.split(' ')
   44.71 +                var firstname='', lastname=''
   44.72 +                firstname = split2[0]
   44.73 +                lastname = split2.slice(1).join(' ')
   44.74 +                if (field_empty('firstname')) {
   44.75 +                    the_form.firstname.value = firstname
   44.76 +                }
   44.77 +                if (field_empty('lastname')) {
   44.78 +                    the_form.lastname.value = lastname
   44.79 +                }
   44.80 +            }
   44.81 +    }
   44.82 +}
   44.83 +
   44.84 +function SubCap(str) {
   44.85 +    switch (str) {
   44.86 +        case 'de': case 'do': case 'da':
   44.87 +        case 'du': case 'von':
   44.88 +            return str;
   44.89 +    }
   44.90 +    if (str.toLowerCase().slice(0,2) == 'mc') {
   44.91 +        return 'Mc'+str.slice(2,3).toUpperCase()+str.slice(3).toLowerCase()
   44.92 +    }
   44.93 +    return str.slice(0,1).toUpperCase()+str.slice(1).toLowerCase()
   44.94 +}
   44.95 +
   44.96 +function Cap(str) {
   44.97 +    var liz = str.split(' ')
   44.98 +    for (var i=0; i<liz.length; i++) {
   44.99 +        liz[i] = SubCap(liz[i])
  44.100 +    }
  44.101 +    return liz.join(' ')
  44.102 +}
  44.103 +
  44.104 +/**
  44.105 + * Takes a domain name (behind the @ part of an email address)
  44.106 + * Customise this to handle the mail domains you're interested in 
  44.107 + */
  44.108 +function default_scnprofile(orga) {
  44.109 +    switch (orga.toLowerCase()) {
  44.110 +        case 'gmx':
  44.111 +        case 'yahoo':
  44.112 +            return ''
  44.113 +        default:
  44.114 +            return orga
  44.115 +    }
  44.116 +}
  44.117 +
    45.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    45.2 +++ b/bugs/templates/slitaz/initial_data.py	Thu Apr 14 01:13:16 2011 +0200
    45.3 @@ -0,0 +1,29 @@
    45.4 +#
    45.5 +# TRACKER INITIAL PRIORITY AND STATUS VALUES
    45.6 +#
    45.7 +pri = db.getclass('priority')
    45.8 +pri.create(name=''"critical", order="1")
    45.9 +pri.create(name=''"standard", order="2")
   45.10 +pri.create(name=''"feature", order="3")
   45.11 +pri.create(name=''"task", order="4")
   45.12 +
   45.13 +stat = db.getclass('status')
   45.14 +stat.create(name=''"unread", order="1")
   45.15 +stat.create(name=''"deferred", order="2")
   45.16 +stat.create(name=''"chatting", order="3")
   45.17 +stat.create(name=''"in-progress", order="4")
   45.18 +stat.create(name=''"feedback", order="5")
   45.19 +stat.create(name=''"resolved", order="6")
   45.20 +
   45.21 +# create the two default users
   45.22 +user = db.getclass('user')
   45.23 +user.create(username="pankso", password=adminpw,
   45.24 +    address=admin_email, roles='Admin')
   45.25 +user.create(username="anonymous", roles='Anonymous')
   45.26 +
   45.27 +# add any additional database creation steps here - but only if you
   45.28 +# haven't initialised the database with the admin "initialise" command
   45.29 +
   45.30 +
   45.31 +# vim: set filetype=python sts=4 sw=4 et si
   45.32 +#SHA: 54e44ed654b0ae4a076ed2d948bbbaaa79590918
    46.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    46.2 +++ b/bugs/templates/slitaz/schema.py	Thu Apr 14 01:13:16 2011 +0200
    46.3 @@ -0,0 +1,176 @@
    46.4 +
    46.5 +#
    46.6 +# TRACKER SCHEMA
    46.7 +#
    46.8 +
    46.9 +# Class automatically gets these properties:
   46.10 +#   creation = Date()
   46.11 +#   activity = Date()
   46.12 +#   creator = Link('user')
   46.13 +#   actor = Link('user')
   46.14 +
   46.15 +# Priorities
   46.16 +pri = Class(db, "priority",
   46.17 +                name=String(),
   46.18 +                order=Number())
   46.19 +pri.setkey("name")
   46.20 +
   46.21 +# Statuses
   46.22 +stat = Class(db, "status",
   46.23 +                name=String(),
   46.24 +                order=Number())
   46.25 +stat.setkey("name")
   46.26 +
   46.27 +# Keywords
   46.28 +keyword = Class(db, "keyword",
   46.29 +                name=String())
   46.30 +keyword.setkey("name")
   46.31 +
   46.32 +# User-defined saved searches
   46.33 +query = Class(db, "query",
   46.34 +                klass=String(),
   46.35 +                name=String(),
   46.36 +                url=String(),
   46.37 +                private_for=Link('user'))
   46.38 +
   46.39 +# add any additional database schema configuration here
   46.40 +
   46.41 +user = Class(db, "user",
   46.42 +                username=String(),
   46.43 +                password=Password(),
   46.44 +                address=String(),
   46.45 +                realname=String(),
   46.46 +                website=String(),
   46.47 +                alternate_addresses=String(),
   46.48 +                queries=Multilink('query'),
   46.49 +                roles=String(),     # comma-separated string of Role names
   46.50 +                timezone=String())
   46.51 +user.setkey("username")
   46.52 +db.security.addPermission(name='Register', klass='user',
   46.53 +                          description='User is allowed to register new user')
   46.54 +
   46.55 +# FileClass automatically gets this property in addition to the Class ones:
   46.56 +#   content = String()    [saved to disk in <tracker home>/db/files/]
   46.57 +#   type = String()       [MIME type of the content, default 'text/plain']
   46.58 +msg = FileClass(db, "msg",
   46.59 +                author=Link("user", do_journal='no'),
   46.60 +                recipients=Multilink("user", do_journal='no'),
   46.61 +                date=Date(),
   46.62 +                summary=String(),
   46.63 +                files=Multilink("file"),
   46.64 +                messageid=String(),
   46.65 +                inreplyto=String())
   46.66 +
   46.67 +file = FileClass(db, "file",
   46.68 +                name=String())
   46.69 +
   46.70 +# IssueClass automatically gets these properties in addition to the Class ones:
   46.71 +#   title = String()
   46.72 +#   messages = Multilink("msg")
   46.73 +#   files = Multilink("file")
   46.74 +#   nosy = Multilink("user")
   46.75 +#   superseder = Multilink("issue")
   46.76 +issue = IssueClass(db, "issue",
   46.77 +                assignedto=Link("user"),
   46.78 +                keyword=Multilink("keyword"),
   46.79 +                priority=Link("priority"),
   46.80 +                status=Link("status"))
   46.81 +
   46.82 +#
   46.83 +# TRACKER SECURITY SETTINGS
   46.84 +#
   46.85 +# See the configuration and customisation document for information
   46.86 +# about security setup.
   46.87 +
   46.88 +#
   46.89 +# REGULAR USERS
   46.90 +#
   46.91 +# Give the regular users access to the web and email interface
   46.92 +db.security.addPermissionToRole('User', 'Web Access')
   46.93 +db.security.addPermissionToRole('User', 'Email Access')
   46.94 +
   46.95 +# Assign the access and edit Permissions for issue, file and message
   46.96 +# to regular users now
   46.97 +for cl in 'issue', 'file', 'msg', 'keyword':
   46.98 +    db.security.addPermissionToRole('User', 'View', cl)
   46.99 +    db.security.addPermissionToRole('User', 'Edit', cl)
  46.100 +    db.security.addPermissionToRole('User', 'Create', cl)
  46.101 +for cl in 'priority', 'status':
  46.102 +    db.security.addPermissionToRole('User', 'View', cl)
  46.103 +
  46.104 +# May users view other user information? Comment these lines out
  46.105 +# if you don't want them to
  46.106 +db.security.addPermissionToRole('User', 'View', 'user')
  46.107 +
  46.108 +# Users should be able to edit their own details -- this permission is
  46.109 +# limited to only the situation where the Viewed or Edited item is their own.
  46.110 +def own_record(db, userid, itemid):
  46.111 +    '''Determine whether the userid matches the item being accessed.'''
  46.112 +    return userid == itemid
  46.113 +p = db.security.addPermission(name='View', klass='user', check=own_record,
  46.114 +    description="User is allowed to view their own user details")
  46.115 +db.security.addPermissionToRole('User', p)
  46.116 +p = db.security.addPermission(name='Edit', klass='user', check=own_record,
  46.117 +    properties=('username', 'password', 'address', 'realname', 'website',
  46.118 +        'alternate_addresses', 'queries', 'timezone'),
  46.119 +    description="User is allowed to edit their own user details")
  46.120 +db.security.addPermissionToRole('User', p)
  46.121 +
  46.122 +# Users should be able to edit and view their own queries. They should also
  46.123 +# be able to view any marked as not private. They should not be able to
  46.124 +# edit others' queries, even if they're not private
  46.125 +def view_query(db, userid, itemid):
  46.126 +    private_for = db.query.get(itemid, 'private_for')
  46.127 +    if not private_for: return True
  46.128 +    return userid == private_for
  46.129 +def edit_query(db, userid, itemid):
  46.130 +    return userid == db.query.get(itemid, 'creator')
  46.131 +p = db.security.addPermission(name='View', klass='query', check=view_query,
  46.132 +    description="User is allowed to view their own and public queries")
  46.133 +db.security.addPermissionToRole('User', p)
  46.134 +p = db.security.addPermission(name='Edit', klass='query', check=edit_query,
  46.135 +    description="User is allowed to edit their queries")
  46.136 +db.security.addPermissionToRole('User', p)
  46.137 +p = db.security.addPermission(name='Retire', klass='query', check=edit_query,
  46.138 +    description="User is allowed to retire their queries")
  46.139 +db.security.addPermissionToRole('User', p)
  46.140 +p = db.security.addPermission(name='Create', klass='query',
  46.141 +    description="User is allowed to create queries")
  46.142 +db.security.addPermissionToRole('User', p)
  46.143 +
  46.144 +
  46.145 +#
  46.146 +# ANONYMOUS USER PERMISSIONS
  46.147 +#
  46.148 +# Let anonymous users access the web interface. Note that almost all
  46.149 +# trackers will need this Permission. The only situation where it's not
  46.150 +# required is in a tracker that uses an HTTP Basic Authenticated front-end.
  46.151 +db.security.addPermissionToRole('Anonymous', 'Web Access')
  46.152 +
  46.153 +# Let anonymous users access the email interface (note that this implies
  46.154 +# that they will be registered automatically, hence they will need the
  46.155 +# "Create" user Permission below)
  46.156 +# This is disabled by default to stop spam from auto-registering users on
  46.157 +# public trackers.
  46.158 +#db.security.addPermissionToRole('Anonymous', 'Email Access')
  46.159 +
  46.160 +# Assign the appropriate permissions to the anonymous user's Anonymous
  46.161 +# Role. Choices here are:
  46.162 +# - Allow anonymous users to register
  46.163 +db.security.addPermissionToRole('Anonymous', 'Register', 'user')
  46.164 +
  46.165 +# Allow anonymous users access to view issues (and the related, linked
  46.166 +# information)
  46.167 +for cl in 'issue', 'file', 'msg', 'keyword', 'priority', 'status':
  46.168 +    db.security.addPermissionToRole('Anonymous', 'View', cl)
  46.169 +
  46.170 +# [OPTIONAL]
  46.171 +# Allow anonymous users access to create or edit "issue" items (and the
  46.172 +# related file and message items)
  46.173 +#for cl in 'issue', 'file', 'msg':
  46.174 +#   db.security.addPermissionToRole('Anonymous', 'Create', cl)
  46.175 +#   db.security.addPermissionToRole('Anonymous', 'Edit', cl)
  46.176 +
  46.177 +
  46.178 +# vim: set filetype=python sts=4 sw=4 et si :
  46.179 +#SHA: d935a2b51c5922fb4e7a5fefc5ed70ef5fcbcac8