Modified: subversion/branches/svn_mutex/tools/dist/release.py URL: http://svn.apache.org/viewvc/subversion/branches/svn_mutex/tools/dist/release.py?rev=1182053&r1=1182052&r2=1182053&view=diff ============================================================================== --- subversion/branches/svn_mutex/tools/dist/release.py (original) +++ subversion/branches/svn_mutex/tools/dist/release.py Tue Oct 11 19:52:34 2011 @@ -36,13 +36,18 @@ # Stuff we need import os +import re import sys +import glob import shutil import urllib2 import hashlib import tarfile import logging import datetime +import tempfile +import operator +import itertools import subprocess import argparse # standard in Python 2.7 @@ -64,11 +69,87 @@ swig_ver = '2.0.4' # Some constants repos = 'http://svn.apache.org/repos/asf/subversion' +people_host = 'minotaur.apache.org' +people_dist_dir = '/www/www.apache.org/dist/subversion' #---------------------------------------------------------------------- # Utility functions +class Version(object): + regex = re.compile('(\d+).(\d+).(\d+)(?:-(?:(rc|alpha|beta)(\d+)))?') + + def __init__(self, ver_str): + # Special case the 'trunk-nightly' version + if ver_str == 'trunk-nightly': + self.major = None + self.minor = None + self.patch = None + self.pre = 'nightly' + self.pre_num = None + self.base = 'nightly' + return + + match = self.regex.search(ver_str) + + if not match: + raise RuntimeError("Bad version string '%s'" % ver_str) + + self.major = int(match.group(1)) + self.minor = int(match.group(2)) + self.patch = int(match.group(3)) + + if match.group(4): + self.pre = match.group(4) + self.pre_num = int(match.group(5)) + else: + self.pre = None + self.pre_num = None + + self.base = '%d.%d.%d' % (self.major, self.minor, self.patch) + + def is_prerelease(self): + return self.pre != None + + def __lt__(self, that): + if self.major < that.major: return True + if self.major > that.major: return False + + if self.minor < that.minor: return True + if self.minor > that.minor: return False + + if self.patch < that.patch: return True + if self.patch > that.patch: return False + + if not self.pre and not that.pre: return False + if not self.pre and that.pre: return False + if self.pre and not that.pre: return True + + # We are both pre-releases + if self.pre != that.pre: + return self.pre < that.pre + else: + return self.pre_num < that.pre_num + + def __str(self): + if self.pre: + if self.pre == 'nightly': + return 'nightly' + else: + extra = '-%s%d' % (self.pre, self.pre_num) + else: + extra = '' + + return self.base + extra + + def __repr__(self): + + return "Version('%s')" % self.__str() + + def __str__(self): + return self.__str() + + def get_prefix(base_dir): return os.path.join(base_dir, 'prefix') @@ -108,12 +189,9 @@ def download_file(url, target): target_file = open(target, 'w') target_file.write(response.read()) -def split_version(version): - parts = version.split('-') - if len(parts) == 1: - return (version, None) - - return parts[0], parts[1] +def assert_people(): + if os.uname()[1] != people_host: + raise RuntimeError('Not running on expected host "%s"' % people_host) #---------------------------------------------------------------------- # Cleaning up the environment @@ -264,15 +342,46 @@ def build_env(args): #---------------------------------------------------------------------- # Create release artifacts +def fetch_changes(repos, branch, revision): + changes_peg_url = '%s/%s/CHANGES@%d' % (repos, branch, revision) + proc = subprocess.Popen(['svn', 'cat', changes_peg_url], + stdout=subprocess.PIPE, stderr=subprocess.STDOUT) + (stdout, stderr) = proc.communicate() + proc.wait() + return stdout.split('\n') + + +def compare_changes(repos, branch, revision): + # Compare trunk's version of CHANGES with that of the branch, + # ignoring any lines in trunk's version precede what *should* + # match the contents of the branch's version. (This allows us to + # continue adding new stuff at the top of trunk's CHANGES that + # might relate to the *next* major release line.) + branch_CHANGES = fetch_changes(repos, branch, revision) + trunk_CHANGES = fetch_changes(repos, 'trunk', revision) + try: + first_matching_line = trunk_CHANGES.index(branch_CHANGES[0]) + except ValueError: + raise RuntimeError('CHANGES not synced between trunk and branch') + + trunk_CHANGES = trunk_CHANGES[first_matching_line:] + saw_diff = False + import difflib + for diff_line in difflib.unified_diff(trunk_CHANGES, branch_CHANGES): + saw_diff = True + logging.debug('%s', diff_line) + if saw_diff: + raise RuntimeError('CHANGES not synced between trunk and branch') + + def roll_tarballs(args): 'Create the release artifacts.' extns = ['zip', 'tar.gz', 'tar.bz2'] - version_base, version_extra = split_version(args.version) if args.branch: branch = args.branch else: - branch = version_base[:-1] + 'x' + branch = 'branches/' + args.version.base[:-1] + 'x' logging.info('Rolling release %s from branch %s@%d' % (args.version, branch, args.revnum)) @@ -286,50 +395,38 @@ def roll_tarballs(args): if not dep.have_usable(): raise RuntimeError('Cannot find usable %s' % dep.label) - # Make sure CHANGES is sync'd if branch != 'trunk': - trunk_CHANGES = '%s/trunk/CHANGES@%d' % (repos, args.revnum) - branch_CHANGES = '%s/branches/%s/CHANGES@%d' % (repos, branch, - args.revnum) - proc = subprocess.Popen(['svn', 'diff', '--summarize', branch_CHANGES, - trunk_CHANGES], - stdout=subprocess.PIPE, - stderr=subprocess.STDOUT) - (stdout, stderr) = proc.communicate() - proc.wait() + # Make sure CHANGES is sync'd. + compare_changes(repos, branch, args.revnum) + + # Ensure the output directory doesn't already exist + if os.path.exists(get_deploydir(args.base_dir)): + raise RuntimeError('output directory \'%s\' already exists' + % get_deploydir(args.base_dir)) - if stdout: - raise RuntimeError('CHANGES not synced between trunk and branch') - - # Create the output directory - if not os.path.exists(get_deploydir(args.base_dir)): - os.mkdir(get_deploydir(args.base_dir)) + os.mkdir(get_deploydir(args.base_dir)) # For now, just delegate to dist.sh to create the actual artifacts extra_args = '' - if version_extra: - if version_extra.startswith('alpha'): - extra_args = '-alpha %s' % version_extra[5:] - elif version_extra.startswith('beta'): - extra_args = '-beta %s' % version_extra[4:] - elif version_extra.startswith('rc'): - extra_args = '-rc %s' % version_extra[2:] - elif version_extra.startswith('nightly'): + if args.version.is_prerelease(): + if args.version.pre == 'nightly': extra_args = '-nightly' + else: + extra_args = '-%s %d' % (args.version.pre, args.version.pre_num) logging.info('Building UNIX tarballs') run_script(args.verbose, '%s/dist.sh -v %s -pr %s -r %d %s' - % (sys.path[0], version_base, branch, args.revnum, + % (sys.path[0], args.version.base, branch, args.revnum, extra_args) ) logging.info('Buildling Windows tarballs') run_script(args.verbose, '%s/dist.sh -v %s -pr %s -r %d -zip %s' - % (sys.path[0], version_base, branch, args.revnum, + % (sys.path[0], args.version.base, branch, args.revnum, extra_args) ) # Move the results to the deploy directory logging.info('Moving artifacts and calculating checksums') for e in extns: - if version_extra and version_extra.startswith('nightly'): - filename = 'subversion-trunk.%s' % e + if args.version.pre == 'nightly': + filename = 'subversion-nightly.%s' % e else: filename = 'subversion-%s.%s' % (args.version, e) @@ -349,30 +446,24 @@ def roll_tarballs(args): def post_candidates(args): 'Post the generated tarballs to web-accessible directory.' - version_base, version_extra = split_version(args.version) - if args.target: target = args.target else: target = os.path.join(os.getenv('HOME'), 'public_html', 'svn', - args.version) - - if args.code_name: - dirname = args.code_name - else: - dirname = 'deploy' + str(args.version)) - if not os.path.exists(target): - os.makedirs(target) + logging.info('Moving tarballs to %s' % target) + if os.path.exists(target): + shutil.rmtree(target) + shutil.copytree(get_deploydir(args.base_dir), target) - data = { 'version' : args.version, + data = { 'version' : str(args.version), 'revnum' : args.revnum, - 'dirname' : dirname, } # Choose the right template text - if version_extra: - if version_extra.startswith('nightly'): + if args.version.is_prerelease(): + if args.version.pre == 'nightly': template_filename = 'nightly-candidates.ezt' else: template_filename = 'rc-candidates.ezt' @@ -381,12 +472,66 @@ def post_candidates(args): template = ezt.Template() template.parse(get_tmplfile(template_filename).read()) - template.generate(open(os.path.join(target, 'index.html'), 'w'), data) + template.generate(open(os.path.join(target, 'HEADER.html'), 'w'), data) + + template = ezt.Template() + template.parse(get_tmplfile('htaccess.ezt').read()) + template.generate(open(os.path.join(target, '.htaccess'), 'w'), data) - logging.info('Moving tarballs to %s' % os.path.join(target, dirname)) - if os.path.exists(os.path.join(target, dirname)): - shutil.rmtree(os.path.join(target, dirname)) - shutil.copytree(get_deploydir(args.base_dir), os.path.join(target, dirname)) + +#---------------------------------------------------------------------- +# Clean dist + +def clean_dist(args): + 'Clean the distribution directory of all but the most recent artifacts.' + + regex = re.compile('subversion-(\d+).(\d+).(\d+)(?:-(?:(rc|alpha|beta)(\d+)))?') + + if not args.dist_dir: + assert_people() + args.dist_dir = people_dist_dir + + logging.info('Cleaning dist dir \'%s\'' % args.dist_dir) + + filenames = glob.glob(os.path.join(args.dist_dir, 'subversion-*.tar.gz')) + versions = [] + for filename in filenames: + versions.append(Version(filename)) + + for k, g in itertools.groupby(sorted(versions), + lambda x: (x.major, x.minor)): + releases = list(g) + logging.info("Saving release '%s'", releases[-1]) + + for r in releases[:-1]: + for filename in glob.glob(os.path.join(args.dist_dir, + 'subversion-%s.*' % r)): + logging.info("Removing '%s'" % filename) + os.remove(filename) + + +#---------------------------------------------------------------------- +# Move to dist + +def move_to_dist(args): + 'Move candidate artifacts to the distribution directory.' + + if not args.dist_dir: + assert_people() + args.dist_dir = people_dist_dir + + if args.target: + target = args.target + else: + target = os.path.join(os.getenv('HOME'), 'public_html', 'svn', + str(args.version)) + + logging.info('Moving %s to dist dir \'%s\'' % (str(args.version), + args.dist_dir) ) + filenames = glob.glob(os.path.join(target, + 'subversion-%s.*' % str(args.version))) + for filename in filenames: + shutil.copy(filename, args.dist_dir) #---------------------------------------------------------------------- @@ -394,17 +539,15 @@ def post_candidates(args): def write_news(args): 'Write text for the Subversion website.' - version_base, version_extra = split_version(args.version) - data = { 'date' : datetime.date.today().strftime('%Y%m%d'), 'date_pres' : datetime.date.today().strftime('%Y-%m-%d'), - 'version' : args.version, - 'version_base' : version_base[0:3], + 'major-minor' : args.version.base[:3], + 'version' : str(args.version), + 'version_base' : args.version.base, } - if version_extra: - if version_extra.startswith('alpha'): - template_filename = 'rc-news.ezt' + if args.version.is_prerelease(): + template_filename = 'rc-news.ezt' else: template_filename = 'stable-news.ezt' @@ -413,19 +556,36 @@ def write_news(args): template.generate(sys.stdout, data) +def get_sha1info(args): + 'Return a list of sha1 info for the release' + sha1s = glob.glob(os.path.join(get_deploydir(args.base_dir), '*.sha1')) + + class info(object): + pass + + sha1info = [] + for s in sha1s: + i = info() + i.filename = os.path.basename(s)[:-5] + i.sha1 = open(s, 'r').read() + sha1info.append(i) + + return sha1info + + def write_announcement(args): 'Write the release announcement.' - version_base, version_extra = split_version(args.version) + sha1info = get_sha1info(args) - data = { 'version' : args.version, - 'sha1info' : 'foo', - 'siginfo' : 'bar', - 'major-minor' : 'boo', + data = { 'version' : str(args.version), + 'sha1info' : sha1info, + 'siginfo' : open('getsigs-output', 'r').read(), + 'major-minor' : args.version.base[:3], + 'major-minor-patch' : args.version.base, } - if version_extra: - if version_extra.startswith('alpha'): - template_filename = 'rc-release-ann.ezt' + if args.version.is_prerelease(): + template_filename = 'rc-release-ann.ezt' else: template_filename = 'stable-release-ann.ezt' @@ -434,6 +594,77 @@ def write_announcement(args): template.generate(sys.stdout, data) +def write_downloads(args): + 'Output the download section of the website.' + sha1info = get_sha1info(args) + + data = { 'version' : str(args.version), + 'fileinfo' : sha1info, + } + + template = ezt.Template(compress_whitespace = False) + template.parse(get_tmplfile('download.ezt').read()) + template.generate(sys.stdout, data) + + +#---------------------------------------------------------------------- +# Validate the signatures for a release + +key_start = '-----BEGIN PGP SIGNATURE-----\n' +fp_pattern = re.compile(r'^pub\s+(\w+\/\w+)[^\n]*\n\s+Key\sfingerprint\s=((\s+[0-9A-F]{4}){10})\nuid\s+([^<\(]+)\s') + +def check_sigs(args): + 'Check the signatures for the release.' + + try: + import gnupg + except ImportError: + import _gnupg as gnupg + gpg = gnupg.GPG() + + if args.target: + target = args.target + else: + target = os.path.join(os.getenv('HOME'), 'public_html', 'svn', + str(args.version)) + + good_sigs = {} + + for filename in glob.glob(os.path.join(target, 'subversion-*.asc')): + text = open(filename).read() + keys = text.split(key_start) + + for key in keys[1:]: + fd, fn = tempfile.mkstemp() + os.write(fd, key_start + key) + os.close(fd) + verified = gpg.verify_file(open(fn, 'rb'), filename[:-4]) + os.unlink(fn) + + if verified.valid: + good_sigs[verified.key_id[-8:]] = True + else: + sys.stderr.write("BAD SIGNATURE for %s\n" % filename) + sys.exit(1) + + for id in good_sigs.keys(): + gpg = subprocess.Popen(['gpg', '--fingerprint', id], + stdout=subprocess.PIPE, stderr=subprocess.STDOUT) + rc = gpg.wait() + gpg_output = gpg.stdout.read() + if rc: + print(gpg_output) + sys.stderr.write("UNABLE TO GET FINGERPRINT FOR %s" % id) + sys.exit(1) + + gpg_output = "\n".join([ l for l in gpg_output.splitlines() + if l[0:7] != 'Warning' ]) + + fp = fp_pattern.match(gpg_output).groups() + print(" %s [%s] with fingerprint:" % (fp[3], fp[0])) + print(" %s" % fp[1]) + + #---------------------------------------------------------------------- # Main entry point for argument parsing and handling @@ -470,7 +701,7 @@ def main(): subparser = subparsers.add_parser('roll', help='''Create the release artifacts.''') subparser.set_defaults(func=roll_tarballs) - subparser.add_argument('version', + subparser.add_argument('version', type=Version, help='''The release label, such as '1.7.0-alpha1'.''') subparser.add_argument('revnum', type=int, help='''The revision number to base the release on.''') @@ -483,31 +714,71 @@ def main(): The default location is somewhere in ~/public_html. ''') subparser.set_defaults(func=post_candidates) - subparser.add_argument('version', + subparser.add_argument('version', type=Version, help='''The release label, such as '1.7.0-alpha1'.''') subparser.add_argument('revnum', type=int, help='''The revision number to base the release on.''') subparser.add_argument('--target', help='''The full path to the destination.''') - subparser.add_argument('--code-name', - help='''A whimsical name for the release, used only for - naming the download directory.''') + + # The clean-dist subcommand + subparser = subparsers.add_parser('clean-dist', + help='''Clean the distribution directory (and mirrors) of + all but the most recent MAJOR.MINOR release. If no + dist-dir is given, this command will assume it is + running on people.apache.org.''') + subparser.set_defaults(func=clean_dist) + subparser.add_argument('--dist-dir', + help='''The directory to clean.''') + + # The move-to-dist subcommand + subparser = subparsers.add_parser('move-to-dist', + help='''Move candiates and signatures from the temporary + post location to the permanent distribution + directory. If no dist-dir is given, this command + will assume it is running on people.apache.org.''') + subparser.set_defaults(func=move_to_dist) + subparser.add_argument('version', type=Version, + help='''The release label, such as '1.7.0-alpha1'.''') + subparser.add_argument('--dist-dir', + help='''The directory to clean.''') + subparser.add_argument('--target', + help='''The full path to the destination used in + 'post-candiates'..''') # The write-news subcommand subparser = subparsers.add_parser('write-news', help='''Output to stdout template text for use in the news section of the Subversion website.''') subparser.set_defaults(func=write_news) - subparser.add_argument('version', + subparser.add_argument('version', type=Version, help='''The release label, such as '1.7.0-alpha1'.''') subparser = subparsers.add_parser('write-announcement', help='''Output to stdout template text for the emailed release announcement.''') subparser.set_defaults(func=write_announcement) - subparser.add_argument('version', + subparser.add_argument('version', type=Version, help='''The release label, such as '1.7.0-alpha1'.''') + subparser = subparsers.add_parser('write-downloads', + help='''Output to stdout template text for the download + table for subversion.apache.org''') + subparser.set_defaults(func=write_downloads) + subparser.add_argument('version', type=Version, + help='''The release label, such as '1.7.0-alpha1'.''') + + # The check sigs subcommand + subparser = subparsers.add_parser('check-sigs', + help='''Output to stdout the signatures collected for this + release''') + subparser.set_defaults(func=check_sigs) + subparser.add_argument('version', type=Version, + help='''The release label, such as '1.7.0-alpha1'.''') + subparser.add_argument('--target', + help='''The full path to the destination used in + 'post-candiates'..''') + # A meta-target subparser = subparsers.add_parser('clean', help='''The same as the '--clean' switch, but as a
Modified: subversion/branches/svn_mutex/tools/dist/templates/nightly-candidates.ezt URL: http://svn.apache.org/viewvc/subversion/branches/svn_mutex/tools/dist/templates/nightly-candidates.ezt?rev=1182053&r1=1182052&r2=1182053&view=diff ============================================================================== --- subversion/branches/svn_mutex/tools/dist/templates/nightly-candidates.ezt (original) +++ subversion/branches/svn_mutex/tools/dist/templates/nightly-candidates.ezt Tue Oct 11 19:52:34 2011 @@ -59,7 +59,4 @@ made available to users who rely on thei packages.</p> <p>If you want to help us test this distribution of Subversion, you -can find the files <a href="[dirname]/">here</a>.</p> - -</body> -</html> +can find the files below.</p> Modified: subversion/branches/svn_mutex/tools/dist/templates/rc-candidates.ezt URL: http://svn.apache.org/viewvc/subversion/branches/svn_mutex/tools/dist/templates/rc-candidates.ezt?rev=1182053&r1=1182052&r2=1182053&view=diff ============================================================================== --- subversion/branches/svn_mutex/tools/dist/templates/rc-candidates.ezt (original) +++ subversion/branches/svn_mutex/tools/dist/templates/rc-candidates.ezt Tue Oct 11 19:52:34 2011 @@ -57,7 +57,4 @@ clearly denotes that this is not the fin purposes. And please don't do so until it has been publicly announced.</p> <p>If you want to help us test this distribution of Subversion, you -can find the files <a href="[dirname]/">here</a>.</p> - -</body> -</html> +can find the files below.</p> Modified: subversion/branches/svn_mutex/tools/dist/templates/rc-news.ezt URL: http://svn.apache.org/viewvc/subversion/branches/svn_mutex/tools/dist/templates/rc-news.ezt?rev=1182053&r1=1182052&r2=1182053&view=diff ============================================================================== --- subversion/branches/svn_mutex/tools/dist/templates/rc-news.ezt (original) +++ subversion/branches/svn_mutex/tools/dist/templates/rc-news.ezt Tue Oct 11 19:52:34 2011 @@ -4,16 +4,16 @@ title="Link to this section">¶</a> </h3> -<p>We are please to announce to release of Apache Subversion [version]. This +<p>We are pleased to announce to release of Apache Subversion [version]. This release is not intended for production use, but is provided as a milestone to encourage wider testing and feedback from intrepid users and maintainers. Please see the <a href="">release announcement</a> for more information about this release, and the - <a href="/docs/release-notes/[version_base].html">release notes</a> and + <a href="/docs/release-notes/[major-minor].html">release notes</a> and <a href="http://svn.apache.org/repos/asf/subversion/tags/[version]/CHANGES"> change log</a> for information about what will eventually be - in the [version_base].0 release.</p> + in the [version_base] release.</p> <p>To get this release from the nearest mirror, please visit our <a href="/download/#pre-releases">download page</a>.</p> Modified: subversion/branches/svn_mutex/tools/dist/templates/stable-candidates.ezt URL: http://svn.apache.org/viewvc/subversion/branches/svn_mutex/tools/dist/templates/stable-candidates.ezt?rev=1182053&r1=1182052&r2=1182053&view=diff ============================================================================== --- subversion/branches/svn_mutex/tools/dist/templates/stable-candidates.ezt (original) +++ subversion/branches/svn_mutex/tools/dist/templates/stable-candidates.ezt Tue Oct 11 19:52:34 2011 @@ -91,7 +91,4 @@ reputation as a packager and Subversion' but only one will deserve it.</p> <p>If you want to help us test this distribution of Subversion, you -can find the files <a href="[dirname]/">here</a>.</p> - -</body> -</html> +can find the files below.</p> Modified: subversion/branches/svn_mutex/tools/dist/templates/stable-release-ann.ezt URL: http://svn.apache.org/viewvc/subversion/branches/svn_mutex/tools/dist/templates/stable-release-ann.ezt?rev=1182053&r1=1182052&r2=1182053&view=diff ============================================================================== --- subversion/branches/svn_mutex/tools/dist/templates/stable-release-ann.ezt (original) +++ subversion/branches/svn_mutex/tools/dist/templates/stable-release-ann.ezt Tue Oct 11 19:52:34 2011 @@ -5,8 +5,8 @@ Please choose the mirror closest to you The SHA1 checksums are: -[sha1info] - +[for sha1info] [sha1info.sha1] [sha1info.filename] +[end] PGP Signatures are available at: http://www.apache.org/dist/subversion/subversion-[version].tar.bz2.asc @@ -16,7 +16,6 @@ PGP Signatures are available at: For this release, the following people have provided PGP signatures: [siginfo] - Release notes for the [major-minor].x release series may be found at: http://subversion.apache.org/docs/release-notes/[major-minor].html Modified: subversion/branches/svn_mutex/tools/examples/get-location-segments.py URL: http://svn.apache.org/viewvc/subversion/branches/svn_mutex/tools/examples/get-location-segments.py?rev=1182053&r1=1182052&r2=1182053&view=diff ============================================================================== --- subversion/branches/svn_mutex/tools/examples/get-location-segments.py (original) +++ subversion/branches/svn_mutex/tools/examples/get-location-segments.py Tue Oct 11 19:52:34 2011 @@ -21,6 +21,7 @@ # import sys import os +import getpass from svn import client, ra, core def printer(segment, pool): @@ -71,6 +72,39 @@ def parse_args(args): return url, peg_revision, start_revision, end_revision +def prompt_func_ssl_unknown_cert(realm, failures, cert_info, may_save, pool): + print "The certficate details are as follows:" + print "--------------------------------------" + print "Issuer : " + str(cert_info.issuer_dname) + print "Hostname : " + str(cert_info.hostname) + print "ValidFrom : " + str(cert_info.valid_from) + print "ValidUpto : " + str(cert_info.valid_until) + print "Fingerprint: " + str(cert_info.fingerprint) + print "" + ssl_trust = core.svn_auth_cred_ssl_server_trust_t() + if may_save: + choice = raw_input( "accept (t)temporarily (p)permanently: ") + else: + choice = raw_input( "(r)Reject or accept (t)temporarily: ") + if choice[0] == "t" or choice[0] == "T": + ssl_trust.may_save = False + ssl_trust.accepted_failures = failures + elif choice[0] == "p" or choice[0] == "P": + ssl_trust.may_save = True + ssl_trust.accepted_failures = failures + else: + ssl_trust = None + return ssl_trust + +def prompt_func_simple_prompt(realm, username, may_save, pool): + username = raw_input("username: ") + password = getpass.getpass(prompt="password: ") + simple_cred = core.svn_auth_cred_simple_t() + simple_cred.username = username + simple_cred.password = password + simple_cred.may_save = False + return simple_cred + def main(): try: url, peg_revision, start_revision, end_revision = parse_args(sys.argv[1:]) @@ -93,6 +127,9 @@ ERROR: %s ctx = client.ctx_t() providers = [ client.get_simple_provider(), + core.svn_auth_get_ssl_server_trust_file_provider(), + core.svn_auth_get_simple_prompt_provider(prompt_func_simple_prompt, 2), + core.svn_auth_get_ssl_server_trust_prompt_provider(prompt_func_ssl_unknown_cert), client.get_username_provider(), client.get_ssl_server_trust_file_provider(), client.get_ssl_client_cert_file_provider(), Modified: subversion/branches/svn_mutex/tools/hook-scripts/svnperms.py URL: http://svn.apache.org/viewvc/subversion/branches/svn_mutex/tools/hook-scripts/svnperms.py?rev=1182053&r1=1182052&r2=1182053&view=diff ============================================================================== --- subversion/branches/svn_mutex/tools/hook-scripts/svnperms.py (original) +++ subversion/branches/svn_mutex/tools/hook-scripts/svnperms.py Tue Oct 11 19:52:34 2011 @@ -285,7 +285,7 @@ Options: -s NAME Use section NAME as permission section (default is repository name, extracted from repository path) -R REV Query revision REV for commit information (for tests) - -A AUTHOR Check commit as if AUTHOR had commited it (for tests) + -A AUTHOR Check commit as if AUTHOR had committed it (for tests) -h Show this message """ Modified: subversion/branches/svn_mutex/tools/server-side/svn-populate-node-origins-index.c URL: http://svn.apache.org/viewvc/subversion/branches/svn_mutex/tools/server-side/svn-populate-node-origins-index.c?rev=1182053&r1=1182052&r2=1182053&view=diff ============================================================================== --- subversion/branches/svn_mutex/tools/server-side/svn-populate-node-origins-index.c (original) +++ subversion/branches/svn_mutex/tools/server-side/svn-populate-node-origins-index.c Tue Oct 11 19:52:34 2011 @@ -122,7 +122,7 @@ build_index(const char *repos_path, apr_ apr_pool_t *subpool; /* Open the repository. */ - SVN_ERR(svn_repos_open(&repos, repos_path, pool)); + SVN_ERR(svn_repos_open2(&repos, repos_path, NULL, pool)); /* Get a filesystem object. */ fs = svn_repos_fs(repos); Modified: subversion/branches/svn_mutex/tools/server-side/svn-rep-sharing-stats.c URL: http://svn.apache.org/viewvc/subversion/branches/svn_mutex/tools/server-side/svn-rep-sharing-stats.c?rev=1182053&r1=1182052&r2=1182053&view=diff ============================================================================== --- subversion/branches/svn_mutex/tools/server-side/svn-rep-sharing-stats.c (original) +++ subversion/branches/svn_mutex/tools/server-side/svn-rep-sharing-stats.c Tue Oct 11 19:52:34 2011 @@ -390,7 +390,7 @@ static svn_error_t *process(const char * both_reps = apr_hash_make(scratch_pool); /* Open the FS. */ - SVN_ERR(svn_repos_open(&repos, repos_path, scratch_pool)); + SVN_ERR(svn_repos_open2(&repos, repos_path, NULL, scratch_pool)); fs = svn_repos_fs(repos); SVN_ERR(is_fs_fsfs(fs, scratch_pool)); Modified: subversion/branches/svn_mutex/win-tests.py URL: http://svn.apache.org/viewvc/subversion/branches/svn_mutex/win-tests.py?rev=1182053&r1=1182052&r2=1182053&view=diff ============================================================================== --- subversion/branches/svn_mutex/win-tests.py (original) +++ subversion/branches/svn_mutex/win-tests.py Tue Oct 11 19:52:34 2011 @@ -79,6 +79,7 @@ def _usage_exit(): print(" --http-library : dav library to use, neon (default) or serf") print(" --http-short-circuit : Use SVNPathAuthz short_circuit on HTTP server") print(" --disable-http-v2 : Do not advertise support for HTTPv2 on server") + print(" --disable-bulk-updates : Disable bulk updates on HTTP server") print(" --javahl : Run the javahl tests instead of the normal tests") print(" --list : print test doc strings only") print(" --milestone-filter=RE : RE is a regular expression pattern that (when") @@ -126,7 +127,7 @@ opts, args = my_getopt(sys.argv[1:], 'hr 'test=', 'url=', 'svnserve-args=', 'fs-type=', 'asp.net-hack', 'httpd-dir=', 'httpd-port=', 'httpd-daemon', 'httpd-server', 'http-library=', 'http-short-circuit', - 'disable-http-v2', 'help', + 'disable-http-v2', 'disable-bulk-updates', 'help', 'fsfs-packing', 'fsfs-sharding=', 'javahl', 'list', 'enable-sasl', 'bin=', 'parallel', 'config-file=', 'server-minor-version=', @@ -148,6 +149,7 @@ httpd_service = None http_library = 'neon' http_short_circuit = False advertise_httpv2 = True +http_bulk_updates = True list_tests = None milestone_filter = None test_javahl = None @@ -199,8 +201,10 @@ for opt, val in opts: http_library = val elif opt == '--http-short-circuit': http_short_circuit = True - elif opt == 'disable-http-v2': + elif opt == '--disable-http-v2': advertise_httpv2 = False + elif opt == '--disable-bulk-updates': + http_bulk_updates = False elif opt == '--fsfs-sharding': fsfs_sharding = int(val) elif opt == '--fsfs-packing': @@ -424,7 +428,7 @@ class Svnserve: class Httpd: "Run httpd for DAV tests" def __init__(self, abs_httpd_dir, abs_objdir, abs_builddir, httpd_port, - service, httpv2, short_circuit): + service, httpv2, short_circuit, bulk_updates): self.name = 'apache.exe' self.httpd_port = httpd_port self.httpd_dir = abs_httpd_dir @@ -434,6 +438,11 @@ class Httpd: else: self.httpv2_option = 'off' + if bulk_updates: + self.bulkupdates_option = 'on' + else: + self.bulkupdates_option = 'off' + self.service = service self.proc_handle = None self.path = os.path.join(self.httpd_dir, 'bin', self.name) @@ -578,6 +587,7 @@ class Httpd: ' SVNParentPath ' + self._quote(path) + '\n' \ ' SVNAdvertiseV2Protocol ' + self.httpv2_option + '\n' \ ' SVNPathAuthz ' + self.path_authz_option + '\n' \ + ' SVNAllowBulkUpdates ' + self.bulkupdates_option + '\n' \ ' AuthzSVNAccessFile ' + self._quote(self.authz_file) + '\n' \ ' AuthType Basic\n' \ ' AuthName "Subversion Repository"\n' \ @@ -646,6 +656,8 @@ if create_dirs: baton = copied_execs for dirpath, dirs, files in os.walk('subversion'): copy_execs(baton, dirpath, dirs + files) + for dirpath, dirs, files in os.walk('tools/client-side/svnmucc'): + copy_execs(baton, dirpath, dirs + files) except: os.chdir(old_cwd) raise @@ -668,7 +680,8 @@ if not list_tests: if run_httpd: daemon = Httpd(abs_httpd_dir, abs_objdir, abs_builddir, httpd_port, - httpd_service, advertise_httpv2, http_short_circuit) + httpd_service, advertise_httpv2, http_short_circuit, + http_bulk_updates) # Start service daemon, if any if daemon: