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

feat: ci awareness to disable terminal prompting within commands #449

Closed
wants to merge 5 commits into from

Conversation

erunion
Copy link
Member

@erunion erunion commented Feb 24, 2022

🚥 Fix RM-3621

🧰 Changes

With our new workflow in #437 there's a new issue that will likely crop up for some folks is that if you don't supply all of the required arguments for a command in a CI environment, our enquirer setup will prompt the terminal for input -- something that will never be answered in a CI environment.

For this we're introducing some new awareness to our commands that ask the user for input to not do that if it's within a CI environment and instead throw an error telling them that they're missing arguments.

I'm also making some other adjustments to a couple commands to clean up their argument structure:

  • versions:create
    • --main and --beta are now booleans
    • --isPublic has been renamed to just --public and it's also been made into a boolean.
    • Make sure usage in README.md is updated
  • versions:update
    • --main and --beta are now booleans
    • --isPublic has been renamed to just --public and it's also been made into a boolean.
    • Make sure usage in README.md is updated

🧬 QA & Testing

If with all the changes I made tests are still passing, 👍

You can also test this behavior out locally by prefixing GITHUB_ACTIONS=true to a ./bin/rdme call:

$ GITHUB_ACTIONS=true ./bin/rdme versions:create --version=1.0.0

We've detected you're running within a GitHub Actions environment, please supply the following required 
arguments for your command instead of relying on our terminal prompt system: fork

@erunion erunion changed the title feat: ci awareness within commands to disable terminal prompting feat: ci awareness to disable terminal prompting within commands Feb 24, 2022
@erunion erunion changed the base branch from main to feat/drop-node12 February 24, 2022 06:29
@@ -37,6 +37,8 @@ jest.mock('../../src/lib/prompts');
describe('rdme versions*', () => {
beforeAll(() => nock.disableNetConnect());

beforeEach(() => jest.resetModules());
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Because we're mocking out process.env.CIRCLECI to test the ci-info package if we don't reset modules here then that package will get loaded within our src/lib/enquirer.js wrapper without the env variable, and cached -- so when the test that does need it, and does mock that environment variable out, the cached module doesn't see it.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I feel like it might make more sense to do this in a global beforeEach call at some point

mockRequest.done();
});

it.todo('should prompt a version list if no `--fork` argument is supplied');
Copy link
Member Author

@erunion erunion Feb 24, 2022

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not having something like promptHandler.createVersionPrompt.mockResolvedValue to mock Enquirer responses with this new setup is annoying but as it is I'm comfortable with the tradeoff we're making with this work and not having to have tests for Enquirer being able to prompt us for questions.

though i'm sure i'l regret this a year from now

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

lmaoo yeah I like that we can mock and reuse responses with that promptHandler, but we have a lot of different patterns in that file that are pretty confusing so I think we should revisit that at some point

{
type: 'select',
name: 'fork',
message: 'Which version would you like to fork from?',
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Having these questions duped in some commands sucks but I'm comfortable with the tradeoff of having duped questions in two commands than having to maintain a question generation library.

Comment on lines 34 to 37
`We've detected you're running within a ${
ci.name
} environment, please supply the following required arguments for your command instead of relying on our terminal prompt system: ${chalk.yellow(
missingArgs.join(',')
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I do not like this sentence I've written; please suggest something better.


describe('ci environments', () => {
beforeEach(() => {
process.env.CIRCLECI = true;
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Purposefully testing it with CIRCLECI here instead of GITHUB_ACTIONS because I know that GITHUB_ACTIONS will always be present in our CI and I don't want to delete that from the workflow runner.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

good thinking!

@erunion erunion added the enhancement New feature or request label Feb 24, 2022
@erunion erunion added this to the v7 milestone Feb 24, 2022
.basicAuth({ user: key })
.reply(200, [{ version }, { version }])
.post('/api/v1/version')
.post('/api/v1/version', {
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We weren't fully testing out the expected API payload. Wish there were a way for us to configure Nock to require this...

Copy link
Member

@kanadgupta kanadgupta left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have one general question about the default export from the enquirer handler (and a few minor comments/suggestions). Big fan of this pattern overall 👏🏽

@@ -37,6 +37,8 @@ jest.mock('../../src/lib/prompts');
describe('rdme versions*', () => {
beforeAll(() => nock.disableNetConnect());

beforeEach(() => jest.resetModules());
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I feel like it might make more sense to do this in a global beforeEach call at some point

mockRequest.done();
});

it.todo('should prompt a version list if no `--fork` argument is supplied');
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

lmaoo yeah I like that we can mock and reuse responses with that promptHandler, but we have a lot of different patterns in that file that are pretty confusing so I think we should revisit that at some point


describe('ci environments', () => {
beforeEach(() => {
process.env.CIRCLECI = true;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

good thinking!

.reply(200, [{ version }, { version }]);

await expect(createVersion.run({ key, version })).rejects.toThrow(
/We've detected you're running within a (.*) environment, please supply the following required arguments for your command instead of relying on our terminal prompt system: fork/
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Any reason why we can't just test for an exact match here?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Because even though I'm setting CIRCLECI to the environment, GITHUB_ACTIONS is also present and ci-info picks that up first so this message says "We've detected you're running within a Github Actions environment" in CI and "within a CircleCI environment" locally.

return enquirer.prompt(questions).catch(err => {
// If the Enquirer promise was rejected without an error then the user killed an open prompt so
// we should abide by their wishes and bail out.
if (!err) process.exit(0);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I feel like we could return a 1 here since it's technically not a success, right? Not sure what the best practices are here 🤔

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Exit code 1 generally means that that app executed with errors but since in this case I'm killing the prompt myself it's not really an error. Jest also returns the same 0 exit code when you exit out of an open --watch.

Exiting Jest before it's able to load any tests:

Screen Shot 2022-02-27 at 7 39 07 PM

Exiting an open --watch process:

Screen Shot 2022-02-27 at 7 39 15 PM

Comment on lines 13 to 18
// Purposefully loading `ci-info` here so we can adequately test it.
const ci = require('ci-info'); // eslint-disable-line global-require
if (!ci.isCI) {
// If we aren't in a CI environment then we shouldn't look for unanswered questions.
return prompt(list);
}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is really clean 🤩

{
type: 'confirm',
name: 'main',
message: 'Would you like to make this version the main version for this project?',
Copy link
Member Author

@erunion erunion Feb 28, 2022

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@kanadgupta Thoughts on slightly reworking this? The double "version" in there reads off.

Suggested change
message: 'Would you like to make this version the main version for this project?',
message: 'Would you like to make this the main version for this project?',

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Agreed! Nice find

@erunion
Copy link
Member Author

erunion commented Feb 28, 2022

After talking through this this morning I'm deciding to close this work out. We have a lot of problems with our existing prompt system (difficult to work with, difficult to test, not every question is mapped to an argument) that while this work aimed to solve it solved it in a backwards way.

Instead of rejecting CI execution of these commands that likely will never be executed from a CI environment anyways, we should instead focus on cleaning up these individual commands instead.

@erunion erunion closed this Feb 28, 2022
@erunion erunion deleted the feat/ci-awareness branch February 28, 2022 17:30
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants