# Security policy ## Reporting a vulnerability Please do not open a public issue for a potential security problem. Report it privately through [the security advisory form](https://github.com/jhipster/generator-jhipster/security/advisories/new), and we will work with you on a fix and a coordinated disclosure. ## The trust model of `.yo-rc.json` `.yo-rc.json` is **not inert configuration data — it is generator input, and almost all of its properties can become part of the generated application**: Java or TypeScript sources, build-script content, file and directory names, dependency coordinates, or the name of an npm package that JHipster installs and executes on your machine. The practical consequence is: > **Running `jhipster` in a project you did not author is equivalent to running the project author's code on your machine, with your user's > privileges.** The same applies to every other file the generator reads as configuration: `.jhipster/*.json` entity files, `.yo-resolve`, JDL files, and any blueprint referenced from them. The `.jhipster/*.json` entity configurations are less dangerous than `.yo-rc.json` — they cannot declare a blueprint — but their path values (entity folder, file and translation key) choose the project files their templates write, so they are generator input and must be checked as well. `.yo-resolve` does not participate in generation itself, but it controls conflict resolution and can force the generator to overwrite existing files without prompting, so it too must be trusted. ### Why the configuration is trust-sensitive **Blueprints are executable code.** The `blueprints` and `generators` entries name npm packages. During generation those packages are resolved, possibly installed, and then **executed** in the generation process — before a single generated file has been reviewed. Their npm lifecycle scripts (`preinstall`, `install`, `postinstall`) run as well. This is the highest-impact property of the file, and validating the other properties does not compensate for it. Installing a package that is not already present prompts for confirmation, but a blueprint that is already resolvable in the environment (globally installed, in `node_modules`, or on a lookup path) is composed and executed with no prompt — so a pre-installed blueprint is all it takes. JDL is equivalent: an application block can declare `blueprints`, which end up in `.yo-rc.json`. **Free-text values are embedded in generated files.** Values such as `baseName`, `packageName`, `jhipsterVersion`, `clientPackageManager`, entity and field names, or validation patterns are interpolated into templates that produce Java sources, `pom.xml` / `build.gradle`, `package.json`, `Dockerfile`s, shell scripts and CI pipeline definitions. A value that is harmless inside the generator process may be harmful in the artifact it produces — for example, a string that closes a build-file element and appends a plugin, or that terminates a line in a generated shell script and appends a command. That code does not run during generation; it runs the first time the developer builds, tests or starts the generated project, which is exactly what the developer does next. **URLs and coordinates redirect the supply chain.** Registry URLs, repository URLs, service discovery endpoints and dependency versions coming from the configuration decide where the generated project fetches artifacts from and what it fetches. A modified value can point the generated build at an attacker-controlled registry, or pin a dependency to a malicious version, without touching a line of application code. ## Executable files in the project `.yo-rc.json` is configuration that the generator reads. The files below are different in kind: they are **JavaScript that the generator imports and runs** — not referenced from the configuration, but picked up by their location alone, so reading it does not reveal them. - **`.blueprint/`** — a directory in the working directory. It is discovered and composed automatically: no `blueprints` entry, no command-line flag and no prompt. Cloning a repository that ships one and running `jhipster` executes its code. - **`.jhipster/sharedOptions.js`** (also `.cjs` and `.mjs`) — imported and executed from the working directory when a blueprint is loaded. A declared blueprint (in `.yo-rc.json` or via `--blueprints`) is what triggers it; blueprint packages expose the same hook as `cli/sharedOptions.js`. Treat these as you would a shell script committed to the repository: running the generator in that directory runs them. ## What this means in practice | Scenario | Trust required | | ------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------- | | You wrote the `.yo-rc.json` yourself | Normal use, no additional risk. | | You cloned a repository from a source you already trust | Normal use — the same trust you already grant its build scripts. | | You cloned a public repository to try it, reproduce a bug report or review a proposal | **Untrusted.** Do not run the generator, `npm install` or the build outside a sandbox. | | A pull request modifies `.yo-rc.json`, `.jhipster/*.json` or a JDL file | **Review it as carefully as source code.** Adding a blueprint is a code-execution change, and it is one line. | JHipster cannot tell these cases apart on its own — only the person running the command can. This trust model is not specific to JHipster: a directory containing a `package.json` can already execute code through npm lifecycle scripts, and the same holds for Maven and Gradle builds. `.yo-rc.json` belongs to that same family of files and deserves the same suspicion. ## Recommendations for users - **Do not run the generator in a repository you would not be willing to build.** If you would hesitate to run `./mvnw` or `npm install` there, hesitate to run `jhipster`. - **Read `.yo-rc.json` before the first run**, especially the `blueprints` and `generators` entries, and look up any blueprint you do not recognize. - **Check for a `.blueprint` directory and a `.jhipster/sharedOptions.*` file**, which are executed without being declared in `.yo-rc.json`. - **Skim the `.jhipster/*.json` files for path values with `..` segments**, which redirect entity files to other files of the project. - **Review configuration files in pull requests** with the same scrutiny as source code. - **Use a sandbox for untrusted projects**: a container, a disposable VM, or a user account without access to your SSH keys, cloud credentials and shell profiles. - **Do not run the generator as root**, and do not run it from your home directory. ## Checking an application you downloaded Downloading an application from a repository and running it means running its code: the build, the tests and the application itself. Before you do, you can tell what JHipster generated from what was changed afterwards: 1. **Keep only the JHipster configuration.** In a copy of the repository, remove every file except `.yo-rc.json`, the `.jhipster/` folder, the `.blueprint/` folder and `.git/`. 2. **Check that the generator and the blueprints are the real JHipster ones.** Each blueprint named in `.yo-rc.json` must be a package you know, installed from the original npm registry (no `registry` override in an `.npmrc`), and `generator-jhipster` must come from npm or from [the main repository](https://github.com/jhipster/generator-jhipster). Read `.blueprint/` and `.jhipster/sharedOptions.*`: they run at the next step. 3. **Regenerate the application** with that generator, in a sandbox and without installing the dependencies (`jhipster --skip-install`). 4. **Compare the regenerated application with the downloaded one** (`git diff`). The comparison shows what was written by hand after the generation: the customizations of the project, and any unexpected or malicious change. Review those before building or running the application. ## Recommendations for CI and hosted generation **Running JHipster as a hosted service — exposing the generator to configurations supplied by other people — is not an officially supported use case.** The generator is built to run on a developer's machine, against input that the developer trusts; a service that generates from attacker-controlled input is outside that model. The guidance below is best-effort hardening for anyone who operates such a service anyway, not a supported configuration. - Run generation in an ephemeral, network-restricted container, and treat the checkout as untrusted input: never generate into a directory shared with credentials, caches or other jobs. - Sandbox the generator process with the Node.js permission model (`node --permission`), granting read access only to the generator installation and the generation directory, and write access only inside the generation directory. The generator can then neither read nor write outside those paths, whatever the configuration asks for; generation still needs a few capability flags for the child processes, worker threads and native addons it uses internally. - A hosted service cannot trust its input, so it must rely on the technical boundaries below rather than on the configuration being benign: run with `--export-application` so nothing is committed to the host filesystem, and with `--disable-blueprints` so no blueprint is resolved or executed. ## What the generator does on its side These are hardening measures, not a replacement for the trust decision described above. They describe the current JHipster version; older versions may lack them or behave differently: - File writes are constrained to descendants of the destination root, so a configured path cannot escape the project directory. - `--export-application` generates into an in-memory store and serializes the result without committing to the host filesystem, so a server-side consumer never writes attacker-controlled paths onto its own disk. - `--disable-blueprints` prevents blueprints from being resolved, installed or executed. None of this makes an untrusted `.yo-rc.json` safe to run, because blueprints are, by design, executable extensions. The trust decision is the actual security boundary.