~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/commands.py

Merge bzr.dev

Show diffs side-by-side

added added

removed removed

Lines of Context:
32
32
import os
33
33
from warnings import warn
34
34
import errno
 
35
import codecs
35
36
 
36
37
import bzrlib
37
38
from bzrlib.errors import (BzrError,
189
190
    hidden
190
191
        If true, this command isn't advertised.  This is typically
191
192
        for commands intended for expert users.
 
193
 
 
194
    encoding_type
 
195
        Command objects will get a 'outf' attribute, which has been
 
196
        setup to properly handle encoding of unicode strings.
 
197
        encoding_type determines what will happen when characters cannot
 
198
        be encoded
 
199
            strict - abort if we cannot decode
 
200
            replace - put in a bogus character (typically '?')
 
201
            exact - do not encode sys.stdout
 
202
 
192
203
    """
193
204
    aliases = []
194
205
    takes_args = []
195
206
    takes_options = []
 
207
    encoding_type = 'strict'
196
208
 
197
209
    hidden = False
198
210
    
213
225
            r[o.name] = o
214
226
        return r
215
227
 
 
228
    def _setup_outf(self):
 
229
        """Return a file linked to stdout, which has proper encoding."""
 
230
        assert self.encoding_type in ['strict', 'exact', 'replace']
 
231
 
 
232
        # Originally I was using self.stdout, but that looks
 
233
        # *way* too much like sys.stdout
 
234
        if self.encoding_type == 'exact':
 
235
            self.outf = sys.stdout
 
236
            return
 
237
 
 
238
        output_encoding = getattr(sys.stdout, 'encoding', None)
 
239
        if not output_encoding:
 
240
            output_encoding = bzrlib.user_encoding
 
241
            mutter('encoding stdout bzrlib.user_encoding %r', output_encoding)
 
242
        else:
 
243
            mutter('encoding stdout log as sys.stdout encoding %r', output_encoding)
 
244
 
 
245
        # use 'replace' so that we don't abort if trying to write out
 
246
        # in e.g. the default C locale.
 
247
        self.outf = codecs.getwriter(output_encoding)(sys.stdout, errors=self.encoding_type)
 
248
 
216
249
    @deprecated_method(zero_eight)
217
250
    def run_argv(self, argv):
218
251
        """Parse command line and run.
243
276
        all_cmd_args = cmdargs.copy()
244
277
        all_cmd_args.update(cmdopts)
245
278
 
 
279
        self._setup_outf()
 
280
 
246
281
        return self.run(**all_cmd_args)
247
282
    
248
283
    def run(self):
512
547
    
513
548
    argv
514
549
       The command-line arguments, without the program name from argv[0]
 
550
       These should already be decoded. All library/test code calling
 
551
       run_bzr should be passing valid strings (don't need decoding).
515
552
    
516
553
    Returns a command status or raises an exception.
517
554
 
534
571
    --lsprof
535
572
        Run under the Python lsprof profiler.
536
573
    """
537
 
    argv = [a.decode(bzrlib.user_encoding) for a in argv]
 
574
    argv = list(argv)
538
575
 
539
576
    opt_lsprof = opt_profile = opt_no_plugins = opt_builtin =  \
540
577
                opt_no_aliases = False
639
676
    ## bzrlib.trace.enable_default_logging()
640
677
    bzrlib.trace.log_startup(argv)
641
678
    bzrlib.ui.ui_factory = TextUIFactory()
642
 
    ret = run_bzr_catch_errors(argv[1:])
 
679
 
 
680
    argv = [a.decode(bzrlib.user_encoding) for a in argv[1:]]
 
681
    ret = run_bzr_catch_errors(argv)
643
682
    mutter("return code %d", ret)
644
683
    return ret
645
684