nodejs/node · error · RuntimeError

Cannot find out dir, did you run build?

Error message

Cannot find out dir, did you run build?

What it means

Raised by get_default_out_dir in Node's tools/build_addons.py on Windows: it tries 'out/<config>' then the bare '<config>' directory and, if neither exists, concludes the project was never built and aborts. On POSIX the single out/<config> path is returned without this check.

Source

Thrown at tools/build_addons.py:104

      continue
    test_dirs.append(full_path)

  with ThreadPoolExecutor() as executor:
    codes = executor.map(node_gyp_rebuild, test_dirs)
    return 0 if all(code == 0 for code in codes) else 1

def get_default_out_dir(args):
  default_out_dir = os.path.join('out', args.config)
  if not args.is_win:
    # POSIX platforms only have one out dir.
    return default_out_dir
  # On Windows depending on the args of GYP and configure script, the out dir
  # could be 'out/Release', 'out/Debug' or just 'Release' or 'Debug'.
  if os.path.exists(default_out_dir):
    return default_out_dir
  if os.path.exists(args.config):
    return args.config
  raise RuntimeError('Cannot find out dir, did you run build?')

def main():
  if sys.platform == 'cygwin':
    raise RuntimeError('This script does not support running with cygwin python.')

  parser = argparse.ArgumentParser(
      description='Install headers and rebuild child directories')
  parser.add_argument('target', help='target directory to build addons')
  parser.add_argument('--headers-dir',
                      help='path to node headers directory, if not specified '
                           'new headers will be generated for building',
                      default=None)
  parser.add_argument('--out-dir', help='path to the output directory',
                      default=None)
  parser.add_argument('--loglevel', help='loglevel of node-gyp',
                      default='silent')
  parser.add_argument('--skip-tests', help='skip building tests',
                      default='')

View on GitHub (pinned to 1b2de5e052)

Solutions

  1. Build Node first with the matching config so out/<config> exists, e.g. vcbuild.bat release or the equivalent configure + build step.
  2. Pass the correct --config matching an existing output dir, or use --out-dir to point at it explicitly.
  3. Run build_addons.py from the Node source root where the out/ tree lives.

Example fix

# before
python tools/build_addons.py ./myaddon --config Release
# after (build node first, then point at the real out dir)
vcbuild.bat release
python tools/build_addons.py ./myaddon --config Release --out-dir out/Release
Defensive patterns

Strategy: validation

Validate before calling

import os
def resolve_out_dir(config: str, out_dir: str = None) -> str:
    if out_dir:
        if not os.path.isdir(out_dir): raise FileNotFoundError(f'--out-dir not found: {out_dir}')
        return out_dir
    for candidate in (os.path.join('out', config), config):
        if os.path.isdir(candidate):
            return candidate
    raise FileNotFoundError(f'No output dir for config {config!r}; build Node first.')

Type guard

null

Try / catch

try:
    out = get_default_out_dir(args)
except RuntimeError:
    print('Build Node for this config first, or pass --out-dir.'); raise

Prevention

When it happens

Trigger: Running build_addons.py on Windows (args.is_win true) where neither out/Release (or out/Debug) nor a top-level Release/Debug directory is present — i.e. node-gyp configure/build was never run for that config.

Common situations: Building native addons on Windows before building Node itself; mis-matched --config value (e.g. --config Release when only Debug was built); running from the wrong working directory so the out/ tree isn't found.

Related errors


AI-assisted analysis of nodejs/node@1b2de5e052 (2026-08-13). Data as JSON: /api/errors/cab998d240100a07. Report an issue: GitHub.