/brz/remove-bazaar

To get this branch, use:
bzr branch http://gegoxaren.bato24.eu/bzr/brz/remove-bazaar

« back to all changes in this revision

Viewing changes to bzrlib/plugins/multiparent.py

  • Committer: Robert Collins
  • Date: 2008-01-06 20:04:22 UTC
  • mto: (3221.11.1 StackableBranch)
  • mto: This revision was merged to the branch mainline in revision 3226.
  • Revision ID: robertc@robertcollins.net-20080106200422-x8yz6cxotlzltvwp
The bzrdir format registry now accepts an ``alias`` keyword to
register_metadir, used to indicate that a format name is an alias for
some other format and thus should not be reported when describing the
format. (Robert Collins)
-------------- This line and the fmllowing will be ignored --------------

modified:
  NEWS
  bzrlib/bzrdir.py
  bzrlib/info.py
  bzrlib/tests/test_bzrdir.py
  bzrlib/tests/test_info.py

=== modified file 'NEWS'
--- a/NEWS      2008-01-02 22:30:46 +0000
+++ b/NEWS      2008-01-06 20:04:15 +0000
@@ -135,6 +135,11 @@
     * Patience Diff now supports arbitrary python objects, as long as they
       support ``hash()``. (John Arbash Meinel)
 
+    * The bzrdir format registry now accepts an ``alias`` keyword to
+      register_metadir, used to indicate that a format name is an alias for
+      some other format and thus should not be reported when describing the
+      format. (Robert Collins)
+
   API BREAKS:
 
   TESTING:

=== modified file 'bzrlib/bzrdir.py'
--- a/bzrlib/bzrdir.py  2008-01-02 22:30:46 +0000
+++ b/bzrlib/bzrdir.py  2008-01-06 19:41:29 +0000
@@ -2447,12 +2447,22 @@
     e.g. BzrDirMeta1 with weave repository.  Also, it's more user-oriented.
     """
 
+    def __init__(self):
+        """Create a BzrDirFormatRegistry."""
+        self._aliases = set()
+        super(BzrDirFormatRegistry, self).__init__()
+
+    def aliases(self):
+        """Return a set of the format names which are aliases."""
+        return frozenset(self._aliases)
+
     def register_metadir(self, key,
              repository_format, help, native=True, deprecated=False,
              branch_format=None,
              tree_format=None,
              hidden=False,
-             experimental=False):
+             experimental=False,
+             alias=False):
         """Register a metadir subformat.
 
         These all use a BzrDirMetaFormat1 bzrdir, but can be parameterized
@@ -2491,10 +2501,10 @@
                 bd.repository_format = _load(repository_format)
             return bd
         self.register(key, helper, help, native, deprecated, hidden,
-            experimental)
+            experimental, alias)
 
     def register(self, key, factory, help, native=True, deprecated=False,
-                 hidden=False, experimental=False):
+                 hidden=False, experimental=False, alias=False):
         """Register a BzrDirFormat factory.
         
         The factory must be a callable that takes one parameter: the key.
@@ -2505,11 +2515,15 @@
         """
         registry.Registry.register(self, key, factory, help,
             BzrDirFormatInfo(native, deprecated, hidden, experimental))
+        if alias:
+            self._aliases.add(key)
 
     def register_lazy(self, key, module_name, member_name, help, native=True,
-                      deprecated=False, hidden=False, experimental=False):
+        deprecated=False, hidden=False, experimental=False, alias=False):
         registry.Registry.register_lazy(self, key, module_name, member_name,
             help, BzrDirFormatInfo(native, deprecated, hidden, experimental))
+        if alias:
+            self._aliases.add(key)
 
     def set_default(self, key):
         """Set the 'default' key to be a clone of the supplied key.
@@ -2518,6 +2532,7 @@
         """
         registry.Registry.register(self, 'default', self.get(key),
             self.get_help(key), info=self.get_info(key))
+        self._aliases.add('default')
 
     def set_default_repository(self, key):
         """Set the FormatRegistry default and Repository default.
@@ -2670,6 +2685,7 @@
     tree_format='bzrlib.workingtree.WorkingTreeFormat4',
     hidden=False,
     )
+# The following two formats should always just be aliases.
 format_registry.register_metadir('development',
     'bzrlib.repofmt.pack_repo.RepositoryFormatPackDevelopment0',
     help='Current development format. Can convert data to and from pack-0.92 '
@@ -2681,6 +2697,7 @@
     branch_format='bzrlib.branch.BzrBranchFormat6',
     tree_format='bzrlib.workingtree.WorkingTreeFormat4',
     experimental=True,
+    alias=True,
     )
 format_registry.register_metadir('development-subtree',
     'bzrlib.repofmt.pack_repo.RepositoryFormatPackDevelopment0Subtree',
@@ -2693,7 +2710,9 @@
     branch_format='bzrlib.branch.BzrBranchFormat6',
     tree_format='bzrlib.workingtree.WorkingTreeFormat4',
     experimental=True,
+    alias=True,
     )
+# And the development formats which the will have aliased one of follow:
 format_registry.register_metadir('development0',
     'bzrlib.repofmt.pack_repo.RepositoryFormatPackDevelopment0',
     help='Trivial rename of pack-0.92 to provide a development format. '

=== modified file 'bzrlib/info.py'
--- a/bzrlib/info.py    2007-11-06 09:00:25 +0000
+++ b/bzrlib/info.py    2008-01-06 20:01:30 +0000
@@ -440,7 +440,9 @@
         tree.bzrdir.root_transport.base):
         branch = None
         repository = None
-    for key in bzrdir.format_registry.keys():
+    non_aliases = set(bzrdir.format_registry.keys())
+    non_aliases.difference_update(bzrdir.format_registry.aliases())
+    for key in non_aliases:
         format = bzrdir.format_registry.make_bzrdir(key)
         if isinstance(format, bzrdir.BzrDirMetaFormat1):
             if (tree and format.workingtree_format !=
@@ -457,11 +459,12 @@
         candidates.append(key)
     if len(candidates) == 0:
         return 'unnamed'
-    new_candidates = [c for c in candidates if c != 'default']
-    if len(new_candidates) > 0:
-        candidates = new_candidates
+    candidates.sort()
     new_candidates = [c for c in candidates if not
         bzrdir.format_registry.get_info(c).hidden]
     if len(new_candidates) > 0:
+        # If there are any non-hidden formats that match, only return those to
+        # avoid listing hidden formats except when only a hidden format will
+        # do.
         candidates = new_candidates
     return ' or '.join(candidates)

=== modified file 'bzrlib/tests/test_bzrdir.py'
--- a/bzrlib/tests/test_bzrdir.py       2007-12-21 20:32:22 +0000
+++ b/bzrlib/tests/test_bzrdir.py       2008-01-06 19:45:00 +0000
@@ -170,6 +170,16 @@
         finally:
             bzrdir.format_registry.set_default_repository(old_default)
 
+    def test_aliases(self):
+        a_registry = bzrdir.BzrDirFormatRegistry()
+        a_registry.register('weave', bzrdir.BzrDirFormat6,
+            'Pre-0.8 format.  Slower and does not support checkouts or shared'
+            ' repositories', deprecated=True)
+        a_registry.register('weavealias', bzrdir.BzrDirFormat6,
+            'Pre-0.8 format.  Slower and does not support checkouts or shared'
+            ' repositories', deprecated=True, alias=True)
+        self.assertEqual(frozenset(['weavealias']), a_registry.aliases())
+    
 
 class SampleBranch(bzrlib.branch.Branch):
     """A dummy branch for guess what, dummy use."""

=== modified file 'bzrlib/tests/test_info.py'
--- a/bzrlib/tests/test_info.py 2007-11-26 13:55:51 +0000
+++ b/bzrlib/tests/test_info.py 2008-01-06 20:02:10 +0000
@@ -126,16 +126,22 @@
 
     def test_describe_tree_format(self):
         for key in bzrdir.format_registry.keys():
-            if key == 'default':
+            if key in bzrdir.format_registry.aliases():
                 continue
             self.assertTreeDescription(key)
 
     def test_describe_checkout_format(self):
         for key in bzrdir.format_registry.keys():
-            if key in ('default', 'weave', 'experimental'):
-                continue
-            if key.startswith('experimental-'):
-                # these are typically hidden or aliases for other formats
+            if key in bzrdir.format_registry.aliases():
+                # Aliases will not describe correctly in the UI because the
+                # real format is found.
+                continue
+            # legacy: weave does not support checkouts
+            if key == 'weave':
+                continue
+            if bzrdir.format_registry.get_info(key).experimental:
+                # We don't require that experimental formats support checkouts
+                # or describe correctly in the UI.
                 continue
             expected = None
             if key in ('dirstate', 'dirstate-tags', 'dirstate-with-subtree',
@@ -149,7 +155,7 @@
 
     def test_describe_branch_format(self):
         for key in bzrdir.format_registry.keys():
-            if key == 'default':
+            if key in bzrdir.format_registry.aliases():
                 continue
             expected = None
             if key in ('dirstate', 'knit'):
@@ -158,7 +164,7 @@
 
     def test_describe_repo_format(self):
         for key in bzrdir.format_registry.keys():
-            if key == 'default':
+            if key in bzrdir.format_registry.aliases():
                 continue
             expected = None
             if key in ('dirstate', 'knit', 'dirstate-tags'):

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
"""Implementation of multiparent diffs for versionedfile-like storage
 
2
 
 
3
Provides mp-regen and mp-extract commands.
 
4
Focus is on comparing size/performance to knits.
 
5
"""
 
6
 
 
7
from bzrlib.lazy_import import lazy_import
 
8
 
 
9
lazy_import(globals(), """
 
10
import (
 
11
        errno,
 
12
        os,
 
13
        sys,
 
14
        time,
 
15
        )
 
16
 
 
17
from bzrlib import (
 
18
    commands,
 
19
    urlutils
 
20
    )
 
21
from bzrlib.workingtree import WorkingTree
 
22
from bzrlib.tests import TestUtil
 
23
 
 
24
from bzrlib.plugins.multiparent.multiparent import (
 
25
    MultiVersionedFile,
 
26
    MultiMemoryVersionedFile,
 
27
    )
 
28
""")
 
29
 
 
30
class cmd_mp_regen(commands.Command):
 
31
    """Generate a multiparent versionedfile"""
 
32
 
 
33
    hidden = True
 
34
 
 
35
    takes_args = ['file?']
 
36
 
 
37
    takes_options = [commands.Option('sync-snapshots',
 
38
                                     help='Snapshots follow source.'),
 
39
                     commands.Option('snapshot-interval', type=int,
 
40
                                     help='Take snapshots every x revisions.'),
 
41
                     commands.Option('outfile', type=unicode,
 
42
                                     help='Write pseudo-knit to this file.'),
 
43
                     commands.Option('memory', help='Use memory, not disk.'),
 
44
                     commands.Option('extract', help='Test extract time.'),
 
45
                     commands.Option('single', help='Use a single parent.'),
 
46
                     commands.Option('verify', help='Verify added texts.'),
 
47
                     commands.Option('cache', help='Aggresively cache.'),
 
48
                     commands.Option('size', help='Aggressive size.'),
 
49
                     commands.Option('build', help='Aggressive build.'),
 
50
                    ]
 
51
    hidden = True
 
52
 
 
53
    def run(self, file=None, sync_snapshots=False, snapshot_interval=26,
 
54
            lsprof_timed=False, dump=False, extract=False, single=False,
 
55
            verify=False, outfile=None, memory=False, cache=False,
 
56
            size=False, build=False):
 
57
        file_weave = get_file_weave(file)
 
58
        url = file_weave.transport.abspath(file_weave.filename)
 
59
        sys.stderr.write('Importing: %s\n' % \
 
60
            urlutils.local_path_from_url(url))
 
61
        if sync_snapshots:
 
62
            sys.stderr.write('Snapshots follow input\n')
 
63
        else:
 
64
            sys.stderr.write('Snapshot interval: %d\n' % snapshot_interval)
 
65
        if not memory:
 
66
            if outfile is None:
 
67
                filename = 'pknit'
 
68
            else:
 
69
                filename = outfile
 
70
            vf = MultiVersionedFile(filename, snapshot_interval)
 
71
        else:
 
72
            vf = MultiMemoryVersionedFile(snapshot_interval)
 
73
        vf.destroy()
 
74
        old_snapshots = set(r for r in file_weave.versions() if
 
75
                        file_weave._index.get_method(r) == 'fulltext')
 
76
        if sync_snapshots:
 
77
            to_sync = old_snapshots
 
78
        elif size or build:
 
79
            assert memory
 
80
            to_sync = set()
 
81
        else:
 
82
            to_sync = vf.select_snapshots(file_weave)
 
83
        sys.stderr.write("%d fulltext(s)\n" % len(old_snapshots))
 
84
        sys.stderr.write("%d planned snapshots\n" % len(to_sync))
 
85
 
 
86
        try:
 
87
            vf.import_versionedfile(file_weave, to_sync, single_parent=single,
 
88
                                    verify=verify, no_cache=not cache)
 
89
            if size:
 
90
                snapshots = vf.select_by_size(len(old_snapshots))
 
91
                for version_id in snapshots:
 
92
                    vf.make_snapshot(version_id)
 
93
            if build:
 
94
                ranking = vf.get_build_ranking()
 
95
                snapshots = ranking[:len(old_snapshots) -\
 
96
                    len(vf._snapshots)]
 
97
                for version_id in snapshots:
 
98
                    vf.make_snapshot(version_id)
 
99
        except:
 
100
            vf.destroy()
 
101
            raise
 
102
        try:
 
103
            sys.stderr.write("%d actual snapshots\n" % len(vf._snapshots))
 
104
            if not cache:
 
105
                vf.clear_cache()
 
106
            if memory:
 
107
                if outfile is not None:
 
108
                    vf_file = MultiVersionedFile(outfile)
 
109
                vf_file.import_diffs(vf)
 
110
            else:
 
111
                vf_file = vf
 
112
        finally:
 
113
            if outfile is None:
 
114
                vf.destroy()
 
115
            else:
 
116
                vf_file.save()
 
117
 
 
118
class cmd_mp_extract(commands.Command):
 
119
    """Test extraction time multiparent knits"""
 
120
 
 
121
    hidden = True
 
122
 
 
123
    takes_options = [
 
124
        commands.Option('lsprof-timed', help='Use lsprof.'),
 
125
        commands.Option('parallel', help='Extract multiple versions at once.'),
 
126
        commands.Option('count', help='Number of cycles to do.', type=int),
 
127
        ]
 
128
 
 
129
    takes_args = ['filename', 'vfile?']
 
130
 
 
131
    def run(self, filename, vfile=None, lsprof_timed=False, count=1000,
 
132
            parallel=False):
 
133
        vf = MultiVersionedFile(filename)
 
134
        vf.load()
 
135
        snapshots = [r for r in vf.versions() if vf.get_diff(r).is_snapshot()]
 
136
        print '%d snapshots' % len(snapshots)
 
137
        revisions = list(vf.versions())
 
138
        revisions = revisions[-count:]
 
139
        print 'Testing extract time of %d revisions' % len(revisions)
 
140
        if parallel:
 
141
            revisions_list = [revisions]
 
142
        else:
 
143
            revisions_list = [[r] for r in revisions]
 
144
        start = time.clock()
 
145
        for revisions in revisions_list:
 
146
            vf = MultiVersionedFile(filename)
 
147
            vf.load()
 
148
            vf.get_line_list(revisions)
 
149
        sys.stderr.write(time.clock() - start)
 
150
        sys.stderr.write('\n')
 
151
        if lsprof_timed:
 
152
            from bzrlib.lsprof import profile
 
153
            vf.clear_cache()
 
154
            ret, stats = profile(vf.get_line_list, revisions_list[-1][-1])
 
155
            stats.sort()
 
156
            stats.pprint()
 
157
        start = time.clock()
 
158
        for revisions in revisions_list:
 
159
            file_weave = get_file_weave(vfile)
 
160
            file_weave.get_line_list(revisions)
 
161
        sys.stderr.write(time.clock() - start)
 
162
        sys.stderr.write('\n')
 
163
 
 
164
 
 
165
def get_file_weave(filename=None, wt=None):
 
166
    if filename is None:
 
167
        wt, path = WorkingTree.open_containing('.')
 
168
        return wt.branch.repository.get_inventory_weave()
 
169
    else:
 
170
        wt, path = WorkingTree.open_containing(filename)
 
171
        file_id = wt.path2id(path)
 
172
        bt = wt.branch.repository.revision_tree(wt.last_revision())
 
173
        return bt.get_weave(file_id)
 
174
 
 
175
 
 
176
commands.register_command(cmd_mp_regen)
 
177
commands.register_command(cmd_mp_extract)