Rev 417: Import bzrsvnserve code. in file:///home/jelmer/bzr-svn/native/
Jelmer Vernooij
jelmer at samba.org
Mon Mar 26 04:09:31 BST 2007
At file:///home/jelmer/bzr-svn/native/
------------------------------------------------------------
revno: 417
revision-id: jelmer at samba.org-20070326030927-gx1sztmko43pepo0
parent: jelmer at samba.org-20070202201250-i5eq4yp3uikabjuz
parent: jelmer at samba.org-20070122185242-0bl6sfrx3zl79ow0
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: native
timestamp: Mon 2007-03-26 05:09:27 +0200
message:
Import bzrsvnserve code.
added:
server/ server-20070326030801-7aa9p7z8zbejqs8d-1
server/__init__.py __init__.py-20061015145107-e1erl7tzb3zk831k-1
server/marshall.py marshall.py-20070122110546-ggdrkocyus0pjsqd-1
server/svnserver.py svnserver.py-20061015150253-0jjovnw1ax00rjlb-1
server/tests/ tests-20070122110405-ydhtxk45zyerq0oh-1
server/tests/__init__.py __init__.py-20070122111740-cibkqznxtxxbyvjt-1
server/tests/test_marshall.py test_marshall.py-20070122110633-944cvow1y1hg6krp-1
server/tests/test_server.py test_server.py-20070122114402-zcwhr4cxc67jvakf-1
------------------------------------------------------------
revno: 0.3.23
merged: jelmer at samba.org-20070122185242-0bl6sfrx3zl79ow0
parent: jelmer at samba.org-20070122162053-ut129mvs7joysh8s
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Mon 2007-01-22 19:52:42 +0100
message:
Add some more stubs, badly needs tests.
------------------------------------------------------------
revno: 0.3.22
merged: jelmer at samba.org-20070122162053-ut129mvs7joysh8s
parent: jelmer at samba.org-20070122161906-lcam7eccas1zq1po
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Mon 2007-01-22 17:20:53 +0100
message:
Lock (matters /a lot/)
------------------------------------------------------------
revno: 0.3.21
merged: jelmer at samba.org-20070122161906-lcam7eccas1zq1po
parent: jelmer at samba.org-20070122155732-vfmbqrbf71u7c8of
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Mon 2007-01-22 17:19:06 +0100
message:
Test for get_log
------------------------------------------------------------
revno: 0.3.20
merged: jelmer at samba.org-20070122155732-vfmbqrbf71u7c8of
parent: jelmer at samba.org-20070122154725-49pirhkzi6pu42lx
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Mon 2007-01-22 16:57:32 +0100
message:
Remove optimizations again..
------------------------------------------------------------
revno: 0.3.19
merged: jelmer at samba.org-20070122154725-49pirhkzi6pu42lx
parent: jelmer at samba.org-20070122154117-zmsnnakil7fjoeih
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Mon 2007-01-22 16:47:25 +0100
message:
Fix revision handling
------------------------------------------------------------
revno: 0.3.18
merged: jelmer at samba.org-20070122154117-zmsnnakil7fjoeih
parent: jelmer at samba.org-20070122154000-ub6ifk1ng4ca3azz
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Mon 2007-01-22 16:41:17 +0100
message:
Typo
------------------------------------------------------------
revno: 0.3.17
merged: jelmer at samba.org-20070122154000-ub6ifk1ng4ca3azz
parent: jelmer at samba.org-20070122153846-bw0hexrt5t91sks5
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Mon 2007-01-22 16:40:00 +0100
message:
don't fetch all revisions at once
------------------------------------------------------------
revno: 0.3.16
merged: jelmer at samba.org-20070122153846-bw0hexrt5t91sks5
parent: jelmer at samba.org-20070122152711-agvhumgzk6qvev1m
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Mon 2007-01-22 16:38:46 +0100
message:
use standard function for time conversions
------------------------------------------------------------
revno: 0.3.15
merged: jelmer at samba.org-20070122152711-agvhumgzk6qvev1m
parent: jelmer at samba.org-20070122152124-obc3p0x76zptffjp
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Mon 2007-01-22 16:27:11 +0100
message:
Fetch multiple revisions at once
------------------------------------------------------------
revno: 0.3.14
merged: jelmer at samba.org-20070122152124-obc3p0x76zptffjp
parent: jelmer at samba.org-20070122151242-1lnsn2vmyjehnukd
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Mon 2007-01-22 16:21:24 +0100
message:
Two trivial fixes
------------------------------------------------------------
revno: 0.3.13
merged: jelmer at samba.org-20070122151242-1lnsn2vmyjehnukd
parent: jelmer at samba.org-20070122144913-r38748l092dto74c
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Mon 2007-01-22 16:12:42 +0100
message:
Very simple implementation of log
------------------------------------------------------------
revno: 0.3.12
merged: jelmer at samba.org-20070122144913-r38748l092dto74c
parent: jelmer at samba.org-20070122142330-jg1h0cci78pnm5zc
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Mon 2007-01-22 15:49:13 +0100
message:
Get log works now (returns empty log for now)
------------------------------------------------------------
revno: 0.3.11
merged: jelmer at samba.org-20070122142330-jg1h0cci78pnm5zc
parent: jelmer at samba.org-20070122135806-vrx4xj1uq5d8v3x1
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Mon 2007-01-22 15:23:30 +0100
message:
get_uuid and get_latest_rev work now.
------------------------------------------------------------
revno: 0.3.10
merged: jelmer at samba.org-20070122135806-vrx4xj1uq5d8v3x1
parent: jelmer at samba.org-20070122131330-os8xa31ka1vyfjml
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Mon 2007-01-22 14:58:06 +0100
message:
Use python-svn for testing server. Currently still fails with 'Malformed network data' error
------------------------------------------------------------
revno: 0.3.9
merged: jelmer at samba.org-20070122131330-os8xa31ka1vyfjml
parent: jelmer at samba.org-20070122125840-sib4iysnuz238g2k
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Mon 2007-01-22 14:13:30 +0100
message:
Trivial support for listening on a TCP/IP port.
------------------------------------------------------------
revno: 0.3.8
merged: jelmer at samba.org-20070122125840-sib4iysnuz238g2k
parent: jelmer at samba.org-20070122114454-s6kqpgg5k3fl0dtf
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Mon 2007-01-22 13:58:40 +0100
message:
Add tests for server code.
------------------------------------------------------------
revno: 0.3.7
merged: jelmer at samba.org-20070122114454-s6kqpgg5k3fl0dtf
parent: jelmer at samba.org-20070122113853-7a2zddf0rsphskmc
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Mon 2007-01-22 12:44:54 +0100
message:
remove duplicate code
------------------------------------------------------------
revno: 0.3.6
merged: jelmer at samba.org-20070122113853-7a2zddf0rsphskmc
parent: jelmer at samba.org-20061015183108-4386822a387571fa
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Mon 2007-01-22 12:38:53 +0100
message:
Add testsuite for marshall/unmarshall code.
------------------------------------------------------------
revno: 0.3.5
merged: jelmer at samba.org-20061015183108-4386822a387571fa
parent: jelmer at samba.org-20061015181131-af775e7692f74f36
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Sun 2006-10-15 20:31:08 +0200
message:
Add parameters for inetd, port and directory to serve.
------------------------------------------------------------
revno: 0.3.4
merged: jelmer at samba.org-20061015181131-af775e7692f74f36
parent: jelmer at samba.org-20061015162538-d5032b56d1f63e09
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Sun 2006-10-15 20:11:31 +0200
message:
Fix literals support.
------------------------------------------------------------
revno: 0.3.3
merged: jelmer at samba.org-20061015162538-d5032b56d1f63e09
parent: jelmer at samba.org-20061015154426-d819257c123de417
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Sun 2006-10-15 18:25:38 +0200
message:
Gets past the first few roundtrips now.
------------------------------------------------------------
revno: 0.3.2
merged: jelmer at samba.org-20061015154426-d819257c123de417
parent: jelmer at samba.org-20061015150308-249217e986bdc16e
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Sun 2006-10-15 17:44:26 +0200
message:
Add marshall/unmarshall functions.
------------------------------------------------------------
revno: 0.3.1
merged: jelmer at samba.org-20061015150308-249217e986bdc16e
committer: Jelmer Vernooij <jelmer at samba.org>
branch nick: bzrsvnserve
timestamp: Sun 2006-10-15 17:03:08 +0200
message:
Initial work on a implementation of the svnserve protocol.
=== added directory 'server'
=== added file 'server/__init__.py'
--- a/server/__init__.py 1970-01-01 00:00:00 +0000
+++ b/server/__init__.py 2007-03-26 03:09:27 +0000
@@ -0,0 +1,93 @@
+# Copyright (C) 2006 Jelmer Vernooij <jelmer at samba.org>
+#
+# 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
+
+from bzrlib.commands import Command, register_command, Option
+from bzrlib.trace import info
+import os
+import sys
+import threading
+
+class cmd_svnserve(Command):
+ """Provide access to a Bazaar branch using the Subversion ra_svn protocol.
+ """
+ takes_options = [
+ Option('inet',
+ help='serve on stdin/out for use from inetd or sshd'),
+ Option('port',
+ help='listen for connections on nominated port of the form '
+ '[hostname:]portnumber. Passing 0 as the port number will '
+ 'result in a dynamically allocated port.',
+ type=str),
+ Option('directory',
+ help='serve contents of directory',
+ type=unicode)
+ ]
+
+ def run(self, inet=None, port=None, directory=None):
+ from svnserver import SVNServer
+
+ if directory is None:
+ directory = os.getcwd()
+
+ if inet:
+ def send_fn(data):
+ sys.stdout.write(data)
+ sys.stdout.flush()
+ server = SVNServer(directory, sys.stdin.read, send_fn)
+ server.serve()
+ else:
+ if port is None:
+ port = 3690
+ else:
+ port = int(port)
+
+ import socket
+ server_sock = socket.socket()
+ server_sock.bind(('0.0.0.0', port))
+ server_sock.listen(5)
+ def handle_new_client(sock):
+ def handle_connection():
+ server.serve()
+ sock.close()
+ server = SVNServer(directory, lambda: sock.recv(1024), sock.send)
+ server_thread = threading.Thread(None, handle_connection, name='svn-smart-server')
+ server_thread.setDaemon(True)
+ server_thread.start()
+
+ while True:
+ sock, _ = server_sock.accept()
+ handle_new_client(sock)
+
+
+register_command(cmd_svnserve)
+
+def test_suite():
+ from unittest import TestSuite
+ import tests
+ result = TestSuite()
+ result.addTest(tests.test_suite())
+ return result
+
+sys.path.append(os.path.dirname(__file__))
+
+try:
+ import uuid
+except ImportError:
+ from bzrlib.errors import BzrError
+ from bzrlib.trace import warning
+ warning('uuid module not available, disabling svnserve plugin')
+ raise BzrError('uuid module not available')
+
=== added file 'server/marshall.py'
--- a/server/marshall.py 1970-01-01 00:00:00 +0000
+++ b/server/marshall.py 2007-03-26 03:09:27 +0000
@@ -0,0 +1,110 @@
+# Copyright (C) 2006-2007 Jelmer Vernooij <jelmer at samba.org>
+#
+# 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
+
+from bzrlib.errors import BzrError
+
+class literal:
+ def __init__(self, txt):
+ self.txt = txt
+
+ def __str__(self):
+ return self.txt
+
+ def __repr__(self):
+ return self.txt
+
+# 1. Syntactic structure
+# ----------------------
+#
+# The Subversion protocol is specified in terms of the following
+# syntactic elements, specified using ABNF [RFC 2234]:
+#
+# item = word / number / string / list
+# word = ALPHA *(ALPHA / DIGIT / "-") space
+# number = 1*DIGIT space
+# string = 1*DIGIT ":" *OCTET space
+# ; digits give the byte count of the *OCTET portion
+# list = "(" space *item ")" space
+# space = 1*(SP / LF)
+#
+
+class MarshallError(BzrError):
+ def __init__(self, msg):
+ BzrError.__init__(self, msg)
+
+
+def marshall(x):
+ if isinstance(x, int):
+ return "%d " % x
+ elif isinstance(x, list) or isinstance(x, tuple):
+ return "( " + "".join(map(marshall, x)) + ") "
+ elif isinstance(x, literal):
+ return "%s " % x
+ elif isinstance(x, basestring):
+ return "%d:%s " % (len(x), x)
+ raise MarshallError("Unable to marshall type %s" % x)
+
+
+def unmarshall(x):
+ whitespace = ['\n', ' ']
+ if len(x) == 0:
+ raise MarshallError("Not enough data")
+ if x[0] == "(" and x[1] == " ": # list follows
+ x = x[2:]
+ ret = []
+ try:
+ while x[0] != ")":
+ (x, n) = unmarshall(x)
+ ret.append(n)
+ except IndexError:
+ raise MarshallError("List not terminated")
+
+ if not x[1] in whitespace:
+ raise MarshallError("Expected space, got %c" % x[1])
+
+ return (x[2:], ret)
+ elif x[0].isdigit():
+ num = ""
+ # Check if this is a string or a number
+ while x[0].isdigit():
+ num += x[0]
+ x = x[1:]
+ num = int(num)
+
+ if x[0] in whitespace:
+ return (x[1:], num)
+ elif x[0] == ":":
+ if len(x) < num:
+ raise MarshallError("Expected string of length %r" % num)
+ return (x[num+2:], x[1:num+1])
+ else:
+ raise MarshallError("Expected whitespace or ':', got '%c" % x[0])
+ elif x[0].isalpha():
+ ret = ""
+ # Parse literal
+ try:
+ while x[0].isalpha() or x[0].isdigit() or x[0] == '-':
+ ret += x[0]
+ x = x[1:]
+ except IndexError:
+ raise MarshallError("Expected literal")
+
+ if not x[0] in whitespace:
+ raise MarshallError("Expected whitespace, got %c" % x[0])
+
+ return (x[1:], ret)
+ else:
+ raise MarshallError("Unexpected character '%c'" % x[0])
=== added file 'server/svnserver.py'
--- a/server/svnserver.py 1970-01-01 00:00:00 +0000
+++ b/server/svnserver.py 2007-03-26 03:09:27 +0000
@@ -0,0 +1,217 @@
+# Copyright (C) 2006 Jelmer Vernooij <jelmer at samba.org>
+#
+# 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
+
+from bzrlib.branch import Branch
+from bzrlib.errors import BzrError
+from bzrlib.trace import mutter
+
+import copy
+import os
+import time
+
+from marshall import marshall, unmarshall, literal, MarshallError
+
+SVN_MAJOR_VERSION = 1
+SVN_MINOR_VERSION = 2
+
+SVN_NODE_NONE = 0
+SVN_NODE_FILE = 1
+SVN_NODE_DIR = 2
+
+class SVNServer:
+ def __init__(self, rootdir, recv_fn, send_fn):
+ self.rootdir = rootdir
+ self.recv_fn = recv_fn
+ self.send_fn = send_fn
+ self.inbuffer = ""
+ self._stop = False
+
+ def send_greeting(self):
+ self.send_success(
+ SVN_MAJOR_VERSION, SVN_MINOR_VERSION, [literal("ANONYMOUS")], [])
+
+ def send_mechs(self):
+ self.send_success([literal("ANONYMOUS")], "")
+
+ def send_failure(self, *contents):
+ self.send_msg([literal("failure"), list(contents)])
+
+ def send_success(self, *contents):
+ self.send_msg([literal("success"), list(contents)])
+
+ def send_unknown(self, cmd):
+ self.send_failure([210001, "Unknown command '%s'" % cmd, __file__, \
+ 52])
+
+ def get_latest_rev(self):
+ self.send_success([], "")
+ self.send_success(self.branch.revno())
+
+ def check_path(self, path, revnum):
+ return SVN_NODE_DIR
+
+ def log(self, target_path, start_rev, end_rev, changed_paths,
+ strict_node, limit=None):
+ def send_revision(revno, rev):
+ self.send_msg([[], revno, [rev.committer],
+ [time.strftime("%Y-%m-%dT%H:%M:%S.00000Z", time.gmtime(rev.timestamp))],
+ [rev.message]])
+ self.send_success([], "")
+ revno = start_rev[0]
+ i = 0
+ self.branch.repository.lock_read()
+ try:
+ # FIXME: check whether start_rev and end_rev actually exist
+ while revno != end_rev[0]:
+ #TODO: Honor target_path, strict_node, changed_paths
+ if end_rev[0] > revno:
+ revno+=1
+ else:
+ revno-=1
+ if limit != 0 and i == limit:
+ break
+ if revno != 0:
+ send_revision(revno, self.branch.repository.get_revision(self.branch.get_rev_id(revno)))
+ finally:
+ self.branch.repository.unlock()
+
+ self.send_msg(literal("done"))
+ self.send_success()
+
+ def reparent(self, parent):
+ self.send_success([], "")
+ self.send_success()
+
+ def stat(self, path, revnum):
+ self.send_success([], "")
+ self.send_success()
+
+ def update(self, rev, target, recurse):
+ import pdb
+ pdb.set_trace()
+ self.send_success([], "")
+ while True:
+ msg = self.recv_msg()
+ assert msg[0] in ["set-path", "finish-report"]
+ if msg[0] == "finish-report":
+ break
+
+ self.send_success([], "")
+ self.send_msg(["target-rev", rev])
+ tree = self.branch.repository.revision_tree(
+ self.branch.get_rev_id(rev[0]))
+ path2id = {}
+ id2path = {}
+ self.send_msg(["open-root", [rev, tree.inventory.root.file_id]])
+ def send_children(self, id):
+ for child in tree.inventory[id].children:
+ if tree.inventory[child].kind in ('symlink', 'file'):
+ self.send_msg(["add-file", [tree.inventory.id2path(child),
+ id, child]])
+ # FIXME
+ self.send_msg(["close-file", [child]])
+ else:
+ self.send_msg(["add-dir", [tree.inventory.id2path(child),
+ id, child]])
+ send_children(child)
+ self.send_msg(["close-dir", [child]])
+ #send_children(tree.inventory.root.file_id)
+ self.send_msg(["close-dir", [tree.inventory.root.file_id]])
+ self.send_msg(["close-edit", []])
+ #msg = self.recv_msg()
+ #self.send_msg(msg)
+
+
+ commands = {
+ "get-latest-rev": get_latest_rev,
+ "log": log,
+ "update": update,
+ "check-path": check_path,
+ "reparent": reparent,
+ "stat": stat,
+ # FIXME: get-dated-rev
+ # FIXME: rev-proplist
+ # FIXME: rev-prop
+ # FIXME: get-file
+ # FIXME: get-dir
+ # FIXME: check-path
+ # FIXME: switch
+ # FIXME: status
+ # FIXME: diff
+ # FIXME: get-locations
+ # FIXME: get-file-revs
+ # FIXME: replay
+ }
+
+ def get_branch_uuid(self):
+ config = self.branch.get_config()
+ uuid = config.get_user_option('svn_uuid')
+ if uuid is None:
+ import uuid
+ uuid = uuid.uuid4()
+ config.set_user_option('svn_uuid', uuid)
+ return str(uuid)
+
+ def send_auth_request(self):
+ pass
+
+ def serve(self):
+ self.send_greeting()
+ (version, capabilities, url) = self.recv_msg()
+ self.capabilities = capabilities
+ self.version = version
+ self.url = url
+ mutter("client supports:")
+ mutter(" version %r" % version)
+ mutter(" capabilities %r " % capabilities)
+ self.send_mechs()
+
+ (mech, args) = self.recv_msg()
+ # TODO: Proper authentication
+ self.send_success()
+
+ import bzrlib.urlutils as urlutils
+ (rooturl, location) = urlutils.split(url)
+
+ self.branch, branch_path = Branch.open_containing(os.path.join(self.rootdir, location))
+ self.send_success(self.get_branch_uuid(), url)
+
+ # Expect:
+ while not self._stop:
+ ( cmd, args ) = self.recv_msg()
+ if not self.commands.has_key(cmd):
+ self.send_unknown(cmd)
+ return
+ else:
+ self.commands[cmd](self, *args)
+
+ def close(self):
+ self._stop = True
+
+ def recv_msg(self):
+ # FIXME: Blocking read?
+ while True:
+ try:
+ self.inbuffer += self.recv_fn()
+ (self.inbuffer, ret) = unmarshall(self.inbuffer)
+ mutter('in: %r' % ret)
+ return ret
+ except MarshallError, e:
+ mutter('ERROR: %r' % e)
+
+ def send_msg(self, data):
+ mutter('out: %r' % data)
+ self.send_fn(marshall(data))
=== added directory 'server/tests'
=== added file 'server/tests/__init__.py'
--- a/server/tests/__init__.py 1970-01-01 00:00:00 +0000
+++ b/server/tests/__init__.py 2007-01-22 12:58:40 +0000
@@ -0,0 +1,28 @@
+# Copyright (C) 2007 Jelmer Vernooij <jelmer at samba.org>
+
+# 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
+
+def test_suite():
+ from unittest import TestSuite, TestLoader
+ from bzrlib.tests import TestUtil
+ loader = TestUtil.TestLoader()
+ suite = TestSuite()
+ testmod_names = [
+ 'test_marshall',
+ 'test_server'
+ ]
+ suite.addTest(loader.loadTestsFromModuleNames(["%s.%s" % (__name__, i) for i in testmod_names]))
+
+ return suite
=== added file 'server/tests/test_marshall.py'
--- a/server/tests/test_marshall.py 1970-01-01 00:00:00 +0000
+++ b/server/tests/test_marshall.py 2007-01-22 13:58:06 +0000
@@ -0,0 +1,87 @@
+# Copyright (C) 2006-2007 Jelmer Vernooij <jelmer at samba.org>
+#
+# 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
+
+from bzrlib.tests import TestCase
+from marshall import literal, MarshallError, marshall, unmarshall
+
+class TestMarshalling(TestCase):
+ def test_literal_txt(self):
+ l = literal("foo")
+ self.assertEqual("foo", l.txt)
+
+ def test_literal_str(self):
+ l = literal("foo bar")
+ self.assertEqual("foo bar", l.__str__())
+
+ def test_literal_rep(self):
+ l = literal("foo bar")
+ self.assertEqual("foo bar", l.__repr__())
+
+ def test_marshall_error(self):
+ e = MarshallError("bla bla")
+ self.assertEqual("bla bla", e.__str__())
+
+ def test_marshall_int(self):
+ self.assertEqual("1 ", marshall(1))
+
+ def test_marshall_list(self):
+ self.assertEqual("( 1 2 3 4 ) ", marshall([1,2,3,4]))
+
+ def test_marshall_list_mixed(self):
+ self.assertEqual("( 1 3 4 3:str ) ", marshall([1,3,4,"str"]))
+
+ def test_marshall_literal(self):
+ self.assertEqual("foo ", marshall(literal("foo")))
+
+ def test_marshall_string(self):
+ self.assertEqual("3:foo ", marshall("foo"))
+
+ def test_marshall_raises(self):
+ self.assertRaises(MarshallError, marshall, dict())
+
+ def test_marshall_list_nested(self):
+ self.assertEqual("( ( ( 3 ) 4 ) ) ", marshall([[[3], 4]]))
+
+ def test_marshall_string_space(self):
+ self.assertEqual("5:bla l ", marshall("bla l"))
+
+ def test_unmarshall_string(self):
+ self.assertEqual(('', "bla l"), unmarshall("5:bla l"))
+
+ def test_unmarshall_list(self):
+ self.assertEqual(('', [4,5]), unmarshall("( 4 5 ) "))
+
+ def test_unmarshall_int(self):
+ self.assertEqual(('', 2), unmarshall("2 "))
+
+ def test_unmarshall_literal(self):
+ self.assertEqual(('', literal("x")), unmarshall("x "))
+
+ def test_unmarshall_empty(self):
+ self.assertRaises(MarshallError, unmarshall, "")
+
+ def test_unmarshall_nospace(self):
+ self.assertRaises(MarshallError, unmarshall, "nospace")
+
+ def test_unmarshall_toolong(self):
+ self.assertRaises(MarshallError, unmarshall, "43432432:bla")
+
+ def test_unmarshall_literal(self):
+ self.assertRaises(MarshallError, unmarshall, ":-3213")
+
+ def test_unmarshall_open_list(self):
+ self.assertRaises(MarshallError, unmarshall, "( 3 4 ")
+
=== added file 'server/tests/test_server.py'
--- a/server/tests/test_server.py 1970-01-01 00:00:00 +0000
+++ b/server/tests/test_server.py 2007-01-22 18:52:42 +0000
@@ -0,0 +1,146 @@
+# Copyright (C) 2006-2007 Jelmer Vernooij <jelmer at samba.org>
+#
+# 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
+
+from bzrlib.bzrdir import BzrDir
+from bzrlib.tests import TestCaseInTempDir
+from bzrlib.trace import mutter
+from bzrlib.workingtree import WorkingTree
+
+from marshall import literal, MarshallError, marshall, unmarshall
+from svnserver import SVNServer
+
+from cStringIO import StringIO
+import os
+import socket
+import threading
+import uuid
+
+class DryTestServer(TestCaseInTempDir):
+ def setUp(self):
+ super(DryTestServer, self).setUp()
+ self.branch_path = os.path.join(self.test_dir, 'a')
+ self.branch = BzrDir.create_branch_convenience(self.branch_path)
+ self.outstr = StringIO()
+ self.server = SVNServer(self.branch_path, None, self.outstr.write)
+
+ def test_send_greeting(self):
+ self.server.send_greeting()
+ self.outstr.seek(0)
+ self.assertEqual("( success ( 1 2 ( ANONYMOUS ) ( ) ) ) ",
+ self.outstr.read())
+
+ def test_unknown_cmd(self):
+ self.server.send_unknown("foobar")
+ self.outstr.seek(0)
+ msg = unmarshall(self.outstr.read())[1]
+ self.assertEqual("failure", msg[0])
+ self.assertEqual(210001, msg[1][0][0])
+ self.assertEqual("Unknown command 'foobar'", msg[1][0][1])
+
+ def test_get_uuid(self):
+ self.server.branch = self.branch
+ self.branch.get_config().set_user_option('svn_uuid',
+ '769e3eee-b09d-4023-bf1b-773dcd4bdb2a')
+ self.assertEqual('769e3eee-b09d-4023-bf1b-773dcd4bdb2a',
+ self.server.get_branch_uuid())
+
+ def test_get_uuid_implicit(self):
+ self.server.branch = self.branch
+ uuid.UUID(self.server.get_branch_uuid())
+
+import svn.client, svn.ra, svn.delta
+from svn.core import Pool
+
+class NativeTestServer(TestCaseInTempDir):
+ def setUp(self):
+ super(NativeTestServer, self).setUp()
+ self.branch_path = os.path.join(self.test_dir, 'a')
+ self.branch = BzrDir.create_branch_convenience(self.branch_path)
+ self.outstr = StringIO()
+ self.pool = Pool()
+ self.client_ctx = svn.client.create_context(self.pool)
+ self.server = SVNServer(self.branch_path, None, self.outstr.write)
+ self.branch.get_config().set_user_option('svn_uuid',
+ '769e3eee-b09d-4023-bf1b-773dcd4bdb2a')
+ server_sock = socket.socket()
+ server_sock.listen(1)
+ addr = server_sock.getsockname()
+ def handle_connection():
+ sock, client_addr = server_sock.accept()
+ self.server = SVNServer(self.branch_path, lambda: sock.recv(1024), sock.send)
+ self.server.serve()
+ self.server_thread = threading.Thread(None, handle_connection, name='svn-smart-server')
+ self.server_thread.setDaemon(True)
+ self.server_thread.start()
+ self.url = "svn://%s:%d/" % addr
+ self.ra = svn.client.open_ra_session(self.url,
+ self.client_ctx, self.pool)
+
+ def tearDown(self):
+ super(NativeTestServer, self).tearDown()
+ self.server.close()
+
+ def test_get_uuid(self):
+ self.assertEqual('769e3eee-b09d-4023-bf1b-773dcd4bdb2a', svn.ra.get_uuid(self.ra))
+
+ def test_get_latest_rev(self):
+ self.assertEqual(0, svn.ra.get_latest_revnum(self.ra))
+
+ def test_get_log_empty(self):
+ def rcvr(orig_paths, rev, author, date, message, pool):
+ pass
+ svn.ra.get_log(self.ra, ["/"], 0, 0, 0, True, True, rcvr, self.pool)
+
+ def test_get_log_onrev(self):
+ self.num = 0
+ def rcvr(orig_paths, rev, author, date, message, pool):
+ self.num += 1
+ self.assertEqual(1, rev)
+ self.assertEqual("someone", author)
+ self.assertEqual("a commit message", message)
+ file('a/file', 'w').write("data")
+ wt = WorkingTree.open('a')
+ wt.add('file')
+ wt.commit("a commit message", committer='someone')
+ svn.ra.get_log(self.ra, ["/"], 0, 1, 0, False, False, rcvr, self.pool)
+
+ def test_checkout(self):
+ file('a/file', 'w').write("data")
+ wt = WorkingTree.open('a')
+ wt.add('file')
+ wt.commit("a commit message", committer='someone')
+ class Editor():
+ pass
+ editor = Editor()
+ edit, edit_baton = svn.delta.make_editor(editor, self.pool)
+ reporter, report_baton = svn.ra.do_update(self.ra, 1, self.url,
+ True, edit, edit_baton)
+ svn.ra.reporter2_invoke_set_path(reporter, report_baton, "",
+ 0, True, None, self.pool)
+ svn.ra.reporter2_invoke_finish_report(reporter, report_baton,
+ self.pool)
+
+ def test_check_path(self):
+ self.assertTrue(svn.ra.check_path(self.ra, '', 0))
+
+ def test_check_path_future(self):
+ self.assertTrue(svn.ra.check_path(self.ra, '', 1))
+
+ def test_reparent(self):
+ svn.ra.reparent(self.ra, 'someurl')
+
+ def test_stat(self):
+ svn.ra.stat(self.ra, '', 1)
More information about the bazaar-commits
mailing list