bin转txt工具_nodejs 工具开发(一)

e053761e2a096c8b0606d8c1090e60dd.png
本文主要讲一些工具开发的前置知识,很基础但很重要!文章的最后有本文涉及到的Github代码仓库。

node.js 是基于 Google V8 引擎的 JavaScript 运行时环境。是前端迈向全栈的重要技术,也是目前最简单的全栈语言。它能做的事情非常多:跨平台、前端、后端、以及各种工具的开发,覆盖的场景也非常广。

工具开发可以说是最常见的使用场景。工程化过程中:dev、build、test、ci、cd等各个环节,从脚手架到各种预编译工具以及构建工具等等可以说是无处不在。

但工作中我们往往是去使用别人开发好的工具,自己很少去实现。

下图参考:

【全文】狼叔:如何正确的学习Node.js - CNode技术社区​cnodejs.org
15b3bda4f92fb5286d89328e966d215f.png

59e7f5d1fe7f7a2c0cbef1a89d91428d.png
node.js 使用场景

目录

  1. 需要了解的基础知识
  2. shell script介绍
  3. 环境变量 PATH 到底是什么?
  4. #!/usr/bin/env node 是什么?
  5. commander.js

一、需要了解的基础知识

以下基础需要有一定了解,当然并不需要很深。
  • 操作系统 os
  • 命令行 command
  • 文件系统 fs
  • 网络通信 net

二、shell script 介绍

shell对于工具开发非常重要,需要有比较全面的了解。

shell相对于我们平时使用的编程语言来说要简单很多。只是很少使用,不熟悉而已。

我们先将shell切换为bash。其实就是因为 shell有很多种类,而bash是大多数系统默认的shell。
Linux chmod命令 | 菜鸟教程​www.runoob.com

脚本切换

$ chsh -s /bin/bash

1.shell

参考:

Shell 教程 | 菜鸟教程​www.runoob.com Shell 是用来解决什么问题的?​www.zhihu.com
  • Shell 是一个用 C 语言编写的程序,它是用户使用 Linux 的桥梁。Shell 既是一种命令语言,又是一种程序设计语言。
  • Shell 是指一种应用程序,这个应用程序提供了一个界面,用户通过这个界面访问操作系统内核的服务。
  • Ken Thompson 的 sh 是第一种 Unix Shell,Windows Explorer 是一个典型的图形界面 Shell。

总结:一种可控制操作系统的程序,将用户输入与kernel沟通,控制硬件工作。

5aa56a002c7997b7c93b1210bf8fad5f.png
Linux

8ac6e4cd4d3dadcd171214a07fece035.png

2.bash、zsh与iterm2

bashzsh:都是shell,而 zsh 兼容bash,功能更强大

item2:和mac的terminal 类似,是终端模拟器

池建强:终极 Shell——ZSH​zhuanlan.zhihu.com
78919587aa327d18d85e9a985789aa3e.png

常见的 shell 脚本解释器

/bin/sh (已经被 /bin/bash 所取代)
/bin/bash (就是 Linux 默认的 shell)
/bin/ksh (Kornshell 由 AT&T Bell lab. 发展出来的,兼容于 bash)
/bin/tcsh (整合 C Shell ,提供更多的功能)
/bin/csh (已经被 /bin/tcsh 所取代)
/bin/zsh (基于 ksh 发展出来的,功能更强大的 shell)

iterm2是一个替代终端和iTerm的后继项目(命令行应用)

官网:

首页-iterm2-Mac OS 终端工具​www.iterm2.cn

3. shell 的实用功能

a.他能记忆使用过的命令:.bash_history
b.命令与文件补全功能: ([tab] 按键的好处)
c.命令别名配置功能: (alias)
d.工作控制、前景背景控制: (job control, foreground, background)
e.程序化脚本: (shell scripts)
f.通配符: (Wildcard)

4.shell script

shell script 是利用 shell 的功能所写的一个程序,这个程序是使用纯文本,将一些 shell 的语法与命令(含外部命令)写在里面, 搭配正规表示法、管线命令与数据流重导向等功能,以达到我们所想要的处理目的。

总结:一个程序,纯文本文件,可利用 shell 与相关工具指令来进行一些操作,无需编译。

如下,在根目录下面创建一个文件夹 shell_demo,然后再循环创建10个子文件。

#!/bin/bash

cd ~
mkdir shell_demo
cd shell_demo

for ((i=0; i<10; i++)); do
	touch test_$i.txt
done

# 【给文件添加执行权限: chmod 777 demo.sh】   【然后执行: ./demo.sh】
# 第1行: 指定脚本解释器,这里是用/bin/sh做解释器的
# 第2行: 切换到当前用户的home目录
# 第3行: 创建一个目录 shell_demo
# 第4行: 切换到shell_tut目录
# 第5行: 循环条件,一共循环10次
# 第6行: 创建一个test_0…9.txt文件
# 第7行: 循环体结束


5.#!/bin/bash 的作用

# 不是注释!/bin/bash#!读作 hashbang,告诉系统其后路径所指定的程序即是解释此脚本文件的 Shell 程序。

  • 使用bash语法
  • 运行时能够加载bash的相关配置文件
  • 如果不写操作系统会自动判断使用的bash (猜测,不一定准确,所以尽量写上)

6.shell 执行方式

[1] 工作目录执行

# 进入目录后执行(也叫相对路径) 
$ ./demo.sh

[2] 绝对路径执行

$ `pwd`/demo.sh

[3] sh执行

# 指的是用脚本对应的sh或bash来接着脚本执行
$ sh demo.sh

[4] shell环境执行

# 指的是在当前的shell环境中执行,可以使用 . /demo.sh 接脚本 或 source 脚本

$ source  demo.sh
# 或

$ . demo.sh

7.执行方式的差异

直接执行会在子程序的 bash 中执行,变量无法回传,exit 值可以;

[1] [2][3] 脚本中创建的所有变量或动作都将会结束而不会回到主程序中

deeb8e83bc005d6c5c19761cf5a18ce0.png

e6ebab13147f0005503e2ab5e77ace78.png

source 会在父程 序中执行

[4] 将变量加入到主程序bash当中

e9a10e71c966faed78a505ae093861d3.png

0ca77caf7bc7b6f1ffbad3d84d9b0618.png

这就是【直接执行】与用【source命令执行】的区别,前者只作用于子进程本身,后者则作用于整个父进程

因此:如要想不注销系统,并让全局配置文件生效,则必须用source命令。

# 在配置 path 环境变量的时候 经常会用到。例如:
$ source /etc/profile

三、环境变量 PATH 到底是什么?

对于习惯用 Mac 的同学,经常会遇到配置各种环境变量文件,很多时候都是在网上搜索,然后粘贴。其实并没有很好的理解其中的原理,导致每次遇到环境问题都需要花很长时间去处理。理解 path 最重要的就是理解各种配置文件的执行顺序。

环境变量的本质就是变量,它的服务对象是 shell 程序,它分为局部环境变量和全局环境变量,分别有不同的作用域和自然生命周期。

以Mac os 为例(环境变量 加载顺序为[1 -> 2 -> 3 -> 4 -> 5 -> 6])

【1.2 系统级别,系统启动后就会加载】
  1 /etc/profile
  2 /etc/paths  


【3.4.5 用户级别的环境变量】
  3 ~/.bash_profile
    【如果.bash_profile 存在4.5忽略不执行,否则以此类推读取后面的文件】
  4  ~/.bash_login
  5 ~/.profile
 
【.bashrc 没有上述规则,它是bash shell 打开的时候载入】
  6 ~/.bashrc

【全局文件】下面的几个文件设置是全局的,修改时需要root权限

1)/etc/paths (全局建议修改这个文件)
编辑 paths,将环境变量添加到 paths文件中 ,一行一个路径


2)/etc/profile (建议不修改这个文件)
全局(公有)配置,不管是哪个用户,登录时都会读取该文件


3)/etc/bashrc (一般在这个文件中添加系统级环境变量)
全局(公有)配置,bash shell 执行时,不管是何种方式,都会读取此文件

【用户文件】单个用户设置,修改时不需要root权限

1)~/.bash_profile (任意一个文件中添加用户级环境变量)
(注:Linux 里面是 .bashrc 而 Mac 是 .bash_profile)
若 bash shell 是以 login 方式执行时,才会读取此文件
 该文件仅仅执行一次!默认情况下,他设置一些环境变量

2)~/.bashrc 同上
如果想立刻生效,则可执行下面的语句:
$ source 相应的文件
一般环境变量更改后,重启后生效

四、#!/usr/bin/env node

如果定义为 #!/usr/bin/env node 内容用js 写,程序会不会运行?【会】

我们来创建一个可执行脚本 hello,参考:

npm scripts 使用指南​www.ruanyifeng.com
ae1a529218257c897bc80bd029358b2a.png
Node.js 命令行程序开发教程​www.ruanyifeng.com
cc909b8e7846f50aabac182f549a9063.png

创建 hello 文件

#!/usr/bin/env node 含义:用node作为解释器,它的查找路径是 /user/bin/env

#!/usr/bin/env node
console.log('hello world');

操作

// 1.执行
node hello
// 输出  hello world

// 2.执行 ./hello
// 无法执行,需要赋执行权限
chmod 755 hello

// 3.再次执行 ./hello
// 输出 hello world

// 4.如果我们想 直接运行 hello 就执行
// 需要创建添加 package.json 配置 

package.json 配置

{
  "name": "hello",
  "bin": {
    "hello": "hello"
  }
}

添加软链接

$ npm link

// 5.再次执行 hello
// 输出 hello world

此时我们的系统中就有了一个可执行 shell 脚本 hello

以上整个过程中介绍了shell 脚本以及一些概念,最后我们用node 实现了一个 非常简单的shell脚本。


五、commander

nodejs 开发出的工具,使用场景大部分都是 命令行工具(Command-Line Interface)形式,也就是 cli。比如: vue-cli。

所以需要先了解一个 commander 工具包,其提供了用户命令行输入和参数解析强大功能,让nodejs 开发命令行工具更加容易。

process

介绍 commander 前,先了解一下 process。

process 对象是一个全局变量,它提供有关当前 Node.js 进程的信息并对其进行控制。 作为一个全局变量,它始终可供 Node.js 应用程序使用,无需使用 require()。我们熟知的参数有:

  • process.env:包含用户环境的对象
  • process.argv:返回一个数组,其中包含当启动 Node.js 进程时传入的命令行参数。 第一个元素是process.execPath。 第二个元素将是正在执行的 JavaScript 文件的路径。 其余元素将是任何其他命令行参数。

官方解释:

process | Node.js API 文档​nodejs.cn

so

process.argv 的规律很简单。我们在写命令行程序时,只需要对process.argv这个数组的第三个元素及其之后的参数进行解析即可。

如果不嫌麻烦,完全可以写出很多判断分支来做。但是现在我们有更好的方法, 就是使用 commander.js。

安装

$ npm install commander

官方例子

test.js

var program = require('commander')
program
  .version('0.1.0')
  .option('-C, --chdir <path>', 'change the working directory')
  .option('-c, --config <path>', 'set config path. defaults to ./deploy.conf')
  .option('-T, --no-tests', 'ignore test hook');

program
  .command('setup [env]')
  .description('run setup commands for all envs')
  .option("-s, --setup_mode [mode]", "Which setup mode to use")
  .action(function(env, options){
    var mode = options.setup_mode || "normal";
    env = env || 'all';
    console.log('setup for %s env(s) with %s mode', env, mode);
  })

program
  .command('exec <cmd>')
  .alias('ex')
  .description('execute the given remote cmd')
  .option("-e, --exec_mode <mode>", "Which exec mode to use")
  .action(function(cmd, options){
    console.log('exec "%s" using %s mode', cmd, options.exec_mode);
  }).on('--help', function() {
    console.log('');
    console.log('Examples:');
    console.log('');
    console.log('  $ deploy exec sequential');
    console.log('  $ deploy exec async');
  })

program
  .command('*')
  .action(function(env){
    console.log('deploying "%s"', env);
  })

program.parse(process.argv)

运行

2f8c5a27e686b68a6ecdc861b5c44620.png

核心API

version

// 用法: 
.version('x.y.z')

// 用于设置命令程序的版本号,

option

// 用法:
.option('-C, --chdir <path>', 'change the working directory')

// 第一个参数是选项定义,分为短定义和长定义。用|,,,连接。
// 参数可以用<>或者[]修饰,前者意为必须参数,后者意为可选参数。
// 第二个参数为选项描述
// 第三个参数为选项参数默认值,可选。

command

// 用法:
.command('init <path>', 'description')

// command的 用法稍微复杂,原则上他可以接受三个参数,第一个为命令定义,第二个命令描述,第三个为命令辅助修饰对象。
// 第一个参数中可以使用<>或者[]修饰命令参数
// 第二个参数可选。
//    当没有第二个参数时,commander.js将返回Command对象,若有第二个参数,将返回原型对象。
//    当带有第二个参数,并且没有显示调用action(fn)时,则将会使用子命令模式。
//    所谓子命令模式即,./pm,./pm-install,./pm-search等。这些子命令跟主命令在不同的文件中。
// 第三个参数一般不用,它可以设置是否显示的使用子命令模式。

description

// 用法:
.description('command description')

// 命令的描述信息

action

// 用法:
.action(fn)

// 用于设置命令执行的相关回调。
// fn可以接受命令的参数为函数形参,顺序与command()中定义的顺序一致。

parse

// 用法:
program.parse(process.argv)

// 此 api 一般是最后调用,用于解析 process.argv。

outputHelp

// 用法:
program.outputHelp()

// 一般用于未录入参数时自动打印帮助信息。

我们应该对脚本有了一定的理解,此时再去用 node 实现 shell 脚本应该是非常容易了。接下来我们用它去实现一个简单的翻译工具。运行效果:

代码地址:github/node-shell

3276739df23ea7edbdb96d67cd377bf5.png

8de5f46cbc477301075223c86e77c658.png

总结:本文主要讲了一些前置知识,接下来我们会基于这些基础知识去实现一个前端工程化中的脚手架工具!

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值