Software Architectย Guide: Designing a RESTful API for a ๐ŸŒ Multi-Tenant Blogging Platform

Building a multi-tenant blogging platform requires thoughtful design of the API to ensure clarity, scalability, and security. In this post, we’ll explore a RESTful API design including versioning, nested resources, and authentication, using clear examples and best practices.


๐Ÿงฉ Understanding the Requirements

Before diving into endpoints, let’s break down what the platform supports:

  • Multiple tenants (e.g., organizations, teams)
  • Each tenant has users
  • Users can create blogs, and each blog has posts
  • Posts can have comments
  • Authentication is required

๐Ÿ“ Versioning

Weโ€™ll use URI-based versioning:

/api/v1/

This helps manage breaking changes cleanly.


๐Ÿ” Authentication

We’ll use token-based authentication (e.g., JWT or API keys). Each request must include:

Authorization: Bearer <token>

๐Ÿ“Œ Base URL

https://api.blogcloud.com/api/v1

๐Ÿ“š API Endpoint Design

๐Ÿ”ธ Tenants

Tenants are top-level entities.

  • GET /tenants โ€“ List all tenants (admin only)
  • POST /tenants โ€“ Create a new tenant
  • GET /tenants/:id โ€“ Show tenant details
  • PATCH /tenants/:id โ€“ Update tenant
  • DELETE /tenants/:id โ€“ Delete tenant

๐Ÿ”ธ Users (Scoped by tenant)

  • GET /tenants/:tenant_id/users โ€“ List users for tenant
  • POST /tenants/:tenant_id/users โ€“ Create user
  • GET /tenants/:tenant_id/users/:id โ€“ Show user
  • PATCH /tenants/:tenant_id/users/:id โ€“ Update user
  • DELETE /tenants/:tenant_id/users/:id โ€“ Delete user

๐Ÿ”ธ Blogs (Belong to users)

  • GET /tenants/:tenant_id/users/:user_id/blogs โ€“ List blogs
  • POST /tenants/:tenant_id/users/:user_id/blogs โ€“ Create blog
  • GET /tenants/:tenant_id/users/:user_id/blogs/:id โ€“ Show blog
  • PATCH /tenants/:tenant_id/users/:user_id/blogs/:id โ€“ Update blog
  • DELETE /tenants/:tenant_id/users/:user_id/blogs/:id โ€“ Delete blog

๐Ÿ”ธ Posts (Belong to blogs)

  • GET /blogs/:blog_id/posts โ€“ List posts
  • POST /blogs/:blog_id/posts โ€“ Create post
  • GET /blogs/:blog_id/posts/:id โ€“ Show post
  • PATCH /blogs/:blog_id/posts/:id โ€“ Update post
  • DELETE /blogs/:blog_id/posts/:id โ€“ Delete post

๐Ÿ”ธ Comments (Belong to posts)

  • GET /posts/:post_id/comments โ€“ List comments
  • POST /posts/:post_id/comments โ€“ Add comment
  • DELETE /posts/:post_id/comments/:id โ€“ Delete comment

โ“Question: what is the full url of comments?

No, the full URL for comments should not be:

https://api.blogcloud.com/api/v1/tenants/:tenant_id/users/:user_id/blogs/posts/:post_id/comments

That nesting is too deep and redundant, because:

  • By the time you’re at a post, you already implicitly know which blog/user/tenant it’s under (assuming proper authorization).
  • Posts have unique IDs across the system (or at least within blogs), so we donโ€™t need the entire hierarchy in every request.

โœ… Correct RESTful URL for Comments

If your post_id is unique (or unique within a blog), the cleanest design is:

https://api.blogcloud.com/api/v1/posts/:post_id/comments

or, if you prefer to keep blog_id context:

https://api.blogcloud.com/api/v1/blogs/:blog_id/posts/:post_id/comments

Use that second version only if post_id is not globally unique, and you need the blog context.

๐Ÿ” Recap of Comments Endpoints

ActionHTTP VerbEndpoint
List commentsGET/api/v1/posts/:post_id/comments
Create commentPOST/api/v1/posts/:post_id/comments
Delete commentDELETE/api/v1/posts/:post_id/comments/:id

๐Ÿง  Design Rule of Thumb

  • โœ… Keep URLs meaningful and shallow.
  • โŒ Don’t over-nest resources unless it’s needed to enforce scoping or clarify context.

๐Ÿ“ฅ Example: Create a Blog Post

Request:

POST /blogs/123/posts
Authorization: Bearer <token>
Content-Type: application/json

{
  "title": "Why REST APIs Still Matter",
  "body": "In this post, we explore the benefits of RESTful design..."
}

Response:

201 Created
{
  "id": 456,
  "title": "Why REST APIs Still Matter",
  "body": "In this post, we explore the benefits of RESTful design...",
  "created_at": "2025-07-03T10:00:00Z"
}


โœ… Best Practices Followed

  • Nesting: Resources are nested to show ownership (e.g., blogs under users).
  • Versioning: Prevents breaking old clients.
  • Consistency: Same verbs and JSON structure everywhere.
  • Authentication: Every sensitive request requires a token.

๐Ÿง  Final Thoughts

Designing a RESTful API for a multi-tenant app like a blogging platform requires balancing structure and simplicity. By properly scoping resources, using versioning, and enforcing auth, you build an API that’s powerful, secure, and easy to maintain.

Bonus Tip: Document your API using tools like Swagger/OpenAPI to make onboarding faster for new developers.

You are an awesome Architect ๐Ÿš€