~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/rio.py

  • Committer: Robert Collins
  • Date: 2009-05-11 01:59:06 UTC
  • mto: This revision was merged to the branch mainline in revision 4593.
  • Revision ID: robertc@robertcollins.net-20090511015906-6zi6a9b8tuuhipc8
Less lock thrashing in check.py.

Show diffs side-by-side

added added

removed removed

Lines of Context:
129
129
                            % (value, type(value)))
130
130
        self.items.append((tag, value))
131
131
 
132
 
    @classmethod
133
 
    def from_pairs(cls, pairs):
134
 
        ret = cls()
135
 
        ret.items = pairs
136
 
        return ret
137
 
 
138
132
    def __contains__(self, find_tag):
139
133
        """True if there is any field in this stanza with the given tag."""
140
134
        for tag, value in self.items:
197
191
 
198
192
        result = []
199
193
        for tag, value in self.items:
200
 
            if value == u'':
201
 
                result.append(tag + u': \n')
202
 
            elif u'\n' in value:
 
194
            if value == '':
 
195
                result.append(tag + ': \n')
 
196
            elif '\n' in value:
203
197
                # don't want splitlines behaviour on empty lines
204
 
                val_lines = value.split(u'\n')
205
 
                result.append(tag + u': ' + val_lines[0] + u'\n')
 
198
                val_lines = value.split('\n')
 
199
                result.append(tag + ': ' + val_lines[0] + '\n')
206
200
                for line in val_lines[1:]:
207
 
                    result.append(u'\t' + line + u'\n')
 
201
                    result.append('\t' + line + '\n')
208
202
            else:
209
 
                result.append(tag + u': ' + value + u'\n')
 
203
                result.append(tag + ': ' + value + '\n')
210
204
        return u''.join(result)
211
205
 
212
206
    def write(self, to_file):
242
236
            d[tag] = value
243
237
        return d
244
238
 
245
 
 
 
239
_tag_re = re.compile(r'^[-a-zA-Z0-9_]+$')
246
240
def valid_tag(tag):
247
 
    return _valid_tag(tag)
 
241
    return bool(_tag_re.match(tag))
248
242
 
249
243
 
250
244
def read_stanza(line_iter):
260
254
 
261
255
    The raw lines must be in utf-8 encoding.
262
256
    """
263
 
    return _read_stanza_utf8(line_iter)
 
257
    unicode_iter = (line.decode('utf-8') for line in line_iter)
 
258
    return read_stanza_unicode(unicode_iter)
264
259
 
265
260
 
266
261
def read_stanza_unicode(unicode_iter):
280
275
    :return: A Stanza object if there are any lines in the file.
281
276
        None otherwise
282
277
    """
283
 
    return _read_stanza_unicode(unicode_iter)
 
278
    stanza = Stanza()
 
279
    tag = None
 
280
    accum_value = None
 
281
 
 
282
    # TODO: jam 20060922 This code should raise real errors rather than
 
283
    #       using 'assert' to process user input, or raising ValueError
 
284
    #       rather than a more specific error.
 
285
 
 
286
    for line in unicode_iter:
 
287
        if line is None or line == '':
 
288
            break       # end of file
 
289
        if line == '\n':
 
290
            break       # end of stanza
 
291
        real_l = line
 
292
        if line[0] == '\t': # continues previous value
 
293
            if tag is None:
 
294
                raise ValueError('invalid continuation line %r' % real_l)
 
295
            accum_value += '\n' + line[1:-1]
 
296
        else: # new tag:value line
 
297
            if tag is not None:
 
298
                stanza.add(tag, accum_value)
 
299
            try:
 
300
                colon_index = line.index(': ')
 
301
            except ValueError:
 
302
                raise ValueError('tag/value separator not found in line %r'
 
303
                                 % real_l)
 
304
            tag = str(line[:colon_index])
 
305
            if not valid_tag(tag):
 
306
                raise ValueError("invalid rio tag %r" % (tag,))
 
307
            accum_value = line[colon_index+2:-1]
 
308
 
 
309
    if tag is not None: # add last tag-value
 
310
        stanza.add(tag, accum_value)
 
311
        return stanza
 
312
    else:     # didn't see any content
 
313
        return None
284
314
 
285
315
 
286
316
def to_patch_lines(stanza, max_width=72):
369
399
    :return: a Stanza
370
400
    """
371
401
    return read_stanza(_patch_stanza_iter(line_iter))
372
 
 
373
 
 
374
 
try:
375
 
    from bzrlib._rio_pyx import (
376
 
        _read_stanza_utf8,
377
 
        _read_stanza_unicode,
378
 
        _valid_tag,
379
 
        )
380
 
except ImportError:
381
 
    from bzrlib._rio_py import (
382
 
       _read_stanza_utf8,
383
 
       _read_stanza_unicode,
384
 
       _valid_tag,
385
 
       )