preface

Now there is an AAa.js file that does the following: prompts the user from the terminal for a project name, then reads, creates the directory in the current directory, and generates a package.json with two dependencies. Install react-dom via NPM I; Finally the terminal notifies you that the installation is complete. Users are only allowed to perform node AAA once and enter the project name to complete these operations

The above content is an interview question sent by Teacher Situ Zhengmei in a wechat group.

Break it down and the questions have the following requirements:

  1. Get user terminal input

  2. Create a user input folder

  3. Generate package.json file

  4. NPM I install React and react-dom

  5. Notifies the user of the dependency installation completion

According to the above requirements to achieve respectively

Get user terminal input

Get the user’s terminal input. This can be done in a variety of ways, from fs.readsync + process.stdin to readline.question, which is a node native module, or a third-party library called Inquirer. End-user interaction for various poses). Here the situation is not that complicated, I use readline.question directly to implement the code:

Const getUserInput = inputTip => {const myReadline = readline.createInterface({input: process.stdin, output: process.stdout }); return new Promise((resolve, reject) => { myReadline.question(inputTip, answer => { myReadline.close(); resolve(answer); }); }); };Copy the code

The readline.question file is not too complicated.

Create a user input folder

To create a folder, this involves the terminal executing the shell command mkdir, which I implemented using child_process.exec

Spawns a shell then executes the command within that shell, buffering any generated output. The command string passed to the exec function is processed directly by the shell and special characters (vary based on shell) need to be dealt with accordingly:

Exec (‘mkdir test’, (error, stdout, stderr) => {}) One thing to note here is whether folders in the current directory already exist. Fs. readdirSync is used to get the list of all files and folders in the current directory, and fs.statSync is used to get the list of folders in the current directory.

Const getDirNameList = path => {let allList = fs.readdirsync (path); let dirList = []; allList.forEach(item => { if (fs.statSync(item).isDirectory()) { dirList.push(item); }}); return dirList; };Copy the code

generatepackage.jsonfile

Fs.writefilesync = fs.writefilesync = fs.writefilesync;

const generatePackageJsonFile = projectName => { const packageJSON = JSON.stringify( { "name": projectName, "version": "1.0.0", "description" : ""," main ":" index. Js ", "scripts" : {" test ", "echo \" Error: No test specified \ "& & exit 1}", "author" : ""," license ":" ISC ", "dependencies" : {" react ":" ^ 16.2.0 ", "the react - dom" : "^ 16.2.0}}"); fs.writeFileSync(`./${projectName}/package.json`, packageJSON); };Copy the code

npm iThe installationreactAs well asreact-dom

Since dependencies are already written to package.json, NPM I can be executed by exec

Notifies the user of the dependency installation completion

Callbacks executed by exec are executed after NPM I ends, so this is fine.

Github code address

conclusion

  1. The above code works with Node 8.9.4 on MAC and is not tested in other environments.

  2. I’m not going to be able to write this naked on the spot. I did it while I was flipping through documents.