This project showcases a REST API that enables store and item management operations. It enables the creation, retrieval, and deletion of stores and items.
- User authentication using JWT tokens
- CRUD operations on stores, items, and tags
- Ability to add and remove tags from items
- Asynchronous email notifications upon user registration
- Error handling for JWT token-related issues (expiry, invalidity, etc.)
ItemModel
: Represents an item with unique name, description, price, and associated store.ItemTags
: Represents a many-to-many relationship between items and tags.StoreModel
: Represents a store with a unique name and associated items and tags.TagModel
: Represents a tag with a unique name and associated items.UserModel
: Represents a user with a unique username and email, and an encrypted password.
item
: Allows CRUD operations on items. All operations require user authentication.store
: Allows CRUD operations on stores. All operations require user authentication.tag
: Allows adding and removing tags from items. Also allows retrieving all tags associated with a store and deleting a tag if it's not associated with any items.user
: Handles user registration and login.
The application has been deployed using the following services:
- Database: PostgreSQL hosted on ElephantSQL
- Backend: Deployed on render.com
- Mail Services: Utilizing Mailgun for email functionality
- Swagger API: Swagger Documentation
You can test things with the link: https://store-rest-api-f4yf.onrender.com/ or use provided Postman Workspace link below.
-
Request:
POST /store
{ "name": "My Store" }
-
Response:
{ "id": "<generated_store_id>", "items": [ { "id": <item_id>, "name": "Your Item", "price": Item Price } ], "name": "My Store", "tags": [] }
-
Request:
GET /store
-
Response:
{ "id": "<generated_store_id>", "items": [ { "id": <item_id>, "name": "Your Item", "price": Item Price } ], "name": "My Store", "tags": [] }
-
Request:
GET /store/<store_id>
-
Response:
{ "id": "<generated_store_id>", "items": [ { "id": <item_id>, "name": "Your Item", "price": Item Price } ], "name": "My Store", "tags": [] }
-
Request:
PUT /store/<store_id>
{ "name": "New Store Name" }
-
Response:
{ "id": "<generated_store_id>", "items": [ { "id": <item_id>, "name": "Your Item", "price": Item Price } ], "name": "New Store Name", "tags": [] }
-
Request:
DELETE /store/<store_id>
-
Response:
{ "message": "Store deleted." }
-
Request:
POST /item
{ "name": "Item Name", "price": Item Price, "store_id": "<store_id>" }
-
Response:
{ "id": <generated_item_id>, "name": "Item Name", "price": Item Price, "store": { "id": <store_id>, "name": "Store Name" }, "tags": [] }
-
Request:
GET /item
-
Response:
{ "id": <item_id>, "name": "Item Name", "price": Item Price, "store": { "id": <store_id>, "name": "Store Name" }, "tags": [] }
-
Request:
GET /item/<item_id>
-
Response:
{ "id": <item_id>, "name": "Item Name", "price": Item Price, "store": { "id": <store_id>, "name": "Store Name" }, "tags": [] }
-
Request:
PUT /item/<item_id>
{ "name": "New Name", "price": New Price, "store_id": <store_id> }
-
Response:
{ "id": <item_id>, "name": "New Name", "price": New Price, "store": { "id": <store_id>, "name": "Store Name" }, "tags": [] }
-
Request:
DELETE /item/<item_id>
-
Response:
{ "message": "Item deleted." }
-
Request:
POST /register
{ "username": "noobietubie", "email": "[email protected]", "password": "password123" }
-
Response:
{ "message": "User created successfully." }
-
Request:
POST /login
{ "username": "noobietubie", "password": "password123" }
-
Response:
{ "access_token": "<access_token>", "refresh_token": "<refresh_token>" }
-
Request:
POST /refresh
-
Response:
{ "access_token": "<new_access_token>" }
-
Request:
POST /logout
-
Response:
{ "message": "Successfully logged out." }
-
Request:
GET /user/<user_id>
-
Response:
{ "id": "<user_id>", "username": "noobie" }
-
Request:
DELETE /user/<user_id>
-
Response:
{ "message": "User deleted." }
-
Request:
POST /store/<store_id>/tag
{ "name": "Tag Name" }
-
Response:
{ "id": <tag_id>, "items": [ { "id": <item_id>, "name": "Your Item", "price": Item Price } ], "name": "Tag name", "store": { "id": <store_id>, "name": "Store Name" } }
-
Request:
GET /tag/<tag_id>
-
Response:
{ "id": <tag_id>, "items": [ { "id": <item_id>, "name": "Your Item", "price": Item Price } ], "name": "Tag name", "store": { "id": <store_id>, "name": "Store Name" } }
-
Request:
GET /store/<store_id>/tag
-
Response:
{ "id": <tag_id>, "items": [ { "id": <item_id>, "name": "Your Item", "price": Item Price } ], "name": "Tag name", "store": { "id": <store_id>, "name": "Store Name" } }
-
Request:
POST /item/<item_id>/tag/<tag_id>
-
Response:
{ "id": <tag_id>, "items": [ { "id": <item_id>, "name": "Your Item", "price": Item Price } ], "name": "Tag name", "store": { "id": <store_id>, "name": "Store Name" } }
-
Request:
DELETE /item/<item_id>/tag/<tag_id>
-
Response:
{ "item": { "id": <item_id>, "name": "Your Item", "price": Item Price, "store": { "id": <store_id>, "name": "Store Name" }, "tags": [] }, "message": "Item removed from tag", "tag": { "id": <tag_id>, "items": [ { "id": <item_id>, "name": "Your Item", "price": Item Price } ], "name": "Tag name", "store": { "id": <store_id>, "name": "Store Name" } } }
-
Request:
DELETE /tag/<tag_id>
-
Response:
{ "message": "Tag deleted." }