## ## Stream Base Class ## class Stream(object): def __init__(self, data): self.data = data def __del__(self): self.data.close() def close(self): self.data.close() def records(self): records = [] for record in self: records.append(record) return records ## ## ParsedStream ## class ParsedStream(object): def __init__(self, stream, parse=None, parse_args=[], parse_kwargs={}): self.stream = stream self.parse = parse self.parse_args = parse_args self.parse_kwargs = parse_kwargs def __iter__(self): return self def next(self): try: record = self.stream.next() args = self.parse_args kwargs = self.parse_kwargs return self.parse(record, *args, **kwargs) except StopIteration: self.stream.close() raise StopIteration ## ## Stream of records separated by newlines ## class NewLineStream(Stream): def __init__(self, data, header=0): Stream.__init__(self, data) for i in range(header): line = self.data.readline() def __iter__(self): return self def next(self): line = self.data.readline() if line: return line.rstrip('\r\n') else: raise StopIteration ## ## Stream of a single record ## class SingleRecordStream(Stream): def __init__(self, data, header=0): Stream.__init__(self, data) for i in range(header): line = self.data.readline() def __iter__(self): return self def next(self): record = [] lines = self.data.readlines() if lines: for line in lines: record.append(line.rstrip('\r\n')) return record else: raise StopIteration ## ## Stream of records separated by blank lines ## class BlankLineStream(Stream): def __init__(self, data, header=0): Stream.__init__(self, data) for i in range(header): line = self.data.readline() def __iter__(self): return self def next(self): record = [] line = self.data.readline() if not line: raise StopIteration while line not in ['\n', '\r\n']: record.append(line.rstrip('\r\n')) line = self.data.readline() if not line: return record return record ## ## Stream of records separated by a single line separator ## class LineSeparatorStream(Stream): def __init__(self, data, separator='\n', header=0): Stream.__init__(self, data) if separator[-1] != '\n': separator = '%s\n' % (separator) self.separator = separator for i in range(header): line = self.data.readline() def __iter__(self): return self def next(self): record = [] line = self.data.readline() if not line: raise StopIteration while line != self.separator: record.append(line.rstrip('\r\n')) line = self.data.readline() if not line: return record return record