Skip to content

Bug: deploy.inputs include filter ignored when referencing build step #448

@fable-coltish

Description

@fable-coltish

Description

When using deploy.inputs with an include filter to copy only specific files from a build step, Railpack ignores the filter and copies the entire /app directory, resulting in unnecessarily large Docker images (e.g. ~1.5GB instead of ~300MB).

This is a critical issue for Next.js standalone builds in monorepos where only the .next/standalone directory is needed for deployment.

Expected Behavior

When specifying:

{
  "deploy": {
    "inputs": [
      {
        "step": "build",
        "include": ["apps/landing/.next/standalone"]
      }
    ]
  }
}

Railpack should copy only the apps/landing/.next/standalone directory to the final image.

Actual Behavior

Railpack ignores the include filter and copies the entire /app directory from the build step, including:

  • /app/node_modules (~1.3GB)
  • /app/packages directory
  • All source files (/app/apps/landing/src)
  • All config files (package.json, tsconfig.json, etc.)
  • Build artifacts that aren't needed (/app/apps/landing/.next except standalone)

Build Log Evidence

The build log shows multiple copy operations copying the entire directory:

#42 copy /app/node_modules
#42 DONE 9.3s

#43 copy /app
#43 DONE 5.4s

Reproduction Steps

  1. Set up a Next.js app in a pnpm monorepo with output: "standalone" in next.config.ts
  2. Create a railpack.json with:
{
  "$schema": "https://schema.railpack.com",
  "caches": {
    "pnpm-store": {
      "directory": "/root/.local/share/pnpm/store"
    },
    "turbo": {
      "directory": ".turbo"
    },
    "next-cache": {
      "directory": "apps/landing/.next/cache"
    }
  },
  "steps": {
    "install": {
      "commands": ["..."]
    },
    "build": {
      "commands": [
        {
          "cmd": "pnpm turbo build --filter=landing"
        },
        {
          "cmd": "sh -c 'mkdir -p /app/apps/landing/.next/standalone/apps/landing/.next && cp -r /app/apps/landing/.next/static /app/apps/landing/.next/standalone/apps/landing/.next/static'"
        },
        {
          "cmd": "sh -c 'mkdir -p /app/apps/landing/.next/standalone/apps/landing && cp -r /app/apps/landing/public /app/apps/landing/.next/standalone/apps/landing/public || true'"
        }
      ]
    }
  },
  "deploy": {
    "base": {
      "image": "ghcr.io/railwayapp/railpack-runtime:latest"
    },
    "inputs": [
      {
        "step": "build",
        "include": ["apps/landing/.next/standalone"]
      }
    ],
    "startCommand": "node /app/apps/landing/.next/standalone/apps/landing/server.js"
  }
}
  1. Run railpack build or deploy via Railway
  2. Observe that the entire /app directory is copied, not just apps/landing/.next/standalone

Environment

  • Railpack version: Latest (via Railway deployment)
  • Node.js: 22.11.0
  • Package manager: pnpm 9.12.3
  • Framework: Next.js 16.1.0 with output: "standalone"
  • Monorepo: Turborepo with pnpm workspaces

Related Issues

This was previously acknowledged 7 months ago on Railway Help Station:
https://station.railway.com/questions/how-to-include-copy-folder-with-railpack-d04c5931

"Currently, when you manually specify a step in a railpack.json file, that entire step's contents will be added to the final output. Basically it will include too much rather than too little (this is why you see the full contents of your repo in the final image even if you are just adding assets to the build step). I'll be working on improving this in the coming week because I agree it is confusing."

This is also related to the broader configuration file confusion discussed in #219, but this issue focuses on the specific bug where the include filter is completely ignored.

Impact

  • Image size: 1.5GB instead of ~300MB (4-5x larger)
  • Deployment time: Slower uploads and pulls
  • Storage costs: Unnecessary storage usage
  • Bandwidth: Wasted bandwidth on every deployment

Workarounds Attempted

  1. Using deployOutputs on build step: Made it worse - caused the build step to be included twice ($build, $build in merge log)
  2. Cleanup commands in build step: Cannot work - cache directories cannot be removed due to "EBUSY: resource busy or locked" errors
  3. Separate cleanup step: Cannot work - due to the bug, the cleanup step would still copy the entire build step first

Additional Context

The official Railpack Next.js example (node-next) does NOT use output: "standalone" and has no railpack.json customization, suggesting that:

  • Railpack's auto-detection is designed for standard Next.js builds
  • Monorepos with standalone output are an edge case not well supported
  • The deploy.inputs filtering feature is incomplete/buggy

Documentation References

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions