goharbor/harbor · error

Failed to read chart.yaml from the chart tgz file. filename

Error message

Failed to read chart.yaml from the chart tgz file. filename {}

What it means

Raised by read_chart_version in Harbor's chart v2->OCI migration tool when find_chart_yaml matched a tar member whose name contains "Chart.yaml" but tarfile.extractfile() returned None. extractfile returns None when the matched member is not a regular file (a directory, symlink, fifo, etc.). The exception is caught in ChartV2.__init__, which logs 'Skipped chart ... illegal chart name' and leaves name/version empty so the chart is skipped during the batch migration.

Source

Thrown at tools/migrate_chart/migrate_chart.py:64

            return os.path.join(path, member.name)

def read_chart_version(chart_tgz_path):
    # Open the chart tgz file
    with tarfile.open(chart_tgz_path, 'r:gz') as tar:
        # Find the path to chart.yaml within the tarball
        chart_yaml_path = find_chart_yaml(tar)
        if chart_yaml_path:
            # Extract the chart.yaml file
            chart_yaml_file = tar.extractfile(chart_yaml_path)
            if chart_yaml_file is not None:
                # Load the YAML content from chart.yaml
                chart_data = yaml.safe_load(chart_yaml_file)
                # Read the version from chart.yaml
                version = chart_data.get('version')
                name = chart_data.get('name')
                return name, version
            else:
                raise Exception("Failed to read chart.yaml from the chart tgz file. filename {}".format(chart_tgz_path))
        else:
            raise Exception("chart.yaml not found in the chart tgz file. filename {}".format(chart_tgz_path))

class ChartV2:

    def __init__(self, filepath:Path):
        self.filepath = filepath
        self.project = self.filepath.parts[-2]
        self.name = ""
        self.version = ""
        try:
            self.name, self.version = read_chart_version(filepath)
            if self.name == "" or self.version == "" or self.name is None or self.version is None :
                raise Exception('chart name: {} is illegal'.format('-'.join(parts)))
        except Exception as e:
            click.echo("Skipped chart: {} due to illegal chart name. Error: {}".format(filepath, e), err=True)
        return

View on GitHub (pinned to 7b2fd08cc5)

Solutions

  1. Inspect the archive: tar -tzvf <file>.tgz and check the entry type of anything matching Chart.yaml
  2. Repackage the chart with helm package, which guarantees a regular-file Chart.yaml at the chart root
  3. Remove or move the offending tgz out of /chart_storage so the batch run proceeds
  4. Patch find_chart_yaml to only consider regular files whose basename is exactly Chart.yaml

Example fix

# before
if "Chart.yaml" in member.name:
    return os.path.join(path, member.name)  # can match dirs/symlinks -> extractfile() returns None
# after
if member.isfile() and os.path.basename(member.name) == "Chart.yaml":
    return member.name  # regular file only, extractfile() succeeds
Defensive patterns

Strategy: validation

Validate before calling

import tarfile

def has_regular_chart_yaml(tgz_path) -> bool:
    with tarfile.open(tgz_path, 'r:gz') as tar:
        return any(m.isfile() and 'Chart.yaml' in m.name for m in tar.getmembers())

# before migration:
# if not has_regular_chart_yaml(f): quarantine(f)

Try / catch

try:
    name, version = read_chart_version(filepath)
except Exception as e:
    # chart is skipped by design; log and continue the batch
    click.echo(f'Skipped chart: {filepath} ({e})', err=True)
    continue

Prevention

When it happens

Trigger: A .tgz under /chart_storage/<project>/ contains an entry matching the substring check ("Chart.yaml" in member.name) that is a directory (e.g. a 'Chart.yaml.d' folder), a symlink, or another non-regular file. Because matching is substring-based, unrelated members whose names merely contain 'Chart.yaml' also hit this path.

Common situations: Hand-repacked tgz archives, charts packed with non-Helm tooling, archives with symlinked Chart.yaml, or unusual nested directory layouts inside the tarball.

Related errors


AI-assisted analysis of goharbor/harbor@7b2fd08cc5 (2026-08-16). Data as JSON: /api/errors/eefef8a45f2f9cc3. Report an issue: GitHub.