~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/branch.py

  • Committer: Jelmer Vernooij
  • Date: 2012-01-05 16:03:11 UTC
  • mfrom: (6432 +trunk)
  • mto: This revision was merged to the branch mainline in revision 6433.
  • Revision ID: jelmer@samba.org-20120105160311-12o5p67kin1v3zps
Merge bzr.dev.

Show diffs side-by-side

added added

removed removed

Lines of Context:
14
14
# along with this program; if not, write to the Free Software
15
15
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
16
16
 
 
17
from __future__ import absolute_import
 
18
 
17
19
import bzrlib.bzrdir
18
20
 
19
21
from cStringIO import StringIO
46
48
from bzrlib.i18n import gettext, ngettext
47
49
""")
48
50
 
 
51
# Explicitly import bzrlib.bzrdir so that the BzrProber
 
52
# is guaranteed to be registered.
 
53
import bzrlib.bzrdir
 
54
 
49
55
from bzrlib import (
 
56
    bzrdir,
50
57
    controldir,
51
58
    )
52
59
from bzrlib.decorators import (
174
181
        For instance, if the branch is at URL/.bzr/branch,
175
182
        Branch.open(URL) -> a Branch instance.
176
183
        """
177
 
        control = controldir.ControlDir.open(base, _unsupported,
178
 
                                     possible_transports=possible_transports)
 
184
        control = controldir.ControlDir.open(base,
 
185
            possible_transports=possible_transports, _unsupported=_unsupported)
179
186
        return control.open_branch(unsupported=_unsupported,
180
187
            possible_transports=possible_transports)
181
188
 
1163
1170
    def _set_config_location(self, name, url, config=None,
1164
1171
                             make_relative=False):
1165
1172
        if config is None:
1166
 
            config = self.get_config()
 
1173
            config = self.get_config_stack()
1167
1174
        if url is None:
1168
1175
            url = ''
1169
1176
        elif make_relative:
1170
1177
            url = urlutils.relative_url(self.base, url)
1171
 
        config.set_user_option(name, url, warn_masked=True)
 
1178
        config.set(name, url)
1172
1179
 
1173
1180
    def _get_config_location(self, name, config=None):
1174
1181
        if config is None:
1175
 
            config = self.get_config()
1176
 
        location = config.get_user_option(name)
 
1182
            config = self.get_config_stack()
 
1183
        location = config.get(name)
1177
1184
        if location == '':
1178
1185
            location = None
1179
1186
        return location
1180
1187
 
1181
1188
    def get_child_submit_format(self):
1182
1189
        """Return the preferred format of submissions to this branch."""
1183
 
        return self.get_config().get_user_option("child_submit_format")
 
1190
        return self.get_config_stack().get('child_submit_format')
1184
1191
 
1185
1192
    def get_submit_branch(self):
1186
1193
        """Return the submit location of the branch.
1189
1196
        pattern is that the user can override it by specifying a
1190
1197
        location.
1191
1198
        """
1192
 
        return self.get_config().get_user_option('submit_branch')
 
1199
        return self.get_config_stack().get('submit_branch')
1193
1200
 
1194
1201
    def set_submit_branch(self, location):
1195
1202
        """Return the submit location of the branch.
1198
1205
        pattern is that the user can override it by specifying a
1199
1206
        location.
1200
1207
        """
1201
 
        self.get_config().set_user_option('submit_branch', location,
1202
 
            warn_masked=True)
 
1208
        self.get_config_stack().set('submit_branch', location)
1203
1209
 
1204
1210
    def get_public_branch(self):
1205
1211
        """Return the public location of the branch.
1218
1224
        self._set_config_location('public_branch', location)
1219
1225
 
1220
1226
    def get_push_location(self):
1221
 
        """Return the None or the location to push this branch to."""
1222
 
        push_loc = self.get_config().get_user_option('push_location')
1223
 
        return push_loc
 
1227
        """Return None or the location to push this branch to."""
 
1228
        return self.get_config_stack().get('push_location')
1224
1229
 
1225
1230
    def set_push_location(self, location):
1226
1231
        """Set a new push location for this branch."""
1559
1564
            heads that must be fetched if present, but no error is necessary if
1560
1565
            they are not present.
1561
1566
        """
1562
 
        # For bzr native formats must_fetch is just the tip, and if_present_fetch
1563
 
        # are the tags.
 
1567
        # For bzr native formats must_fetch is just the tip, and
 
1568
        # if_present_fetch are the tags.
1564
1569
        must_fetch = set([self.last_revision()])
1565
1570
        if_present_fetch = set()
1566
 
        c = self.get_config()
1567
 
        include_tags = c.get_user_option_as_bool('branch.fetch_tags',
1568
 
                                                 default=False)
1569
 
        if include_tags:
 
1571
        if self.get_config_stack().get('branch.fetch_tags'):
1570
1572
            try:
1571
1573
                if_present_fetch = set(self.tags.get_reverse_tag_dict())
1572
1574
            except errors.TagsNotSupported:
1581
1583
 
1582
1584
    Formats provide three things:
1583
1585
     * An initialization routine,
1584
 
     * a format string,
 
1586
     * a format description
1585
1587
     * an open routine.
1586
1588
 
1587
1589
    Formats are placed in an dict by their format string for reference
1993
1995
            self.revision_id)
1994
1996
 
1995
1997
 
1996
 
class BranchFormatMetadir(bzrdir.BzrDirMetaComponentFormat, BranchFormat):
 
1998
class BranchFormatMetadir(bzrdir.BzrFormat, BranchFormat):
1997
1999
    """Base class for branch formats that live in meta directories.
1998
2000
    """
1999
2001
 
2000
2002
    def __init__(self):
2001
2003
        BranchFormat.__init__(self)
2002
 
        bzrdir.BzrDirMetaComponentFormat.__init__(self)
 
2004
        bzrdir.BzrFormat.__init__(self)
2003
2005
 
2004
2006
    @classmethod
2005
2007
    def find_format(klass, controldir, name=None):
2043
2045
        control_files.create_lock()
2044
2046
        control_files.lock_write()
2045
2047
        try:
2046
 
            utf8_files += [('format', self.get_format_string())]
 
2048
            utf8_files += [('format', self.as_string())]
2047
2049
            for (filename, content) in utf8_files:
2048
2050
                branch_transport.put_bytes(
2049
2051
                    filename, content,
2091
2093
    def supports_leaving_lock(self):
2092
2094
        return True
2093
2095
 
 
2096
    def check_support_status(self, allow_unsupported, recommend_upgrade=True,
 
2097
            basedir=None):
 
2098
        BranchFormat.check_support_status(self,
 
2099
            allow_unsupported=allow_unsupported, recommend_upgrade=recommend_upgrade,
 
2100
            basedir=basedir)
 
2101
        bzrdir.BzrFormat.check_support_status(self, allow_unsupported=allow_unsupported,
 
2102
            recommend_upgrade=recommend_upgrade, basedir=basedir)
 
2103
 
2094
2104
 
2095
2105
class BzrBranchFormat5(BranchFormatMetadir):
2096
2106
    """Bzr branch format 5.
2298
2308
        branch_transport = a_bzrdir.get_branch_transport(self, name=name)
2299
2309
        branch_transport.put_bytes('location',
2300
2310
            target_branch.user_url)
2301
 
        branch_transport.put_bytes('format', self.get_format_string())
 
2311
        branch_transport.put_bytes('format', self.as_string())
2302
2312
        branch = self.open(
2303
2313
            a_bzrdir, name, _found=True,
2304
2314
            possible_transports=[target_branch.bzrdir.root_transport])
2706
2716
        self._transport.put_bytes('last-revision', out_string,
2707
2717
            mode=self.bzrdir._get_file_mode())
2708
2718
 
 
2719
    @needs_write_lock
 
2720
    def update_feature_flags(self, updated_flags):
 
2721
        """Update the feature flags for this branch.
 
2722
 
 
2723
        :param updated_flags: Dictionary mapping feature names to necessities
 
2724
            A necessity can be None to indicate the feature should be removed
 
2725
        """
 
2726
        self._format._update_feature_flags(updated_flags)
 
2727
        self.control_transport.put_bytes('format', self._format.as_string())
 
2728
 
2709
2729
 
2710
2730
class FullHistoryBzrBranch(BzrBranch):
2711
2731
    """Bzr branch which contains the full revision history."""
2961
2981
        """See Branch.set_push_location."""
2962
2982
        self._master_branch_cache = None
2963
2983
        result = None
2964
 
        config = self.get_config()
 
2984
        conf = self.get_config_stack()
2965
2985
        if location is None:
2966
 
            if config.get_user_option('bound') != 'True':
 
2986
            if not conf.get('bound'):
2967
2987
                return False
2968
2988
            else:
2969
 
                config.set_user_option('bound', 'False', warn_masked=True)
 
2989
                conf.set('bound', 'False')
2970
2990
                return True
2971
2991
        else:
2972
2992
            self._set_config_location('bound_location', location,
2973
 
                                      config=config)
2974
 
            config.set_user_option('bound', 'True', warn_masked=True)
 
2993
                                      config=conf)
 
2994
            conf.set('bound', 'True')
2975
2995
        return True
2976
2996
 
2977
2997
    def _get_bound_location(self, bound):
2978
2998
        """Return the bound location in the config file.
2979
2999
 
2980
3000
        Return None if the bound parameter does not match"""
2981
 
        config = self.get_config()
2982
 
        config_bound = (config.get_user_option('bound') == 'True')
2983
 
        if config_bound != bound:
 
3001
        conf = self.get_config_stack()
 
3002
        if conf.get('bound') != bound:
2984
3003
            return None
2985
 
        return self._get_config_location('bound_location', config=config)
 
3004
        return self._get_config_location('bound_location', config=conf)
2986
3005
 
2987
3006
    def get_bound_location(self):
2988
 
        """See Branch.set_push_location."""
 
3007
        """See Branch.get_bound_location."""
2989
3008
        return self._get_bound_location(True)
2990
3009
 
2991
3010
    def get_old_bound_location(self):
2998
3017
        ## self._check_stackable_repo()
2999
3018
        # stacked_on_location is only ever defined in branch.conf, so don't
3000
3019
        # waste effort reading the whole stack of config files.
3001
 
        config = self.get_config()._get_branch_data_config()
 
3020
        conf = _mod_config.BranchOnlyStack(self)
3002
3021
        stacked_url = self._get_config_location('stacked_on_location',
3003
 
            config=config)
 
3022
                                                config=conf)
3004
3023
        if stacked_url is None:
3005
3024
            raise errors.NotStacked(self)
3006
 
        return stacked_url
 
3025
        return stacked_url.encode('utf-8')
3007
3026
 
3008
3027
    @needs_read_lock
3009
3028
    def get_rev_id(self, revno, history=None):
3213
3232
 
3214
3233
        # Copying done; now update target format
3215
3234
        new_branch._transport.put_bytes('format',
3216
 
            format.get_format_string(),
 
3235
            format.as_string(),
3217
3236
            mode=new_branch.bzrdir._get_file_mode())
3218
3237
 
3219
3238
        # Clean up old files
3232
3251
        format = BzrBranchFormat7()
3233
3252
        branch._set_config_location('stacked_on_location', '')
3234
3253
        # update target format
3235
 
        branch._transport.put_bytes('format', format.get_format_string())
 
3254
        branch._transport.put_bytes('format', format.as_string())
3236
3255
 
3237
3256
 
3238
3257
class Converter7to8(object):
3242
3261
        format = BzrBranchFormat8()
3243
3262
        branch._transport.put_bytes('references', '')
3244
3263
        # update target format
3245
 
        branch._transport.put_bytes('format', format.get_format_string())
 
3264
        branch._transport.put_bytes('format', format.as_string())
3246
3265
 
3247
3266
 
3248
3267
class InterBranch(InterObject):