Skip to content

Book sharing system

This section explains what the book-sharing system does, how the main content fits together, and how members move through it.

At a product level, the system supports four things:

  1. keeping a clean shared book catalog
  2. letting members track their own reading activity
  3. letting members publish reading updates and thoughts
  4. letting other members respond with comments and reactions

We designed it this way because book sharing is not just one kind of activity.

  • Some content should be stable and reusable, like books and authors.
  • Some content is personal and changes over time, like a reading journey.
  • Some content is lightweight and social, like a reading share or reaction.

If all of these were stored as one generic "post" model, the system would be easier to start but harder to govern later. Search, moderation, visibility rules, and analytics would all get messier.

The important split underneath that is this:

  • Directus collections define the shape of the data.
  • Directus relations define how records connect and what happens on delete.
  • Directus flows block bad writes and auto-fill ownership fields.
  • The app layer still handles some read filtering, especially share_author_only comment visibility.

That split is deliberate.

  • The CMS is good at storing structured content.
  • Relations are good at keeping connected records consistent.
  • Flows are good at enforcing cross-record rules.
  • The app layer is still the best place for nuanced viewer-specific read decisions.

At a glance

Area Main collections Why it exists
Book catalog books, authors, book_authors Stores canonical book and author records
Reading activity reading_journeys, reading_shares, reading_share_images Stores a member's personal reading progress and share posts
Comments reading_share_comments, reading_journey_comments, book_comments Stores user-written discussion content
Reactions reading_share_reactions, reading_journey_reactions, book_reactions Stores one-like-per-user interaction rows

How a member experiences it

Most members will move through the system in a simple loop:

  1. discover a book
  2. start a reading journey or post a reading share
  3. update progress or thoughts
  4. get replies or reactions from others

That makes the system feel social, but the model underneath is fairly strict. Books are the stable public reference point. Journeys and shares are personal activity records. Comments and reactions hang off those records.

We chose this split to avoid mixing editorial content with member activity.

  • A book should stay the same no matter who is reading it.
  • A reading journey belongs to one member and one reading process.
  • A reading share is a publishable moment inside that process, or sometimes outside it.

This keeps the public catalog clean while still letting the community be expressive.

System map

flowchart TD
    A[authors] <-- M2M via book_authors --> B[books]
    B --> C[reading_journeys]
    B --> D[reading_shares]
    C --> D
    D --> E[reading_share_comments]
    D --> F[reading_share_reactions]
    C --> G[reading_journey_comments]
    C --> H[reading_journey_reactions]
    B --> I[book_comments]
    B --> J[book_reactions]
    D <-- M2M via reading_share_images --> K[directus_files]
    U[directus_users] --> C
    U --> D
    U --> E
    U --> F
    U --> G
    U --> H
    U --> I
    U --> J

Core user flows

1. Browse a book and join the conversation

flowchart LR
    A[Member opens a book page] --> B[Reads book details and linked authors]
    B --> C[Views public comments and reactions]
    C --> D[Adds a comment or reaction if the book is published]

This is the simplest flow in the system. The book acts as the public anchor record, and members can discuss it directly.

It is designed this way so conversation can gather around one shared reference point. If every member had their own copy of a book record, comments and reactions would fragment across duplicates.

2. Start a reading journey

flowchart LR
    A[Member chooses a book] --> B[Creates a reading journey]
    B --> C[Sets title, status, and visibility]
    C --> D[Updates the journey over time]
    D --> E[Receives public comments or reactions if the journey is public]

Reading journeys are for longer-running reading activity. They connect one member to one book over time.

This exists because not every reading update should become a public post. A journey gives the member a persistent place to track progress, status, and context even when they are not actively publishing shares.

3. Publish a reading share

flowchart LR
    A[Member writes a reading share] --> B[Links it to a book]
    B --> C[Optionally links it to a reading journey]
    C --> D[Adds text and images]
    D --> E[Publishes the share]
    E --> F[Other members can comment or react if it is public]

Reading shares are more like posts. They can stand alone or sit inside a longer reading journey.

That flexibility is intentional. Some members want to post a quick thought without maintaining a full journey. Others want a series of shares attached to one reading timeline. The model supports both without forcing one behavior.

4. React safely to someone else's content

flowchart LR
    A[Member clicks comment or react] --> B[System checks target state]
    B --> C[System assigns the acting user automatically]
    C --> D[System blocks invalid or duplicate writes]
    D --> E[Interaction is saved]

This is where the Directus flows matter most. The user experience stays simple, but the backend makes sure the interaction is allowed and correctly attributed.

We designed the interaction path this way so the client can stay lightweight. The frontend does not need to be trusted with ownership or moderation logic, which reduces the chance of accidental or abusive writes.

What the system is trying to protect

The design is mostly about keeping user-generated content trustworthy.

  • Users should not be able to pretend to be someone else.
  • Users should not be able to comment or react on targets that are private or not meant for interaction.
  • Users should not be able to create duplicate reactions on the same target.
  • Deleting a book, journey, or share should clean up attached interaction rows automatically.
  • Deleting a user should not wipe out the rest of the conversation history.

Main content types

Content type What it represents Typical owner
Book A canonical shared book record Editorial or managed content
Author A canonical author record Editorial or managed content
Reading journey A member's ongoing reading record for one book Member
Reading share A member's post about reading progress or reflection Member
Comment A member's written response to a book, journey, or share Member
Reaction A member's lightweight one-like response Member

Why the model looks like this

The system does not treat everything as a generic post.

  • Books stay clean and reusable across the platform.
  • Reading journeys capture a longer story around one book.
  • Reading shares capture smaller moments, updates, or reflections.
  • Comments and reactions stay attached to a specific target, which makes moderation and visibility rules much easier to reason about.

That is the main design idea behind the whole system: stable reference content at the top, personal activity in the middle, and social interaction at the edge.