| # Copyright 2014 the Melange authors. |
| # |
| # Licensed under the Apache License, Version 2.0 (the "License"); |
| # you may not use this file except in compliance with the License. |
| # You may obtain a copy of the License at |
| # |
| # http://www.apache.org/licenses/LICENSE-2.0 |
| # |
| # Unless required by applicable law or agreed to in writing, software |
| # distributed under the License is distributed on an "AS IS" BASIS, |
| # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| # See the License for the specific language governing permissions and |
| # limitations under the License. |
| |
| # all targets are PHONY because they don't actually generate a file with the |
| # name of the target. |
| .PHONY: setup test pylint lint localserver gitclean help |
| .PHONY: pyunit functionaltest jstest _ptests ptest |
| |
| help: |
| @echo |
| @echo Common Commands: |
| @echo local-docker - build and run a local docker container |
| @echo docker - enter the docker container |
| @echo setup - setup environment |
| @echo css - rebuild css |
| @echo docs - build the python and javascript documentation |
| @echo localserver - run local development server |
| @echo gitclean - reset to clean checkout |
| @echo lint - run lint and safety checks |
| @echo test - run all tests |
| @echo ptest - run all tests in parallel |
| @echo functionaltest - run functional tests |
| @echo do-release - make production release |
| @echo do-dev-release APP=foo - make dev release |
| @echo |
| @echo To make a release... |
| @echo " make gitclean && make setup && make ptest && make do-release" |
| @echo |
| |
| # try and avoid downloading things more than once. |
| DOWNLOAD_CACHE=/var/tmp/melange-download-cache-$(USER) |
| ifdef DOWNLOAD_CACHE |
| DOWNLOAD_CACHE_SENTINEL=$(DOWNLOAD_CACHE)/.sentinel |
| # where should bootstrap store its download cache? |
| DOWNLOAD_CACHE_ARG=download-cache=$(DOWNLOAD_CACHE) |
| # where should PIP store its download cache? |
| export PIP_DOWNLOAD_CACHE=$(DOWNLOAD_CACHE)/pip |
| export npm_config_cache=$(DOWNLOAD_CACHE)/npm |
| endif |
| |
| # bootstrap gets unhappy if the directory doesn't exist |
| $(DOWNLOAD_CACHE_SENTINEL): |
| ifdef DOWNLOAD_CACHE_SENTINEL |
| mkdir -p $(DOWNLOAD_CACHE) |
| touch $(DOWNLOAD_CACHE_SENTINEL) |
| endif |
| |
| # initial setup for the development environment |
| initial-setup: .initial-setup |
| .initial-setup: $(DOWNLOAD_CACHE_SENTINEL) |
| virtualenv venv |
| venv/bin/pip install -U setuptools |
| venv/bin/python -c 'import lxml' || venv/bin/pip install -U lxml |
| venv/bin/python bootstrap.py $(DOWNLOAD_CACHE_ARG) bootstrap |
| touch $@ |
| |
| # run buildout |
| buildout: .buildout |
| .buildout: $(DOWNLOAD_CACHE_SENTINEL) buildout.cfg setup.py |
| bin/buildout $(DOWNLOAD_CACHE_ARG) |
| touch $@ |
| |
| # clear the sentinel files that prevent buildout and initial-setup from |
| # running again unless a dependency has changed. |
| clean-setup: |
| rm -f .buildout .initial-setup |
| @echo now re-run 'make setup' |
| |
| # build and run a local copy of the melange docker container |
| local-docker: |
| docker build -t $(USER)/melange . |
| docker run -ti --rm -v $(PWD):/workspace -p 8080:8080 $(USER)/melange |
| |
| # enter the docker container |
| docker: |
| @echo You are now working in a docker container. |
| @echo Type 'exit' to leave the container |
| @docker run -ti --rm -v $(PWD):/workspace -p 8080:8080 melange/melange-dev |
| |
| # setup target sets up the basics of the development environment |
| setup: APP=local-devel |
| setup: initial-setup buildout |
| bin/gen-app-yaml -f $(APP) |
| bin/paver build --skip-docs |
| |
| # force all setup dependencies to run again |
| force-setup: clean-setup setup |
| |
| # update python and js generated docs |
| docs: |
| bin/paver build_docs |
| bin/grunt documentation |
| |
| # run all the tests |
| test: |
| bin/run-tests |
| |
| # which directories and paths should we run pylint on |
| PYLINT_PATHS:=app/codein app/melange app/soc app/summerofcode |
| PYLINT_PATHS+=app/settings.py app/urls.py app/main.py |
| PYLINT_PATHS+=scripts tests |
| PYLINT_PATHS+=configuration/buildbot/*.py configuration/buildbot/*.cfg |
| PYLINT_PATHS+=pavement.py setup.py |
| PYLINT_FLAGS:= |
| |
| # how much parallelism for pylint? |
| # (pylint doesn't parallelize on Melange very well, so there's not a |
| # lot of improvement once you get much past 2.) |
| PYLINT_JOBS:=4 |
| # run pylint |
| pylint: |
| bin/pylint --jobs=$(PYLINT_JOBS) --rcfile=$(PWD)/pylintrc \ |
| $(PYLINT_FLAGS) $(PYLINT_PATHS) |
| |
| # *** pylint-verbose enables more checks |
| # In the rcfile(pylintrc) errors-only option is |
| # set. PYLINT_VERBOSE_FLAGS defines other errors that we might want to |
| # turn on. |
| # Include fancier output: |
| PYLINT_VERBOSE_FLAGS+=--reports=yes |
| # R and C modules are just too chatty, we can however turn a few of |
| # the more useful ones on explicitly: |
| PYLINT_VERBOSE_FLAGS:=--enable=W,F |
| # We may want to enable these in the future: |
| PYLINT_VERBOSE_FLAGS+=--disable=protected-access,attribute-defined-outside-init |
| # TODO(nathaniel): fix all occurences and enable this: |
| PYLINT_VERBOSE_FLAGS+=--disable=abstract-method |
| # These are just plain useless, we don't ever want to these: |
| PYLINT_VERBOSE_FLAGS+=--disable=fixme,unused-argument,star-args,bad-builtin,locally-disabled |
| # These are somewhat debatable, but not realistic for Melange: |
| PYLINT_VERBOSE_FLAGS+=--disable=no-init,super-init-not-called |
| # TODO(nathaniel): fix all occurences and move this to pylintrc file: |
| PYLINT_VERBOSE_FLAGS+=--enable=line-too-long |
| |
| pylint-verbose: PYLINT_FLAGS=$(PYLINT_VERBOSE_FLAGS) |
| pylint-verbose: pylint |
| |
| lint: pylint |
| |
| # run only the pyunit tests |
| pyunit: PROCESSES=$(if $(PTESTS),4,-1) |
| pyunit: |
| bin/run-tests -t pyunit --processes=$(PROCESSES) |
| |
| functionaltest: |
| bin/run-tests -t functional |
| |
| jstest: |
| bin/run-tests -t js |
| |
| # helper target for ptest target (specifies which tests to run) |
| _ptests: PTESTS=1 |
| _ptests: functionaltest pyunit pylint jstest |
| @echo |
| |
| # run tests in parallel (note, output will be interleaved) |
| ptest: |
| make -j _ptests |
| |
| # build less files into css |
| css: |
| bin/grunt less |
| |
| # some files (like css) are generated dynamically, group them all in |
| # one target |
| generated: css |
| |
| # start a local instance. defaults to port 8080 for the app and 8000 |
| # for the appengine console |
| localserver: |
| thirdparty/google_appengine/dev_appserver.py build |
| |
| # return to a pristine git checkout. *DELETES EVERYTHING WITHOUT PROMPTING* |
| gitclean: |
| git clean -xdf |
| |
| # Targets related to making a release --- |
| |
| .PHONY: update-template-version commit-release push-release-to-appengine |
| .PHONY: do-release |
| |
| # define an string equality function. call with $(call eq,1,2) |
| eq = $(and $(findstring $(1),$(2)),$(findstring $(2),$(1))) |
| |
| BRANCH=$(shell git rev-parse --abbrev-ref HEAD) |
| BRANCH_CLEAN=$(shell echo $(BRANCH) \ |
| | tr 'A-Z' 'a-z' \ |
| | sed -r 's/[^a-z0-9-]/-/g' \ |
| | cut -c 1-34) |
| VERSION_SUFFIX=$(if $(call eq,$(BRANCH),master),,-$(BRANCH_CLEAN)) |
| |
| # Sets the version in app.yaml.template to the version as specified by |
| # the current day. |
| # If you need to specify a patchlevel (i.e. -1, -2), you must specify |
| # the whole VERSION on the make command line. |
| # For development versions, use the output of git describe --tags |
| _update_app_yaml_template: |
| sed -i -r 's/^(version: )[^ \t]+/\1$(VERSION)/' app/app.yaml.template |
| |
| # only updates the version in app.yaml |
| _update_app_yaml: |
| sed -i -r 's/^(version: )[^ \t]+/\1$(VERSION)/' app/app.yaml |
| |
| update-version: VERSION=2-1-$(shell date +%Y%m%d)$(VERSION_SUFFIX) |
| update-version: _update_app_yaml_template |
| |
| # update-dev-version only updates the version in |
| # app/app.yaml, not in the template. |
| update-dev-version: VERSION=$(shell git describe --tags | cut -c2-)$(VERSION_SUFFIX) |
| update-dev-version: _update_app_yaml |
| |
| commit-release: VERSION=$(shell awk '/^version: / { print $$2 }' app/app.yaml.template) |
| commit-release: |
| git commit -e -m "Set new Melange version number to $(VERSION)." app/app.yaml.template |
| git tag v$(VERSION) HEAD |
| |
| gen-app-yaml: app/app.yaml |
| app/app.yaml: app/app.yaml.template scripts/gen_app_yaml.py |
| bin/gen-app-yaml -f $(APP) |
| |
| # TODO(robert): set the default value of APP to local-devel? |
| push-release-to-appengine: |
| thirdparty/google_appengine/appcfg.py \ |
| --application=$(APP) \ |
| --noauth_local_webserver \ |
| --oauth2 update build |
| |
| do-dev-release: APP=YOU_MUST_SPECIFY_A_VALID_APP |
| do-dev-release: generated update-dev-version push-release-to-appengine |
| @echo |
| @echo ========================================================== |
| @echo Melange dev release $(VERSION) pushed successfully! |
| @echo *. go to the App Engine control panel and send it traffic |
| @echo https://appengine.google.com/deployment?app_id=s~$(APP) |
| |
| do-release: APP=google-melange |
| do-release: generated update-version gen-app-yaml \ |
| commit-release push-release-to-appengine |
| @echo |
| @echo ========================================================== |
| @echo Melange release $(VERSION) pushed successfully! |
| @echo 1. push the release commit to the repository |
| @echo git push --tags origin master |
| @echo 2. go to the App Engine control panel and send it traffic |
| @echo https://appengine.google.com/deployment?app_id=s~$(APP) |