Criar aplicações e projetos front-end é fácil, o difícil é organizar, estruturar e arquitetar. Muitas vezes alguns detalhes acabam passando despercebidos e poderiam facilmente ser resolvidos.
Quando trabalhamos em projetos front-end utilizando bibliotecas ou frameworks, como: React, Angular ou Vue, usamos muito os módulos para deixar nossos projetos modularizados.
Mas nem tudo são flores. Podemos facilmente encontrar componentes ou arquivos com as seguintes importações:
import { sum } from '../../../../../utils/numeros'
import App from '../../../containers/App'
import ComponentaA from '../../../../componentes/ComponenteA'
Veja o quanto é ruim esse código acima. Podemos destacar alguns pontos:
- Precisamos voltar todas as pastas até encontrar os diretórios que precisamos
- Estamos criando um vínculo muito forte entre estrutura e arquivos
Antes de tentarmos procurar soluções, vamos entender cada um dos problemas mencionados
Encontrar os diretórios que precisamos
Ter a necessidade de ir voltando e subindo o nível de todas as pastas até encontrarmos o diretório que estamos procurando é muito chato.
Muitas vezes estamos em pastas de quinto nível e precisamos voltar para a raiz. Assim, surge a necessidade de colocar infinitos ../
, o que não é só feio como também ruim e cansativo.
Vínculo muito forte entre estrutura e arquivos
Criar esse vínculo pode ser perigoso, pois caso surja a necessidade de trocar a pasta componentes
para inglês (components
), vamos precisar arrumar em todos nossos arquivos (sim, pode ser feito de maneira automática).
Além disso, se um dia precisarmos criar uma nova pasta pai de componentes
, também teremos retrabalho e manutenção.
Veja que independente do cenário – por ter esse vínculo muito forte, qualquer mudança na estrutura irá gerar uma manutenção (às vezes grande).
Agora que entendemos um pouco mais sobre ambos os problemas, como será que podemos resolvê-los?
Para isso, podemos fazer uso do Webpack – mais especificamente, podemos configurar os alias
(apelidos/paths simbólicos).
Para realizar a configuração dos apelidos (gosto de chamar de path simbólicos), precisamos abrir nosso webpack.config.js
, e na raiz do objeto de configuração começamos adicionando uma chave chamada resolve
.
module.exports = {
// configurações otimidas
resolve: { }
}
Agora, dentro do resolve
, precisamos adicionar uma propriedade chamada alias
:
module.exports = {
// configurações otimidas
resolve: {
alias: { }
}
}
E dentro do nosso alias
será onde vamos definir todos os apelidos ou path simbólicos. Vamos começar definindo três paths referentes ao exemplo anterior de importação, sendo eles: utils
, containers
e componentes
.
const path = require('path')
module.exports = {
// configurações otimidas
resolve: {
alias: {
'@components': path.resolve(__dirname, 'src', 'componentes'),
'@containers': path.resolve(__dirname, 'src', 'containers'),
'@utils': path.resolve(__dirname, 'src', 'utils')
}
}
}
Maravilha, agora dentro dos nossos arquivos podemos mudar as importações para:
import { sum } from '@utils/numeros'
import App from '@containers/App'
import ComponentaA from '@components/ComponenteA'
Veja que ficou muito mais simples, fácil e prático. Além desses ganhos, se um dia a pasta componentes
mudar para components
, precisamos apenas atualizar nosso alias
, e o resto da aplicação continuará funcionando e não exigirá manutenção, retrabalho ou find em arquivos .js
.
Saiba mais
Se você é atento, deve ter reparado no @
em todos os paths. Eu gosto de defini-los para deixar explicito que trata-se de um alias
ou path simbólico. Além disso, sem o @
podemos encontrar alguns conflitos. Por exemplo:
import { history } from 'history`
Dessa maneira, não estamos importando o nosso objeto history
, e sim o pacote history
instalado através de npm
. Portanto, se adicionarmos o @
:
import { history } from '@history`
Agora sim, não terá o conflito e estamos importando o nosso objeto.
Por se tratar de uma configuração feita no Webpack e diversas aplicações hoje em dia utilizarem o mesmo, a criação e definição dos alias
pode ser feita em projetos com React, Angular e Vue sem o menor problema, mas claro que cada um terá seu jeito de ser configurado. Vamos ver alguns exemplos?
Configurando no React
Para realizar a configuração dos alias
em projetos React existem duas maneiras:
- Projetos criados com
create-react-app
com versão menor que a 2. Ou seja,version < 2
. - Projetos criados com
create-react-app
com versão maior ou igual que a 2. Ou seja,version >= 2
.
Vamos aos exemplos de cada um deles.
Precisamos começar ejetando as configuração padrão do projeto. Isso pode ser feito através do comando eject
:
yarn eject
Ou com npm
:
npm run eject
Observação: garanta que o projeto esteja comitado – caso contrário apresentará alguns problemas.
Após realizar o eject
e ser finalizado, em projetos com a versão 1.x do create-react-app
, uma pasta config
será criada na raiz do projeto. Dentro dela, teremos dois arquivos responsáveis pelas configurações do Webpack, sendo eles:
webpack.config.dev.js
webpack.config.prod.js
O próprio nome já diz, o .dev.js
será configurado para ambiente de desenvolvimento e o .propd.js
para realizar o build final do projeto.
Dentro de cada um deles temos a opção resolve
, e dentro dela a opção alias
(com valores defaults). O resto vocês já sabem fazer, não muda da maneira que fizemos no começo.
Em projetos que possuem a versão 2.x do create-react-app
, ao ejetar as configurações, também será criada uma pasta chamada config
.
Porém, dentro dela terá apenas um arquivo webpack.config.js
. O mesmo serve tanto para dev
quando para prod
. O resto das configurações é igual, procure a opção resolve
e dentro dela o alias
.
Configurando no Angular
No Angular, apesar de também utilizar Webpack, essa configuração pode ser feita no tsconfig.json
. Para que tudo funcione, precisamos configurar duas propriedades: baseUrl
e paths
.
A propriedade baseUrl
definirá a pasta base para montar os paths. Por exemplo:
{
"baseUrl": "./src"
}
Estamos dizendo que nossos paths devem ser procurados dentro da pasta src
. Agora, através da propriedade paths
podemos criar os apelidos:
{
"baseUrl": "./src",
"paths": {
"@components/*": [ "app/components/*" ],
"@containers/*": [ "app/containers/*" ],
"@utils/*": [ "app/utils/*" ]
}
}
Repare que precisamos colocar o *
tanto na definição do path como na busca. O mesmo deve para pegar tudo que vier depois de @components
. Exemplo:
import ComponentaA from '@components/ComponenteA'
Neste exemplo o *
será ComponenteA
. Portanto, nosso path ficaria:
"@components/ComponenteA": [ "app/components/ComponenteA" ]
Lembrando que o mesmo será procurando dentro de src
. Sendo assim, o path final ficaria:
src/app/components/ComponenteA
Configurando no Vue
Para configurar os alias
no Vue é bem similar ao React. Oprimeiro passo será criar um arquivo vue.config.js
na raiz do projeto.
Ele será o responsável por adicionar novas configurações no Webpack. Dentro dele devemos exportar um objeto JSON contendo as propriedades resolve
e alias
, assim como no React:
const path = require('path')
module.exports = {
configureWebpack: {
resolve: {
alias: {
'@components': path.resolve(__dirname, 'src', 'components')
}
}
}
}
Repare que, para merger nossa configuração com a configuração atual do Webpack, precisamos criar uma chave configureWebpack
, e dentro dela adicionar o que precisamos. Assim, o Vue irá pegar as configurações padrões e mergear com a nossa.
Saiba mais
Alguns paths que geralmente eu crio nos projetos:
'@': path.resolve(__dirname, '..', 'src'),
'@cfg': path.resolve(__dirname, '..', 'src', '_config'),
'@components': path.resolve(__dirname, '..', 'src', 'components'),
'@config': path.resolve(__dirname, '..', 'src', '_config', 'config'),
'@constants': path.resolve(__dirname, '..', 'src', 'constants'),
'@containers': path.resolve(__dirname, '..', 'src', 'containers'),
'@css': path.resolve(__dirname, '..', 'src', '_assets', 'css'),
'@env': path.resolve(__dirname, '..', 'src', '_environments'),
'@features': path.resolve(__dirname, '..', 'src', 'features'),
'@fonts': path.resolve(__dirname, '..', 'src', '_assets', 'fonts'),
'@helpers': path.resolve(__dirname, '..', 'src', 'helpers'),
'@hoc': path.resolve(__dirname, '..', 'src', 'hoc'),
'@http': path.resolve(__dirname, '..', 'src', '_config', 'http'),
'@i18n': path.resolve(__dirname, '..', 'src', '_translate', 'i18n'),
'@icons': path.resolve(__dirname, '..', 'src', '_assets', 'icons'),
'@img': path.resolve(__dirname, '..', 'src', '_assets', 'img'),
'@js': path.resolve(__dirname, '..', 'src', '_assets', 'js'),
'@mocks': path.resolve(__dirname, '..', 'src', '_config', 'mocks'),
'@routes': path.resolve(__dirname, '..', 'src', '_config', 'routes'),
'@utils': path.resolve(__dirname, '..', 'src', 'utils')
Se você não entende o porquê desse monte de path, dê uma olhada no artigo “Como organizar projetos em React“. Nele eu dou dicas de como estruturar projetos React.
Conclusão
Nesse artigo mostrei como configurar alias
dentro do Webpack de forma nativa, mas também vimos as mesmas configurações para React, Angular e Vue. Geralmente eu prefiro chamar esses “apelidos” de “links simbólicos”.
E aí, você já conhecia o alias
? Não deixe de comentar!
Até a próxima!