This function collects the values from one run.
        Only columns that should be part of the table are collected.

def create_from_xml(sourcefileTag, get_value_from_logfile, listOfColumns,
                        correct_only, log_zip_cache, columns_relevant_for_diff,
                        result_file_or_url):
        '''
        This function collects the values from one run.
        Only columns that should be part of the table are collected.
        '''

        def read_logfile_lines(log_file):
            if not log_file:
                return []
            log_file_url = Util.make_url(log_file)
            url_parts = urllib.parse.urlparse(log_file_url, allow_fragments=False)
            log_zip_path = os.path.dirname(url_parts.path) + ".zip"
            log_zip_url = urllib.parse.urlunparse((url_parts.scheme, url_parts.netloc,
                log_zip_path, url_parts.params, url_parts.query, url_parts.fragment))
            path_in_zip = urllib.parse.unquote(
                os.path.relpath(url_parts.path, os.path.dirname(log_zip_path)))
            if log_zip_url.startswith("file:///") and not log_zip_path.startswith("/"):
                # Replace file:/// with file: for relative paths,
                # otherwise opening fails.
                log_zip_url = "file:" + log_zip_url[8:]

            try:
                with Util.open_url_seekable(log_file_url, 'rt') as logfile:
                    return logfile.readlines()
            except IOError as unused_e1:
                try:
                    if log_zip_url not in log_zip_cache:
                        log_zip_cache[log_zip_url] = zipfile.ZipFile(
                            Util.open_url_seekable(log_zip_url, 'rb'))
                    log_zip = log_zip_cache[log_zip_url]

                    try:
                        with io.TextIOWrapper(log_zip.open(path_in_zip)) as logfile:
                            return logfile.readlines()
                    except KeyError:
                        logging.warning("Could not find logfile '%s' in archive '%s'.",
                                        log_file, log_zip_url)
                        return []

                except IOError as unused_e2:
                    logging.warning("Could not find logfile '%s' nor log archive '%s'.",
                                    log_file, log_zip_url)
                    return []

        status = Util.get_column_value(sourcefileTag, 'status', '')
        category = Util.get_column_value(sourcefileTag, 'category', result.CATEGORY_MISSING)
        score = result.score_for_task(
            sourcefileTag.get('properties', '').split(), category, status)
        logfileLines = None

        values = []

        for column in listOfColumns: # for all columns that should be shown
            value = None # default value
            if column.title.lower() == 'status':
                value = status

            elif not correct_only or category == result.CATEGORY_CORRECT:
                if not column.pattern or column.href:
                    # collect values from XML
                    value = Util.get_column_value(sourcefileTag, column.title)

                else: # collect values from logfile
                    if logfileLines is None: # cache content
                        logfileLines = read_logfile_lines(sourcefileTag.get('logfile'))

                    value = get_value_from_logfile(logfileLines, column.pattern)

            if column.title.lower() == 'score' and value is None and score is not None:
                # If no score column exists in the xml, take the internally computed score,
                # if available
                value = str(score)
            values.append(value)

        sourcefiles = sourcefileTag.get('files')
        if sourcefiles:
            if sourcefiles.startswith('['):
                sourcefileList = [s.strip() for s in sourcefiles[1:-1].split(',') if s.strip()]
                sourcefiles_exist = True if sourcefileList else False
            else:
                raise AssertionError('Unknown format for files tag:')
        else:
            sourcefiles_exist = False

        return RunResult(get_task_id(sourcefileTag, result_file_or_url if sourcefiles_exist else None),
                         status, category, score,
                         sourcefileTag.get('logfile'), listOfColumns, values,
                         columns_relevant_for_diff, sourcefiles_exist=sourcefiles_exist)