langgenius/dify · error · ValueError

Unsupported legacy dataset permission: {permission}

Error message

Unsupported legacy dataset permission: {permission}

What it means

ValueError raised by _dataset_permission_enum when DatasetPermissionEnum(permission) raises ValueError - i.e. the stored permission string (or value) does not correspond to any DatasetPermissionEnum member. The function accepts None (defaults to ONLY_ME) but any non-None unresolvable value triggers this.

Source

Thrown at api/commands/rbac.py:298

            )
        )
    else:
        click.echo(
            click.style(
                f"RBAC member-role migration completed. Scanned {scanned_count} members across {tenant_count} tenants, "
                f"migrated {migrated_count}, skipped {skipped_count} already up-to-date.",
                fg="green",
            )
        )


def _dataset_permission_enum(permission: DatasetPermissionEnum | str | None) -> DatasetPermissionEnum:
    if permission is None:
        return DatasetPermissionEnum.ONLY_ME
    try:
        return DatasetPermissionEnum(permission)
    except ValueError as exc:
        raise ValueError(f"Unsupported legacy dataset permission: {permission}") from exc


def _rbac_dataset_scope_for_legacy_permission(permission: DatasetPermissionEnum) -> RBACResourceWhitelistScope:
    if permission is DatasetPermissionEnum.ALL_TEAM:
        return RBACResourceWhitelistScope.ALL
    if permission in {DatasetPermissionEnum.ONLY_ME, DatasetPermissionEnum.PARTIAL_TEAM}:
        return RBACResourceWhitelistScope.SPECIFIC
    raise ValueError(f"Unsupported legacy dataset permission: {permission}")


def _emit_dataset_permission_migration_event(payload: dict[str, object]) -> None:
    click.echo(json.dumps(payload, sort_keys=True))


@click.command(
    "rbac-migrate-dataset-permissions",
    help=(
        "Migrate legacy dataset permission scopes and partial members into RBAC dataset access bindings. "

View on GitHub (pinned to ef8544b173)

Solutions

  1. Query `SELECT DISTINCT permission FROM dataset_permissions;` to find the offending value(s).
  2. Map or correct unknown values to a supported DatasetPermissionEnum member.
  3. If a new permission was introduced, extend DatasetPermissionEnum and the migration mapping.
  4. Back up the table before mutating permission values.

Example fix

-- before
SELECT DISTINCT permission FROM dataset_permissions;
-- 'all'  (not a valid enum value)

-- after
UPDATE dataset_permissions SET permission='all_team' WHERE permission='all';
Defensive patterns

Strategy: type-guard

Validate before calling

def is_supported_dataset_permission(value: str | None) -> bool:
    if value is None:
        return True
    try:
        DatasetPermissionEnum(value)
        return True
    except ValueError:
        return False

Type guard

def is_valid_permission_enum(value: str | None) -> bool:
    if value is None:
        return True
    try:
        DatasetPermissionEnum(value)
        return True
    except ValueError:
        return False

Try / catch

try:
    perm = _dataset_permission_enum(raw)
except ValueError as exc:
    click.echo(f"Skipping dataset with unknown permission: {exc}", err=True)
    continue

Prevention

When it happens

Trigger: Triggered when DatasetPermission.permission in the DB holds a string/value that is not one of the DatasetPermissionEnum members (ALL_TEAM, ONLY_ME, PARTIAL_TEAM).

Common situations: A legacy or custom permission value was written to the dataset_permissions table, an enum member was renamed across versions, or corrupt data inserted an unknown code.

Related errors


AI-assisted analysis of langgenius/dify@ef8544b173 (2026-08-12). Data as JSON: /api/errors/595234857c4e3f77. Report an issue: GitHub.