Todos os dias, milhões de desenvolvedores, ao criar seus aplicativos JavaScript, recorrem ao npm (ou ao Yarn). A execução de comandos como
npm init
ou
npx create-react-app
se tornou uma maneira familiar de começar a trabalhar em quase qualquer projeto JavaScript. Pode ser um servidor, cliente ou mesmo um aplicativo de desktop.
Mas o utilitário npm não é apenas capaz de inicializar projetos ou instalar pacotes. O autor do material, cuja tradução publicamos hoje, quer falar sobre truques de 13 npm que permitirão espremer tudo o que for possível com esse sistema. Aqui, consideraremos técnicas de vários tamanhos - desde o uso de atalhos até a personalização do comportamento do
npm init
.

Muitos programadores usam npm diariamente. Isso significa que, a longo prazo, mesmo uma pequena economia de tempo pode mudar algo para melhor. Este material é destinado principalmente a desenvolvedores iniciantes e desenvolvedores de nível intermediário. No entanto, mesmo se você é um profissional, o autor do material espera encontrar aqui algumas coisas interessantes que você nunca encontrou antes.
Se você não estiver familiarizado com o npm - saiba que o programa de seu interesse está instalado com o
Node.js. Se você estiver trabalhando no Windows, é recomendável instalar o
Git Bash para reproduzir um pouco do que está sendo discutido aqui.
1. Breves opções para gravar comandos básicos
Vamos começar com o básico. Ao gastar um pouco de tempo explorando versões abreviadas dos comandos npm mais comuns, você economizará muito tempo no futuro.
- Instale pacotes. Opção normal:
npm install
. Atalho: npm i
. - Executando testes. Opção normal:
npm test
. Atalho: npm t
. - Ligue para a ajuda. Opção comum:
npm --help
. Atalho: npm -h
. - Sinalizador de configuração global. Opção comum: -
--global
. Atalho: -g
. - Sinalizador de instalação de pacote como uma dependência de desenvolvimento. A opção usual é
--save-dev
. Atalho: -D
. npm init
configurações padrão de npm init
. A opção usual é npm init --yes
npm init --force
ou npm init --force
. Atalho: npm init -y
ou npm init -f
.
Agora você não precisa usar o
--save
ou
-S
para salvar pacotes. Pacotes são salvos por padrão. E para instalar um pacote sem salvá-lo, você pode usar o sinalizador
--no-save
.
Opções de gravação curtas para comandos menos comuns
Aqui estão algumas abreviações mais úteis, que, no entanto, não são usadas tão amplamente quanto as que acabamos de revisar.
- Salvando um pacote como uma dependência opcional. A opção usual:
--save-optional
. Atalho: -O
. - Salvando informações sobre a versão exata do pacote. A opção usual é
--save-exact
. Atalho: -E
.
O uso do comando
npm install
com a opção
--save-bundle
ou
-B
faz com que as entradas nos bundles instalados apareçam em
package.json
, na seção
bundledDependencies
. Esses pacotes serão empacotados com o projeto após a publicação. Para criar um arquivo tarball contendo arquivos e pacotes de projeto listados em
bundledDependencies
, você pode usar o comando
npm pack
.
▍ Abreviação para o diretório raiz
Normalmente, o símbolo de ponto (
.
) É usado para representar o diretório raiz de um aplicativo ou (dependendo do contexto) para representar um ponto de entrada para um aplicativo. No npm, é isso que é definido como o valor da propriedade
main
no arquivo
package.json
:
{ "main": "index.js" }
Essa abreviação pode ser usada, por exemplo, com comandos como
npx create-react-app
. Portanto, em vez de executar este comando na forma de
npx create-react-app my-app
(que levará à criação de uma nova pasta
my-app
), você pode executar este comando da seguinte maneira:
npx create-react-app .
(preste atenção ao ponto que vem após o comando). Isso permitirá que você crie um projeto de modelo de aplicativo React na pasta em que está no momento em que o comando é executado.
2. Configurando valores padrão para npm init
Ao executar constantemente o comando
npm init
para criar um novo projeto, você provavelmente encontrará os mesmos dados repetidamente em resposta às perguntas do sistema. Por exemplo - é provável que você seja o autor da maioria dos projetos criados. Para economizar tempo ao inserir os mesmos dados, você pode definir seus próprios valores padrão para os campos correspondentes:
npm config set init.author.name "Joe Bloggs" npm config set init.author.email "joebloggs@gmail.com" npm config set init.author.url "joebloggs.com" npm config set init.license "MIT"
Para verificar a correção de adicionar essas informações ao sistema, digite o comando
npm config edit
. Isso abrirá o arquivo de configuração no editor do sistema. Se você deseja editar os parâmetros globais do npm, use o comando
npm config edit -g
.
Para retornar às configurações padrão, você pode usar o seguinte script. Sua primeira linha exclui os dados de configuração do arquivo e a segunda os preenche com os valores padrão.
echo "" > $(npm config get userconfig) npm config edit
O script acima redefine os valores padrão para o usuário. O script a seguir redefine os padrões globais:
echo "" > $(npm config get globalconfig) npm config --global edit
3. Scripts entre plataformas
Qualquer código executado na linha de comando pode encontrar problemas de compatibilidade. Isto é especialmente verdade para incompatibilidades entre sistemas baseados em Windows e Unix (isso inclui Mac e Linux). Isso não é um problema se você e apenas você estiver trabalhando em um determinado projeto. Mas, em muitos casos, a compatibilidade de scripts entre plataformas é importante. Por exemplo, trabalhar independentemente do sistema operacional é uma enorme vantagem para qualquer projeto de código aberto, treinamento ou demonstração.
Felizmente, resolver o problema de compatibilidade de scripts não é particularmente difícil. Temos várias opções à nossa disposição. No entanto, aqui eu gostaria de falar sobre um deles, sobre o uso dos quais obtive os melhores resultados. Este é um pacote
cross-env . Ele deve ser instalado como uma dependência de desenvolvimento usando o
npm i -D cross-env
. Então você precisa colocar o ambiente
cross-env
na frente de cada variável de ambiente. Por exemplo, pode ser assim:
{ "scripts": { "build": "cross-env NODE_ENV=production webpack --config build/webpack.config.js" }
Descobri que o pacote entre ambientes é a ferramenta mais conveniente para obter compatibilidade de scripts entre plataformas. Mas será útil que você dê uma olhada nas duas ferramentas populares a seguir que podem ajudar na solução desse problema:
- Pacote Rimraf . Ele, para executar scripts de plataforma cruzada, pode ser instalado globalmente.
- Pacote ShellJS . Esta é uma implementação portátil do Node.js. do shell de comando do Unix.
4. Execução de script paralelo
Para organizar a execução seqüencial de comandos no shell do Linux, a construção
&&
é usada. Que tal executar scripts paralelos? Para conseguir isso, você pode escolher o pacote npm apropriado. Os pacotes mais populares desse tipo são
simultaneamente e
npm-run-all . Aqui demonstramos o uso do pacote simultâneo.
Primeiro, o pacote selecionado deve ser instalado como uma dependência de desenvolvimento:
npm i -D concurrently
. Em
package.json
você pode usar uma construção do seguinte formulário:
{ "start": "concurrently \"command1 arg\" \"command2 arg\"" }
5. Executando scripts localizados em vários diretórios
Às vezes, você encontra aplicativos que possuem vários arquivos
package.json
localizados em diretórios diferentes. Seria conveniente, por exemplo, executar scripts declarados neles, estando no diretório raiz do projeto. Isso é muito melhor do que ter que viajar para pastas diferentes sempre que você precisar executar um script. Para fazer isso, você pode usar as duas abordagens a seguir.
Para começar, você pode usar o
cd
para navegar automaticamente para o diretório desejado. Pode ser algo como isto:
cd folder && npm start && cd ..
Mas esse problema pode ser resolvido de uma maneira mais interessante. Consiste em usar o sinalizador
--prefix
, com o qual você pode especificar o caminho:
npm start --prefix path/to/your/folder
A seguir, é apresentado um exemplo de aplicação desta solução a partir de um aplicativo real. Aqui, precisamos executar o
npm start
para as partes do cliente e servidor do projeto. Seu código, respectivamente, está localizado nas pastas
client
e
server
.
"start": "concurrently \"(npm start --prefix client)\" \"(npm start --prefix server)\"",
6. Atrasando o lançamento do script até que um recurso esteja disponível
Ao desenvolver aplicativos de pilha completa, muitas vezes surge a necessidade de executar as partes do cliente e do servidor do aplicativo. O pacote de
espera permite sincronizar a execução de determinados processos. No nosso caso, é necessário que antes de iniciar a parte do aplicativo do cliente, uma certa porta esteja disponível.
Por exemplo, existe um script de desenvolvimento usado em um aplicativo Electron cuja interface é gravada usando o React. O script, usando
concurrently
, executa a camada de apresentação do aplicativo e a janela Electron em paralelo. Porém, usando a
wait-on
você pode abrir a janela Electron apenas quando a camada de apresentação do React estiver pronta para uso e disponível em
http://localhost:3000
. Veja como é o uso da
wait-on
:
"dev": "concurrently \"cross-env BROWSER=none npm run start\" \"wait-on http://localhost:3000 && electron .\"",
Além disso, o comportamento padrão dos projetos React é abrir automaticamente uma janela do navegador. Se estiver usando React with Electron, isso não é necessário. Isso pode ser
BROWSER=none
usando a variável de ambiente
BROWSER=none
, antes da qual, por uma questão de compatibilidade entre plataformas da solução, existe o comando
cross-env
.
7. Listando e trabalhando com scripts disponíveis
Para listar os scripts disponíveis no
package.json
, basta ir ao diretório raiz do projeto e executar o comando
npm run
no terminal.
Mas existe uma maneira ainda mais conveniente de listar scripts. Ao usá-lo, o script desejado pode ser imediatamente selecionado na lista e executado. Para usar essa maneira de trabalhar com scripts, precisamos instalar globalmente o
ntl
(Npm Task List):
npm i -g ntl
Em seguida, na pasta do projeto, você precisa executar o comando
ntl
. Ele exibirá uma lista de scripts disponíveis e lhe dará a oportunidade de selecionar o script que você deseja executar. Aqui está como fica.
Usando o comando ntlEsse recurso pode ser muito útil se você não souber exatamente quais scripts estão no projeto. Também é bom nos casos em que o programador deseja substituir a entrada de um comando longo para executar um script pela entrada de um comando curto e pressionar rapidamente mais algumas teclas do teclado.
8. Executando pré-scripts e pós-scripts
Você pode estar familiarizado com os scripts de
postbuild
prebuild
e
postbuild
que permitem executar algum código antes e depois da execução do script de
build
. Esses scripts pré e pós podem ser definidos para qualquer outro script. Incluindo aqueles cujas descrições foram adicionadas ao p
ackage.json
pelo programador.
Isso não apenas permite tornar o código mais limpo, mas também ajuda a executar pré e pós-scripts isoladamente.
9. Controle de versão do aplicativo
Em vez de alterar manualmente a versão do aplicativo, o programador pode usar comandos especiais do
npm
. Para aumentar a parte correspondente do número da versão do aplicativo, você pode usar o comando
npm version
seguido por
major
,
minor
ou
patch
:
// 1.0.0 npm version patch // 1.0.1 npm version minor // 1.1.0 npm version major // 2.0.0
Dependendo da frequência com que você atualiza seu aplicativo, você pode economizar tempo aumentando automaticamente o número da versão cada vez que implanta uma nova versão do aplicativo. Por exemplo, assim:
{ "predeploy": "npm version patch" }
10. Editando package.json a partir da linha de comandos
O arquivo package.json é um arquivo json comum, portanto pode ser editado diretamente da linha de comandos usando o utilitário
json . Isso abre novas possibilidades em situações em que você precisa modificar o
package.json
, permitindo criar suas próprias versões abreviadas de comandos. Instale o pacote
json
globalmente:
npm install -g json
Em seguida, o utilitário
json
pode ser usado para
editar rapidamente
o arquivo usando a
-I
. Por exemplo, para adicionar um novo script
foo
com a
bar
valor ao arquivo, você pode usar o seguinte comando:
json -I -f package.json -e 'this.scripts.foo="bar"'
Na próxima seção, você verá um exemplo mais prático do uso do utilitário
json
.
11. Automação da instalação e abertura do repositório
Se houver uma entrada de
"repository"
no arquivo
package.json
, isso significa que você pode abrir a página do repositório no navegador usado pelo sistema por padrão. Para fazer isso, use o comando
npm repo
.
Se o seu projeto já estiver conectado ao repositório remoto e você tiver o utilitário de linha de comando
git
instalado, isso significa que você poderá descobrir o endereço do seu repositório usando o seguinte comando:
git config --get remote.origin.url
Mas isso não é tudo. Se, de acordo com a dica anterior, você instalou o utilitário
json
, poderá usar o seguinte script para adicionar automaticamente as informações corretas do repositório ao
package.json
:
json -I -f package.json -e "this.repository=\"$(git config --get remote.origin.url)\""
12. Criando seu próprio script para controlar o comando npm init
Agora vamos falar sobre como resolver uma tarefa maior. Nomeadamente, vamos desenvolver nosso próprio script que controla a operação do comando
npm init
, que aceita a URL do repositório GitHub e envia automaticamente a primeira confirmação para ele. Aqui falamos sobre como criar esses scripts. E na próxima seção, que será nossa última dica, falaremos sobre como trabalhar com o
git
.
Você pode personalizar o comportamento do comando
npm init
usando o
.npm-init.js
. Vamos criar esse arquivo no diretório inicial do usuário atual (no Windows geralmente é
C:/Users/<username>
e no Mac é
/Users/<username>
). Depois disso, execute o seguinte comando que informa ao npm onde exatamente esse arquivo está localizado:
npm config set init-module ~\.npm-init.js
Antes de integrar ao
git
, vejamos um exemplo simples do
.npm-init.js
, que reproduz as perguntas que o sistema faz ao usuário ao usar o comando
npm init
sem configurações adicionais:
module.exports = { name: prompt('package name', basename || package.name), version: prompt('version', '0.0.0'), decription: prompt('description', ''), main: prompt('entry point', 'index.js'), repository: prompt('git repository', ''), keywords: prompt(function (s) { return s.split(/\s+/) }), author: prompt('author', 'Joe Bloggs <joe.bloggs@gmail.com> (joebloggs.com)'), license: prompt('license', 'ISC') }
Cada pergunta é baseada no seguinte modelo:
nameInPackage: prompt('nameInPrompt', 'defaultValue')
Para indicar um determinado valor e não fazer uma pergunta ao usuário, basta remover o método
prompt
.
Se você quiser retornar às configurações padrão do
npm init
, exclua o
.npm-init.js
.
13. Enviando o primeiro commit no repositório GitHub usando o npm init
Para executar comandos
git
no
.npm-init.js
precisamos encontrar uma maneira de trabalhar com a linha de comando. Você pode usar o módulo
child_process
para
child_process
. Nós o conectamos na parte superior do arquivo e, como precisamos apenas da função
execSync
, apenas a importamos, usando a desestruturação:
const { execSync } = require('child_process');
Além disso, criaremos uma função auxiliar que exibe os resultados de nossa função no console:
function run(func) { console.log(execSync(func).toString()) }
E, finalmente, vamos criar o bloco de prompt apropriado para lidar com a URL do repositório GitHub. Se o script tiver a URL, criaremos o arquivo
README.md
e enviaremos a primeira confirmação para o repositório.
Portanto, um dos elementos do objeto
.npm-init.js
deve ser o seguinte código:
repository: prompt('github repository url', '', function (url) { if (url) { run('touch README.md'); run('git init'); run('git add README.md'); run('git commit -m "first commit"'); run(`git remote add origin ${url}`); run('git push -u origin master'); return url; })
Aqui está como o código completo do arquivo
.npm-init.js
deve cuidar dessa adição:
const { execSync } = require('child_process'); function run(func) { console.log(execSync(func).toString()) } module.exports = { name: prompt('package name', basename || package.name), version: prompt('version', '0.0.0'), decription: prompt('description', ''), main: prompt('entry point', 'index.js'), keywords: prompt(function (s) { return s.split(/\s+/) }), author: prompt('author', 'Joe Bloggs <joe.bloggs@gmail.com> (joebloggs.com)'), license: prompt('license', 'ISC'), repository: prompt('github repository url', '', function (url) { if (url) { run('touch README.md'); run('git init'); run('git add README.md'); run('git commit -m "first commit"'); run(`git remote add origin ${url}`); run('git push -u origin master'); return url; }), }
É assim que o arquivo
package.json
que o sistema cria usando esse
.npm-init.js
:
{ "name": "Custom npm init", "version": "0.0.0", "decription": "A test project, to demonstrate a custom npm init script.", "main": "index.js", "keywords": [], "author": "Joe Bloggs <joe.bloggs@gmail.com> (joebloggs.com)", "license": "ISC", "repository": { "type": "git", "url": "git+https://github.com/JoeBloggs/custom.git" }, "bugs": { "url": "https://github.com/JoeBloggs/custom/issues" }, "homepage": "https://github.com/JoeBloggs/custom#readme" }
Ao configurar o processo de inicialização de novos projetos, você pode ir além. Por exemplo, para garantir que, ao criar um projeto, um novo repositório seja criado.
Sumário
Espero que este material tenha ajudado você a ver o que você pode conseguir com o npm. Quero acreditar que você encontrou algo aqui que permitirá que você trabalhe de forma mais produtiva - se estamos falando sobre o uso de versões reduzidas de comandos, sobre scripts do
package.json
ou sobre a configuração do
npm init
para atender às suas necessidades.
Caros leitores! Você automatiza o trabalho com npm?
