A catalog
The front end that is not tossing, what is the difference with the salted fish
table of Contents |
---|
A catalog |
Two preface |
Three Node solutions for writing bash scripts |
Four programming front |
Five closed ports |
Six delete files/folders |
Seven Git operations |
7.1 Commonly used Git commands in work |
7.2 Switch branches |
Eight summary |
Nine references |
Two preface
Today jsliang 160f8ca2b04893 took a at work and opened a VIP channel:
- Download Excel files automatically
- Copy to the specified directory
- Perform multilingual import operations
git push
imported resource 060f8ca2b04926
Although the rough operation looks like this, there is nothing to say.
But in operation, it may be more cumbersome. For example, after importing resources, the git
operation is performed:
- Add staging area:
git add .
- Switch branch:
git checkout -b <branch>
- Submit the local repository:
git commit -m "feat: "multilingual" new resource #master_0720"
- Submit remote branch:
git push --set-upstream origin <branch>
Of course, it's not just this, you must check whether the build can pass smoothly after adding your multilingual resources before submitting...
bash
about it, in fact, it is purely to elicit the operation of the 060f8ca2b04a52 instruction.
At work, you may encounter:
- Git series operations
- Close the occupied system port
- Delete specified files/folders, etc.
- ……
However, for these operations, you may forget its instructions for a while, or its instructions are too cumbersome, so jsliang feels that it is not easy to install these contents?
Three Node solutions for writing bash scripts
In fact, regarding this solution, jsliang is still too troublesome, so I went directly to ShellJS
:
If you feel that it is a bit abrupt to directly go to the plan like this, you can see:
The author compared Node's own child_process
API, ShellJS
and zx
, and finally adopted the zx
plan.
Of course, jsliang work. ShellJS
don’t want to be so tired to explore similar libraries, so install ShellJS
~
- Installation:
npm i shelljs
- Install TS to compile:
npm i @types/shelljs -D
After the installation is complete, start tossing!
Four programming front
In order to make the code not look so stinky and long.
jsliang finishing writing the article, I read the whole article more than 3 times, and the repetitive code and problem situation in the following are organized here, so before you copy the code, please read this chapter carefully, please ~
warn! please read the following carefully
The full-text catalog is as follows, please remember to create a new catalog in advance:
Then repeat the code as follows:
src/common/index.ts
import { inquirer } from '../base/inquirer';
import { Result } from '../base/interface';
// 系统操作
import { sortCatalog } from '../base/file/sortDir';
import { deleteDir } from '../base/file/deleteDir';
// 多语言
import { downLoadExcel } from './language/download';
import { importLanguage } from './language/import';
import { exportLanguage } from './language/export';
// shell 操作
import { closePort } from '../base/shell/closePort';
import { gitCheckout } from '../base/shell/gitCheckout';
// 问题记录器
const answers = {
q0: '',
q1: '',
q2: '',
q3: '',
q4: '',
q5: '',
q6: '',
q7: '',
q8: '',
};
const common = (): void => {
// 问题路线:看 questionList.ts
const questionList = [
// q0
{
type: 'list',
message: '请问需要什么服务?',
choices: ['公共服务', '多语言'],
},
// q1
{
type: 'list',
message: '当前公共服务有:',
choices: ['文件排序', '关闭端口', '删除文件夹', 'Git 操作'],
},
// q2
{
type: 'input',
message: '需要排序的文件夹为?(绝对路径)',
},
// q3
{
type: 'list',
message: '请问多语言需要什么支持?',
choices: [
'下载多语言资源',
'导入多语言资源',
'导出多语言资源',
],
},
// q4
{
type: 'input',
message: '资源下载地址(HTTP)?',
default: 'https://www.kdocs.cn/l/sdwvJUKBzkK2',
},
// q5
{
type: 'input',
message: '你需要关闭的端口是?',
},
// q6
{
type: 'input',
message: '你需要删除的路径是?(全路径)',
},
// q7
{
type: 'list',
message: '请问 Git 需要什么支持?',
choices: [
'切换分支',
// More...
],
},
// q8
{
type: 'inupt',
message: 'Git 分支名是?',
},
];
const answerList = [
// q0 - 请问需要什么服务?
async (result: Result, questions: any) => {
answers.q0 = result.answer;
switch (result.answer) {
case '公共服务':
questions[1]();
break;
case '多语言':
questions[3]();
break;
default: break;
}
},
// q1 - 当前公共服务有:
async (result: Result, questions: any) => {
answers.q1 = result.answer;
switch (result.answer) {
case '文件排序': questions[2](); break;
case '关闭端口': questions[5](); break;
case '删除文件夹': questions[6](); break;
case 'Git 操作': questions[7](); break;
default: break;
}
},
// q2 - 需要排序的文件夹为?(绝对路径)
async (result: Result, _questions: any, prompts: any) => {
answers.q2 = result.answer;
const sortResult = await sortCatalog(result.answer);
if (sortResult) {
console.log('排序成功!');
prompts.complete();
}
},
// q3 - 请问多语言需要什么支持?
async (result: Result, questions: any, prompts: any) => {
answers.q3 = result.answer;
switch (result.answer) {
case '下载多语言资源':
case '导入多语言资源':
questions[4]();
break;
case '导出多语言资源':
const exportResult = await exportLanguage();
if (exportResult) {
console.log('导出成功!');
prompts.complete();
}
default: break;
}
},
// q4 - 资源下载地址(HTTP)?
async (result: Result) => {
answers.q4 = result.answer;
const download = async (): Promise<any> => {
const downloadResult = await downLoadExcel(result.answer);
if (downloadResult) {
console.log('下载成功!');
return true;
}
};
switch (answers.q3) {
case '下载多语言资源':
await download();
break;
case '导入多语言资源':
await download();
const importResult = await importLanguage();
if (importResult) {
console.log('导入完毕!');
}
default:
break;
}
},
// q5 - 你需要关闭的端口是?
async (result: Result, _questions: any, prompts: any) => {
answers.q5 = result.answer;
const closeResult = await closePort(result.answer);
if (closeResult) {
console.log('关闭成功');
prompts.complete();
}
},
// q6 - 你需要删除的路径是?(全路径)
async (result: Result, _questions: any, prompts: any) => {
answers.q6 = result.answer;
const deleteResult = await deleteDir(result.answer);
if (deleteResult) {
console.log('删除成功');
prompts.complete();
}
},
// q7 - 请问 Git 需要什么支持?
async (result: Result, questions: any) => {
answers.q7 = result.answer;
questions[8]();
},
// q8 - Git 分支名是?
async (result: Result, _questions: any, prompts: any) => {
answers.q8 = result.answer;
const checkoutResult = await gitCheckout(result.answer);
if (checkoutResult) {
console.log('切换成功');
prompts.complete();
}
},
];
inquirer(questionList, answerList);
};
export default common;
src/common/questionList.ts
// common 板块的问题咨询路线
export const questionList = {
'公共服务': { // q0
'文件排序': { // q1
'需要排序的文件夹': 'Work 工作', // q2
},
'关闭端口': { // q1
'需要关闭的端口': 'Work 工作', // q5
},
'删除文件夹': { // q1
'需要删除的路径': 'Work 工作', // q6
},
'Git 操作': { // q1
'切换分支': { // q7
'分支名': 'Work 工作', // q8
},
},
},
'多语言': { // q0
'下载多语言资源': { // q3
'下载地址': 'Work 工作', // q4
},
'导入多语言资源': { // q3
'下载地址': 'Work 工作', // q4
},
'导出多语言资源': { // q3
'导出全量资源': 'Work 工作',
'导出单门资源': 'Work 工作',
}
},
};
The following article shows:
Update src/common/index.ts
Update src/common/questionList.ts
In this case, you don't need to operate it. There are 3 places in this article that have this description.
Similarly, in order to avoid reporting TypeScript errors when quoting and running the code, the three newly added files are also listed at the beginning:
src/base/file/deleteDir.ts
import shell from 'shelljs';
export const deleteDir = async (path: string): Promise<boolean> => {
console.log(path)
};
src/base/shell/closePort.ts
import shell from 'shelljs';
export const closePort = async (port: string): Promise<boolean> => {
console.log(port);
};
src/base/shell/gitCheckout.ts
import shell from 'shelljs';
/**
* @name 切换分支
* @description 指令合并:
* 1. git checkout ${branch}
* 2. git pull
* @param {string} branch 分支名
*/
export const gitCheckout = (branch: string): boolean => {
console.log(branch)
};
In addition,common
undersortCatalog.ts
migrated to thebase/file
directory and renamedsortDir.ts
.
So, when you are ready, start outputting!
Five closed ports
When starting some magical services, you will encounter scenarios where the port is occupied. At this time, you need to close the port:
- View port occupancy:
netstat -ano|findstr "port number"
PS F:\xxx> netstat -ano|findstr "3001"
TCP 0.0.0.0:3001 0.0.0.0:0 LISTENING 33396
TCP 10.13.144.170:63001 183.2.199.241:443 ESTABLISHED 28228
TCP [::]:3001 [::]:0 LISTENING 33396
- Terminate PID:
taskkill -F -PID PID number
PS F:\xxx> taskkill -F -PID 33396
成功: 已终止 PID 为 33396 的进程。
So when you get to the Node tool library, you definitely don't want to do this by yourself, let's find a way to save trouble:
Update src/common/index.ts
Update src/common/questionList.ts
Then write closePort.ts
:
src/base/shell/closePort.ts
import shell from 'shelljs';
export const closePort = async (port: string): Promise<boolean> => {
await shell.exec(`netstat -ano | findstr :${port}`);
// Windows 下会返回一个端口占用清单,需要自行删除
console.log('已找到上面清单列表,请执行指令删除端口:taskkill -F -PID PID号');
return await true;
};
Note: The PID number at the end of the Windows print result
Of course, because 3001
may have several ip
corresponding to 060f8ca2b05130, we only made a prompt in the next step, instead of closing all 3001
ports (users need to operate manually).
But this is better than memorizing this instruction (after all, operating instructions such as Windows and Mac are still unavailable)
Execute npm run jsliang
and the results are as follows:
In this way, we have encapsulated the port closure, because it is not completely closed with one key, the practical index is given to ☆☆☆
Six delete files/folders
In order to study Windows how to quickly delete node_modules
, jsliang in the company before, I really checked the information and found 3 ways to delete files/folders:
cmd.exe
:rd /s /q <path>
PowerShell
:rd -r <path>
Mac
:rm -rf <path>
After much experience in the company of 32G of memory, 500 SSD desktop computer, by PowerShell
deletion than cmd.exe
fast (do not ask me why, anyway, is quick, only personal experience, not scientific support) .
Then I took a look at ShellJS
, there is a way to delete it:
- ShellJS:
rm()
deletes files,rm('rf', <path>)
deletes folders
of course! In the spirit of exploration, let's take a look at how its source code is implemented:
function rmdirSyncRecursive(dir, force, fromSymlink) {
// 1. 先删除目录中的所有文件
let files = fs.readdirSync(dir);
for (var i = 0; i < files.length; i++) {
// 1.1 如果是目录则递归调用 rmdirSyncRecursive()
// 1.2 如果是文件则调用 fs.unlinkSync() 执行删除
}
// 2. 再删除目录
fs.rmdirSync();
}
Of course, some of the details are well written, so I won’t explain them in detail here. Interested friends can click on the link above to explore the source code.
So, let's use the method of ShellJS
If you feel uncomfortable later, replace it with system commands.
Update src/common/index.ts
Update src/common/questionList.ts
Then start writing deleteDir.ts
:
src/base/file/deleteDir.ts
import shell from 'shelljs';
export const deleteDir = async (path: string): Promise<boolean> => {
/**
* cmd.exe:rd /s /q <path>
* PowerShell:rd -r <path>
* Mac:rm -rf <path>
* ShellJS:rm() 删除文件,rm('rf', <path>) 删除文件夹
*/
await shell.rm('-rf', path);
return true;
};
Execute npm run jsliang
, the print content is as follows:
Get it done, call it a day! Because it’s not clear which Node operation or system command is faster, so tentatively set a practical index☆☆☆
Seven Git operations
So finally, come to the re-start of Git operations.
Presumably some friends will be as lazy as jsliang
git add .
git commit -m "xxx"
git push
Has reached a numb state, jsliang even developed a specific VS Code plug-in:
Note: VS Code is also volume, the update is too fast and I cannot accept the plug-in (to a certain extent, the latest VS Code cannot use the plug-in), so my VS Code version is locked v1.53.2
, and I will update this plug-in when I have free operation
In the VS Code plug-in, perform quick submission operations.
So we still hope to encapsulate some regular Git operations (you don't need to remember instructions, and don't want to click on the page, let it run by itself)
7.1 Commonly used Git commands in work
jsliang is often used in work and remembered the corresponding instructions:
git pull
: Pull the code and merge it automatically, jsliang will also usegit pull --rebase origin master
here, indicating that the remote branch is pulled and changes are made based on the branchgit checkout -b <newBranch>
: Cut a new branch from the current branchgit branch -D <branch>
: Delete the specified branch according to the branch namegit add <files>
: Submit to the staging areagit commit <description>
: Submit to the local repository. If your warehouse haseslint
inspections and the like,git commit -m "xxx" --no-verify
strongly recommended (sometimes I don’t want to do any inspections)git push
: Submit to the remote library. The general new branch operation isgit push -- set upstream origin <branch>
git cherry-pick <commitHash>
: Apply the specified commit (commit
) to other branchesgit stash
: Temporarily store content. Store the contents of the temporary storage area in the stack (multiple timesstash
can be launched by multiple timespop
git stash pop
: Check out content.git stash
out the content in 060f8ca2b0579agit reset --soft HEAD^
: Roll back the version and keep the content. ThisHEAD^
refers to the previous version, and can also be written asHEAD~1
(that is, the commit id)
It is worth mentioning that jsliang also tried before: git worktree
, it can modify multiple versions at the same time.
But because it is too troublesome (remember instructions), it is useless
In the same Git repository, multiple branches need to be modified at the same time, or the A branch needs to be modified with reference to the content of the B branch.
Of course, in this case, you can use git clone
copy a new warehouse, but if your warehouse is a bit large (a few gigabytes), it is still a bit troublesome.
So there is git worktree
, the instruction is as follows:
# 将 abc 分支切出到另一个目录 jsliang 中
# 注意:这个目录不能在主仓库中
git worktree add ../jsliang abc # git add [<选项>] <路径> [<提交>]
# 获取帮助
git worktree -h
# 查看每个工作树的详细信息
git worktree list
# 更完整的工作树信息
# git worktree list --porcelain
# 锁定内容,防止被自动删除
git worktree lock
# 解锁内容
git worktree unlock
# 迁移到新目录
git worktree move abc ../jsliang2
# 删除某条工作树
git worktree remove ../jsliang
# 清除工作树信息
git worktree prune
Commonly used git worktree
instructions:
- Cut out the branch:
git worktree add ../jsliang abc
- Common operations:
git add .
,git commit -m "xxx"
,git push
- Close branch:
git worktree prune
Of course, there is also Git to set up the proxy
In the case of scientific Internet access, sometimes Git does not take effect, and cloning or push
is as slow as the operation, so you need to set up a Git proxy.
- Set up proxy
git config --global http.proxy proxy address
git config --global https.proxy proxy address
- Cancel proxy
git config --global --unset http.proxy
git config --global --unset https.proxy
- View the proxy that has been set
git config --global --get http.proxy
git config --global --get https.proxy
git config --global http.proxy http://127.0.0.1:10809
with my current scientific Internet proxy software, and the smoothness of Git has improved a lot.
7.2 Switch branches
Let's talk about it, let's do some real work, let's make a simple switch branch:
Update src/common/index.ts
Update src/common/questionList.ts
Then update gitCheckout.ts
:
src/base/shell/gitCheckout.ts
import shell from 'shelljs';
/**
* @name 切换分支
* @description 指令合并:
* 1. git checkout ${branch}
* 2. git pull
* @param {string} branch 分支名
*/
export const gitCheckout = (branch: string): boolean => {
if (!shell.which('git')) {
shell.echo('Error: 请先安装 Git!');
shell.exit(1);
}
console.log('开始切换分支:');
const checkoutResult = shell.exec(`git checkout ${branch}`);
if (checkoutResult.code !== 0) {
shell.echo('Error: 切分支失败!');
shell.exit(1);
}
console.log('开始拉取代码,请稍等:');
const pullResult = shell.exec('git pull');
const { stdout, stderr } = pullResult;
if (pullResult.code === 0) {
if (stdout.includes('from the remote, but no such ref was fetched.')) {
console.log('你的分支是最新的');
}
} else if (pullResult.code === 1) {
if (stderr.includes('There is no tracking information for the current branch.')) {
console.log('不存在远程分支');
}
}
return true;
};
Then run: npm run jsliang
, follow the instructions to enter the branch name:
At this time, because it is a branch that we randomly input, it indicates that the switch branch failed.
Of course, friends can load more content into it based on the real business, so I won’t explain it in detail here, just do a good job first~
Eight summary
In fact, in the last two days, we have bash
instructions, but since we will not think of a better project example for a while, we did not explain them one by one, so my friends encountered this situation. , Welcome to comment and leave a message, sincerely hope to discuss with friends.
So, let’s pave the way ShellJS
jsliang will add some interesting knowledge points in life and work.
So, see you next time!
Nine references
- GitHub:ShellJS - Unix shell commands for Node.js
- Nuggets: 👏 The ultimate solution for nodejs to write bash scripts!
- GitHub: Git worktree function and use
- short book: the use of git worktree
- Know: Git Dragon Slaying Skill: Use Git Worktree to develop and test in parallel
- and enterprise cloud front-end team: How do I use Git in my work
- SegmentFault: Git Dragon Slaying Technique: Use Git Worktree to develop and test in parallel
- Where's the road to programming: How Git uses a proxy (VPN)
- Yifeng: cherry-pick
jsliang's document library is by 160f8ca2b060df Liang Junrong using Creative Commons Attribution-Non-commercial Use-Same Method Sharing 4.0 International License Agreement . <br/>Based on the works https://github.com/LiangJunrong/document-library <br/>The use rights not authorized by this license agreement can be obtained from [ https://creativecommons.org/licenses/by-nc-sa/2.5/cn/](https://creativecommons.org/licenses/by -nc-sa/2.5
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。