## # Makefile to help manage docker-compose services # # Built on top of those resources: # https://gist.github.com/iNamik/cafef08f9d931cbf7acb012075052912 # https://github.com/krom/docker-compose-makefile/tree/master/samples # # Include environment files include .env include .env.docker export # Other variables THIS_FILE := Makefile DOCKER := docker DOCKER_COMPOSE := docker-compose DOCKER_COMPOSE_FILES := -f docker-compose.yml -f docker-compose.databases.yml ifeq ($(DOCKER_ENV),staging) DOCKER_COMPOSE_FILES := -f docker-compose.yml -f docker-compose.databases.yml endif ifeq ($(DOCKER_ENV),production) DOCKER_COMPOSE_FILES := -f docker-compose.yml -f docker-compose.databases.yml endif CERT_DOMAIN := $(VHOST) IMAGE_DEFAULT := app CONTAINER_DEFAULT := paneln8n-app-1 SERVICES_DEFAULT := app mysql adminer ifeq ($(DOCKER_ENV),staging) SERVICES_DEFAULT := app mysql adminer endif ifeq ($(DOCKER_ENV),production) SERVICES_DEFAULT := app mysql adminer endif SERVICE_DEFAULT := app NETWORK := app NETWORK_PROXY := nginx-proxy BACKUP_SERVICE := backup RESTORE_SERVICE := restore SHELL_CMD := /bin/bash container ?= $(CONTAINER_DEFAULT) image ?= $(IMAGE_DEFAULT) service ?= services ?= $(SERVICES_DEFAULT) .DEFAULT_GOAL := help ## # help # help: ifeq ($(CONTAINER_DEFAULT),) $(warning WARNING: CONTAINER_DEFAULT is not set. Please edit makefile) endif @echo @echo "Make targets:" @echo @cat $(THIS_FILE) | \ sed -n -E 's/^([^.][^: ]+)\s*:(([^=#]*##\s*(.*[^[:space:]])\s*)|[^=].*)$$/ \1 \4/p' | \ sort -u | \ expand -t15 @echo @echo @echo "Target arguments:" @echo @echo " " "service" "\t" "Target service for docker-compose actions (default=all-services)" @echo " " " " "\t" " - make start" @echo " " " " "\t" " - make start services=app" @echo " " "services" "\t" "Target services for docker-compose actions (default=all-services, space separated)" @echo " " " " "\t" " - make stop services='app mysql'" @echo " " "container""\t" "Target container for docker actions (default='$(CONTAINER_DEFAULT)')" @echo " " " " "\t" " - make bash container=$(container)" @echo " " "image" "\t" "Target image for interactive shell (default='$(IMAGE_DEFAULT)')" @echo " " " " "\t" " - make it image=$(image)" @echo " " " " "\t" " - make it image=node" ## # services # services: ## Lists services @$(DOCKER_COMPOSE) $(DOCKER_COMPOSE_FILES) ps --services ## # start # all: dev ## See 'dev' start: dev ## See 'dev' dev: ## Start containers for development [service|services] @$(DOCKER_COMPOSE) $(DOCKER_COMPOSE_FILES) up -d $(services) $(MAKE) logs ## # startinbg # startinbg: ## Start containers in background @$(DOCKER_COMPOSE) $(DOCKER_COMPOSE_FILES) up -d $(services) ## # stop # stop: ## Stop containers [service|services] @$(DOCKER_COMPOSE) $(DOCKER_COMPOSE_FILES) stop $(services) ## # restart # restart: ## Restart containers [service|services] @$(DOCKER_COMPOSE) $(DOCKER_COMPOSE_FILES) restart $(services) ## # down # down: ## Removes containers (preserves images and volumes) @$(DOCKER_COMPOSE) $(DOCKER_COMPOSE_FILES) down create-network: ifeq ($(DOCKER_ENV),local) @echo @echo "Creating proper network ($(NETWORK)) for the project" @$(DOCKER) network create $(NETWORK) 2> /dev/null || true @echo "Creating proper network ($(NETWORK_PROXY)) for the nginx proxy" @$(DOCKER) network create $(NETWORK_PROXY) 2> /dev/null || true endif ## # build # build: create-network ## Builds service images [service|services] ifeq ($(DOCKER_ENV),local) if [ ! -d "docker/certs" ]; then mkdir -p "docker/certs"; fi test -f docker/certs/$(CERT_DOMAIN).key && test -f docker/certs/$(CERT_DOMAIN).crt || mkcert -key-file docker/certs/$(CERT_DOMAIN).key -cert-file docker/certs/$(CERT_DOMAIN).crt $(CERT_DOMAIN) "*.$(CERT_DOMAIN)" test -f docker/certs/$(CERT_ALT_DOMAIN).key && test -f docker/certs/$(CERT_ALT_DOMAIN).crt || mkcert -key-file docker/certs/$(CERT_ALT_DOMAIN).key -cert-file docker/certs/$(CERT_ALT_DOMAIN).crt $(CERT_ALT_DOMAIN) "*.$(CERT_ALT_DOMAIN)" endif @$(DOCKER_COMPOSE) $(DOCKER_COMPOSE_FILES) build $(services) ## # rebuild # rebuild: ## Build containers without cache [service|services] @$(DOCKER_COMPOSE) $(DOCKER_COMPOSE_FILES) build --no-cache $(services) ## # ps # status: ps ## See 'ps' ps: ## Show status of containers @$(DOCKER_COMPOSE) $(DOCKER_COMPOSE_FILES) ps ## # interact # interact: it ## See `it' it: ## Run a new container in interactive mode. Needs image name [image] ifeq ($(image),) $(error ERROR: 'image' is not set. Please provide 'image=' argument or edit makefile and set CONTAINER_DEFAULT) endif @echo @echo "Starting interactive shell ($(SHELL_CMD)) in image container '$(image)'" @$(DOCKER_COMPOSE) $(DOCKER_COMPOSE_FILES) run -i --no-deps --entrypoint "$(SHELL_CMD)" $(image) ## # bash # sh: bash ## See 'bash' shell: bash ## See 'bash' bash: ## Brings up a shell in default (or specified) container [container] ifeq ($(container),) $(error ERROR: 'container' is not set. Please provide 'container=' argument or edit makefile and set CONTAINER_DEFAULT) endif @echo @echo "Starting shell ($(SHELL_CMD)) in container '$(container)'" @$(DOCKER) exec -it "$(container)" "$(SHELL_CMD)" ## # attach # at: attach ## See 'attach' attach: ## Attach to a running container [container] ifeq ($(container),) $(error ERROR: 'container' is not set. Please provide 'container=' argument or edit makefile and set CONTAINER_DEFAULT) endif @echo @echo "Attaching to '$(container)'" @$(DOCKER) attach $(container) ## # log # log: ## Shows log from a specific container (in 'follow' mode) [container] ifeq ($(container),) $(error ERROR: 'container' is not set. Please provide 'container=' argument or edit makefile and set CONTAINER_DEFAULT) endif @echo @echo "Log in $(container)" @$(DOCKER) logs -f $(container) ## # logs # logs: ## Shows output of running containers (in 'follow' mode) [service|services] @echo @echo "Logs in $(services)" @$(DOCKER_COMPOSE) $(DOCKER_COMPOSE_FILES) logs -f $(services) ## # rmimages # rmimages: ## Remove images @echo @echo "Remove local images" @$(DOCKER_COMPOSE) $(DOCKER_COMPOSE_FILES) down --rmi local ## # rmvols # rmvols: ## Remove volumes @echo @echo "Remove named volumes declared in the volumes section of the Compose file and anonymous volumes attached to containers" @$(DOCKER_COMPOSE) $(DOCKER_COMPOSE_FILES) down -v ## # rm # rm: rmimages rmvols ## Remove volumes and images ## # clean # clean: ## Remove containers, images and volumes @echo @echo "Remove containers, images and volumes" @$(DOCKER_COMPOSE) $(DOCKER_COMPOSE_FILES) down --volumes --rmi all ## # backup # backup: ## Run 'backup' service @echo @echo "Running '$(BACKUP_SERVICE)'" @$(DOCKER_COMPOSE) $(DOCKER_COMPOSE_FILES) run $(BACKUP_SERVICE) ## # restore # restore: ## Run 'restore' service @echo @echo "Running '$(BACKUP_SERVICE)'" @$(DOCKER_COMPOSE) $(DOCKER_COMPOSE_FILES) run $(RESTORE_SERVICE) ## # dumplog # dumplog: ## Run 'dumplog' [service|services] if [ ! -d "docker/logs" ]; then mkdir -p "docker/logs"; fi @echo @echo "Running 'dumplog'" @$(DOCKER_COMPOSE) $(DOCKER_COMPOSE_FILES) logs --no-color --since 24h --timestamps $(services) ## # staging # staging: ## Make a temporary deploy to staging server @echo @echo "🔧 Building assets in node container" @$(DOCKER_COMPOSE) $(DOCKER_COMPOSE_FILES) exec node npm run build > /dev/null @echo @echo "📤 Deploying to staging" @$(RSYNC_CMD) -e "ssh -J $(RSYNC_BRIDGE)" $(RSYNC_OPTIONS) ./ $(RSYNC_USER)@$(RSYNC_HOST):$(RSYNC_PATH) > /dev/null ifneq ($(strip $(TELEGRAM_BOT_TOKEN)),) @echo "📣 Notifying Telegram" @curl -s -X POST https://api.telegram.org/bot$(TELEGRAM_BOT_TOKEN)/sendMessage \ -d chat_id=$(TELEGRAM_CHAT_ID) \ -d text="🚀 Staging se ha actualizado correctamente." > /dev/null endif @echo "Done!" .PHONY: help services all start startinbg dev stop restart down create-network build rebuild status ps interact it sh shell bash at attach log logs rm rmimages rmvols clean backup restore dumplog staging