graphql-engine/server/CONTRIBUTING.md
Soham Chowdhury dbdf81b26d
docs: note libkrb5-dev dep on Debian, update GHC version (#5377)
* docs: note libkrb5-dev dep on Debian, update GHC version

* docs: note openssl/libssl-dev requirements on Debian
2020-07-15 11:03:33 +05:30

186 lines
6.6 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# Contributing
This guide explains how to set up the graphql-engine server for development on your
own machine and how to contribute.
## Pre-requisites
- [GHC](https://www.haskell.org/ghc/) 8.10.1 and [cabal-install](https://cabal.readthedocs.io/en/latest/)
- There are various ways these can be installed, but [ghcup](https://www.haskell.org/ghcup/) is a good choice if youre not sure.
- [Node.js](https://nodejs.org/en/) (>= v8.9)
- npm >= 5.7
- [gsutil](https://cloud.google.com/storage/docs/gsutil)
- libpq-dev
- libkrb5-dev
- openssl and libssl-dev
- python >= 3.5 with pip3 and virtualenv
The last few prerequisites can be installed on Debian or Ubuntu with:
$ sudo apt install libpq-dev libkrb5-dev python3 python3-pip python3-venv openssl libssl-dev
Additionally, you will need a way to run a Postgres database server. The `dev.sh` script (described below) can set up a Postgres instance for you via [Docker](https://www.docker.com), but if you want to run it yourself, youll need:
- [PostgreSQL](https://www.postgresql.org) >= 9.5
- [postgis](https://postgis.net)
### Upgrading npm
If your npm is too old (>= 5.7 required):
$ npm install -g npm@latest # sudo may be required
or update your nodejs.
## Development workflow
You should fork the repo on github and then `git clone https://github.com/<your-username>/graphql-engine`.
After making your changes
### Compile
...console assets:
$ cd console
$ npm ci
$ npm run server-build
$ cd ..
...and the server:
$ cd server
$ ln -s cabal.project.dev cabal.project.local
$ cabal new-update
$ cabal new-build
To set up the project configuration to coincide with the testing scripts below, thus avoiding recompilation when testing locally, rather use `cabal.project.dev-sh.local` instead of `cabal.project.dev`:
$ ln -s cabal.project.dev-sh.local cabal.project.local
### Run and test via `dev.sh`
The `dev.sh` script in the top-level `scripts/` directory is a turnkey solution to build, run, and
test `graphql-engine` using a Docker container to run a Postgres database. **Docker is necessary to
use `dev.sh`.**
To use `dev.sh`, first launch a new postgres container with:
$ scripts/dev.sh postgres
Then in a new terminal launch `graphql-engine` in dev mode with:
$ scripts/dev.sh graphql-engine
The `dev.sh` will print some helpful information and logs from both services
will be printed to screen.
You can run the test suite with:
$ scripts/dev.sh test
This should run in isolation. The output format is described in the [pytest documentation](https://docs.pytest.org/en/latest/usage.html#detailed-summary-report). Errors and failures are indicated by `F`s and `E`s.
### Run and test manually
If you want, you can also run the server and test suite manually against a Postgres instance of your choosing.
#### Run
The following command can be used to build and launch a local `graphql-engine` instance:
```
cabal new-run -- exe:graphql-engine \
--database-url='postgres://<user>:<password>@<host>:<port>/<dbname>' \
serve --enable-console --console-assets-dir=../console/static/dist
```
This will launch a server on port 8080, and it will serve the console assets if they were built with `npm run server-build` as mentioned above.
#### Test
`graphql-engine` has two test suites:
1. A small set of unit tests and integration tests written in Haskell.
2. An extensive set of end-to-end tests written in Python.
Both sets of tests require a running Postgres database.
##### Running the Haskell test suite
```
cabal new-run -- test:graphql-engine-tests \
--database-url='postgres://<user>:<password>@<host>:<port>/<dbname>'
```
##### Running the Python test suite
1. To run the Python tests, youll need to install the necessary Python dependencies first. It is
recommended that you do this in a self-contained Python venv, which is supported by Python 3.3+
out of the box. To create one, run:
```
python3 -m venv .python-venv
```
(The second argument names a directory where the venv sandbox will be created; it can be anything
you like, but `.python-venv` is `.gitignore`d.)
With the venv created, you can enter into it in your current shell session by running:
```
source .python-venv/bin/activate
```
(Source `.python-venv/bin/activate.fish` instead if you are using `fish` as your shell.)
2. Install the necessary Python dependencies into the sandbox:
```
pip3 install -r tests-py/requirements.txt
```
3. Start an instance of `graphql-engine` for the test suite to use:
```
env EVENT_WEBHOOK_HEADER=MyEnvValue \
WEBHOOK_FROM_ENV=http://localhost:5592/ \
cabal new-run -- exe:graphql-engine \
--database-url='postgres://<user>:<password>@<host>:<port>/<dbname>' \
serve --stringify-numeric-types
```
The environment variables are needed for a couple tests, and the `--stringify-numeric-types` option is used to avoid the need to do floating-point comparisons.
4. With the server running, run the test suite:
```
cd tests-py
pytest --hge-urls http://localhost:8080 \
--pg-urls 'postgres://<user>:<password>@<host>:<port>/<dbname>'
```
This will run all the tests, which can take a couple minutes (especially since some of the tests are slow). You can configure `pytest` to run only a subset of the tests; see [the `pytest` documentation](https://doc.pytest.org/en/latest/usage.html) for more details.
Some other useful points of note:
- It is recommended to use a separate Postgres database for testing, since the tests will drop and recreate the `hdb_catalog` schema, and they may fail if certain tables already exist. (Its also useful to be able to just drop and recreate the entire test database if it somehow gets into a bad state.)
- You can pass the `-v` or `-vv` options to `pytest` to enable more verbose output while running the tests and in test failures. You can also pass the `-l` option to display the current values of Python local variables in test failures.
### Create Pull Request
- Make sure your commit messages meet the [guidelines](../CONTRIBUTING.md).
- If you changed the versions of any dependencies, run `cabal new-freeze` to update the freeze file.
- Create a pull request from your forked repo to the main repo.
- Every pull request will automatically build and run the tests.
## Code conventions
This helps enforce a uniform style for all committers.
- Compiler warnings are turned on, make sure your code has no warnings.
- Use [hlint](https://github.com/ndmitchell/hlint) to make sure your code has no warnings.
- Use [stylish-haskell](https://github.com/jaspervdj/stylish-haskell) to format your code.