npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2024 – Pkg Stats / Ryan Hefner

@amarppatel/generator-jhipster-multiple-human-readable-foreign-key-fields

v1.0.3

Published

Multiple Human Readable Foreign Key Fields Application

Downloads

9

Readme

In this article, the word attribute is equivalent to the word field as they relate to entities. Both the words field and attribute will be used interchangeably.

This is a side-by-side JHipster 7 blue print showing how to put human-readable foreign key field in place of UUIDs into the user interface where entities have relationships with other entities. Sometimes having a UUID makes it difficult for the human in the loop to figure out what the entity on the other side actually is (without clicking on the UUID link). This solution makes it easier for the user to see what the other related entity actually is. Futhermore, this solution is based on adding @customAnnotation’s to entity field(s), in the JDL file, that would be shown in replacement of UUIDs. If multiple entity fields are necessary to replace the UUID, the fields can be delimmited via a specified delimiter using a @customAnnotation, as well.

There is a solution in the JDL syntax to display a field is documented here: https://www.jhipster.tech/jdl/relationships. The JDL syntax to display a field is:

relationship (OneToMany | ManyToOne | OneToOne | ManyToMany) {
  <from entity>[{<relationship name>[(<display field>)]}] to <to entity>[{<relationship name>[(<display field>)]}]+
}

An example of the above built-in syntax is (from Matt Raible’s "Micro Frontends for Java Microservices" article / github.com code is below):

entity Blog {
  name String required minlength(3)
  handle String required minlength(2)
}

entity Post {
  title String required
  content TextBlob required
  date Instant required
}

relationship ManyToOne {
  Blog{user(login)} to User
  Post{blog(name)} to Blog
}

In the above example, the blog’s UUID will be replaced by the blog’s name in the user interface wher the post will be displayed.

However, the built-in JDL syntax does not provide the ability to display multiple fields to futher distinguish a complex entity. For example, if multiple blogs can have the same name, we would not be able to tell which blog is in the relationship with the post. If we could dispaly the blog’s name and handle (assuming no 2 blogs can have the same handle), then we would be able to tell which blog is related to the post. Consequently, this blueprint serves the purpose of relpacing UUIDs with multiple attributes/fields of the other-side relationship with a given entity to help differentiate the entity’s relationship on the user interface.

This example also show how to create a JHipster 7 blueprint.

Prerequisites:

Setup for Generating JHipster Blueprints

  1. Install JHipster 7.9.3:

    npm i -g [email protected]
  2. There is a bug, at least on macOS Ventura 13.1, that requires a slight change to the yeoman-environment’s package.json file. You will see an error when running the command:

    jhipster --version
  3. If you see the following error, there is an easy fix below:

    INFO! Using bundled JHipster
    node:internal/modules/cjs/loader:556
          throw e;
          ^
    
    Error [ERR_PACKAGE_PATH_NOT_EXPORTED]: Package subpath './lib/util/namespace' is not defined by "exports" in /usr/local/lib/node_modules/generator-jhipster/node_modules/yeoman-environment/package.json
        at new NodeError (node:internal/errors:399:5)
        at exportsNotFound (node:internal/modules/esm/resolve:266:10)
        at packageExportsResolve (node:internal/modules/esm/resolve:602:9)
        at resolveExports (node:internal/modules/cjs/loader:550:36)
        at Module._findPath (node:internal/modules/cjs/loader:619:31)
        at Module._resolveFilename (node:internal/modules/cjs/loader:1046:27)
        at Module._load (node:internal/modules/cjs/loader:905:27)
        at Module.require (node:internal/modules/cjs/loader:1127:19)
        at require (node:internal/modules/helpers:112:18)
        at Object.<anonymous> (/usr/local/lib/node_modules/generator-jhipster/utils/blueprint.js:19:25) {
      code: 'ERR_PACKAGE_PATH_NOT_EXPORTED'
    }
    
    Node.js v19.6.0
  4. Add the line "./lib/util/namespace": "./lib/util/namespace.js" to the global yoeman-environment’s package.json at the end of the "exports" section as follows. You will need to add a "," after "./package.json".

    vi /usr/local/lib/node_modules/generator-jhipster/node_modules/yeoman-environment/package.json
    
      "exports": {
        ".": "./lib/environment.js",
        "./cli/": "./cli/",
        "./lib/": "./lib/",
        "./lib/util/": "./lib/util/",
        "./adapter": "./lib/adapter.js",
        "./conflicter": "./lib/util/conflicter.js",
        "./log": "./lib/util/log.js",
        "./transform": "./lib/util/transform.js",
        "./package.json": "./package.json",
        "./lib/util/namespace": "./lib/util/namespace.js"
      },
  5. Now run the jhipster version command again and you will see the version as below.

    jhipster --version
    INFO! Using bundled JHipster
    7.9.3

Build JHipster Blueprint for Multiple Human-readable Foreign Key Fields.

  1. To generate a JHipster blueprint, run the following command:

    cd ~
    mkdir generator-jhipster-multiple-human-readable-foreign-key-fields
    cd generator-jhipster-multiple-human-readable-foreign-key-fields
    jhipster generate-blueprint
    
    INFO! Using bundled JHipster
    
            ██╗ ██╗   ██╗ ████████╗ ███████╗   ██████╗ ████████╗ ████████╗ ███████╗
            ██║ ██║   ██║ ╚══██╔══╝ ██╔═══██╗ ██╔════╝ ╚══██╔══╝ ██╔═════╝ ██╔═══██╗
            ██║ ████████║    ██║    ███████╔╝ ╚█████╗     ██║    ██████╗   ███████╔╝
      ██╗   ██║ ██╔═══██║    ██║    ██╔════╝   ╚═══██╗    ██║    ██╔═══╝   ██╔══██║
      ╚██████╔╝ ██║   ██║ ████████╗ ██║       ██████╔╝    ██║    ████████╗ ██║  ╚██╗
       ╚═════╝  ╚═╝   ╚═╝ ╚═══════╝ ╚═╝       ╚═════╝     ╚═╝    ╚═══════╝ ╚═╝   ╚═╝
                                https://www.jhipster.tech
    Welcome to JHipster v7.9.3
    
    ⬢ Welcome to the JHipster Project Name ⬢
    ? What is the base name of your application? multiple-human-readable-foreign-key-fields
    ? What is the project name of your application? Multiple Human Readable Foreign Key Fields Application
    ? Do you want to generate a local blueprint inside your application? No
    ? Which sub-generators do you want to override? cypress, entity-client
    ? Comma separated additional sub-generators.
    ? Add a cli? Yes
    ? Is cypress generator a side-by-side blueprint? Yes
    ? Is cypress generator a cli command? No
    ? What task do you want do implement at cypress generator? initializing
    ? Is entity-client generator a side-by-side blueprint? Yes
    ? Is entity-client generator a cli command? No
    ? What task do you want do implement at entity-client generator? initializing
    ? What is the default indentation? 2
       create .prettierrc.yml
       create package.json
       create .eslintrc.json
        force .yo-rc.json
       create .mocharc.cjs
       create README.md
       create test/utils.mjs
       create cli/cli.mjs
       create .github/workflows/generator.yml
       create .prettierignore
       create .gitignore
       create .gitattributes
       create .editorconfig
       create generators/cypress/index.mjs
       create generators/cypress/generator.spec.mjs
       create generators/cypress/generator.mjs
       create generators/entity-client/generator.mjs
       create generators/entity-client/index.mjs
        force .yo-rc.json
  2. If you see the following error, there is an easy fix below:

    Error [ERR_PACKAGE_PATH_NOT_EXPORTED]: Package subpath './lib/util/namespace' is not defined by "exports" in ~/workspace/generator-jhipster-multiple-human-readable-foreign-key-fields/node_modules/generator-jhipster/node_modules/yeoman-environment/package.json
        at new NodeError (node:internal/errors:399:5)
        at exportsNotFound (node:internal/modules/esm/resolve:266:10)
        at packageExportsResolve (node:internal/modules/esm/resolve:602:9)
        at resolveExports (node:internal/modules/cjs/loader:550:36)
        at Module._findPath (node:internal/modules/cjs/loader:619:31)
        at Module._resolveFilename (node:internal/modules/cjs/loader:1046:27)
        at Module._load (node:internal/modules/cjs/loader:905:27)
        at Module.require (node:internal/modules/cjs/loader:1127:19)
        at require (node:internal/modules/helpers:112:18)
        at Object.<anonymous> (/Users/amarppatel/workspace/generator-jhipster-multiple-human-readable-foreign-key-fields/node_modules/generator-jhipster/utils/blueprint.js:19:25)
        at Module._compile (node:internal/modules/cjs/loader:1246:14)
        at Module._extensions..js (node:internal/modules/cjs/loader:1300:10)
        at Module.load (node:internal/modules/cjs/loader:1103:32)
        at Module._load (node:internal/modules/cjs/loader:942:12)
        at Module.require (node:internal/modules/cjs/loader:1127:19)
        at require (node:internal/modules/helpers:112:18)
        at Object.<anonymous> (/Users/amarppatel/workspace/generator-jhipster-multiple-human-readable-foreign-key-fields/node_modules/generator-jhipster/cli/environment-builder.js:27:82)
        at Module._compile (node:internal/modules/cjs/loader:1246:14)
        at Module._extensions..js (node:internal/modules/cjs/loader:1300:10)
        at Module.load (node:internal/modules/cjs/loader:1103:32)
        at Module._load (node:internal/modules/cjs/loader:942:12)
        at Module.require (node:internal/modules/cjs/loader:1127:19)
        at require (node:internal/modules/helpers:112:18)
        at Object.<anonymous> (/Users/amarppatel/workspace/generator-jhipster-multiple-human-readable-foreign-key-fields/node_modules/generator-jhipster/cli/program.js:26:28)
        at Module._compile (node:internal/modules/cjs/loader:1246:14)
        at Module._extensions..js (node:internal/modules/cjs/loader:1300:10)
        at Module.load (node:internal/modules/cjs/loader:1103:32)
        at Module._load (node:internal/modules/cjs/loader:942:12)
        at ModuleWrap.<anonymous> (node:internal/modules/esm/translators:168:29)
        at ModuleJob.run (node:internal/modules/esm/module_job:193:25)
  3. Add the line "./lib/util/namespace": "./lib/util/namespace.js" to the local project yoeman-environment package.json at the end of the "exports" section as follows. You will need to add a "," after "./package.json".

    vi ~/workspace/generator-jhipster-multiple-human-readable-foreign-key-fields/node_modules/generator-jhipster/node_modules/yeoman-environment/package.json
  4. This is what the package.json should look like:

      "exports": {
        ".": "./lib/environment.js",
        "./cli/": "./cli/",
        "./lib/": "./lib/",
        "./lib/util/": "./lib/util/",
        "./adapter": "./lib/adapter.js",
        "./conflicter": "./lib/util/conflicter.js",
        "./log": "./lib/util/log.js",
        "./transform": "./lib/util/transform.js",
        "./package.json": "./package.json",
        "./lib/util/namespace": "./lib/util/namespace.js"
      },
  5. Then run the blueprint command again, to finish generating the blueprint

    cd ~/workspace/generator-jhipster-multiple-human-readable-foreign-key-fields
    jhipster generate-blueprint
  6. You should see success message now:

    Application successfully committed to Git from ~/workspace/generator-jhipster-multiple-human-readable-foreign-key-fields.
    Congratulations, JHipster execution is complete!
    Sponsored with ❤️  by @oktadev.

Use the Blueprint Locally to Generate Code

  1. Link the blueprint locally

    cd ~/workspace/generator-jhipster-multiple-human-readable-foreign-key-fields
    npm link

Modify the Blueprint to Enable Multiple Human-readable Foreign key Fields.

  1. Added the following files:

    generators/constants-saathratri.js
    generator/utils-saathratri.js
    generators/entity-client/templates/angular/src/main/webapp/app/entities/entity.model.ts.ejs
    generators/entity-client/templates/angular/src/main/webapp/app/entities/detail/entity-management-detail.component.html.ejs
    generators/entity-client/templates/angular/src/main/webapp/app/entities/list/entity-management.component.html.ejs
    generators/entity-client/templates/angular/src/main/webapp/app/entities/update/entity-management-update.component.html.ejs

Have Fun with Creating JHipster Blueprints!

I hope you enjoyed this demo, and it helped you understand how to build blueprints with JHipster.

☕️ Find the code on GitHub: https://github.com/amarpatel-xx/generator-jhipster-multiple-human-readable-foreign-key-fields

🤓 Read the README.md post at https://github.com/amarpatel-xx/jhipster-multiple-human-readable-foreign-key-fields-example to see a working example of a microservices architecture using an Angular client that was generated using this blueprint. You will see how multiple foreign key fields are displayed when a relationship’s fields are shown.