SFTT API Specification
This is the official API specification for the SFTT back end. The back end is implemented as is described in the documentation below and should correspond exactly with how the back end behaves. If you find any inconsistencies please create a PR to amend the error.
JSON Web Tokens (JWT)
In every request header is a JWT. The JWT will contain the user's id value and the user's privilege level. It is assumed that the user making the request (as specified in the JWT header) is the person the action is being performed by.
Enums
Privilege Level
The privilege level enum is all the possible privilege levels a user can have. This is stored in the users table as the privilege_level field. The possible options are:
STANDARD
- A regular member of the platform and usually a volunteer for Speak for the Trees.ADMIN
- A more senior SFTT volunteer, might be in charge of a neighborhood or someone that works for SFTT. They are able to mark blocks for QA, change normal or admin user privilege levels and other activities that require elevated privileges.SUPER_ADMIN
- A super user with elevated privileges such as being able to import data into the database.
Site Owner
The site owner enum is all of the possible groups that a site can be owned by. This is stored in the sites table as the owner field. The possible options are:
ROW
- A Right of Way (Street) site. It is planted, owned, and maintained by the city of Boston.Park
- A Park site. It is planted, owned, and maintained by the city of Boston.State
- A site owned by the state (usually on MBTA or DCR land).Federal
- A site owned by the federal government.Private
- A site owned by a private company or resident.
Team Role
The team role enum is all the possible states a use can be in in relation to a team. This is stored in the users_teams table on the backend as the team_role field. The possible options are:
NONE
- The user is not on the team. This is possible after a user is rejected from a team or leaves a team.MEMBER
- The is a member of the team.LEADER
- The user is a leader of the team. This grants them special privileges such as being able to accept or reject pending members and being able to disband the team.PENDING
- The user has applied to the team but has not been accepted or rejected yet. If they're accepted they become a member, if they're rejected their status is set toNONE
A user is said to be on a team if their role is MEMBER
or LEADER
.
Reservation Action
The reservation action enum is all the possible action types a reservation can have. This is how blocks are marked as open, complete, reserved, etc. It is stored in the reservation tables as the action_type field. The possible options are:
RESERVE
- Marks a block as reserved.COMPLETE
- Marks a block as completed.RELEASE
- Marks a block as released, meaning a user cancelled their reservation and the block is now open again. Anyone can reserve it again now.UNCOMPLETE
- Marks a block as uncomplete, meaning an admin opened the block back up from its previous state. Anyone can reserve it again now.QA
- Indicates a block needs QA. It will remain in this state until an admin either approves or denies the completion. If approved, the block will be markedCOMPLETE
. If denied, the block will be markedUNCOMPLETE
.
Auth Router
This router is used to authenticate users. It handles logins, logouts, signups but also things like resetting passwords and secret keys. All of these parts are public, as in users don't need to be authenticated yet to call these routes.
Login
POST api/v1/user/login
Used for logging in.
Request Body
1 2 3 4 |
|
An EMAIL is a string representing a user's email.
Responses
201 Created
1 2 3 4 |
|
400 Bad Request
Malformed request.
401 Unauthorized
The username/password combination is invalid.
Sign Up
POST api/v1/user/signup
Used for signing up a new user.
Request Body
1 2 3 4 5 6 7 |
|
- EMAIL: Is a valid email string.
- PASSWORD: Is a valid password string that is at least 8 characters.
Responses
201 Created
The username and email are still available, and an account has been successfully created.
1 2 3 4 |
|
400 Bad Request
Malformed request body.
409 Conflict
The given email or username is already in use.
1 |
|
1 |
|
Log Out
DELETE api/v1/user/login
Used for logging out.
Request Body
1 2 |
|
Responses
204 No Content
Logout successful.
Refresh Access Token
POST api/v1/user/login/refresh
Used for getting a new access token.
Request body
1 2 3 |
|
Responses
201 Created
The refresh token is valid and has not yet expired. Response includes a new unique access_token.
1 2 3 |
|
401 Unauthorized
The refresh token is invalid.
Request Password Reset
POST api/v1/user/forgot_password/request
Used to send a reset password email to a user if they have forgotten their password
Request Body
1 2 3 |
|
Responses
200 OK
The email was sent to the user successfully
400 BAD REQUEST
The given email is not associated with any user account
Reset Password
POST api/v1/user/forgot_password/reset
Used to reset a user's password after they have requested a forget password link. The secret key will be contained in the forgot password link.
Request Body
1 2 3 4 |
|
Passwords should be strings with length >= 8 characters.
Responses
200 OK
The user's identity was confirmed and the password was changed successfully.
400 BAD REQUEST
The new password that was given is an invalid password.
401 UNAUTHORIZED
The given secret key is invalid and does not refer to an account or was created too long ago to be valid.
Create Secret Key
This route still needs to be implemented
GET api/v1/user/create_secret/:user_id
Used to create secret keys for users.
Request Body
None. The user_id
parameter is the id of the user the secret key should be linked to.
Responses
200 OK
A secret key was created and stored for the given user.
400 BAD REQUEST
The user_id
is not associated with a user.
Verify Secret Key
GET api/v1/user/verify/:secret_key
Used for confirming an account's email.
Request Body
None. The secret key parameter is a randomly generated key and sent to the user to verify their email.
Responses
200 OK
The user's secret key has been verified.
401 Unauthorized
The secret key is invalid or expired.
Users Router
This router is used for routes that affects user accounts. It can only be called when a user is authenticated, as opposed to the auth router which is public.
Change Username
POST api/v1/protected/user/change_username
Allows a user to change their username. The new username must not be in use already.
Request Body
1 2 3 4 |
|
Responses
200 OK
The username change was successful.
400 BAD REQUEST
If the request was malformed.
401 Unauthorized
The password does not match the calling user's current password.
409 Conflict
The given newUsername
is already in use.
Change Password
POST api/v1/protected/user/change_password
Allows a user to change their password when already authenticated. Passwords should be strings with a length of at least 8 characters.
Request Body
1 2 3 4 |
|
Responses
200 OK
The password change was successful.
400 BAD REQUEST
If the request was malformed.
401 Unauthorized
The currentPassword does not match the calling user's current password.
Change Email
POST api/v1/protected/user/change_email
Allows a user to change their email address. The new email address cannot be in use already. Also sends the user a confirmation email.
Request Body
1 2 3 4 |
|
Responses
200 OK
The email address change was successful.
400 BAD REQUEST
If the request was malformed.
401 Unauthorized
The password does not match the calling user's current password.
409 Conflict
The given newEmail
is already in use.
Get User Data
GET api/v1/protected/user/data
Get the calling user's data.
Request Body
No request body.
Responses
200 OK
1 2 3 4 5 6 |
|
400 BAD REQUEST
If the calling user does not exist.
Get User Teams
GET api/v1/protected/user/teams
Get all the teams the calling user is part of.
Request Body
No request body.
Responses
200 OK
1 2 3 4 5 6 7 8 9 |
|
400 BAD REQUEST
If the calling user does not exist.
Delete User
POST api/v1/protected/user/delete
Sets this users deleted_at timestamp to now, thereby marking this account as deleted in the database.
Request Body
1 2 3 |
|
Responses
200 OK
Successfully deleted this user.
400 BAD REQUEST
If the user_id
is not associated with a user.
401 Unauthorized
If the password is wrong.
Change Privilege Level (Admin Only)
POST api/v1/protected/user/change_privilege
Allows admins to create more admins or demote other admins.
Request Body
1 2 3 4 5 |
|
Responses
200 OK
The privilege level change was successful.
400 Bad Request
The requested user already has the given privilege level.
400 Bad Request
There is no user associated with the given email.
400 BAD REQUEST
If the request was malformed.
401 Unauthorized
The password does not match the calling user's current password.
401 Unauthorized
The user does not have a high enough privilege level to change the given users privilege level.
- An 'ADMIN' user tries to change the privilege level of a 'SUPER_ADMIN'
- An 'ADMIN' user tries to give another user 'SUPER_ADMIN' privilege
Create Child Account (Admin Only)
POST api/v1/protected/user/create_child
Allows admins to create a child user linked to the admin's account through the parent_accounts table.
Request Body
(Request fields are for the child account)
1 2 3 4 5 6 7 |
|
Responses
201 Created
The username and email are still available, and a child user has been successfully created.
400 Bad Request
Malformed request body.
401 Unauthorized
The user does not have a high enough privilege level to create a child user.
409 Conflict
The given email or username is already in use.
1 |
|
1 |
|
Get Child User Data
GET api/v1/protected/user/child_data
Get the user data for all of the calling user's child accounts, including their first and last names, emails, and usernames.
Request Body
No request body.
Responses
200 OK
1 2 3 4 5 6 7 8 9 10 11 |
|
400 BAD REQUEST
If the calling user does not exist.
Map Router
This router is used to retrieve the data necessary to render blocks, neighborhoods and sites (plantings sites and trees). It makes a call to the backend, which returns the required data from the database in GeoJSON format. The router is public since much of this information is also rendered on the home page.
Get All Blocks in GeoJSON
GET api/v1/map/blocks
Returns all the blocks in GeoJSON format.
Request Body
No request body.
Responses
200 OK
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 |
|
Get All Neighborhoods in GeoJSON
GET api/v1/map/neighborhoods
Returns all the neighborhoods in GeoJSON format. The completion_perc
field in the properties is the percentage of blocks marked as completed compared to the total amount of blocks in that neighborhood.
Request Body
No request body.
Responses
200 OK
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 |
|
Get All Sites in GeoJSON
GET api/v1/map/sites
Returns all the sites in GeoJSON format.
Request Body
No request body.
Responses
200 OK
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 |
|
Import Router
The import router will be used to fill the database tables that have either static information, such as the blocks and neighborhoods tables, or if already recorded information needs to be carried over. All routes can only be called by super admins.
The geometry
field represents the polygon, multi-polygon or other geometric shape that is associated with the the feature. This will consist of the entire geometry
field found in a .geojson
file. The JSON will be encoded as a String when sent to the import API. JSON example:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 |
|
Import Blocks (Super Admin Only)
POST api/v1/protected/import/blocks
Used to import blocks into the database. Since blocks reference neighborhoods with a foreign key make sure all neighborhoods are imported first.
Request Body
1 2 3 4 5 6 7 8 9 10 11 12 |
|
Responses
200 OK
Blocks imported successfully.
400 BAD REQUEST
If the request was malformed.
401 UNAUTHORIZED
If the user is not a super admin.
Import Neighborhoods (Super Admin Only)
POST api/v1/protected/import/neighborhoods
Used to import neighborhoods into the database. Must be called before importing blocks since blocks reference neighborhoods.
Request Body
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
|
Responses
200 OK
Neighborhoods imported successfully.
400 BAD REQUEST
If the request was malformed.
401 UNAUTHORIZED
If the user is not a super admin.
Import Reservations (Super Admin Only)
POST api/v1/protected/import/reservations
Used to import reservations into the database. The referenced blocks, users and teams must be in the database. If they're not an error will occur when the "invalid" reservation is reached. userId
and teamId
can be left blank, in which case the reservation will be attributed to the super admin calling the route. performedAt
must be in the form "mm\/dd\/yyyy"
.
Request Body
1 2 3 4 5 6 7 8 9 10 11 12 |
|
Responses
200 OK
Reservations imported successfully.
400 BAD REQUEST
If the request was malformed.
401 UNAUTHORIZED
If the user is not a super admin.
Import Sites (Super Admin Only)
POST api/v1/protected/import/sites
Used to import sites into the database. See below for a description of each ambiguous field.
status
: "Alive" or "Dead but standing"
confidence
: Confidence in species or genus identification
coverage
: Percent of tree that is green
pruning
: Amount of pruning seen in tree
condition
: Tree condition ("Good", "Fair", "Poor", "Dead")
discoloring
: Discoloring of leaves
leaning
: Tree is leaning
constricting_grate
: Metal grate constricting tree trunk growth
wounds
: Trunk wounds
pooling
: Pooling water in tree pit
stakes_with_wires
: Wooden stakes near tree WITH wires around tree
stakes_without_wires
: Wooden stakes near tree WITHOUT wires
lights
: Lights in tree
bicycle
: Bicycle locked to tree trunk
bag_empty
: Watering bag that is empty
bag_filled
: Watering bag that has water in it
tape
: Tape around trunk
site_type
: "Pit", "Continuous/Lawn" or "Planter"
material
: Material in site ("Plain dirt", "mulch", "grass", etc.)
fence
: Do you see a fence or perimeter guard?
trash
: Do you see loose trash?
wires
: Wires overhead?
grate
: Do you see a metal grate, either with or without a tree?
melnea_cass_trees
: Part of a program, not used anymore, only in database
mcb_number
: Melnea Cass number, not used anymore, only in database
tree_dedicated_to
: Tree dedication, not used currently
Request Body
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 |
|
Responses
200 OK
Sites imported successfully.
400 BAD REQUEST
If the request was malformed.
401 UNAUTHORIZED
If the user is not a super admin.
Neighborhoods Router
The neighborhoods router is used to handle all the neighborhoods.
Edit Canopy Coverage (Admin Only)
POST api/v1/protected/neighborhoods/:neighborhood_id/edit_canopy
Used to edit the specified neighborhood's canopy_coverage
.
Request Body
1 2 3 |
|
Responses
200 OK
Neighborhood's canopy_coverage
successfully edited to canopyCoverage
.
400 BAD REQUEST
If the request body is malformed or if the given canopyCoverage
is negative or greater than one.
401 UNAUTHORIZED
If the calling user is not an admin.
Send Email (Admin Only)
POST api/v1/protected/neighborhoods/send_email
Sends an email with the given subject and content to users with the given emails.
Request Body
1 2 3 4 5 6 7 8 9 |
|
Responses
200 OK
Email successfully sent to the given users.
400 BAD REQUEST
If the request body is malformed.
401 UNAUTHORIZED
If the calling user is not an admin.
Sites Router
The sites router is used to handle all the sites and create new ones. A site can be either a planting site without a tree or there can be a tree present. They are differentiated by the field tree_present
in the site_entries
table.
Add Site
POST api/v1/protected/sites/add
Used to create a new site. Will create two entries in the database. One in the sites
table to record the permanent information (location, address, block_id) and one in the site_entries
table to record the state of the site (species, foliage, leaning, trash, etc.). Every field besides lat
, lng
, city
, zip
, address
, and owner
is allowed to be NULL
.
NULL
BOOLEAN
s will be treated as false
.
All measurements should be given in inches. Note that while some measurements are accepted as strings to work with existing data, new measurements should be given as numbers and assumed to be in inches.
Request Body
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 |
|
Responses
200 OK
Site successfully added.
400 BAD REQUEST
If the request body is malformed.
Add Sites (Admin Only)
POST api/v1/protected/sites/add_sites
Used to add multiple new sites. The request body is the content of a CSV file. Every column besides lat
, lng
, and neighborhoodId
is allowed to be NULL
and optional. All columns may appear in any order. Blank cell values are treated as default or empty values (null
, ""
, false
, etc.).
For more information, refer to the documentation on adding a site (https://docs.c4cneu.com/sftt/sftt-api-spec/#add-a-site).
Request Body
1 2 3 |
|
Responses
200 OK
All sites successfully added.
400 BAD REQUEST
If the request body is malformed.
401 UNAUTHORIZED
If the calling user is not an admin.
Add Potential Site
This route still needs to be implemented
POST api/v1/protected/sites/create_potential
Creates a potential site, which is a place where the city could potentially place a planting site. Below is a description of each field.
light_pole
: 10 feet from light pole
drive_way
: 10 feet from driveway
hydrant
: 10 feet from hydrant
intersection
: 20 feet from intersections
building_entrance
: Not in front of a building entrance
Request Body
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
|
Responses
200 OK
Site successfully added.
400 BAD REQUEST
If the request body is malformed.
Get Site
GET api/v1/sites/:site_id
Returns all the info about a specific site. This includes all the entries linked to the site, in reverse chronological order (most recent first). Measurements are given in inches.
Request Body
No request body.
Responses
200 OK
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 |
|
400 BAD REQUEST
If the site_id
specified is invalid.
Edit Site (Admin Only)
POST api/v1/protected/sites/:site_id/edit
Used to edit the features of a site. This is done by querying the appropriate site and setting the given features. Only the block_id
field is not required.
Request Body
1 2 3 4 5 6 7 8 9 10 |
|
Responses
200 OK
Features of site successfully edited.
400 BAD REQUEST
If any of the specified site_id
, block_id
, or neighborhood_id
are invalid. An invalid id is a non-existent id or the id of a deleted site, block, or neighborhood.
401 UNAUTHORIZED
If the calling user is not an admin.
Delete Site (Admin Only)
POST api/v1/protected/sites/:site_id/delete
Used to delete a site. This is done by setting deleted_at
in the sites
table to the current timestamp.
Request Body
No request body.
Responses
200 OK
Site successfully deleted.
400 BAD REQUEST
If the site_id
specified is invalid.
401 UNAUTHORIZED
If the calling user is not an admin.
Add Site Entry
POST api/v1/protected/sites/:site_id/update
Used to update the state of a site. A new entry will be made in the site_entries
table that will
record the latest state of the site and so update the state of that site. Every field can be NULL
.
NULL
BOOLEAN
s will be treated as false
.
All measurements should be given in inches. Note that while some measurements are accepted as strings to work with existing data, new measurements should be given as numbers and assumed to be in inches.
Request Body
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 |
|
Responses
200 OK
Site successfully updated.
400 BAD REQUEST
If the request body is malformed. If the id specified is invalid. An invalid id is a non-existent id or the id of a deleted site.
Edit Site Entry (Admin Only)
POST api/v1/protected/sites/edit_entry/:entry_id
Updates a site's existing site entry with the given values. Every field can be NULL
. NULL
BOOLEAN
s will be treated as false
. All measurements should be given as numbers in inches.
Updates the user_id
and updated at
site entry attributes to the logged in admin and time of editing respectively.
Request Body
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 |
|
Responses
200 OK
Specified site entry successfully edited.
400 BAD REQUEST
If the request body is malformed.
If the entry_id
specified is not associated with an existing site entry.
401 UNAUTHORIZED
If the calling user is not an admin.
Delete Site Entry (Admin Only)
This route still needs to be implemented
DELETE api/v1/protected/sites/delete_entry/:entry_id
Deletes the specified site entry from the database along with all other information related to the entry. Only admins and super admins can perform this action.
This action cannot be done if the site associated with the given entry has no other entries, i.e. this action would delete the site's only entry.
Request Body
No request body.
Responses
200 OK
Site entry successfully deleted.
400 BAD REQUEST
If the entry_id
specified is not associated with an existing activity.
401 UNAUTHORIZED
If the calling user is not an admin.
403 FORBIDDEN
If deleting this entry would leave the associated site with no other entries.
Get Unapproved Images (Admin only)
This route still needs to be implemented
GET api/v1/protected/sites/unapproved_images
Retrieves any user-uploaded images that are awaiting approval from admins that meet the given criteria. Only Admins or Super Admins can perform this action.
An image matches the criteria if:
-
submittedStart
: the image was submitted on or after this date -
submittedEnd
: the image was submitted on or before this date -
siteIds
: the site of the entry the image is for is in this list -
neighborhoodIds
: the neighborhood of the image's site is in this list
If a condition is null, i.e. not specified, then that condition will not be checked.
Request Params
Note: since this is a GET request, these parameters will come from the request URL and not the body.
1 2 3 4 5 6 |
|
Responses
200 OK
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
|
400 BAD REQUEST
If the request parameters are incorrect.
401 UNAUTHORIZED
If a standard user attempts to call this route.
Upload Site Image (Admin and Owner only)
POST api/v1/protected/sites/upload_image/:entry_id
Adds an image of a site's most recent site entry. Any user can upload an image, as long as they have less than 20 images currently awaiting approval. Admins are exempt from this limit. The imageEncoding
field must be a valid base 64 encoding of the image to upload.
Request Body
1 2 3 4 |
|
Responses
200 OK
Image successfully added.
400 BAD REQUEST
If the request body is malformed. If the specified site ID is non-existent. If the given base64 encoding of the image is non-null and invalid.
403 UNAUTHORIZED
If a standard user with 20 or more images awaiting approval tries to upload an image.
Delete Site Image (Admin and Uploader only)
DELETE api/v1/protected/sites/delete_image/:image_id
Deletes the site image with the given image_id
. Only the image's uploader, Admins, or Super Admins can perform this action.
Request Body
No request body.
Responses
200 OK
Image successfully deleted.
400 BAD REQUEST
If the image_id
specified is not associated with an existing site image.
401 UNAUTHORIZED
If a non-admin or a user that didn't upload the image tries to perform this action.
Approve site image (Admin only)
PUT api/v1/protected/sites/approve_image/:image_id
Approves the site image with the given image_id
, allowing it to be shown publically on site pages. Only Admins or Super Admins can perform this action.
Request Body
No request body.
Responses
200 OK
Image successfully approved.
400 BAD REQUEST
If the image_id
specified is not associated with an existing site image.
401 UNAUTHORIZED
If a non-admin tries to perform this action.
Reject site image (Admin only)
DELETE api/v1/protected/sites/reject_image/:image_id
Rejects the site image with the given image_id
, removing it from the database and sending the uploader a notification email with the reason, if given. Only Admins or Super Admins can perform this action.
Request Body
1 2 3 |
|
Response
200 OK
Image successfully deleted and rejection email successfully sent.
400 BAD REQUEST
If the image_id
specified is not associated with an existing site image.
401 UNAUTHORIZED
If a non-admin tries to perform this action.
Mark Site for QA (Admin Only)
This route still needs to be implemented
POST api/v1/protected/sites/:site_id/qa
Used to indicate that a site needs to be checked. This can be done for an individual site or can be part of marking an entire block for QA and then every site associated with that block will be marked for QA. This is done by creating a new entry in the site_entries
table with qa
set to true
.
Request Body
No request body.
Responses
200 OK
Site successfully marked for QA.
400 BAD REQUEST
If the site_id
specified is invalid.
401 UNAUTHORIZED
If the calling user is not an admin.
Adopt Site
POST api/v1/protected/sites/:site_id/adopt
Adopt the given site. Creates a record in the adopted sites table linking the user and the site.
Request Body
No request body.
Responses
200 OK
Site successfully marked as adopted.
400 BAD REQUEST
If the site_id
specified does not exist or is already adopted.
Parent Adopt Site for Child
POST api/v1/protected/sites/:site_id/parent_adopt
Adopt the given site on behalf of a specified child account. Creates a record in the adopted sites table linking the child user and the site.
Request Body
1 2 3 |
|
Responses
200 OK
Site successfully marked as adopted.
400 BAD REQUEST
If the site_id
specified does not exist or is already adopted.
400 BAD REQUEST
If the user corresponding to the childUserId either does not exist or is not a child account of the parent user.
Unadopt Site
POST api/v1/protected/sites/:site_id/unadopt
Remove this site as adopted for the calling user. Removes the record from the adopted sites table.
Request Body
No request body.
Responses
200 OK
Successfully removed site as adopted.
400 BAD REQUEST
If the site_id
specified does not exist.
400 BAD REQUEST
If the site is not adopted by the user.
Force Unadopt Site (Admin only)
POST api/v1/protected/sites/:site_id/force_unadopt
Remove this site as adopted for whoever currently adopts it. Can only be called by a user of a higher privilege level than the adopter. Removes the record from the adopted sites table.
Request Body
No request body.
Responses
200 OK
Successfully removed site as adopted.
400 BAD REQUEST
If the site_id
specified does not exist.
401 UNAUTHORIZED
If the user calling is not of the proper privilege level.
Get Adopted Sites
GET api/v1/protected/sites/adopted_sites
Get all the adopted sites of the calling user.
Request Body
No request body.
Responses
200 OK
Return a list of integers representing the site ID's of the users adopted sites. Can be an empty list.
1 2 3 4 5 6 7 8 |
|
Record Stewardship Activity
POST api/v1/protected/sites/:site_id/record_stewardship
Records a stewardship activity for the given site. Date is the day on which the activity was performed, which can be in the past if the user is adding a past activity. Indicate True
if the activity (watered, mulched, etc.) was completed, else False
. At least one activity must be True
.
Request Body
1 2 3 4 5 6 7 8 |
|
Responses
200 OK
Activity successfully recorded.
400 BAD REQUEST
If the site_id
specified does not exist.
400 BAD REQUEST
If all activities are False
.
Parent Record Stewardship Activity for Child
POST api/v1/protected/sites/:site_id/parent_record_stewardship
Records a stewardship activity on behalf of the specified child account. Date is the day on which the activity was performed, which can be in the past if the parent is adding a past activity for the child. Indicate True
if the activity (watered, mulched, etc.) was completed, else False
. At least one activity must be True
.
Request Body
1 2 3 4 5 6 7 8 9 |
|
Responses
200 OK
Activity successfully recorded.
400 BAD REQUEST
If the site_id
specified does not exist.
400 BAD REQUEST
If the user corresponding to the childUserId either does not exist or is not a child account of the parent user.
400 BAD REQUEST
If all activities are False
.
Edit Stewardship Activity (Admin and Author Only)
POST api/v1/protected/sites/edit_stewardship/:activity_id
Edits an existing stewardship activity. Indicate True
if the activity (watered, mulched, etc.) was completed, else False
. At least one activity must be True
. date
is the day on which the activity was performed, which can be in the past if the activity was performed in the past.
Request Body
1 2 3 4 5 6 7 8 |
|
Responses
200 OK
Activity information successfully edited.
400 BAD REQUEST
If the activity_id
specified is not associated with an existing activity.
400 BAD REQUEST
If all activities are False
.
401 UNAUTHORIZED
If the calling user is not an admin or the user listed on the activity.
Delete Stewardship Activity (Admin and Author Only)
POST api/v1/protected/sites/delete_stewardship/:activity_id
Deletes the stewardship activity from the database. This is in case either SFTT believes the activity was not performed or if the activity recorder made a mistake.
Request Body
No request body.
Responses
200 OK
Activity successfully removed.
400 BAD REQUEST
If the activity_id
specified is not associated with an existing activity.
401 UNAUTHORIZED
If the calling user is not an admin or the user listed on the activity.
Get Stewardship Activities By Site
GET api/v1/sites/:site_id/stewardship_activities
Returns all the recorded stewardship activities for the indicated site. Array will be sorted by date, from most recent to least recent, and a secondary sort on id.
Request Body
No request body.
Responses
200 OK
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
|
400 BAD REQUEST
If the site_id
specified does not exist.
Name Site Entry
POST api/v1/protected/sites/:site_id/name_entry
Names the latest site entry of the given site. If the entry is already named, renames it. If passed an empty string, resets the name.
Request Body
1 2 3 |
|
Responses
200 OK
Site entry successfully named.
400 BAD REQUEST
If the site_id
specified does not exist or if name
is more than 60 characters long or name
is NULL
.
401 UNAUTHORIZED
If the user is not the site's adopter.
Calculate Tree Benefits
GET api/v1/sites/:site_id/calculate_benefits
Calculates and returns the environmental impacts of the latest site entry of the site with the given site_id
. This includes the following values: energy conserved, stormwater filtered, air quality improved, carbon dioxide removed, and carbon dioxide stored, as well as the amount of money saved for each category.
Request Body
No request body.
Responses
200 OK
1 2 3 4 5 6 7 8 9 10 11 12 |
|
400 BAD REQUEST
If there is no site with the given site_id
.
Filter Sites (Admin Only)
GET api/v1/protected/sites/filter_sites
Return data on sites matching all of the given criteria: common names of tree, range of adopted date, range of last stewardship activity recorded date, and neighborhood. A criterion is ignored (i.e. sites are not filtered on a criterion) if its value is NULL
. See below for a description of each criterion.
A site matches the criterion if:
treeCommonNames
: the common names of the site's latest site entry is in the listadoptedStart
: the site has been adopted by a user on or after this dateadoptedEnd
: the site has been adopted by a user on or before this datelastActivityStart
: the site's latest stewardship activity was recorded on or after this datelastActivityEnd
: the site's latest stewardship activity was recorded on or before this dateneighborhoodIds
: the site is located in a neighborhood in the listactivityCountMin
: the number of stewardship activities recorded by the site's current adopter is greater than or equal to this minimumactivityCountMax
: the number of stewardship activities recorded by the site's current adopter is less than or equal to this maximum
Request Body
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
|
Responses
200 OK
In the JSON below, adopterId
is the adopter's user ID, adopterActivityCount
is the number of stewardship activities performed within the given lastActivity
range, if applicable, and lastActivityWeeks
is the number of weeks since the last stewardship activity.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
|
400 BAD REQUEST
If the request body is malformed.
401 UNAUTHORIZED
If the calling user is not an admin.
Report Site For Issues
This route still needs to be implemented
POST api/v1/protected/sites/:site_id/report
Reports the site for any issues on the site page, such as incorrect information or inapproriate names. Making a report sends an email to admins with the given information.
Request Body
1 2 3 4 |
|
Responses
200 OK
Report was successfully sent.
400 BAD REQUEST
If the request body is malformed, or if reason
is empty.
404 NOT FOUND
If the given site does not exist.
Report Router
The report router is used to get reports on the status of trees and adoptions.
Get Community Stats
GET api/v1/report/stats
Get statistics on trees and adoptions available to the public.
Request Body
No request body.
Responses
200 OK
Returns the number of current adopters, trees currently adopted, and all stewardship activities ever performed.
1 2 3 4 5 6 7 |
|
Get Adoption Report (Admin Only)
GET api/v1/protected/report/adoption
Get information about adopted sites.
Request Body
No request body.
Responses
200 OK
Returns a list of information about adopters and stewardship activities for each currently adopted site, grouped by user and in alphabetical order.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
|
401 UNAUTHORIZED
If the user is not an admin.
Get Adoption Report as CSV (Admin Only)
GET api/v1/protected/report/csv/adoption?previousDays=INT
Get information about adopted sites as a CSV.
Query Params
previousDays: INT
The number of days in the past that the report covers. The report only includes information about
sites adopted in the past previousDays
. This value should be specified, by default it is set to
include all adopted sites.
Responses
200 OK
Returns a list of information about adopters and stewardship activities for each currently adopted site, grouped by user and in alphabetical order, as a CSV formatted as a string.
1 2 |
|
400 BAD REQUEST
If the previousDays
parameter is not an integer, such as a decimal or a non-numeric value.
401 UNAUTHORIZED
If the user is not an admin.
Get Stewardship Report (Admin Only)
GET api/v1/protected/report/stewardship
Get information about all stewardship activities.
Request Body
No request body.
Responses
200 OK
Returns a list of information about adopters and the actions performed for each stewardship activity ever performed, grouped by site_id
and in reverse chronological order (most recent first).
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
|
401 UNAUTHORIZED
If the user is not an admin.
Get Stewardship Report as CSV (Admin Only)
GET api/v1/protected/report/csv/stewardship?previousDays=INT
Get information about stewardship activities as a CSV.
Query Params
previousDays: INT
The number of days in the past that the report covers. The report only includes information about
stewardship activities performed in the past previousDays
. This value should be specified, by default it is set to
include all stewardship activities.
Responses
200 OK
Returns a list of information about adopters and the actions performed for each stewardship activity
ever performed, grouped by site_id
and in reverse chronological order (most recent first),
as a CSV formatted as a string.
1 2 |
|
400 BAD REQUEST
If the previousDays
parameter is not an integer, such as a decimal or a non-numeric value.
401 UNAUTHORIZED
If the user is not an admin.
Reservations Router
This router is used to manage reservations. A reservation is when a user claims a block and thereby commits to going around this block and mapping every tree they see on their side of the block. A block is completed when they have walked around the block, mapped every tree and subsequently confirmed on the app that they did completed those activities. The way our reservation system is set is that it creates a new entry into the reservation table every time an action is performed on a block. These possible actions are:
reserve
- Reserve the given block for the given user.complete
- Complete the given block.release
- Release the given block, meaning to cancel the reservation.uncomplete
- Admin only. Used to invalidate a completed reservation for any reason (not actually completed, want to inventory the block again, etc.)QA
- Admin only. Mark this block for QA, meaning that SFTT wants to go through the trees counted here and make sure everything looks okay.
If the user specifies doesn't specify a team at the time of reservation the user is solely responsible for the block. If they do specify a team, then their team can also complete this block for them. This leads to two options when completing a block.
- The user who reserved the block completes the block, and can choose which, if any, team to credit it to. Credit goes to the reserving user and the team of their choosing.
- A teammate completes the block. The teammate cannot specify the team, since it was reserved by another user. Credit goes to the user who completes the block, not the reserving user, and their shared team.
Make a Reservation
POST api/v1/protected/reservations/reserve
Must be called on an open (not marked reserved, completed or QA) block. Will create a reservation for the user making the request for the given block. team_id
is the team that the user wants to count this block with. This can always be left NULL
. The purpose of specifying a team at the time of reservation is that it allows other team members to complete this block.
Request Body
1 2 3 4 |
|
Responses
200 OK
This block was reserved successfully.
400 BAD REQUEST
If there is not a block associated with the given block_id
.
400 BAD REQUEST
If there is not a team associated with the given team_id
.
400 BAD REQUEST
If the block does not have status 'open'.
401 UNAUTHORIZED
If the user is not a member of the given team.
Complete a Reservation
POST api/v1/protected/reservations/complete
Must be called on a block reserved by the user or by a team they're on. team_id
is the team that the user wants to credit with this block completion. This can always be left NULL
.
Request Body
1 2 3 4 |
|
Responses
200 OK
This reservation was completed successfully.
400 BAD REQUEST
If the block_id
specified is not associated with an existing block.
400 BAD REQUEST
If the team_id
specified is not associatd with an existing team.
400 BAD REQUEST
If the block does not have status 'reserved'.
401 UNAUTHORIZED
If the user is not a member of the given team.
Release a Reservation
POST api/v1/protected/reservations/release
Must be called on a reservation belonging to the user or a team they're the leader of.
Request Body
1 2 3 |
|
Responses
200 OK
This reservation was cancelled successfully.
400 BAD REQUEST
If the block_id
specified is not associated with an existing block.
400 BAD REQUEST
If the block does not have status 'reserved'.
Uncomplete a Reservation (Admin Only)
POST api/v1/protected/reservations/uncomplete
Can only by called by admins. Will invalidate the last completion for the given block and opens the block back up for inventory.
Request Body
1 2 3 |
|
Responses
200 OK
This reservation was marked as incomplete successfully.
400 BAD REQUEST
If the block_id
specified is not associated with an existing block.
400 BAD REQUEST
If the block does not have status 'complete'.
Mark for QA (Admin Only)
POST api/v1/protected/reservations/qa
Can only by called by admins on completed blocks. Will indicate that this block needs QA.
Request Body
1 2 3 |
|
Responses
200 OK
This block has been selected for QA.
400 BAD REQUEST
If the block_id
specified is not associated with an existing block.
401 UNAUTHORIZED
If the calling user is not an admin.
Pass QA (Admin Only)
POST api/v1/protected/reservations/pass_qa
Can only by called by admins on blocks with a QA status. Will duplicate the completion entry from before it was marked for QA and add it as a new entry for the block completion. This preserves the QA as part of the blocks record and returns the block back to its previous state from before it was marked for QA.
Request Body
1 2 3 |
|
Responses
200 OK
This block has passed QA.
400 BAD REQUEST
If the block_id
specified is not associated with an existing block.
401 UNAUTHORIZED
If the calling user is not an admin.
Fail QA (Admin Only)
POST api/v1/protected/reservations/fail_qa
Can only by called by admins on blocks with a QA status. Will mark the block as open by using the UNCOMPLETE
action.
Request Body
1 2 3 |
|
Responses
200 OK
This block has failed QA.
400 BAD REQUEST
If the block_id
specified is not associated with an existing block.
401 UNAUTHORIZED
If the calling user is not an admin.
Teams Router
This router is used to manage teams. A team consists of a group of users which work together to reach their set goals. Teams can have a leader, members and pending members. Users can also be marked as having NONE
team role, meaning they have left the team or have been rejected.
Create a Team
POST api/v1/protected/teams/create
Create a team. The team will only contain the member that created it who is now specified as the team leader. It will not have any goals.
Request Body
1 2 3 4 5 6 7 8 |
|
Responses
200 OK
Returns the same response as the "Get a Team" route for the newly created team.
400 BAD REQUEST
If the team name is taken or if any of the email addresses is invalid.
Get a Team
Used to get all the information about a given team. The team_role
field for each user is one of the values in the team roles enum.
GET api/v1/protected/teams/:team_id
Request Body
No request body.
Responses
200 OK
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 |
|
400 BAD REQUEST
If the team_id
specified is not associated with an existing team.
Add a Goal
POST api/v1/protected/teams/:team_id/add_goal
Team leader only. Adds a goal to this team's list of goals.
Request Body
1 2 3 4 5 |
|
400 BAD REQUEST
If the goal is negative.
400 BAD REQUEST
If the complete_by
date is before the start_at
date.
400 BAD REQUEST
If the team_id
specified is not associated with an existing team.
401 UNAUTHORIZED
If the calling user is not team leader.
Delete a Goal
Team leader only. Deletes a goal from this team's list of goals. Simply removes the record from the table.
POST api/v1/protected/teams/:team_id/delete_goal/:goal_id
Request Body
No request body.
400 BAD REQUEST
If the goal_id
specified is not associated with an existing goal.
400 BAD REQUEST
If the team_id
specified is not associated with an existing team.
401 UNAUTHORIZED
If the calling user is not team leader.
Invite a User
This route still needs to be implemented
POST api/v1/protected/teams/:team_id/invite
Invite someone to join a team. Will send an email to all specified people that includes a link. Link will direct them to the team page where they can join once they are authenticated. If one of the email addresses is invalid or the user is already on the team that invite will not be send out, the other ones will be and a 200 OK
response is returned.
Request Body
1 2 3 4 5 6 7 8 9 |
|
Responses
200 OK
Users invited.
400 BAD REQUEST
If the team_id
specified is not associated with an existing team.
401 UNAUTHORIZED
If the calling user is not team leader.
Get Applicants
GET api/v1/protected/teams/:team_id/applicants
Get the userIds for anyone that has requested to join this team as a map from userId to the "PENDING" team status
Request Body
No request body.
Responses
200 OK
1 2 3 4 5 6 7 |
|
400 BAD REQUEST
If the team_id
specified is not associated with an existing team.
Apply to a Team
POST api/v1/protected/teams/:team_id/apply
Apply to join this team. Any member can apply to join a team that they are not currently on. They will have to be approved by the team leader before becoming an actual member of the team.
Request Body
No request body.
Responses
200 OK
Applied successfully.
400 BAD REQUEST
If the team_id
specified is not associated with an existing team.
400 BAD REQUEST
If the user is already on the team or the user's status on this team is "PENDING".
Approve a User
POST api/v1/protected/teams/:team_id/applicants/:user_id/approve
Team Leader only. Approve this applicant's request to join the team. The user_id will be the same as the id returned in the GET applicants API call.
Request Body
No request body.
Responses
200 OK
This member has joined the team.
400 BAD REQUEST
If the team_id
specified is not associated with an existing team.
400 BAD REQUEST
If the user_id
specified is not associated with a user with status "PENDING" on this team.
400 BAD REQUEST
If the user that created the request no longer exists.
401 Unauthorized
If the user is not a team leader.
Reject a User
POST api/v1/protected/teams/:team_id/applicants/:user_id/reject
Team Leader only. Reject this applicant's request to join the team. The user_id will be the same as the id returned in the GET applicants API call. Their team role will be set to NONE
.
Request Body
No request body.
Responses
200 OK
This applicant has been removed from the applicant's list.
400 BAD REQUEST
If the team_id
specified is not associated with an existing team.
400 BAD REQUEST
If the user_id
specified is not associated with a user with status "PENDING" on this team.
400 BAD REQUEST
If the user that created the request no longer exists.
401 Unauthorized
If the user is not a team leader.
Kick a User
POST api/v1/protected/teams/:team_id/members/:member_id/kick
Leader only. Kicks a member off this team. Sets their team role to NONE
.
Request Body
No request body.
Responses
200 OK
Successfully kicked user.
400 BAD REQUEST
If the team_id
specified is not associated with an existing team.
400 BAD REQUEST
If the user is no longer on the team.
401 Unauthorized
If the user is not a team leader.
Leave a Team
POST api/v1/protected/teams/:team_id/leave
Leave this team that you are a part of. Cannot be called by the leader of the team. Will set team role to NONE
.
Request Body
No request body.
Responses
200 OK
Successfully left team.
400 BAD REQUEST
If the team_id
specified is not associated with an existing team.
400 BAD REQUEST
If the user is not on the team.
400 BAD REQUEST
If the user is the leader of the team.
Disband a Team
POST api/v1/protected/teams/:team_id/disband
Leader only. Disband this team. The deleted_at
field will be set to the current timestamp.
Request Body
No request body.
Responses
200 OK
Successfully deleted team.
400 BAD REQUEST
If the team_id
specified is not associated with an existing team.
401 UNAUTHORIZED
If the user is not the team leader.
Transfer Team Ownership
POST api/v1/protected/teams/:team_id/transfer_ownership
Leader only. Makes the current team leader a regular team member and the specified user the team leader.
Request Body
1 2 3 |
|
Responses
200 OK
Success.
400 BAD REQUEST
If the user_id
specified is not associated with a user.
400 BAD REQUEST
If the given user is not on the team.
401 UNAUTHORIZED
If the requesting user is not the team leader.
Leaderboard Router
The leaderboard router is used to get the information displayed on the leaderboard, which is blocks completed per user. It is public so that a future release can include a public leaderboard page. Since none of the information here is strictly private, the consequences of making it public are minimal.
A completed block is a block for which the last entry is either complete
or qa
. The user and team that are referenced in that last entry are the user and team that should be credited with the completion. If the user is NULL
, no user will be credited with that completion, and the same goes for a NULL
team field. The tie breaker for users or teams with the same number of completed blocks is whatever order the database returns the values in.
Get Users Leaderboard
GET api/v1/leaderboard/users?previousDays=INT
Returns a list of the top 100 users with counted blocks, of usernames and the blocks those users counted, in order of the number of blocks they counted from most to least. All users with SUPER_ADMIN
privilege level are excluded.
Query Params
previousDays: INT
The number of days in the past the leaderboard is representing. Only blocks completed within the last specified number of days will be counted towards the leaderboard. This value should be specified, by default it is set to 100 days.
Responses
200 OK
1 2 3 4 5 6 7 8 9 10 |
|
400 BAD REQUEST
If the request was malformed.
Get Teams Leaderboard
GET api/v1/leaderboard/teams?previousDays=INT
Returns a list of the top 100 team's names and the blocks those teams counted, in order of the number of blocks they counted from most to least. Only teams with blocks counted will be shown.
Query Params
previousDays: INT
The number of days in the past the leaderboard is representing. Only blocks completed within the last specified number of days will be counted towards the leaderboard. This value should be specified, by default it is set to 100 days.
Responses
200 OK
1 2 3 4 5 6 7 8 9 10 |
|
400 BAD REQUEST
If the request was malformed.
Emailer Router
The emailer router is used to manage the retrieval, addition, modification, and deletion of HTML email templates. It may also manage the sending of emails. It is protected so that only admins have access.
Add Email Template (Admin Only)
POST api/v1/protected/emailer/add_template/
Uploads an HTML file named 'name
_template.html' with template
as the content and the admin ID as 'x-amz-meta-userid' metadata to the 'email_templates/' folder of the 'sftt-user-uploads' S3 bucket.
Request Body
1 2 3 4 |
|
Responses
200 OK
Template successfully added.
400 BAD REQUEST
If the request was malformed.
403 FORBIDDEN
If the S3 bucket policy does not permit access.
Delete Email Template (Admin Only)
DELETE api/v1/protected/emailer/delete_template/:template_name
Deletes an existing HTML file named 'template_name
_template.html' in the 'email_templates/' folder of the 'sftt-user-uploads' S3 bucket.
Request Body
No Request Body
Responses
200 OK
Template successfully deleted.
400 BAD REQUEST
If the request was malformed.
403 FORBIDDEN
If the S3 bucket policy does not permit access.
Load Email Template (Admin Only)
GET api/v1/protected/emailer/load_template/:template_name
Loads an existing HTML file named 'template_name
_template.html' in the 'email_templates/' folder of the 'sftt-user-uploads' S3 bucket.
Request Body
No Request Body
Responses
200 OK
Template successfully loaded.
1 2 3 4 5 |
|
400 BAD REQUEST
If the request was malformed.
403 FORBIDDEN
If the S3 bucket policy does not permit access.
Get Email Template Names (Admin only)
GET api/v1/protected/emailer/template_names
Retrieves the names of all existing email templates currently stored in S3.
Request Body
No request body.
Responses
200 OK
1 2 3 4 5 6 |
|
401 UNAUTHORIZED
If a standard user tries to perform this action.