I have the following in a Makefile for the purpose of recreating my database including destroying it if necessary. It does not work.
.PHONY: rebuilddb exists=$(psql postgres --tuples-only --no-align --command "SELECT 1 FROM pg_database WHERE datname='the_db'") if [ $(exists) -eq 1 ]; then dropdb the_db fi createdb -E UTF8 the_db
Running it results in an error:
$ make rebuilddb exists= if [ -eq 1 ]; then /bin/sh: -c: line 1: syntax error: unexpected end of file make: *** [rebuilddb_postgres] Error 2
Why is this wrong? It looks like valid Bash as far as I can tell? Are there special considerations I must make when doing this in a Makefile?
UPDATE:
Using the answer I arrived at a working version:
.PHONY: rebuilddb exists=$$(psql postgres --tuples-only --no-align --command "SELECT 1 FROM pg_database WHERE datname='the_db'"); \ if [ "$$exists" == "1" ]; then \ dropdb the_db; \ fi; createdb -E UTF8 the_db
So put SHELL := /bin/bash at the top of your makefile, and you should be good to go. See "Target-specific Variable Values" in the documentation for more details. That line can go anywhere in the Makefile, it doesn't have to be immediately before the target.
$(shell) $(shell) is a special function in gmake that runs an external command and captures the output for use in the makefile.
There are at least two considerations. $()
references a Make variable. You must escape the $
to do command substitution. Also, the shell commands must be all on one line. Try:
exists=$$(psql postgres --tuples-only --no-align --command "SELECT 1 FROM \ pg_database WHERE datname='the_db'"); \ if [ "$$exists" -eq 1 ]; then \ dropdb the_db; \ fi; \ createdb -E UTF8 the_db
On the other hand, it seems like it would be simpler to just always try to drop the database, and allow failure:
rebuilddb: -dropdb the_db # Leading - instructs make to not abort on error createdb -E UTF8 the_db
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With