apache/hadoop · error · AccessControlException

Permission denied: user=%s, path=\"%s\":%s:%s:%s%s

Error message

Permission denied: user=%s, path=\"%s\":%s:%s:%s%s

What it means

FileSystem.access(path, mode) resolves the status (StatusProbeEnum.ALL) then delegates to the audit manager's checkAccess(path, stat, mode). When the configured audit/authorization layer denies the requested FsAction, S3A increments the audit_access_check_failure statistic and throws AccessControlException formatted with the acting user, path, owner, group, a 'd'/'-' directory indicator and the requested mode. The default no-op audit manager returns true, so this exception means an authorizing auditor is active and rejected the request.

Source

Thrown at hadoop-tools/hadoop-aws/src/main/java/org/apache/hadoop/fs/s3a/S3AFileSystem.java:3912

  /**
   * Soft check of access by forwarding to the audit manager
   * and so on to the auditor.
   * {@inheritDoc}
   */
  @Override
  @AuditEntryPoint
  public void access(final Path f, final FsAction mode)
      throws AccessControlException, FileNotFoundException, IOException {
    Path path = qualify(f);
    LOG.debug("check access mode {} for {}", path, mode);
    trackDurationAndSpan(
        INVOCATION_ACCESS, path, () -> {
          final S3AFileStatus stat = innerGetFileStatus(path, false,
              StatusProbeEnum.ALL);
          if (!getAuditManager().checkAccess(path, stat, mode)) {
            incrementStatistic(AUDIT_ACCESS_CHECK_FAILURE);
            throw new AccessControlException(String.format(
                "Permission denied: user=%s, path=\"%s\":%s:%s:%s%s",
                getOwner().getUserName(),
                stat.getPath(),
                stat.getOwner(), stat.getGroup(),
                stat.isDirectory() ? "d" : "-", mode));
          }
          // simply for the API binding.
          return true;
        });
  }

  /**
   * Return a file status object that represents the path.
   * @param f The path we want information from
   * @return a FileStatus object
   * @throws FileNotFoundException when the path does not exist
   * @throws IOException on other problems.
   */

View on GitHub (pinned to 2add963021)

Solutions

  1. Compare the acting user (getOwner().getUserName() in the message) against the authorization policy and grant the needed access
  2. Fix ownership expectations: ensure the creating user and the accessing user align with the policy
  3. If the denial is unexpected, inspect the fs.s3a.audit.* / authorizer configuration to confirm which layer rejected it
Defensive patterns

Strategy: try-catch

Validate before calling

// Deliberate permission probe with a clear failure
try {
  fs.access(path, FsAction.READ);
} catch (AccessControlException e) {
  LOG.warn("denied: {}", e.getMessage()); // contains user/owner/group/mode
  throw e;
}

Type guard

static boolean isAccessDenied(Throwable t) {
  return t instanceof org.apache.hadoop.security.AccessControlException;
}

Try / catch

Catch AccessControlException specifically (before IOException) wherever access() or an authorized operation runs; parse user/owner/group from the message for the error report, and surface it as a policy/authorization problem, not an S3 outage.

Prevention

When it happens

Trigger: fs.access(path, FsAction.READ/WRITE/EXECUTE) when the active authorization layer denies that mode for the current user; frameworks (Hive, policy engines, distcp permission checks) calling access() before performing operations.

Common situations: Cluster-wide authorization/auditing plugin enabled after code worked unauthenticated; object owner/group differing from the acting user under enforced authorization; jobs migrated from permissive clusters.

Understand the failure class

Background: Permission denied / not authorized / 403 Forbidden: access-control rejections when the caller lacks the required role, grant, or ownership — this error's family across 18 libraries.

Related errors


AI-assisted analysis of apache/hadoop@2add963021 (2026-08-22). Data as JSON: /api/errors/f405ee2bc3a79c76. Report an issue: GitHub.