Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

add jwt to internet module #1282

Open
xDivisionByZerox opened this issue Aug 18, 2022 · 15 comments · May be fixed by #2936
Open

add jwt to internet module #1282

xDivisionByZerox opened this issue Aug 18, 2022 · 15 comments · May be fixed by #2936
Assignees
Labels
c: feature Request for new feature good first issue Good for newcomers help wanted Extra attention is needed m: internet Something is referring to the internet module s: accepted Accepted feature / Confirmed bug
Milestone

Comments

@xDivisionByZerox
Copy link
Member

xDivisionByZerox commented Aug 18, 2022

Clear and concise description of the problem

As a developer, I use faker to "seed" my documentation examples. I was currently writing a section about the usage of the JWT token in my system. For visualization purposes, I wanted to provide an example JWT so developers can see what to expect. Sadly faker doesn't provide such a feature (at least not in the internet module where I would expect it).

Suggested solution

Add a basic jwt function to the internet module that returns a string that is a JWT. So it should be "decryptable" but has a random signature.

I don't think it's necessary to input a payload object since that would get too close to a real implementation (?).

Alternative

Currently, I use a hardcoded JWT (with incorrect signature and expired) for my documentation.

Additional context

No response


Note

This issue has been marked with "good first issue". If you'd like to get started contributing to this project, this is the issue for you! The issue can be solved by following the acceptance criteria layed out in the team decision comment

@xDivisionByZerox xDivisionByZerox added c: feature Request for new feature m: internet Something is referring to the internet module labels Aug 18, 2022
@ST-DDT
Copy link
Member

ST-DDT commented Aug 18, 2022

What would be the benefit of a generated invalid token over a static expired one?

@xDivisionByZerox
Copy link
Member Author

Just so I understand you correctly. You suggest doing the following:

@MyDocumentationDecorator({
  example: myJwtLib.generate(realPayload, secret, { expiresIn: dateInThePast }),
})

This is not possible for me because the part where I write the documentation doesn't depend on the implementation of the JWT generation (or any business logic tbh). So I'm not able to access myJwtLib because it's abstracted in a way that only the service that is responsible for JWT generation knows the exact implementation.
And to go a step further I'm not able to use that service in the documentation due to it (the documentation) being a decorator based and the services have to be injected by the framework for dependency resolution.

One more thing:
My current solution works perfectly fine (with a static/hardcoded JWT string). I just like to have example values change every time you reload to documentation, but its not required.

@xDivisionByZerox xDivisionByZerox added the s: waiting for user interest Waiting for more users interested in this feature label Feb 15, 2023
@BrianMcBrayer
Copy link

I'd be interested in Faker having this too.

@ST-DDT ST-DDT added this to the vFuture milestone Mar 21, 2023
@xDivisionByZerox
Copy link
Member Author

Please upvote the issue if you are interested in having this in Faker. That way we can track user interest.

@BrianMcBrayer
Copy link

Please upvote the issue if you are interested in having this in Faker. That way we can track user interest.

Silly question but how do I upvote?

@xDivisionByZerox
Copy link
Member Author

With "upvote" we mean the +1 (👍) reaction in issues and PRs.

But I saw that you already found it 👍


More information on reactions can be found on "Add Reactions to Pull Requests, Issues, and Comments"

@ST-DDT ST-DDT added s: waiting for user interest Waiting for more users interested in this feature and removed s: waiting for user interest Waiting for more users interested in this feature labels May 5, 2023
@github-actions
Copy link

github-actions bot commented May 5, 2023

Thank you for your feature proposal.

We marked it as "waiting for user interest" for now to gather some feedback from our community:

  • If you would like to see this feature be implemented, please react to the description with an up-vote (:+1:).
  • If you have a suggestion or want to point out some special cases that need to be considered, please leave a comment, so we are aware about them.

We would also like to hear about other community members' use cases for the feature to give us a better understanding of their potential implicit or explicit requirements.

We will start the implementation based on:

  • the number of votes (:+1:) and comments
  • the relevance for the ecosystem
  • availability of alternatives and workarounds
  • and the complexity of the requested feature

We do this because:

  • There are plenty of languages/countries out there and we would like to ensure that every method can cover all or almost all of them.
  • Every feature we add to faker has "costs" associated to it:
    • initial costs: design, implementation, reviews, documentation
    • running costs: awareness of the feature itself, more complex module structure, increased bundle size, more work during refactors

View more issues which are waiting for user interest

@Shinigami92
Copy link
Member

An example call could look like:

const jwt: string = faker.internet.jwt({
  algorithm: faker.internet.jwtAlgorithm(),
  refDate: faker.date.past(),
});

But what should be returned?
Should header contain { alg, typ }?
Should payload contain { sub, name, exp, iat }?

@ST-DDT
Copy link
Member

ST-DDT commented Apr 18, 2024

Or more specifically:

What are your requirements/expectations?

  • Which headers?
  • Which values?
  • Valid signature?

@xDivisionByZerox
Copy link
Member Author

xDivisionByZerox commented Apr 23, 2024

Proposal for minimalistic API implementation

The following text uses "Requirement Levels" based on RFC 2119

What are your requirements/expectations?

As stated in my original feature request:

Add a basic jwt function to the internet module that returns a string that is a JWT. So it should be "decryptable" but has a random signature.

I don't think it's necessary to input a payload object since that would get too close to a real implementation (?).

We can asset multiple things here:

  • the JWT value MUST fulfil the semantical contract based on RFC7519
  • the JWT signature MAY be valid
  • the generation function MAY take a payload argument
  • the generation function MUST provide a default payload argument (to fulfill the contract)
  • the generation function MAY take a header argument
  • the generation function MUST take a header argument (to fulfill the contract)

Additionally, I suggest that the initial method SHOULD be as minimalistic as possible.

The following sections are suggestions that should summarize the higher level implementation details for faker.internet.jwt.

Headers

  • The header MUST be a base64 encoded object
  • The header object MUST include the properties "typ" and "alg"
  • The typ property SHOULD always be 'JWT'
  • The alg property SHOULD be chosen randomly from a list of valid algorithm values as defined in RFC7518

Payload

  • The payload MUST be a base64 encoded object
  • The payload object MUST include the properties "exp" and "iat"
    • The property "exp" MAY be a number given by faker.date.anytime().valueOf()
    • The property "iat" MAY be a number given by faker.date.anytime().valueOf()
  • The payload MAY include any other Registered Claim Names
    • The property "iss" MAY be a random company name given by faker.company.name()
    • The property "sub" MAY be a UUID given by faker.string.uuid()
    • The property "aud" MAY be a UUID given by faker.string.uuid()
    • The property "nbf" MAY be a datetim string given by faker.date.anytime()
    • The property "jti" MAY be a UUID given by faker.string.uuid()
  • The payload MUST NOT include any other property not stated so far

Signature

  • The signature MUST NOT fulfill the contract of RFC7518
  • The signature MAY be an alphanumeric string
  • The signature MAY have a random length
  • The signature MUST be at least 20 character

Example implementation

jwt(): string {
  const header = {
    alg: randomJwtHeaderAlgorythm(), // abstracted here
    typ: 'JWT',
  };
  const payload = {
    iat: this.faker.date.anytime().valueOf(),
    exp: this.faker.date.anytime().valueOf(),
  };

  const encodedHeader = Buffer.from(JSON.stringify(header)).toString('base64url');
  const encodedPayload = Buffer.from(JSON.stringify(payload)).toString('base64url');
  const signature = faker.random.alphaNumeric(64);

  return `${encodedHeader}.${encodedPayload}.${signature}`;
};

Feel free to give feedback on the proposal.

@ST-DDT
Copy link
Member

ST-DDT commented Apr 23, 2024

  • The header object MUST include the properties "typ" and "alg"

These headers are also optional according to the spec. I didn't find any specifics regarding alg at all.
Maybe lets consider alg as required.

  • The payload object MUST include the properties "exp" and "iat"

These claim names are also optional according to the spec.

Additionally, I suggest that the initial method SHOULD be as minimalistic as possible.

If it should be as minimalisistic as possible, it should omit all optional fields.
Which basically results in {"alg": "HS256"}.{}.ZRrHA1JJJW8opsbCGfG_HACGpVUMN_a9IV7pAx_Zmeo

eyJhbGciOiJIUzI1NiJ9.e30.ZRrHA1JJJW8opsbCGfG_HACGpVUMN_a9IV7pAx_Zmeo

What is your intention doing with such a value?
Since it doesn't contain any values (and is invalid) what can you do with it?
If you cannot do anything with it, why not hardcode the first two parts? Or just use 3 random base64 strings?

It would be a different matter if you could provide the/additional header and payload entries.
Then you could actually create JWT tokens according to your needs (except their signature).
But then again why would your application ever process a JWT token, that isn't valid?

Providing a valid signature isn't possible without specific libraries, not available in all environments (e.g. node:crypto)

@xDivisionByZerox
Copy link
Member Author

  • The header object MUST include the properties "typ" and "alg"

These headers are also optional according to the spec. I didn't find any specifics regarding alg at all. Maybe lets consider alg as required.

  • The payload object MUST include the properties "exp" and "iat"

These claim names are also optional according to the spec

My comment was not a summary of RFC7519 but a "Proposal for minimalistic API implementation" (as stated in the first heading) - a suggested specification for the implementation. If this intent was not clear enough, I apologize for that.

Additionally, I suggest that the initial method SHOULD be as minimalistic as possible.

If it should be as minimalisistic as possible, it should omit all optional fields. Which basically results in {"alg": "HS256"}.{}.ZRrHA1JJJW8opsbCGfG_HACGpVUMN_a9IV7pAx_Zmeo

eyJhbGciOiJIUzI1NiJ9.e30.ZRrHA1JJJW8opsbCGfG_HACGpVUMN_a9IV7pAx_Zmeo

While this would be true when strictly following the RFC, I'd argue that real-world use cases nearly always include the "typ" property in the header as well as the properties "exp" and "iat" in the payload. That's the reason why I suggested including them.

What is your intention doing with such a value? Since it doesn't contain any values (and is invalid) what can you do with it? If you cannot do anything with it, why not hardcode the first two parts? Or just use 3 random base64 strings?

It would be a different matter if you could provide the/additional header and payload entries. Then you could actually create JWT tokens according to your needs (except their signature). But then again why would your application ever process a JWT token, that isn't valid?

As stated in my original comment as well:
The workaround with a static value works for me. My use case was to generate dynamic example values in the documentation I was working on back then. Non-tech people (testers) had to use an API interface (think swagger) and had to extract the JWT they got from a response. The documentation showed them the value of the format that they could expect. My use case might not be the most sophisticated but seeing that this issue collected over 20 upvotes during the last year I'd say that the necessity from the community is given.

Providing a valid signature isn't possible without specific libraries, not available in all environments (e.g. node:crypto)

Agreed, this is why I made the statements in the suggestion, covering the necessity to not include valid signatures.

@ST-DDT
Copy link
Member

ST-DDT commented Apr 25, 2024

Team Decision

  • We accept the faker.internet.jwt feature.
  • We will have header and payload options that replace the default values
  • The defaults will be defined according to the sample/spec outlined here: add jwt to internet module  #1282 (comment)
  • Additionally:
    • exp should be derived from iat (faker.date.soon({refDate: iat}))
    • iat should be faker.date.recent()

@ST-DDT ST-DDT added s: accepted Accepted feature / Confirmed bug and removed s: waiting for user interest Waiting for more users interested in this feature labels Apr 25, 2024
@ST-DDT ST-DDT modified the milestones: vFuture, vAnytime Apr 25, 2024
@ST-DDT ST-DDT added good first issue Good for newcomers help wanted Extra attention is needed labels Apr 25, 2024
@eLoyyyyy eLoyyyyy linked a pull request Jun 4, 2024 that will close this issue
@eLoyyyyy
Copy link

eLoyyyyy commented Jun 5, 2024

I'll get this feature. This is going to be my first, so please be kind.

@ST-DDT
Copy link
Member

ST-DDT commented Jun 5, 2024

Welcome to the project. I assigned the issue to you.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
c: feature Request for new feature good first issue Good for newcomers help wanted Extra attention is needed m: internet Something is referring to the internet module s: accepted Accepted feature / Confirmed bug
Projects
None yet
Development

Successfully merging a pull request may close this issue.

5 participants