-1

Makefile cho developer: không chỉ dành cho C/C++

Makefile không chỉ dành cho compile C/C++. Mình dùng nó như một task runner đơn giản cho mọi dự án.

Tại sao Makefile?

  • Không cần cài thêm tool (có sẵn trên mọi Linux/Mac)
    • Tự document: make help liệt kê tất cả commands
    • Dependency tracking: chỉ chạy lại khi cần

Makefile cho dự án Python

.PHONY: help install test lint format run clean

help:  ## Hiện danh sách commands
	@grep -E '^[a-zA-Z_-]+:.*?## .*$$' $(MAKEFILE_LIST) | \
    		awk 'BEGIN {FS = ":.*?## "}; {printf "  \033[36m%-15s\033[0m %s\n", $$1, $$2}'
            
            install:  ## Cài dependencies
            	pip install -r requirements.txt
                	pip install -r requirements-dev.txt
                    
                    test:  ## Chạy tests
                    	pytest tests/ -v --cov=src --cov-report=term-missing
                        
                        lint:  ## Check code style
                        	ruff check src/ tests/
                            	mypy src/
                                
                                format:  ## Format code
                                	ruff format src/ tests/
                                    
                                    run:  ## Chạy app
                                    	python -m src.main
                                        
                                        clean:  ## Xóa cache files
                                        	find . -type d -name __pycache__ -exec rm -rf {} +
                                            	find . -type f -name "*.pyc" -delete
                                                	rm -rf .pytest_cache .mypy_cache .ruff_cache
                                                    ```
                                                    
                                                    ## Makefile cho dự án Node.js
                                                    
                                                    ```makefile
                                                    .PHONY: dev build test deploy
                                                    
                                                    dev:  ## Start dev server
                                                    	npm run dev
                                                        
                                                        build:  ## Build production
                                                        	npm ci
                                                            	npm run build
                                                                
                                                                test:  ## Run tests
                                                                	npm test
                                                                    
                                                                    deploy: build  ## Deploy (build trước)
                                                                    	rsync -avz dist/ server:/app/public/
                                                                        	ssh server 'pm2 restart app'
                                                                            
                                                                            docker-up:  ## Start Docker containers
                                                                            	docker compose up -d
                                                                                
                                                                                docker-down:  ## Stop Docker containers
                                                                                	docker compose down
                                                                                    
                                                                                    logs:  ## Xem logs
                                                                                    	docker compose logs -f --tail=100
                                                                                        ```
                                                                                        
                                                                                        ## Makefile cho dự án có Docker
                                                                                        
                                                                                        ```makefile
                                                                                        IMAGE := myapp
                                                                                        TAG := $(shell git rev-parse --short HEAD)
                                                                                        
                                                                                        build:  ## Build Docker image
                                                                                        	docker build -t $(IMAGE):$(TAG) .
                                                                                            	docker tag $(IMAGE):$(TAG) $(IMAGE):latest
                                                                                                
                                                                                                push:  ## Push to registry
                                                                                                	docker push $(IMAGE):$(TAG)
                                                                                                    	docker push $(IMAGE):latest
                                                                                                        
                                                                                                        shell:  ## Shell vào container
                                                                                                        	docker run -it --rm $(IMAGE):latest /bin/sh
                                                                                                            
                                                                                                            db-migrate:  ## Run database migrations
                                                                                                            	docker compose exec api python manage.py migrate
                                                                                                                
                                                                                                                db-seed:  ## Seed database
                                                                                                                	docker compose exec api python manage.py seed
                                                                                                                    ```
                                                                                                                    
                                                                                                                    ## Variables và Conditionals
                                                                                                                    
                                                                                                                    ```makefile
                                                                                                                    ENV ?= development  # Default, có thể override: make deploy ENV=production
                                                                                                                    
                                                                                                                    deploy:
                                                                                                                    ifeq ($(ENV),production)
                                                                                                                    	@echo "Deploying to PRODUCTION..."
                                                                                                                        	./deploy.sh production
                                                                                                                            else
                                                                                                                            	@echo "Deploying to staging..."
                                                                                                                                	./deploy.sh staging
                                                                                                                                    endif
                                                                                                                                    ```
                                                                                                                                    
                                                                                                                                    ## Tips
                                                                                                                                    
                                                                                                                                    1. **`.PHONY`**: Khai báo targets không phải file, tránh conflict với file cùng tên
                                                                                                                                    2. **`@` prefix**: Ẩn command, chỉ hiện output
                                                                                                                                    3. **`##` comment**: Dùng cho `make help` tự động
                                                                                                                                    4. **Tab, không space**: Makefile BẮT BUỘC dùng tab để indent recipes
                                                                                                                                    
                                                                                                                                    ---
                                                                                                                                    
                                                                                                                                    Bạn có dùng Makefile không? Hay prefer npm scripts / just / task runner khác?

All rights reserved

Viblo
Hãy đăng ký một tài khoản Viblo để nhận được nhiều bài viết thú vị hơn.
Đăng kí