A simple Web GIS application developed in Django, Django REST framework, and Leaflet. This app renders bus stops from the database and parses them into a leaflet map.
This is a simple web geographic information systems (GIS) application that demonstrates full-stack GIS web development using Django, Django REST framework, JavaScript, CSS and HTML and one that can be forked and customized to your preference.
- Python - https://www.python.org/downloads/
- PostgreSQL - https://www.postgresql.org/download/
- PostGIS - https://postgis.net/install/
- Docker (optional but fast to deploy). - https://docs.docker.com/get-docker/
Features present in this project include:
- Responsive and mobile-friendly user interface.
- Map location markers with event-driven capabilities.
- Static files (css, javascript, and images) management.
- Development and production environment configurations.
- Containerized deployment configuration.
- Code formatting / linting support.
- Unit testing (To be done).
Software used in the development of this project include:
- Python - Core programming language used in the development of this project. Specific version is referenced in the development and production build configurations.
- Django - Python web development framework that is the main framework used in this project.
- Git - Used for version control in development of this project.
- Docker Desktop Windows - Software for handling development operations (DevOps) using graphical user interface (GUI) in Windows. Installs Docker Command Line Interface, Docker Compose etc.
- Docker Desktop Linux - Software for handling development operations (DevOps) using graphical user interface (GUI) in Linux.
- Postgres - Object Relational Database Management System used to store and support DB operations in this project. Specific version is referenced in development and production configurations.
This project's initial dependencies are listed in the Pipfile include:
- Django as the base framework
- django-rest-framework for REST api functionalities.
- django-rest-framework-gis To provide Geographic add-ons for Django REST Framework.
- django-environ for management of environment variables
- django-geojson for manipulating GeoJSON with Django
- django-leaflet for adding leaflet functionality and assets to Django/GeoDjango
- django-storages support for Amazon's S3 storage backend. Can be used with other storage backends e.g. Digital Ocean, DropBox, Google Cloud etc.
- django-cloudinary-storage Package that facilitates integration with Cloudinary using Django File Storage APIon the management of media and static files. Read more from Cloudinary documentation
- psycopg-binary database adapter to facilitate database connectivity and other operations.
- django-cors-headers Applied in handling the server headers required for Cross-Origin Resource Sharing (CORS).
- Django Debug Toolbar to help with debugging during development
- whitenoise for managing static and user uploads in developement and production
- gunicorn HTTP server for supporting serving of this project over the web
- dj-database-url support for database URL environment variable
- boto3 supporting Amazon's S3 capabilities
- black for linting and automatically formatting the code during development
- Faker for generating fake data for use/test in this project (TODO)
- coverage for measuring code coverage (TODO)
The minimum requirement required to deploy this project is Docker Engine. Docker Engine contains docker, docker compose, and if on a Desktop environment and prefer a graphical user interface, one can make use of Docker Desktop.
Make is used in this project to execute docker commands present in the Makefile for the purpose of saving time that is used during executing long docker commands. This is optional but recommended and can be installed using the following guides
-
Installing Make on Windows requires a bit of setup since Make is not natively available on the platform. Here are the steps to follow:
-
Download and install the Windows Subsystem for Linux (WSL) from the Microsoft Store. This will allow you to run a Linux environment on your Windows machine.
-
Once WSL is installed, open the Microsoft Store and search for a Linux distribution that includes make, such as Ubuntu. Download and install the distribution.
-
Open the Linux distribution from the Start menu or by typing the name of the distribution in the search bar.
-
In the Linux terminal, type sudo apt-get update to update the package list.
-
Next, type `sudo apt-get install build-essential to install the necessary tools for building software, including make.
-
Once the installation is complete, you should be able to use Make in the Linux terminal.
-
Note that you must be familiar with using a Linux command-line interface to use make on Windows.
These are steps that one should take towards deploying this project successfully in a local or development environment which could be in a local machine or similar.
- Clone the repository to your local machine.
git clone https://github.com/jkariukidev/nairobi-busstops.git
- Rename the .env_local.sample file to
.env
to be used by docker. - Add the values for the environment variables. One of the reasons for environment variables is to avoid hard-coding passwords and sensitive information on the code. The environment variables include:
COMPOSE_PROJECT_NAME
- The name (prefix) for the docker-compose services.SECRET_KEY
- Django cryptography key described in detail here.DEBUG
- Variable used in local/development to enable debugging (hence set toTrue
in development). Read more details here.ALLOWED_HOSTS
- List of host/domain names that this Django site can serve. Has been set tolocalhost
.ENGINE
- Database backend to use. This project uses PostgreSQL backend by default but can be changed in the environment variables.POSTGRES_USER
- Specifies a user with superuser privileges and a database with the same name. Postgres uses the default user when this is empty.POSTGRES_PASSWORD
- Postgres requires a password to function properly, which is the purpose of this mandatory variable.POSTGRES_PORT
- Network port used by the database is also defined in the docker-compose files.POSTGRES_HOST
- The network host used by the database is also defined in the docker-compose files.GIS_DB_USER
- Specifies a database user to be used in this project separate from the database superuser above.GIS_DB_PASSWORD
- Geodatabase's password.GIS_DB_NAME
- Refers to the geodatabase name.DATABASE_URL
- Defines the database URL schema and other parameters using the 12-factor. A definition of URL schemas for different databases can be read here.
- Build the required docker images for this project using the command.
make build-dev
- Run the development server on http://127.0.0.1:8000 by running.
make runserver-dev
- Apply migrations to synchronize the database state with the current set of models and migration using.
in the event mywebgis models are altered, one can update migrations which generate the SQL commands for apps by running
make migrate-dev
make makemigrations-dev
- Load geospatial data into the geodatabase making use of GeoDjango's functionalities.
make load-geospatial-data-dev
- Optional: Load initial admin login data making use of django fixtures.
- Admin - This creates a default superuser (testadmin) and a standard user (testuser). The superuser can log into the Django admin panel and change settings etc.
make load-admin-data-dev
- Admin - This creates a default superuser (testadmin) and a standard user (testuser). The superuser can log into the Django admin panel and change settings etc.
- If skipped the previous step, create your own additional superuser by running.
make superuser-dev
- If populated the database using step 7 above, one can try logging in using the following:
- Navigate to the admin login URL at http://127.0.0.1:8000/geoadmin/
- Log in using
geouser
as user andGe0Aw3s0menes$
as password. (NOTE: this is the superuser with full privileges on this app)
- Logs can be monitored by running.
make logs-dev
- Prints log outputmake logs-interactive-dev
- Show logs interactively
- On shutting down the development server, run the following.
make shutdown-dev
which stops the running containers (web and database)make shutdown-volumes-dev
which stops the running containers and deletes volumes that contain persisted data.
These are steps that one should take towards deploying this project successfully in a production environment which could be in a cloud virtual machine (VM) making the project accessible through the internet. Some variable names are the same as the ones in the development environment and have not been repeated below i.e. database environment variables.
-
Clone this project using
git clone
command.git clone https://github.com/jkariukidev/my-demo-website.git
-
Navigate into the cloned project folder and using a terminal/shell or otherwise, rename the env_prod.sample to
.env
in production to be recognized by docker. -
Edit the environment variables as required and ensure you do not share passwords and security keys with the public. The additional environment variables for production include:
COMPOSE_PROJECT_NAME
- The name (prefix) for the docker-compose services.DEBUG
- Must be set toFalse
to avoid leaking sensitive project and server information displayed during development.ALLOWED_HOSTS
- List of host/domain names that this Django site can serve. Has been set to your domain otherwise the website may not be accessed.USE_CLOUDINARY
- Variable with a Boolean value that directs the app to use Cloudinary settings for static files management.CLOUDINARY_CLOUD_NAME
- Variable pointing to the name of the cloud provided by cloudinaryCLOUDINARY_API_KEY
- Mandatory API key associated with a given Cloudinary account. Please refer to the Cloudinary documentation for more.CLOUDINARY_API_SECRET
- Secret key associated with theCLOUDINARY_API_KEY
CLOUDINARY_URL
- Combination of theCLOUDINARY_API_KEY
,CLOUDINARY_API_SECRET
andCLOUDINARY_CLOUD_NAME
which consists of the Cloudinary URL.USE_S3
- Variable with Boolean value that directs the app to use Amazon Web Services (AWS) S3 settings for static files management.AWS_ACCESS_KEY_ID
- AWS access key, as a string.AWS_SECRET_ACCESS_KEY
- AWS access key, as a string.AWS_STORAGE_BUCKET_NAME
- AWS storage bucket name, as a string.AWS_S3_CUSTOM_DOMAIN
- Parameter configured when using AWS CloudFront services.AWS_S3_OBJECT_PARAMETERS
- Set parameters on all AWS S3 objects.AWS_LOCATION
- Path prefix that will be prepended to all uploads to AWS S3.USE_WHITENOISE
- Variable with Boolean value that directs the app to use AWS S3 settings for static files management.
-
Run the docker services for this project using compose in production environment.
make runserver
-
Propagate models into your database schema using the migrate command. Note that this command is being run inside the docker web container. Refer for more on exec docker command.
make migrate
-
One can copy the static files using the Django's collectstatic command depending on the static files management settings above.
make collectstatic
-
Load initial data using the same steps as specified in development section above. Using the
make load-admin-data
andmake load-geospatial-data
commands. -
Check logs using
make logs
or to view the logs interactively usemake logs-interactive
For several other commands, view them in the Makefile
- Creating GeoWeb applications.
- GIS data management across the web.
- Geo-visualization
- Testing and deployment of GeoWeb applications.
- Static files assets management using services; Cloudinary, AWS S3 etc.
Unit tests are a fundamental part of the testing framework that allows you to verify the correctness of your code at a granular level. Unit tests focus on testing individual components, such as models, views, forms, and utility functions, in isolation to ensure they behave as expected.
Check the project test for more. To execute tests, use the following command:
make test-project
Distributed under the GNU General Public LICENSE.
Contact me via:
- Docker Documentation - DevOps centric especially for development and deployment.
- Docker Compose Django Example - Deployment centric specific to Django projects.
- GeoDjango Documentation - WebGIS development using GeoDjango API.