This repository has been archived on 2023-02-21. You can view files and clone it, but cannot push or open issues or pull requests.
glasnost/shared/common/xhtmlgenerator.py

469 lines
16 KiB
Python

# -*- coding: iso-8859-15 -*-
# Glasnost
# By: Odile Bénassy <obenassy@entrouvert.com>
# Romain Chantereau <rchantereau@entrouvert.com>
# Nicolas Clapiès <nclapies@easter-eggs.org>
# Pierre-Antoine Dejace <padejace@entrouvert.be>
# Thierry Dulieu <tdulieu@easter-eggs.com>
# Florent Monnier <monnier@codelutin.com>
# Cédric Musso <cmusso@easter-eggs.org>
# Frédéric Péters <fpeters@entrouvert.be>
# Benjamin Poussin <poussin@codelutin.com>
# Emmanuel Raviart <eraviart@entrouvert.com>
# Sébastien Régnier <regnier@codelutin.com>
# Emmanuel Saracco <esaracco@easter-eggs.com>
#
# Copyright (C) 2000, 2001 Easter-eggs & Emmanuel Raviart
# Copyright (C) 2002 Odile Bénassy, Code Lutin, Thierry Dulieu, Easter-eggs,
# Entr'ouvert, Frédéric Péters, Benjamin Poussin, Emmanuel Raviart,
# Emmanuel Saracco & Théridion
# Copyright (C) 2003 Odile Bénassy, Romain Chantereau, Nicolas Clapiès,
# Code Lutin, Pierre-Antoine Dejace, Thierry Dulieu, Easter-eggs,
# Entr'ouvert, Florent Monnier, Cédric Musso, Ouvaton, Frédéric Péters,
# Benjamin Poussin, Rodolphe Quiédeville, Emmanuel Raviart, Sébastien
# Régnier, Emmanuel Saracco, Théridion & Vecam
#
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 2
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
__doc__ = """Glasnost XHTML Generator"""
__version__ = '$Revision$'[11:-2]
import base64
import urlparse
from tools import extractApplicationHostName, extractApplicationPort
import context
from XhtmlGenerator import *
buttonLabels = {
'about': N_('About Glasnost'),
'abstain': N_('Abstain'),
'add': N_('Add'),
'add-article': N_('Add Article'),
'add-candidate': N_('Add Candidate'),
'apply': N_('Apply'),
'back': N_('Back'),
'cancel': N_('Cancel'),
'change-password': N_('Change Password'),
'change-translation': N_('Change Translation'),
'clone': N_('Duplicate'),
'compute': N_('Compute'),
'create': N_('Create'),
'delete': N_('Delete'),
'diff': N_('Differences'),
'download': N_('Download Glasnost'),
'edit': N_('Edit'),
'edit-arguments': N_('Edit Arguments'),
'evaluate': N_('Evaluate'),
'every-article': N_('Every Article'),
'find': N_('Find'),
'history': N_('History'),
'implement': N_('New Implementation'),
'license': N_('Read the License'),
'login': N_('Login'),
'logout': N_('Exit'),
'modify': N_('Modify'),
'next': N_('Next'),
'new': N_('New'),
'new-account': N_('New Account'),
'ok': N_('OK'),
'pester-abstentionnists': N_('Pester Absentionnists'),
'post-comment': N_('Post a Comment'),
'post-reply': N_('Reply'),
'prefs': N_('Preferences'),
'pretion': N_('Pretion'),
'preview': N_('Preview'),
'propose': N_('Submit For Evaluation'),
'refuse': N_('Refuse'),
'send-by-email': N_('Send by Email'),
'send-password-by-email': N_('Send Password by Email'),
'settings': N_('Settings'),
'spell': N_('Spell Check'),
'source': N_('Source'),
'translate': N_('Translate'),
'update-translation': N_('Update Translation'),
'use': N_('Use'),
'validate': N_('Validate'),
'version': N_('Version'),
'view-definition': N_('Definition'),
'view-list': N_('List'),
'view-type': N_('Type'),
'view-utilization': N_('Utilization'),
'view-widget': N_('Widget'),
'vote': N_('Vote '),
'vote-blank': N_('Vote Blank'),
}
class accountingCell(td):
def __init__(self, text = '', **attributes):
td.__init__(self, **attributes)
self.append(text)
self.text = text
def getText(self):
return self.text
class accountingTable(table):
def __init__(self, top = '', row=[]):
self.top = top
self.row = row
def getAsXml(self):
numCols = max(1, len(self.row))
topTd = td(colspan = numCols)
topTd.append([nbsp] * 4)
topTd.append(self.top)
topTr = tr(topTd)
rowTr = tr(self.row)
return table(topTr, rowTr).getAsXml()
class buttonInForm:
key = None
name = None
def __init__(self, key, name):
self.key = key
self.name = name
def getAsXml(self, **keywords):
if buttonLabels.has_key(self.key):
text = _(buttonLabels[self.key]).strip()
else:
text = self.key
trueTag = input(_class = 'button', name = self.name,
type = 'submit', value = text)
# The following solutions don't work with Internet Explorer.
## trueTag = button(_class = 'button', name = 'button',
## type = 'submit', value = self.name)(text)
## trueTag = button(_class = 'button', name = self.name,
## type = 'submit', value = self.name)(text)
return trueTag.getAsXml(**keywords)
class buttonPopup:
href = None
key = None
def __init__(self, key, href):
self.key = key
self.href = href
def getAsXml(self, **keywords):
if buttonLabels.has_key(self.key):
text = _(buttonLabels[self.key]).strip()
else:
text = self.key
jScript = "window.open('%s','comment','toolbar=no,location=no,"\
"directories=no,status=no,menubar=no,scrollbars=yes,"\
"width=566,height=333'); return false;" % self.href
trueTag = a(_class = 'button', href = self.href, OnClick=jScript)(text)
return trueTag.getAsXml(**keywords)
class buttonStandalone:
href = None
key = None
def __init__(self, key, href):
self.key = key
self.href = href
def getAsXml(self, **keywords):
if buttonLabels.has_key(self.key):
text = _(buttonLabels[self.key]).strip()
else:
text = self.key
trueTag = a(_class = 'button', href = self.href)(text)
return trueTag.getAsXml(**keywords)
def objectHypertextLabel(objectId):
import faults
from glasnost.proxy.tools import getObjectLabelTranslated
if not objectId:
return ''
try:
label = getObjectLabelTranslated(
objectId, context.getVar('readLanguages'))
except faults.MissingItem:
return span(_class = 'deleted')(_('Missing Object (%s)') % objectId)
return a(href = glasnostUrl(objectId))(label)
class smallAccountingTable(table):
def __init__(self, side, amount=0):
assert (side=='debit' or side=='credit')
self.amount = str(amount)
self.side = side
def getAsXml(self, parent = None, indent = 0, **keywords):
width = 12
td1 = td(width=width)(self.amount)
td2 = td(width=width)(nbsp)
r = tr()
if self.side == 'debit':
r.append(td1)
r.append(td2)
else:
r.append(td2)
r.append(td1)
return table(r).getAsXml()
_httpUrl = httpUrl
class httpUrl(httpUrl):
pathPrefix = None
def __init__(self, protocol = None, hostNameAndPort = None,
hostName = None, port = None, path = None, parameters = None,
query = None, fragment = None):
httpScriptDirectoryPath = context.getVar(
'httpScriptDirectoryPath')
if httpScriptDirectoryPath is not None:
self.pathPrefix = httpScriptDirectoryPath
_httpUrl.__init__(
self, protocol = protocol, hostNameAndPort = hostNameAndPort,
hostName = hostName, port = port, path = path,
parameters = parameters, query = query, fragment = fragment)
def addKeywords(self, keywords):
# The following code doesn't work when the keywords variables are too
# big:
# for name, value in keywords.items():
# self.args[name] = value
# return self
if not keywords:
return self
session = context.getVar('session')
if session is None:
# This case should not happen.
for name, value in keywords.items():
self.add(name, value)
return self
encodedKeywords = {}
for name, value in keywords.items():
if type(value) in [types.StringType, types.UnicodeType]:
encodedKeywords[name] = base64.encodestring(value)
else:
encodedKeywords[name] = value
session['keywords'] = encodedKeywords
session['isDirty'] = 1
return self.add('keywords', 1)
def getArgumentNames(self):
argumentNames = _httpUrl.getArgumentNames(self)
canUseCookie = context.getVar('canUseCookie', default = 0)
sessionToken = context.getVar('sessionToken')
if not canUseCookie:
if sessionToken is not None \
and not 'sessionToken' in argumentNames:
argumentNames.append('sessionToken')
elif 'sessionToken' in argumentNames:
argumentNames.remove('sessionToken')
return argumentNames
def getArguments(self):
canUseCookie = context.getVar('canUseCookie', default = 0)
sessionToken = context.getVar('sessionToken')
if not canUseCookie:
if sessionToken is not None:
self.argument_sessionToken = sessionToken
arguments = _httpUrl.getArguments(self)
if not canUseCookie:
if sessionToken is not None:
del self.argument_sessionToken
return arguments
def getPath(self, **keywords):
if self.pathPrefix is not None:
pathPrefix = self.pathPrefix
else:
pathPrefix = context.getVar(
'httpScriptDirectoryPath')
if pathPrefix is None:
pathPrefix = '/'
path = _httpUrl.getPath(self, **keywords)
if path and path[0] == '/':
path = path[1:]
path = '%s%s' % (pathPrefix, path)
return path
class glasnostUrl(httpUrl):
dispatcherHostName = None
dispatcherPort = None
localId = None
role = None
def __init__(self, id = None, hostNameAndPort = None, hostName = None,
port = None, role = None, action = None, localId = None):
from tools import splitId
if id is not None:
hostNameAndPort, role, localId = splitId(id)
if hostNameAndPort is not None:
infos = hostNameAndPort.split(':', 1)
hostName = infos[0]
if len(infos) < 2:
port = None
else:
port = infos[1]
if hostName is not None:
self.dispatcherHostName = hostName
else:
dispatcherId = context.getVar('dispatcherId')
if dispatcherId is not None:
dispatcherHostName = extractApplicationHostName(dispatcherId)
self.dispatcherHostName = dispatcherHostName
if port is not None:
self.dispatcherPort = port
else:
dispatcherId = context.getVar('dispatcherId')
if dispatcherId is not None:
dispatcherPort = extractApplicationPort(dispatcherId)
self.dispatcherPort = dispatcherPort
if role is not None:
self.role = role
else:
serverRole = context.getVar('serverRole')
if serverRole is not None:
self.role = serverRole
if localId is not None:
self.localId = localId
self.action = action
def getPath(self, **keywords):
knownRoles = context.getVar('knownRoles')
id = 'glasnost://%s/%s/%s' % (
self.dispatcherHostName, self.role, self.localId)
### FIXME: why doens't this method use getUrlId() ?
### (or the other way)
if knownRoles and 'pagenames' in knownRoles:
from glasnost.proxy.tools import getProxyForServerRole
pageNamesProxy = getProxyForServerRole('pagenames')
if pageNamesProxy:
computedId = '/%s' % pageNamesProxy.getNameByMappedId(id)
if computedId[1:]:
if self.action:
computedId = computedId + '/%s' % self.action
return computedId
if self.role is not None:
role = self.role
else:
serverRole = context.getVar('serverRole')
if serverRole is not None:
role = serverRole
else:
role = None
if knownRoles and not role in knownRoles:
return ''
raise Exception('Unknown server role = %s' % role)
httpScriptDirectoryPath = context.getVar(
'httpScriptDirectoryPath')
if httpScriptDirectoryPath is None:
httpScriptDirectoryPath = '/'
dispatcherId = context.getVar('dispatcherId')
if dispatcherId is not None:
dispatcherHostName = extractApplicationHostName(dispatcherId)
dispatcherPort = extractApplicationPort(dispatcherId)
else:
dispatcherHostName = None
dispatcherPort = None
if (self.dispatcherHostName is None \
or self.dispatcherHostName == dispatcherHostName) \
and (self.dispatcherPort is None \
or self.dispatcherPort == dispatcherPort):
templatePrefix = context.getVar('templatePrefix')
if templatePrefix:
if self.action:
action = '/%s%s' % (templatePrefix, self.action)
else:
action = '/%sview' % templatePrefix
else:
if self.action:
action = '/%s' % self.action
else:
action = ''
return '%s%s/%s%s' % (
httpScriptDirectoryPath, role, self.localId, action)
else:
if self.dispatcherHostName is not None:
dispatcherHostName = self.dispatcherHostName
elif dispatcherHostName is None:
dispatcherHostName = 'localhost'
if self.dispatcherPort is not None:
dispatcherPort = self.dispatcherPort
if dispatcherPort is None \
or dispatcherPort == str(context.getVar('dispatcherPort')):
dispatcherHostNameAndPort = dispatcherHostName
else:
dispatcherHostNameAndPort = '%s:%s' % (
dispatcherHostName, dispatcherPort)
if self.action:
action = '/%s' % self.action
else:
action = ''
return '%s%s/glasnost/%s/%s%s' % (
httpScriptDirectoryPath, role,
dispatcherHostNameAndPort, self.localId, action)
def url(url):
if url.startswith('glasnost://'):
return glasnostUrl(id = url)
else:
parsedUrl = urlparse.urlparse(url)
if parsedUrl[0]:
protocol = parsedUrl[0]
else:
protocol = None
if parsedUrl[1]:
hostNameAndPort = parsedUrl[1]
else:
hostNameAndPort = None
if parsedUrl[2]:
path = parsedUrl[2]
else:
path = None
if parsedUrl[3]:
parameters = parsedUrl[3]
else:
parameters = None
if parsedUrl[4]:
query = parsedUrl[4]
else:
query = None
if parsedUrl[5]:
fragment = parsedUrl[5]
else:
fragment = None
return httpUrl(
protocol = protocol, hostNameAndPort = hostNameAndPort,
path = path, parameters = parameters, query = query,
fragment = fragment)