def test_filter_binary_logs_by_sequence(self):
        # Generate test filenames.
        test_files = []
        for i in range(1, 10):
            test_files.append('my-bin.00000{0}'.format(i))
        for i in range(3, 8):
            test_files.append('my-relay-bin.00000{0}'.format(i))

        # Test filtering filenames by sequence number.
        test_seq = [(2, 4), 6]
        expected_files = ['my-bin.000002', 'my-bin.000003', 'my-bin.000004',
                          'my-bin.000006', 'my-relay-bin.000003',
                          'my-relay-bin.000004', 'my-relay-bin.000006']
        self.assertEqual(filter_binary_logs_by_sequence(test_files, test_seq),
                         expected_files)

        test_seq = [1, (4, 5), 7, (9, 15)]
        expected_files = ['my-bin.000001', 'my-bin.000004', 'my-bin.000005',
                          'my-bin.000007', 'my-bin.000009',
                          'my-relay-bin.000004',
                          'my-relay-bin.000005', 'my-relay-bin.000007']
        self.assertEqual(filter_binary_logs_by_sequence(test_files, test_seq),
                         expected_files)

        test_seq = [2, 3, 6, 8]
        expected_files = ['my-bin.000002', 'my-bin.000003', 'my-bin.000006',
                          'my-bin.000008', 'my-relay-bin.000003',
                          'my-relay-bin.000006']
        self.assertEqual(filter_binary_logs_by_sequence(test_files, test_seq),
                         expected_files)

        test_seq = [(3, 5), (8, 10)]
        expected_files = ['my-bin.000003', 'my-bin.000004', 'my-bin.000005',
                          'my-bin.000008', 'my-bin.000009',
                          'my-relay-bin.000003', 'my-relay-bin.000004',
                          'my-relay-bin.000005']
        self.assertEqual(filter_binary_logs_by_sequence(test_files, test_seq),
                         expected_files)
def _move_binlogs(source,
                  destination,
                  log_type,
                  options,
                  basename=None,
                  index_file=None,
                  skip_latest=False):
    """Move binary log files of the specified type.

    This auxiliary function moves the binary log files of a specific type
    (i.e., binary or relay) from the given source to the specified destination
    directory. It gets the files only for the specified binary log type and
    applies any filtering in accordance to the specified options. Resulting
    files are moved and the respective index file updated accordingly.

    source[in]          Source location of the binary log files to move.
    destination[in]     Destination directory for the binary log files.
    log_type[in]        Type of the binary log files ('bin' or 'relay').
    options[in]         Dictionary of options (modified_before, sequence,
                        verbosity).
    basename[in]        Base name for the binary log files, i.e. filename
                        without the extension (sequence number).
    index_file[in]      Path of the binary log index file. If not specified it
                        is assumed to be located in the source directory and
                        determined based on the basename of the first found
                        binary log file.
    skip_latest[in]     Bool value indication if the latest binary log file
                        (with the higher sequence value; in use by the
                        server) will be skipped or not. By default = False,
                        meaning that no binary log file is skipped.

    Returns the number of files moved.
    """
    verbosity = options['verbosity']
    binlog_files = []
    file_type = '{0}-log'.format(log_type)
    if basename:
        # Ignore path from basename if specified, source is used instead.
        _, basename = os.path.split(basename)
    # Get binary log files to move.
    for _, _, filenames in os.walk(source):
        for f_name in sorted(filenames):
            if is_binary_log_filename(f_name, log_type, basename):
                binlog_files.append(f_name)
        break
    if skip_latest:
        # Skip last file (with the highest sequence).
        # Note; filenames are sorted by ascending order.
        binlog_files = binlog_files[:-1]
    if not binlog_files:
        # No binary log files found to move.
        print(_WARN_MSG_NO_FILE.format(file_type=file_type))
    else:
        # Apply filters.
        sequence = options.get('sequence', None)
        if sequence:
            print("#")
            print(
                _INFO_MSG_APPLY_FILTERS.format(filter_type='sequence',
                                               file_type=file_type))
            binlog_files = filter_binary_logs_by_sequence(
                binlog_files, sequence)
        modified_before = options.get('modified_before', None)
        if modified_before:
            print("#")
            print(
                _INFO_MSG_APPLY_FILTERS.format(filter_type='modified date',
                                               file_type=file_type))
            binlog_files = filter_binary_logs_by_date(binlog_files, source,
                                                      modified_before)
        # Move files.
        print("#")
        if binlog_files:
            if index_file is None:
                # Get binary log index file.
                index_file = get_index_file(source, binlog_files[0])
                if verbosity > 0:
                    print(
                        _INFO_MSG_INDEX_FILE.format(file_type=file_type,
                                                    index_file=index_file))
                    print("#")
            print(_INFO_MSG_MOVE_FILES.format(file_type=file_type))
            for f_name in binlog_files:
                try:
                    print("# - {0}".format(f_name))
                    move_binary_log(source, destination, f_name, index_file)
                except (shutil.Error, IOError) as err:
                    raise UtilError(
                        _ERR_MSG_MOVE_FILE.format(filename=f_name, error=err))
            return len(binlog_files)
        else:
            print(_INFO_MSG_NO_FILES_TO_MOVE.format(file_type=file_type))
            return 0
Example #3
0
def _move_binlogs(source, destination, log_type, options, basename=None,
                  index_file=None, skip_latest=False):
    """Move binary log files of the specified type.

    This auxiliary function moves the binary log files of a specific type
    (i.e., binary or relay) from the given source to the specified destination
    directory. It gets the files only for the specified binary log type and
    applies any filtering in accordance to the specified options. Resulting
    files are moved and the respective index file updated accordingly.

    source[in]          Source location of the binary log files to move.
    destination[in]     Destination directory for the binary log files.
    log_type[in]        Type of the binary log files ('bin' or 'relay').
    options[in]         Dictionary of options (modified_before, sequence,
                        verbosity).
    basename[in]        Base name for the binary log files, i.e. filename
                        without the extension (sequence number).
    index_file[in]      Path of the binary log index file. If not specified it
                        is assumed to be located in the source directory and
                        determined based on the basename of the first found
                        binary log file.
    skip_latest[in]     Bool value indication if the latest binary log file
                        (with the higher sequence value; in use by the
                        server) will be skipped or not. By default = False,
                        meaning that no binary log file is skipped.

    Returns the number of files moved.
    """
    verbosity = options['verbosity']
    binlog_files = []
    file_type = '{0}-log'.format(log_type)
    if basename:
        # Ignore path from basename if specified, source is used instead.
        _, basename = os.path.split(basename)
    # Get binary log files to move.
    for _, _, filenames in os.walk(source):
        for f_name in sorted(filenames):
            if is_binary_log_filename(f_name, log_type, basename):
                binlog_files.append(f_name)
        break
    if skip_latest:
        # Skip last file (with the highest sequence).
        # Note; filenames are sorted by ascending order.
        binlog_files = binlog_files[:-1]
    if not binlog_files:
        # No binary log files found to move.
        print(_WARN_MSG_NO_FILE.format(file_type=file_type))
    else:
        # Apply filters.
        sequence = options.get('sequence', None)
        if sequence:
            print("#")
            print(_INFO_MSG_APPLY_FILTERS.format(filter_type='sequence',
                                                 file_type=file_type))
            binlog_files = filter_binary_logs_by_sequence(binlog_files,
                                                          sequence)
        modified_before = options.get('modified_before', None)
        if modified_before:
            print("#")
            print(_INFO_MSG_APPLY_FILTERS.format(filter_type='modified date',
                                                 file_type=file_type))
            binlog_files = filter_binary_logs_by_date(binlog_files, source,
                                                      modified_before)
        # Move files.
        print("#")
        if binlog_files:
            if index_file is None:
                # Get binary log index file.
                index_file = get_index_file(source, binlog_files[0])
                if verbosity > 0:
                    print(_INFO_MSG_INDEX_FILE.format(file_type=file_type,
                                                      index_file=index_file))
                    print("#")
            print(_INFO_MSG_MOVE_FILES.format(file_type=file_type))
            for f_name in binlog_files:
                try:
                    print("# - {0}".format(f_name))
                    move_binary_log(source, destination, f_name, index_file)
                except (shutil.Error, IOError) as err:
                    raise UtilError(_ERR_MSG_MOVE_FILE.format(filename=f_name,
                                                              error=err))
            return len(binlog_files)
        else:
            print(_INFO_MSG_NO_FILES_TO_MOVE.format(file_type=file_type))
            return 0