littermap / littermap-aws-backend

Cloud-native backend for the Litter Map application -- (Join us on: https://discord.gg/JvEQMSQaYr)
https://littermap.com
GNU Affero General Public License v3.0
3 stars 2 forks source link
aws gis-platform serverless

Litter Map

Humanity’s calling for the next hundred years is restoring natural beauty to Mother Earth. We believe that the planet is more of a being to be in communion with, rather than a resource to be extracted. To assist in this mission, we are providing a platform to help with global pollution and litter cleanup. This work belongs to the future of the human race, and therefore, we are using technology to provide community support for the cleanup effort. Its host of features is not just valuable to our users, but also to the planet itself.

Mission

We are advancing humanity’s mission of waste and plastic-pollution cleanup for the protection of Nature from harm and to improve the lives of human and non-human inhabitants. We provide a hub for the mission of cleaning up the planet for many different individuals and organizations, and we aim to be the ultimate resource and center of the cleanup effort.

Background

We are a team of deeply devoted environmentalists who have a passion for restoring natural beauty. The planet is our common home, we borrow it from our children, and we inherit it from our parents. Caring for our common home with all living things will call forth into the future a life with less war, famine, destruction, climate disaster, hate, and division.

Community

Software development live sessions happen on our public discord channel.

Litter Map is also a registered nonprofit organization with open board meetings on discord.

Technical Documentation

This repository is the cloud native back-end for the Litter Map application.

Architecture

Requirements

Software involved

Useful utilities

Mobile apps

How to deploy

First install the requirements.

There are multiple ways to install a version of sam-cli, but if in doubt try installing with pip as a user package:

Configuring AWS

If you don't have an AWS account, create one.

Using your root AWS account, create a new user with programmatic access to the AWS API. Make sure this user has membership in a group with AdministratorAccess privileges.

Select the created user on the users page, and in the Security credentials tab choose Create access key. Select Show to see the secret access key. You will not have access to the key again using the web interface, so make sure to store it in a secure location. The reference guide explains AWS security credentials and best practices in detail.

With this information on hand, configure your AWS credentials with the access key and secret key along with the desired deployment region by running:

Your credentials will now be stored in a local file ~/.aws/credentials and the AWS command line tools will now be able to execute commands on behalf of this account.

If you've already done that before (e.g., in the context of another deployment), take a look at how to create and switch between named profiles. It is assumed that separate instances (testing, staging, production) will be deployed under their own separate user accounts. In this case, run:

Deploying the serverless stack

If this is a fresh clone of this source code repository, prepare the configuration files by running:

Fetch the latest package of the image scaling lambda function as described in "Provide a built package", because it is a compiled binary that is not included with the source code.

Prepare the stack template and function code for deployment:

Deploy the stack (ignore values you don't know for now):

Carefully note the values returned in the Outputs section. You will need them to configure the front-end client.

Authorize outside network access to the database (by default, access is restricted by security group rules):

Perform first-time initialization on the littermap database:

This will initialize PostGIS and create the tables and access roles.

Take note of the geometry_type_objectid value in the output. It is necessary to provide it after every database initialization, so redeploy the stack and manually specify the DBGeometryTypeOID parameter now:

If you forget the oid, you can retrieve it by running:

Configuring "Sign-in with Google" integration

Building and deploying native binary lambda functions

Each lambda function is packaged and deployed as a separate service, which means they do not all have to be implemented using the same technology stack. While a lambda function that is written entirely in one of the supported interpreted languages (JavaScript, Python, Ruby) requires a remote machine equipped with the appropriate runtime interpreter to execute it, a native lambda is designed to be run directly by the CPU. If the lambda function executable or any of its dependencies need to be provided as a binary, it will need to be built and packaged.

To provide a native binary lambda deployment package, there are two options:

Provide a built package

There is currently one native lambda:

If you have a built package ready, just place scale-image.zip into functions/scale-image/build/. The build/ directory may need to be created.

Build it

Native lambdas can be built inside a specialized container that has the appropriate reproducible build environment that is isolated from your host system.

Make sure you've got Docker installed.

The build environment can currently be built for one of two 64-bit CPU architectures: x86 or arm. Since all deration of concerns ployed lambda functions are set to require the newer ARM CPU (due to its cost effectiveness), to build a package that will execute when deployed, it must be built and packaged together with its native linked libraries inside an arm build environment container.

At this time, the only available build environment definition is for building lambdas from C++ source code using the official AWS C++ SDK and AWS C++ Runtime libraries. It also includes the libvips high performance image processing library. Additional build environments can be developed in the future that will allow building lambdas based on other technology stacks.

Either of the build environments (or both) can be built with:

If your host machine is one or the other and the architecture is not explicitly specified it will by default build an environment for the same architecture as your host machine.

Even if the deployed lambdas are specified to require an arm machine, an x86 build environment may come in handy for iterating during development if you are developing on an x86 machine because the native build process is much faster.

If the build environment isn't the same as your host machine's native architecture, Docker will run it using user space emulation and building the image may take an hour or longer. If it doesn't work out of the box, it may require having qemu installed along with binary format support.

Once you have one or both of these environments built, they should be listed with:

Now, to build scale-image for the arm architecture:

If the build process completes successfully, it will produce a deployment-ready zip package at functions/scale-image/build/scale-image.zip.

Deploying the front-end

The serverless stack includes S3 buckets for hosting the front-end and user uploaded media content. To deploy a version of the front-end:

If you turned on EnableCDN, the front-end will now available through the CloudFront CDN endpoint.

Updating the front-end

To deploy the latest version:

To deploy a specific branch or commit:

Don't forget to edit publish/config.json before publishing.

Manual interaction with the service

In the following instructions, replace $BASE with the API URL that looks something like:

Or with the CloudFront URL (if deployed with the CDN):

The active URL for the deployed API can be viewed by running:

Add a location (anonymous submit must be enabled):

Retrieve a location:

Log in (with Google):

Add a location as a logged in user (get the session value from the Set-Cookie reponse header):

Log out:

View today's event log (in UTC):

View event log for any particular day (specified in UTC):

Administration

API management

Export the API schema:

Database interaction

Perform arbitrary queries on the database by running:

For example, retrieve all the stored locations with:

The database can be completely reset by running:

Connect to the database as an administrator (must have postgresql installed to have the psql utility):

To see that you're logged into the database system as the correct user:

Show all tables in the world schema (as opposed to the public schema):

Show all locations stored in the locations table:

Type \help to see available database commands.

To save money while not using the database during development, it can be temporarily hibernated with:

Wake it back up with:

How to remove this service from the cloud

To take this service down, run:

If that doesn't go smoothly, troubleshoot the issue or delete the stack in the CloudFormation dashboard.

Development

The general procedure for changeset deployment after making changes is:

However, during development it can be much quicker to use sam sync. See:

For a better understanding, read:

Modifying the serverless stack definition

After making adjustments to the stack definition in template.yml, optionally check it for errors with:

If no errors are found, prepare the deployment files and then deploy the changes with:

After running sam build, the intermediate template is available at .aws-sam/build/template.yaml.

To change any parameter values before deployment, run sam deploy -g.

To learn more about the deployment process and options run:

Be aware that deleting or changing the properties of individual running resources manually (e.g. in the AWS dashboard) will result in stack drift and can create difficulties that must be resolved in order to manage the stack wtih sam.

tl;dr

Did you change the template code?

Did you change the JavaScript?

Did you update a native binary lambda function?

Need to adjust a stack configration parameter?

Tips

Knowledge resources

Serverless infrastructure with AWS

Videos

Reading

Amazon RDS database

Database used to store locations

Amazon RDS is a scalable relational database service that is API-compatible with PostgreSQL.

DynamoDB database

Database engine used to store user profiles, sessions, and event logs

DynamoDB is a fast and flexible NoSQL database that is simple by design but challenging to master. If used correctly, it will scale to terabytes and beyond with no performance degradation.

Technical guides

General articles

Geospatial indexing articles

Technical articles

More information

Security

Reference

Cheatsheets

Quick links

License

Copyright (C) Litter Map contributors (see AUTHORS.md)

This program is free software: you can redistribute it and/or modify it under the terms of the GNU Affero General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.

This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for more details.

You should have received a copy of the GNU Affero General Public License along with this program. If not, see https://www.gnu.org/licenses/.