swagger-api / swagger-api/swagger-codegen

[BUG][JAVA] AbstractGenerator.java leaks mustache template file handles in templateDir - blocker when using templateDir with gradle plugin due to long running gradle daemons

Open
#9,173 0 comments 0 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

Dominant language
Mustache
Stars
17.8k
Forks
6k
PR merge metrics
No merged PRs in 30d

Description

Bug Report Checklist
  • Have you provided a full/minimal spec to reproduce the issue?
    => default petstore is perfectly fine
  • Have you validated the input using an OpenAPI validator (example)?
    => yes
  • What's the version of OpenAPI Generator used?
    => 3.3.4
  • Have you search for related issues/PRs?
    => yes, no match identified
  • What's the actual output vs expected output?
    => not related to generator output
  • [Optional] Bounty to sponsor the fix (example)
Description

The problem is that AbstractGenerator.java leaves mustache template file handles open. This is fine if the generator process completes quickly and the process terminates, because operating system then closes all file handles. On the other hand, when using gradle plugin, the gradle daemon process may remain in memory and the handles remain open, preventing deletion of custom templateDir.

openapi-generator version

version 3.3.4, not a regression issue, seems the issue exists since the initial commit

OpenAPI declaration file content or url

Can use default pet store. The issue is not related to OpenAPI specs, but rather to the use of templateDir with custom templates together with gradle plugin.

Command line used for generation

actually, used the gradle plugin, the main point is that templateDir is used with custom templates together with the gradle plugin and gradle daemon process remains running in the background

Steps to reproduce
  • copy default set of templates for a generator to a newly created templateDir
  • run the generator using gradle plugin (gradle daemon enabled by default), passing the created templateDir
  • after the generator is done, try deleting the templateDir, it cannot be done due to file locks -- the file handles are still open.
  • open Windows Task Manager and kill java.exe process running gradle, the templateDir can now be deleted
Related issues/PRs

no PR on my part, I suggest a simple fix below, it's really a trivial thing to fix once you're aware of what it going on, please see "Suggest a fix" below

Suggest a fix

Culprit method: readTemplate()
Culprit file: AbstractGenerator.java
Full path: openapi-generator/modules/openapi-generator/src/main/java/org/openapitools/codegen/AbstractGenerator.java

Lines causing the issue are commented out in the following snippet and replaced with the solution (using Java 7 try-with-resources, but can be done without it as well, could as well close the scanner in a finally block)

  public String readTemplate(String name) {
    try {
        Reader reader = getTemplateReader(name);
        if (reader == null) {
            throw new RuntimeException("no file found");
        }

        // BEGIN OLD LINES
        // Scanner s = new Scanner(reader).useDelimiter("\\A");
        // return s.hasNext() ? s.next() : "";
        // END OLD LINES

        // BEGIN NEW LINES
        try (Scanner s = new Scanner(reader)) {
          s.useDelimiter("\\A");
          return s.hasNext() ? s.next() : "";
        }
        // END NEW LINES

    } catch (Exception e) {
        LOGGER.error(e.getMessage());
    }
    throw new RuntimeException("can't load template " + name);
  }

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start with readTemplate() in modules/openapi-generator/src/main/java/org/openapitools/codegen/AbstractGenerator.java and inspect how the Reader and Scanner are managed. Run the Gradle-plugin reproduction with a custom templateDir; done means generation completes without retaining template file handles, so the directory can be deleted while the daemon remains running.

Written by the indexing model from the issue text.

Assessment

Tech stack
java
Domain
tooling
Issue type
Bug
Difficulty
1/5
Estimated time
Under an hour
Activity status
Stale
Clarity
Clearly specified
Newbie friendliness
45/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.