def __iadd__(self, other): """Operator overloading += example:: book += book2 book += book2["Sheet1"] """ if isinstance(other, Book): names = other.sheet_names() for name in names: new_key = name if len(names) == 1: new_key = other._filename if new_key in self.__name_array: uid = local_uuid() new_key = "%s_%s" % (name, uid) self.__sheets[new_key] = Sheet(other[name].array, new_key) elif isinstance(other, Sheet): new_key = other.name if new_key in self.__name_array: uid = local_uuid() new_key = "%s_%s" % (other.name, uid) self.__sheets[new_key] = Sheet(other.to_array(), new_key) else: raise TypeError self.__name_array = list(self.__sheets.keys()) return self
def test_random_access_to_unknown_area(): test_content = [[1, 2]] sheet = Sheet(test_content) eq_(sheet.to_array(), test_content) expected = [[1, 2, ''], ['', '', ''], ['', '', 100]] sheet[2, 2] = 100 eq_(sheet.array, expected)
def test_random_access(): test_content = [[1, 2]] sheet = Sheet(test_content) eq_(sheet.to_array(), test_content) expected = dedent(""" pyexcel sheet: +---+-----+ | 1 | 100 | +---+-----+""").strip('\n') sheet[0, 1] = 100 eq_(str(sheet), expected)
def test_named_sheet_access(): test_content = [['A', 'B'], [1, 2]] sheet = Sheet(test_content, name_columns_by_row=0) eq_(sheet.to_array(), test_content) expected = dedent(""" pyexcel sheet: +-----+---+ | A | B | +=====+===+ | 100 | 2 | +-----+---+""").strip('\n') sheet[0, 'A'] = 100 print(str(sheet)) eq_(str(sheet), expected)
def test_random_access_to_unknown_area(): test_content = [[1, 2]] sheet = Sheet(test_content) eq_(sheet.to_array(), test_content) expected = dedent(""" pyexcel sheet: +---+---+-----+ | 1 | 2 | | +---+---+-----+ +---+---+-----+ | | | 100 | +---+---+-----+""").strip('\n') sheet[2, 2] = 100 eq_(str(sheet), expected)
def test_data_frame_access(): test_content = [['', 'A', 'B'], ['R', 1, 2]] sheet = Sheet(copy.deepcopy(test_content), name_columns_by_row=0, name_rows_by_column=0) eq_(sheet.to_array(), test_content) expected = dedent(""" pyexcel sheet: +---+-----+---+ | | A | B | +===+=====+===+ | R | 100 | 2 | +---+-----+---+""").strip('\n') sheet['R', 'A'] = 100 print(str(sheet)) eq_(str(sheet), expected)
def test_sheet_content(self): array = [[1, 2]] sheet = Sheet(array) expected = dedent(""" +---+---+ | 1 | 2 | +---+---+""").strip('\n') self.assertEqual(str(sheet.content), expected)
def test_sheet_content(): array = [[1, 2]] sheet = Sheet(array) expected = dedent(""" +---+---+ | 1 | 2 | +---+---+""").strip('\n') eq_(str(sheet.content), expected)
def save_as(**keywords): """Save a sheet from a data source to another one It accepts two sets of keywords. Why two sets? one set is source, the other set is destination. In order to distinguish the two sets, source set will be exactly the same as the ones for :meth:`pyexcel.get_sheet`; destination set are exactly the same as the ones for :class:`pyexcel.Sheet.save_as` but require a 'dest' prefix. :param keywords: additional keywords can be found at :meth:`pyexcel.get_sheet` :param dest_file_name: another file name. **out_file** is deprecated though is still accepted. :param dest_file_type: this is needed if you want to save to memory :param dest_session: the target database session :param dest_table: the target destination table :param dest_model: the target django model :param dest_mapdict: a mapping dictionary, see :meth:`pyexcel.Sheet.save_to_memory` :param dest_initializer: a custom initializer function for table or model :param dest_mapdict: nominate headers :param dest_batch_size: object creation batch size. it is Django specific if csv file is destination format, python csv `fmtparams <https://docs.python.org/release/3.1.5/ library/csv.html#dialects-and-formatting-parameters>`_ are accepted for example: dest_lineterminator will replace default '\r\n' to the one you specified :returns: IO stream if saving to memory. None otherwise ================= ============================================= Saving to source parameters ================= ============================================= file dest_file_name, dest_sheet_name, keywords with prefix 'dest' memory dest_file_type, dest_content, dest_sheet_name, keywords with prefix 'dest' sql dest_session, table, dest_initializer, dest_mapdict django model dest_model, dest_initializer, dest_mapdict, dest_batch_size ================= ============================================= """ dest_keywords, source_keywords = _split_keywords(**keywords) sheet_params = {} for field in constants.VALID_SHEET_PARAMETERS: if field in source_keywords: sheet_params[field] = source_keywords.pop(field) sheet = sources.get_sheet_stream(**source_keywords) if sheet_params != {}: sheet = Sheet(sheet.payload, sheet.name, **sheet_params) return sources.save_sheet(sheet, **dest_keywords)
def get_sheet(**keywords): """Get an instance of :class:`Sheet` from an excel source :param file_name: a file with supported file extension :param file_content: the file content :param file_stream: the file stream :param file_type: the file type in *content* :param session: database session :param table: database table :param model: a django model :param adict: a dictionary of one dimensional arrays :param url: a download http url for your excel file :param with_keys: load with previous dictionary's keys, default is True :param records: a list of dictionaries that have the same keys :param array: a two dimensional array, a list of lists :param keywords: additional parameters, see :meth:`Sheet.__init__` :param sheet_name: sheet name. if sheet_name is not given, the default sheet at index 0 is loaded Not all parameters are needed. Here is a table ========================== ========================================= source parameters ========================== ========================================= loading from file file_name, sheet_name, keywords loading from string file_content, file_type, sheet_name, keywords loading from stream file_stream, file_type, sheet_name, keywords loading from sql session, table loading from sql in django model loading from query sets any query sets(sqlalchemy or django) loading from dictionary adict, with_keys loading from records records loading from array array loading from an url url ========================== ========================================= see also :ref:`a-list-of-data-structures` """ sheet_params = {} for field in constants.VALID_SHEET_PARAMETERS: if field in keywords: sheet_params[field] = keywords.pop(field) named_content = sources.get_sheet_stream(**keywords) sheet = Sheet(named_content.payload, named_content.name, **sheet_params) return sheet
def load_from_sheets(self, sheets): """ Load content from existing sheets :param dict sheets: a dictionary of sheets. Each sheet is a list of lists """ self.__sheets = compact.OrderedDict() if sheets is None: return keys = sheets.keys() if not isinstance(sheets, compact.OrderedDict): # if the end user does not care about the order # we put alphatical order keys = sorted(keys) for name in keys: sheet = Sheet(sheets[name], name) # this sheets keep sheet order self.__sheets.update({name: sheet}) # this provide the convenience of access the sheet self.__dict__[name] = sheet self.__name_array = list(self.__sheets.keys())
def save_as(**keywords): """Save a sheet from a data source to another one It accepts two sets of keywords. Why two sets? one set is source, the other set is destination. In order to distinguish the two sets, source set will be exactly the same as the ones for :meth:`pyexcel.get_sheet`; destination set are exactly the same as the ones for :class:`pyexcel.Sheet.save_as` but require a 'dest' prefix. :param file_name: a file with supported file extension :param file_content: the file content :param file_stream: the file stream :param file_type: the file type in *content* :param session: database session :param table: database table :param model: a django model :param adict: a dictionary of one dimensional arrays :param url: a download http url for your excel file :param with_keys: load with previous dictionary's keys, default is True :param records: a list of dictionaries that have the same keys :param array: a two dimensional array, a list of lists :param keywords: additional parameters, see :meth:`Sheet.__init__` :param sheet_name: sheet name. if sheet_name is not given, the default sheet at index 0 is loaded :param dest_file_name: another file name. **out_file** is deprecated though is still accepted. :param dest_file_type: this is needed if you want to save to memory :param dest_session: the target database session :param dest_table: the target destination table :param dest_model: the target django model :param dest_mapdict: a mapping dictionary, see :meth:`pyexcel.Sheet.save_to_memory` :param dest_initializer: a custom initializer function for table or model :param dest_mapdict: nominate headers :param dest_batch_size: object creation batch size. it is Django specific :returns: IO stream if saving to memory. None otherwise if csv file is destination format, python csv `fmtparams <https://docs.python.org/release/3.1.5/ library/csv.html#dialects-and-formatting-parameters>`_ are accepted for example: dest_lineterminator will replace default '\r\n' to the one you specified ========================== ========================================= source parameters ========================== ========================================= loading from file file_name, sheet_name, keywords loading from memory file_type, content, sheet_name, keywords loading from sql session, table loading from sql in django model loading from query sets any query sets(sqlalchemy or django) loading from dictionary adict, with_keys loading from records records loading from array array loading from an url url ========================== ========================================= ================= ============================================= Saving to source parameters ================= ============================================= file dest_file_name, dest_sheet_name, keywords with prefix 'dest' memory dest_file_type, dest_content, dest_sheet_name, keywords with prefix 'dest' sql dest_session, dest_table, dest_initializer, dest_mapdict django model dest_model, dest_initializer, dest_mapdict, dest_batch_size ================= ============================================= In addition, this function use :class:`pyexcel.Sheet` to render the data which could have performance penalty. In exchange, parameters for :class:`pyexcel.Sheet` can be passed on, e.g. `name_columns_by_row`. """ dest_keywords, source_keywords = _split_keywords(**keywords) sheet_params = {} for field in constants.VALID_SHEET_PARAMETERS: if field in source_keywords: sheet_params[field] = source_keywords.pop(field) sheet_stream = sources.get_sheet_stream(**source_keywords) sheet = Sheet(sheet_stream.payload, sheet_stream.name, **sheet_params) return sources.save_sheet(sheet, **dest_keywords)
def get_sheet(self, array, name): """Create a sheet from a list of lists""" return Sheet(array, name)