remoteintech/remote-jobs · error
Could not read file: ${err.message}
Error message
Could not read file: ${err.message} What it means
Caught inside validateCompanyFile at lines 91-96. readFileSync(filePath, 'utf-8') is wrapped in try/catch; on any I/O failure (ENOENT, EACCES, EISDIR, ENOTDIR, etc.) the validator pushes `Could not read file: <err.message>` and returns early. The script still exits 1 because results.summary.failed becomes > 0.
Source
Thrown at .github/scripts/validate-companies.js:94
currentArrayKey = null;
}
}
return data;
}
/**
* Validate a single company file. Returns an array of error strings.
*/
function validateCompanyFile(filePath) {
const errors = [];
const warnings = [];
let content;
try {
content = readFileSync(filePath, "utf-8");
} catch (err) {
errors.push(`Could not read file: ${err.message}`);
return { errors, warnings };
}
// Parse frontmatter
const data = parseFrontmatter(content);
if (!data) {
errors.push(
"Missing YAML frontmatter. The file must start with `---` followed by YAML fields and a closing `---`."
);
return { errors, warnings };
}
// Check required fields
for (const field of REQUIRED_FIELDS) {
if (!data[field] || (typeof data[field] === "string" && !data[field].trim())) {
errors.push(`Missing required field: \`${field}\``);
}
}View on GitHub (pinned to b1dd8deb19)
Solutions
- Run `ls -l <printed path>` to confirm existence and permissions.
- If running under pull_request_target, verify the pr-head/ stripping at line 220 produced a real filesystem path.
- Regenerate the changed-files list from git diff rather than a stale matrix.
- Match the path casing exactly to what git tracks.
Defensive patterns
Strategy: try-catch
Validate before calling
import { existsSync, readFileSync } from 'node:fs';
function readCompany(filePath) {
if (!existsSync(filePath)) {
return { errors: [`File not found: ${filePath}`], warnings: [] };
}
return readFileSync(filePath, 'utf-8');
} Try / catch
try {
content = readFileSync(filePath, 'utf-8');
} catch (err) {
errors.push(`Could not read file: ${err.message}`);
return { errors, warnings };
} Prevention
- Filter the changed-files list through existsSync before invoking the validator.
- Surface err.code (ENOENT/EACCES/EISDIR) alongside err.message for faster diagnosis.
- Verify the pr-head/ stripping logic at line 220 matches the actual checkout layout.
When it happens
Trigger: The changed-files argument list names a path that doesn't exist on disk (ENOENT); the pr-head/ prefix from a pull_request_target checkout wasn't stripped correctly (line 220) leaving an unresolvable path; the file was deleted in the PR but still listed; CI runner lacks read permission (EACCES); the path is actually a directory (EISDIR).
Common situations: Renaming a company file but the workflow still references the old path; checkout action didn't fetch the file at the expected location; case-sensitive filesystem mismatch (macOS dev vs Linux CI); a glob included a path that was removed in a force-push.
Related errors
AI-assisted analysis of remoteintech/remote-jobs@b1dd8deb19 (2026-08-13).
Data as JSON: /api/errors/46a724d9311765b9.
Report an issue: GitHub.