nystudio107 | Using Make & Makefiles to Automate your Frontend…

Using Make & Makefiles to Automate your Frontend Workflow

Make is a build automa­tion tool that’s been used for decades to build soft­ware. Learn how you can lever­age make to auto­mate fron­tend web development

Make makefile

make is a Unix tool that’s been around since the mid 1970’s, and is still wide­ly used today for automat­ing soft­ware build processes.

make is the OG of build tools

The make tool is avail­able for just about every plat­form you can imag­ine, and is installed with the XCode CLI Tools on the Mac, and WSL2 on Win­dows. Prob­a­bly you have these installed already if you’re doing development.

This arti­cle describes how you can lever­age make to auto­mate your fron­tend web devel­op­ment via a stan­dard­ized CLI API of your own design.

Link Why use make?

With all of the build tools and auto­mat­ed sys­tems out there, why should we use make? A few reasons:

  • It lets you define a sim­ple, stan­dard­ized CLI API your team can use across projects
  • The verb-noun seman­tics of make target are easy to digest & remember
  • You effec­tive­ly get local com­mand alias­es for each project that are con­text and project aware
  • The tool­ing under the hood is abstract­ed away, and can be swapped out at any time
  • make is already installed on your devel­op­ment machines, and is designed to auto­mate builds

So peo­ple on your team (or just you, if you’re a team of one) can just type make dev to spin up a local devel­op­ment envi­ron­ment, with­out hav­ing to know what hap­pens under the hood to make that happen.

If you decide to use a dif­fer­ent local dev envi­ron­ment, you can swap it out, and make dev will still do the thing” to make it happen.

Link Real World Examples

As dis­cussed in the An Anno­tat­ed Dock­er Con­fig for Fron­tend Web Devel­op­ment arti­cle, I use Dock­er for a local devel­op­ment envi­ron­ment, and as dis­cussed in the An Anno­tat­ed web­pack 4 Con­fig for Fron­tend Web Devel­op­ment arti­cle, I use web­pack as a build system.

As such, it’s much nicer to be able to type, say, make dev than it is to type docker-compose up when I want to work on a project.

How­ev­er the real key here is that no mat­ter what machin­ery needs to be run under the hood, make dev spins up the devel­op­ment environment.

Abstracting away what does the thing from the command has many benefits

So here’s an exam­ple of some of the com­mands I have in my Makefile, and what they do:

  • make dev — does what­ev­er needs to be done to spin up the pro­jec­t’s local dev envi­ron­ment, so I can work on the project
  • make build — does what­ev­er needs to be done to build a pro­jec­t’s pro­duc­tion ready resources for deployment
  • make clean — does what­ev­er needs to be done to rebuild the project envi­ron­ment from scratch
  • make docs — for my plu­g­ins, does what­ev­er needs to be done to build the documentation

There are more com­mands of course, but these are a few exam­ples that show how easy it is to onboard some­one onto a project.

For a real-world exam­ple, try spin­ning up the dev​Mode​.fm web­site locally!

Link How make works

When you run make via your CLI ter­mi­nal, it might look some­thing like this:

Make build command makefile

Run­ning make

make looks for a plain text file named Makefile in the cur­rent direc­to­ry. This file has any num­ber of tar­gets that look like this:

Anatomy of a makefile rule

Anato­my of a Make­file rule

  • Tar­get — this is nor­mal­ly a file or direc­to­ry that needs to be built.
  • Pre­req­ui­sites — oth­er files or tar­gets that need to be built before the tar­get can be built.
  • Recipe — pre­ced­ed by a tab, a series of any num­ber of shell com­mands that are exe­cut­ed to build the target

So in the above exam­ple when we type make build it will first do what­ev­er is need­ed to build the tar­get named up (which is a pre­req­ui­site), and then it’ll run the com­mands in the recipe to build the tar­get named build.

make will rebuild a tar­get when either the tar­get file or direc­to­ry does­n’t exist, or when any of its pre­req­ui­sites have been mod­i­fied and so are new­er than the target.

This Make­file Cheat­sheet may come in handy when learn­ing how Make­files work.

Anatomy of makefile variables

Anato­my of a Make­file preamble

You also can define and use vari­ables in your Make­files, the ?= con­di­tion­al assign­ment oper­a­tor used above assigns a default val­ue if the vari­able isn’t set already.

This can be use­ful in assign­ing default val­ues that can be over­rid­den via shell envi­ron­ment vari­ables.

Using make, we can get local aliases to run project-specific commands

We men­tioned ear­li­er that tar­gets are nor­mal­ly files or direc­to­ries, but we can use the spe­cial built-in tar­get named .PHONY to spec­i­fy that the tar­get is just a list of com­mands that should always be run.

We lever­age this to use our Makefile to define local alias­es that run com­mands to do var­i­ous things with our project.

So let’s have a look at a few examples.

Link Craft Scaffolding Makefile

This Make­file is one I use in my Craft CMS scaf­fold­ing. The CMS or frame­work in use does­n’t real­ly mat­ter, the applied prin­ci­ples are what is important.

CONTAINER?=$(shell basename $(CURDIR))_php_1
BUILDCHAIN?=$(shell basename $(CURDIR))_webpack_1

.PHONY: build clean composer dev npm pulldb restoredb up

build: up
	docker exec -it ${BUILDCHAIN} npm run build
	docker-compose down -v
	docker-compose up --build
composer: up
	docker exec -it ${CONTAINER} composer \
		$(filter-out $@,$(MAKECMDGOALS))
craft: up
	docker exec -it ${CONTAINER} php craft \
		$(filter-out $@,$(MAKECMDGOALS))
dev: up
npm: up
	docker exec -it ${BUILDCHAIN} npm \
		$(filter-out $@,$(MAKECMDGOALS))
pulldb: up
	cd scripts/ && ./docker_pull_db.sh
restoredb: up
	cd scripts/ && ./docker_restore_db.sh \
		$(filter-out $@,$(MAKECMDGOALS))
	docker-compose down
	rm -f cms/composer.lock
	rm -f buildchain/package-lock.json
	docker-compose up
	docker-compose down
	rm -f cms/composer.lock
	rm -rf cms/vendor/
	rm -f buildchain/package-lock.json
	rm -rf buildchain/node_modules/
	docker-compose up
	if [ ! "$$(docker ps -q -f name=${CONTAINER})" ]; then \
        docker-compose up; \
# ref: https://stackoverflow.com/questions/6273608/how-to-pass-argument-to-makefile-from-command-line
当前网页内容, 由 大妈 ZoomQuiet 使用工具: ScrapBook :: Firefox Extension 人工从互联网中收集并分享;
若有不妥, 欢迎评注提醒:


订阅 substack 体验古早写作:

点击注册~> 获得 100$ 体验券: DigitalOcean Referral Badge

关注公众号, 持续获得相关各种嗯哼:


关于 ~ DebugUself with DAMA ;-)
公安备案号: 44049002000656 ...::