background
In development, we may need some scripts to batch process our business logic in specific situations. How to call shell scripts in nodejs?
newly build
-
Create a new script file under the project
touch newFile.sh
-
Modify file permissions
chmod 777 newFile.sh Modify the file to be readable, writable and executable
Nodejs call
File reading
//Using the file reading method in the child process of nodejs
const { execFile } = require(‘child_process’);
Examples
DocsService.publishAllDocs = (req, res) => {
req.session.touch();
const { docName, pathName, saveDocsList, docType } = req.body;
var docText = req.body.docText;
var newGit = req.body.newGit;
//Get file path
var filepath = path.join(__dirname, '../../bin/rnsource/publishAllDocs.sh');
var fileArr, fileName, spath, dirnameBack, docbackList = [], docbackPath, docPath = "";
var username = req.session.user_name;
var str = docName+'/'+ pathName + '|'+ username;
var reg = new RegExp(`^(${str})`);
saveDocsList.map((item, index)=>{
fileArr = item.pathName.split("/");
fileName = fileArr[fileArr.length-1];
if(docType == "docsify"){
dirnameBack = fileName != "" ? `../../gitlib/docBackup/${docName}/docs/${item.pathName}`:`../../gitlib/docBackup/${docName}/docs/README.md`
}else{
spath = item.pathName.split(fileName)[0];
dirnameBack = spath != "" ?'../../gitlib/docBackup/'+ docName+'/'+ spath +'/'+fileName:'../../gitlib/docBackup/'+ docName+'/' + fileName;
}
docbackPath = path.join(__dirname, dirnameBack);
docbackList.push(docbackPath);
docPath += docbackPath + " ";
})
docPath += ""
//CWD sets the current path. What I set here is the current location of nodejs code
execFile(filepath, [docName, docPath, docType], { cwd: '.' }, function(err, stdout, stderr){
logger.info(stdout);
if(err){
loggerFileError({ user:username , docName:docName , pathname: 'all', operate: "gitbook file one click publishing", err});
res.json({
respCode: -1,
Errmsg: "one click publish failed"
})
}else{
res.json({
respCode: 0,
MSG: "one click publishing succeeded"
})
gitPush({ docName, fileName, docbackPath: docbackList, username, pathName, docType })
unblockFile({ docName, username, pathName, reg });
}
})
}
Callback
Successful execution will return the command executed by the script
execFile
- The first parameter: the external program to call, here is the file to read
- The second parameter: the parameter passed to the external program (must be placed in the array)
- The third parameter: callback function, in which the execution result of external program can be returned
shell
publishAllDocs.sh Idea: all the scripts described here are shell scripts not in windows. Bat scripts in windows are not explained here
#$1 document outermost directory $2 currently modified file name $3 currently modified file directory
cd $(pwd)/gitlib/docs/$1
echo "come in"
for item in $2; do
echo "${item}"
cp -f ${item} ${item/docBackup/docs}
done
#Echo "initialization entry"
echo "$(pwd)/gitlib/docs/$1"
if [ "$3" == "docsify" ];then
#Copy the files in the specified directory, such as $1 / $3 / $2 docs / CST / 7e4ce1de04621e0b/
#Such as CP - RF.. /. / DocBackup / wireless / docs / CST / 7e4ce1de04621e0b / 10708d589 eedfffd.md ./docs/cst/7e4ce1de04621e0b/
cp -rf ./docs ../../../public/docs/$1
else
#Handling gitbook type documents
gitbook build
Echo "copy document"
cp -rf ./_book/* ../../../public/docs/$1
fi
Parameter receiving
- The parameters are obtained according to the data transferred during business call
- Directly use “$” to get
- The order of data acquisition is the order of data transmission
- Remember that it’s not the value of the array corner, and the first parameter of the array is $1
The use of for loop
- Using the form for… In in shell
-
Example of loop body data requiring loop
"/Users/Desktop/work/docManager/docServer/gitlib/docBackup/mygitbook/docs/d09985fc67088b35/d09985fc67088b35.md /Users/Desktop/work/docManager/docServer/gitlib/docBackup/mygitbook/docs/d09985fc67088b35/d09985fc67088b35/6f7a2c61c9bac0a3.md /Users/Desktop/work/docManager/docServer/gitlib/docBackup/mygitbook/README.md /Users/Desktop/work/docManager/docServer/gitlib/docBackup/mygitbook/docs/d09985fc67088b35/d09985fc67088b35/6f7a2c61c9bac0a3.md "
- The data of the loop body in the shell script is special, not our regular array or JSON
- Directly is a string separated by spaces, such as: “a B C D E”
##$2 is the data that is spliced according to the format of the service parameters received in the script, as shown in the above data example
##Loop for... In remember that you must add do to execute the loop body and use done to end the loop
##Each subitem of the item loop body, such as: users / desktop / work / docmanager / docserver / gitlib / DocBackup / mygitbook / docs / d09985fc67088b35 / d09985fc67088b35.md
for item in $2; do
echo "${item}"
cp -f ${item} ${item/docBackup/docs}
done
##${item / DocBackup / docs} string replacement
##Here, replace DocBackup in the item path with docs. For a detailed explanation, please see the following shell string replacement
Shell specifies string substitution
In JS, we can use replace to replace strings. How to implement the change in shell?
Example:
string “abc12342341”
- Echo ${string / 23 / BB} / / abc1bb42341 replace once
- Echo ${string / / 23 / BB} / / abc1bb4bb41 double slashes replace all matches
- Echo ${string / # ABC / BB} / / bb12342341 # start with what to match, the ^ in root PHP is a bit like
- echo
${string/%41/bb}
//What does abc123423bb% end with? The $in root PHP is a bit like that
The use of if condition judgment
grammar
if[];then
...
else
...
fi
Examples
##Conditional judgment is to use [] instead of ()
##Add after;
if [ "$3" == "docsify" ];then
#Copy the files in the specified directory, such as $1 / $3 / $2 docs / CST / 7e4ce1de04621e0b/
#Such as CP - RF.. /. / DocBackup / wireless / docs / CST / 7e4ce1de04621e0b / 10708d589 eedfffd.md ./docs/cst/7e4ce1de04621e0b/
cp -rf ./docs ../../../public/docs/$1
else
#Handling gitbook type documents
gitbook build
Echo "copy document"
cp -rf ./_book/* ../../../public/docs/$1
fi
be careful
- “Double quotation marks” should be used for string in condition judgment
- If there is a variable (string) in the condition judgment, the variable should also be added with “” double quotation marks
- Conditional judgment should be added after, and then should be used to continue execution
- Fi should be used at the end of conditional judgment