name: sanitiseJavaProjectName()

in packages/type-safe-api/src/project/codegen/generate.ts [284:618]


        name: sanitiseJavaProjectName(packageName),
        artifactId: sanitiseJavaArtifactId(packageName),
        groupId: "com.generated.api",
        ...options.javaOptions,
      });
    }
    default:
      throw new Error(`Unknown ${suffix} language ${language}`);
  }
};

const generateLanguageProjects = (
  suffix: string,
  languages: Language[],
  projectConstructors: Record<Language, new (...args: any[]) => Project>,
  options: GenerateLanguageProjectOptions
) => {
  const projects: { [language: string]: Project } = {};
  languages.forEach((language) => {
    const project = generateLanguageProject(
      suffix,
      language,
      projectConstructors,
      options
    );
    if (project != null) {
      projects[language] = project;
    }
  });

  return projects;
};

/**
 * Generated handlers projects
 */
export interface GeneratedHandlersProjects {
  /**
   * Java handlers project
   */
  readonly java?: GeneratedJavaHandlersBaseProject;
  /**
   * Python handlers project
   */
  readonly python?: GeneratedPythonHandlersBaseProject;
  /**
   * TypeScript handlers project
   */
  readonly typescript?: GeneratedTypescriptHandlersBaseProject;
}

export interface GenerateInfraProjectOptions
  extends GenerateRuntimeProjectsOptions {
  /**
   * Generated runtime projects
   */
  readonly generatedRuntimes: {
    readonly java?: GeneratedJavaRuntimeBaseProject;
    readonly python?: GeneratedPythonRuntimeBaseProject;
    readonly typescript?: GeneratedTypescriptRuntimeBaseProject;
  };
  readonly generatedHandlers: GeneratedHandlersProjects;
}

/**
 * Returns a generated infrastructure project for the given language
 */
export const generateInfraProject = (
  language: Language,
  options: GenerateInfraProjectOptions
): Project => {
  return _generateInfraProject(
    language,
    {
      [Language.JAVA]: GeneratedJavaCdkInfrastructureProject,
      [Language.PYTHON]: GeneratedPythonCdkInfrastructureProject,
      [Language.TYPESCRIPT]: GeneratedTypescriptCdkInfrastructureProject,
    },
    options
  );
};

/**
 * Returns a generated async infrastructure project for the given language
 */
export const generateAsyncInfraProject = (
  language: Language,
  options: GenerateInfraProjectOptions
): Project => {
  return _generateInfraProject(
    language,
    {
      [Language.JAVA]: GeneratedJavaAsyncCdkInfrastructureProject,
      [Language.PYTHON]: GeneratedPythonAsyncCdkInfrastructureProject,
      [Language.TYPESCRIPT]: GeneratedTypescriptAsyncCdkInfrastructureProject,
    },
    options
  );
};

export const _generateInfraProject = (
  language: Language,
  projectConstructors: LanguageProjectConstructors,
  options: GenerateInfraProjectOptions
): Project => {
  new TextFile(
    options.parent,
    path.join(options.generatedCodeDir, "README.md"),
    {
      lines: [
        "## Generated Infrastructure",
        "",
        "This directory contains a generated type-safe CDK construct which can provision the API gateway infrastructure for an API based on your model.",
      ],
      readonly: true,
    }
  );

  return generateLanguageProject("infra", language, projectConstructors, {
    ...options,
    typescriptOptions: {
      ...options.typescriptOptions,
      generatedTypescriptTypes: options.generatedRuntimes.typescript,
    },
    pythonOptions: {
      ...options.pythonOptions,
      generatedPythonTypes: options.generatedRuntimes.python,
    },
    javaOptions: {
      ...options.javaOptions,
      generatedJavaTypes: options.generatedRuntimes.java,
    },
  });
};

export interface GenerateHandlersBaseProjectOptions
  extends GenerateRuntimeProjectsOptions {
  /**
   * Generated runtime projects
   */
  readonly generatedRuntimes: {
    readonly java?: GeneratedJavaRuntimeBaseProject;
    readonly python?: GeneratedPythonRuntimeBaseProject;
    readonly typescript?: GeneratedTypescriptRuntimeBaseProject;
  };
}

export interface GenerateHandlersProjectOptions
  extends GenerateHandlersBaseProjectOptions {
  /**
   * Generated runtime projects
   */
  readonly generatedRuntimes: {
    readonly java?: GeneratedJavaRuntimeProject;
    readonly python?: GeneratedPythonRuntimeProject;
    readonly typescript?: GeneratedTypescriptRuntimeProject;
  };
}

export interface GenerateAsyncHandlersProjectOptions
  extends GenerateHandlersBaseProjectOptions {
  /**
   * Generated runtime projects
   */
  readonly generatedRuntimes: {
    readonly java?: GeneratedJavaAsyncRuntimeProject;
    readonly python?: GeneratedPythonAsyncRuntimeProject;
    readonly typescript?: GeneratedTypescriptAsyncRuntimeProject;
  };
}

/**
 * Create handlers projects in the given languages
 * @param languages the languages to generate for
 * @param options options for the projects to be created
 */
export const generateHandlersProjects = (
  languages: Language[],
  options: GenerateHandlersProjectOptions
): { [language: string]: Project } => {
  return _generateHandlersProjects(
    languages,
    {
      [Language.JAVA]: GeneratedJavaHandlersProject,
      [Language.PYTHON]: GeneratedPythonHandlersProject,
      [Language.TYPESCRIPT]: GeneratedTypescriptHandlersProject,
    },
    options
  );
};

/**
 * Create async handlers projects in the given languages
 * @param languages the languages to generate for
 * @param options options for the projects to be created
 */
export const generateAsyncHandlersProjects = (
  languages: Language[],
  options: GenerateAsyncHandlersProjectOptions
): { [language: string]: Project } => {
  return _generateHandlersProjects(
    languages,
    {
      [Language.JAVA]: GeneratedJavaAsyncHandlersProject,
      [Language.PYTHON]: GeneratedPythonAsyncHandlersProject,
      [Language.TYPESCRIPT]: GeneratedTypescriptAsyncHandlersProject,
    },
    options
  );
};

const _generateHandlersProjects = (
  languages: Language[],
  projectConstructors: LanguageProjectConstructors,
  options: GenerateHandlersBaseProjectOptions
): { [language: string]: Project } => {
  if (languages.length > 0) {
    new TextFile(
      options.parent,
      path.join(options.generatedCodeDir, "README.md"),
      {
        lines: [
          "## Handlers",
          "",
          "This directory contains lambda handlers for implementing your API.",
          "",
          "Whenever an operation is annotated with the `@handler` trait in Smithy (or the `x-handler` vendor extension in OpenAPI), a stub handler implementation will be generated for you, which you are free to modify.",
        ],
        readonly: true,
      }
    );
  }

  return generateLanguageProjects("handlers", languages, projectConstructors, {
    ...options,
    typescriptOptions: {
      ...options.typescriptOptions,
      generatedTypescriptTypes: options.generatedRuntimes.typescript,
    },
    pythonOptions: {
      ...options.pythonOptions,
      generatedPythonTypes: options.generatedRuntimes.python,
    },
    javaOptions: {
      ...options.javaOptions,
      generatedJavaTypes: options.generatedRuntimes.java,
    },
  });
};

/**
 * Create runtime projects in the given languages
 * @param languages the languages to generate for
 * @param options options for the projects to be created
 */
export const generateRuntimeProjects = (
  languages: Language[],
  options: GenerateRuntimeProjectsOptions
): { [language: string]: Project } => {
  return _generateRuntimeProjects(
    languages,
    {
      [Language.JAVA]: GeneratedJavaRuntimeProject,
      [Language.PYTHON]: GeneratedPythonRuntimeProject,
      [Language.TYPESCRIPT]: GeneratedTypescriptRuntimeProject,
    },
    options
  );
};

/**
 * Create async runtime projects in the given languages
 * @param languages the languages to generate for
 * @param options options for the projects to be created
 */
export const generateAsyncRuntimeProjects = (
  languages: Language[],
  options: GenerateRuntimeProjectsOptions
): { [language: string]: Project } => {
  return _generateRuntimeProjects(
    languages,
    {
      [Language.JAVA]: GeneratedJavaAsyncRuntimeProject,
      [Language.PYTHON]: GeneratedPythonAsyncRuntimeProject,
      [Language.TYPESCRIPT]: GeneratedTypescriptAsyncRuntimeProject,
    },
    options
  );
};

const _generateRuntimeProjects = (
  languages: Language[],
  projectConstructors: LanguageProjectConstructors,
  options: GenerateRuntimeProjectsOptions
): { [language: string]: Project } => {
  new TextFile(
    options.parent,
    path.join(options.generatedCodeDir, "README.md"),
    {
      lines: [
        "## Generated Runtimes",
        "",
        "This directory contains generated runtime projects based on your API model.",
        "",
        "Each runtime project includes types from your API model, as well as type-safe client and server code.",
      ],
      readonly: true,
    }
  );

  return generateLanguageProjects(
    "runtime",
    languages,
    projectConstructors,
    options
  );
};

/**
 * Returns a generated client project for the given language
 */
const generateLibraryProject = (
  library: Library,
  options: GenerateLibraryProjectsOptions
): Project => {
  const packageName = `${options.parentPackageName}-${library}`;
  const commonOptions = {
    outdir: path.join(options.generatedCodeDir, library),
    specPath: options.parsedSpecPath,
    parent: options.parent,
  };

  switch (library) {
    case Library.TYPESCRIPT_REACT_QUERY_HOOKS: {
      return new TypescriptReactQueryHooksLibrary({