r"""
Trac Server Proxy for Doctesting
This module provides substitutes for the server proxy used by
:class:`sage.dev.trac_interface.TracInterface` for doctesting.
AUTHORS:
- Julian Rueth: initial version
"""
import sage.dev.trac_interface
class DoctestServerProxy(object):
r"""
A server proxy which can be used by
:meth:`sage.dev.test.trac_interface.DoctestTracInterface._anonymous_server_proxy`
for doctesting.
EXAMPLES::
sage: from sage.dev.test.server_proxy import DoctestServerProxy
sage: from sage.dev.test.trac_server import DoctestTracServer
sage: DoctestServerProxy(DoctestTracServer())
<sage.dev.test.server_proxy.DoctestServerProxy object at 0x...>
"""
def __init__(self, server):
r"""
Initialization.
TESTS::
sage: from sage.dev.test.trac_interface import DoctestTracInterface
sage: from sage.dev.test.config import DoctestConfig
sage: from sage.dev.test.user_interface import DoctestUserInterface
sage: from sage.dev.test.trac_server import DoctestTracServer
sage: config = DoctestConfig()
sage: UI = DoctestUserInterface(config['UI'])
sage: trac = DoctestTracInterface(config['trac'], UI, DoctestTracServer())
sage: type(trac._anonymous_server_proxy)
<class 'sage.dev.test.server_proxy.DoctestServerProxy'>
"""
self._server = server
self.ticket = DoctestTicketProxy(self)
self.sshkeys = DoctestSshkeysProxy(self)
def _check_authentication(self, privilege):
r"""
Check whether the user has sufficient permissions to perform an action
which requires ``privilege``.
EXAMPLES::
sage: from sage.dev.test.trac_interface import DoctestTracInterface
sage: from sage.dev.test.config import DoctestConfig
sage: from sage.dev.test.user_interface import DoctestUserInterface
sage: from sage.dev.test.trac_server import DoctestTracServer
sage: config = DoctestConfig()
sage: config['trac']['password'] = 'secret'
sage: UI = DoctestUserInterface(config['UI'])
sage: trac = DoctestTracInterface(config['trac'], UI, DoctestTracServer())
sage: trac._anonymous_server_proxy._check_authentication("TICKET_CREATE")
Traceback (most recent call last):
...
TracInternalError: <Fault 403: "TICKET_CREATE privileges are required to perform this operation. You don't have the required permissions.">
sage: trac._authenticated_server_proxy._check_authentication("TICKET_CREATE")
"""
from sage.dev.trac_error import TracInternalError
import xmlrpclib
raise TracInternalError(xmlrpclib.Fault(403, "%s privileges are required to perform this operation. You don't have the required permissions."%privilege))
class AuthenticatedDoctestServerProxy(DoctestServerProxy):
r"""
A server proxy which can be used by
:meth:`sage.dev.test.trac_interface.DoctestTracInterface._anonymous_server_proxy`
for doctesting.
EXAMPLES::
sage: from sage.dev.test.server_proxy import AuthenticatedDoctestServerProxy
sage: from sage.dev.test.trac_server import DoctestTracServer
sage: AuthenticatedDoctestServerProxy(DoctestTracServer(), 'username', 'password')
<sage.dev.test.server_proxy.AuthenticatedDoctestServerProxy object at 0x...>
"""
def __init__(self, server, username, password):
r"""
Initialization.
TESTS::
sage: from sage.dev.test.trac_interface import DoctestTracInterface
sage: from sage.dev.test.config import DoctestConfig
sage: from sage.dev.test.user_interface import DoctestUserInterface
sage: from sage.dev.test.trac_server import DoctestTracServer
sage: config = DoctestConfig()
sage: config['trac']['password'] = 'secret'
sage: UI = DoctestUserInterface(config['UI'])
sage: trac = DoctestTracInterface(config['trac'], UI, DoctestTracServer())
sage: type(trac._authenticated_server_proxy)
<class 'sage.dev.test.server_proxy.AuthenticatedDoctestServerProxy'>
"""
DoctestServerProxy.__init__(self, server)
self._username = username
self._password = password
def _check_authentication(self, privilege):
r"""
Check whether the user has sufficient permissions to perform an action
which requires ``privilege``.
EXAMPLES::
sage: from sage.dev.test.trac_interface import DoctestTracInterface
sage: from sage.dev.test.config import DoctestConfig
sage: from sage.dev.test.user_interface import DoctestUserInterface
sage: from sage.dev.test.trac_server import DoctestTracServer
sage: config = DoctestConfig()
sage: config['trac']['password'] = 'secret'
sage: UI = DoctestUserInterface(config['UI'])
sage: trac = DoctestTracInterface(config['trac'], UI, DoctestTracServer())
sage: trac._anonymous_server_proxy._check_authentication("TICKET_CREATE")
Traceback (most recent call last):
...
TracInternalError: <Fault 403: "TICKET_CREATE privileges are required to perform this operation. You don't have the required permissions.">
sage: trac._authenticated_server_proxy._check_authentication("TICKET_CREATE")
"""
pass
class DoctestSshkeysProxy(object):
r"""
A proxy object for the ``sshkeys`` property of a
:class:`DoctestServerProxy`.
EXAMPLES::
sage: from sage.dev.test.server_proxy import DoctestServerProxy
sage: from sage.dev.test.trac_server import DoctestTracServer
sage: DoctestServerProxy(DoctestTracServer()).sshkeys
<sage.dev.test.server_proxy.DoctestSshkeysProxy object at 0x...>
"""
def __init__(self, server_proxy):
r"""
Initialization.
TESTS::
sage: from sage.dev.test.trac_interface import DoctestTracInterface
sage: from sage.dev.test.config import DoctestConfig
sage: from sage.dev.test.user_interface import DoctestUserInterface
sage: from sage.dev.test.trac_server import DoctestTracServer
sage: config = DoctestConfig()
sage: UI = DoctestUserInterface(config['UI'])
sage: trac = DoctestTracInterface(config['trac'], UI, DoctestTracServer())
sage: type(trac._anonymous_server_proxy.sshkeys)
<class 'sage.dev.test.server_proxy.DoctestSshkeysProxy'>
"""
self._server_proxy = server_proxy
def addkey(self, public_key):
r"""
Add public key ``public_key`` for the authenticated user.
INPUT:
- ``public_key`` -- a string
EXAMPLES::
sage: from sage.dev.test.trac_interface import DoctestTracInterface
sage: from sage.dev.test.config import DoctestConfig
sage: from sage.dev.test.user_interface import DoctestUserInterface
sage: from sage.dev.test.trac_server import DoctestTracServer
sage: config = DoctestConfig()
sage: config['trac']['password'] = 'secret'
sage: UI = DoctestUserInterface(config['UI'])
sage: trac = DoctestTracInterface(config['trac'], UI, DoctestTracServer())
sage: trac._authenticated_server_proxy.sshkeys.addkey('foo')
0
"""
from sage.dev.trac_error import TracInternalError
try:
self._server_proxy._check_authentication('SSHKEYS')
except TracInternalError:
import xmlrpclib
raise TracInternalError(xmlrpclib.Fault(1, "'cannot set ssh keys for anonymous users' while executing 'sshkeys.addkey()'"))
pass
return 0
class DoctestTicketProxy(object):
r"""
A proxy object for the ``ticket`` property of a
:class:`DoctestServerProxy`.
EXAMPLES::
sage: from sage.dev.test.server_proxy import DoctestServerProxy
sage: from sage.dev.test.trac_server import DoctestTracServer
sage: DoctestServerProxy(DoctestTracServer()).ticket
<sage.dev.test.server_proxy.DoctestTicketProxy object at 0x...>
"""
def __init__(self, server_proxy):
r"""
Initialization.
TESTS::
sage: from sage.dev.test.trac_interface import DoctestTracInterface
sage: from sage.dev.test.config import DoctestConfig
sage: from sage.dev.test.user_interface import DoctestUserInterface
sage: from sage.dev.test.trac_server import DoctestTracServer
sage: config = DoctestConfig()
sage: UI = DoctestUserInterface(config['UI'])
sage: trac = DoctestTracInterface(config['trac'], UI, DoctestTracServer())
sage: type(trac._anonymous_server_proxy.ticket)
<class 'sage.dev.test.server_proxy.DoctestTicketProxy'>
"""
self._server_proxy = server_proxy
def create(self, summary, description, attributes, notify=False):
r"""
Create a new ticket and return its ticket number.
EXAMPLES::
sage: from sage.dev.test.trac_interface import DoctestTracInterface
sage: from sage.dev.test.config import DoctestConfig
sage: from sage.dev.test.user_interface import DoctestUserInterface
sage: from sage.dev.test.trac_server import DoctestTracServer
sage: config = DoctestConfig()
sage: config['trac']['password'] = 'secret'
sage: UI = DoctestUserInterface(config['UI'])
sage: trac = DoctestTracInterface(config['trac'], UI, DoctestTracServer())
sage: trac._authenticated_server_proxy.ticket.create('summary', 'description', {})
1
"""
self._server_proxy._check_authentication("TICKET_CREATE")
from trac_server import Ticket
ticket = len(self._server_proxy._server.tickets)+1
self._server_proxy._server.tickets[ticket] = Ticket(ticket, summary, description, attributes)
return ticket
def update(self, ticket, comment, attributes, notify=False):
r"""
Add a ``comment`` and update ``attributes`` of ``ticket``.
OUTPUT:
Returns a fake URL of the ticket.
EXAMPLES::
sage: from sage.dev.test.trac_interface import DoctestTracInterface
sage: from sage.dev.test.config import DoctestConfig
sage: from sage.dev.test.user_interface import DoctestUserInterface
sage: from sage.dev.test.trac_server import DoctestTracServer
sage: config = DoctestConfig()
sage: config['trac']['password'] = 'secret'
sage: UI = DoctestUserInterface(config['UI'])
sage: trac = DoctestTracInterface(config['trac'], UI, DoctestTracServer())
sage: ticket = trac._authenticated_server_proxy.ticket.create('summary', 'description', {})
sage: trac._authenticated_server_proxy.ticket.update(ticket, 'comment', {'component':'algebra'})
'https://trac.sagemath.org/ticket/1#comment:1'
"""
self._server_proxy._check_authentication("TICKET_MODIFY")
ticket = self._server_proxy._server.tickets[ticket]
ticket.comments.append(comment)
ticket.attributes = attributes
from sage.env import TRAC_SERVER_URI
import urlparse
return urlparse.urljoin(TRAC_SERVER_URI, 'ticket/%s#comment:%s'%(ticket.id, len(ticket.comments)))
def get(self, ticket):
r"""
Return a tuple ``(ticket, time_created, time_changed, attributes)`` for
``ticket``.
EXAMPLES::
sage: from sage.dev.test.trac_interface import DoctestTracInterface
sage: from sage.dev.test.config import DoctestConfig
sage: from sage.dev.test.user_interface import DoctestUserInterface
sage: from sage.dev.test.trac_server import DoctestTracServer
sage: config = DoctestConfig()
sage: config['trac']['password'] = 'secret'
sage: UI = DoctestUserInterface(config['UI'])
sage: trac = DoctestTracInterface(config['trac'], UI, DoctestTracServer())
sage: ticket = trac._authenticated_server_proxy.ticket.create('summary', 'description', {})
sage: trac._anonymous_server_proxy.ticket.get(ticket)
[1, 'not implemented', 'not implemented', {'description': 'description', 'summary': 'summary'}]
"""
if ticket not in self._server_proxy._server.tickets:
from sage.dev.trac_error import TracInternalError
import xmlrpclib
raise TracInternalError(xmlrpclib.Fault(404, "ticket does not exist"))
ticket = self._server_proxy._server.tickets[ticket]
return [ticket.id, ticket.time_created, ticket.time_changed, ticket.attributes]
def listAttachments(self, ticket):
r"""
Return a list of attachments to this ticket.
EXAMPLES::
sage: from sage.dev.test.trac_interface import DoctestTracInterface
sage: from sage.dev.test.config import DoctestConfig
sage: from sage.dev.test.user_interface import DoctestUserInterface
sage: from sage.dev.test.trac_server import DoctestTracServer
sage: config = DoctestConfig()
sage: config['trac']['password'] = 'secret'
sage: UI = DoctestUserInterface(config['UI'])
sage: trac = DoctestTracInterface(config['trac'], UI, DoctestTracServer())
sage: ticket = trac._authenticated_server_proxy.ticket.create('summary', 'description', {})
sage: trac._anonymous_server_proxy.ticket.listAttachments(ticket)
[]
"""
if ticket not in self._server_proxy._server.tickets:
from sage.dev.trac_error import TracInternalError
import xmlrpclib
raise TracInternalError(xmlrpclib.Fault(404, "ticket does not exist"))
ticket = self._server_proxy._server.tickets[ticket]
return [ [k,None,None,None,None] for k in ticket.attachments.keys()]