Files
vmall/openspec/specs/reviews/spec.md
T

4.8 KiB

reviews Specification

Purpose

TBD - created by archiving change add-product-reviews. Update Purpose after archive.

Requirements

Requirement: One review per completed order line

A signed-in customer SHALL create a review only for a product line of their own completed (received) order that has not been reviewed yet. A review SHALL carry a 1-5 star rating, text content, and optional image URLs, and the rating and content snapshot SHALL never change after creation. The database SHALL enforce at most one review per order line through a unique index on the order line, and creation SHALL validate the order-line precondition before insert.

Scenario: review a completed order line

  • WHEN a customer reviews a product line of their own completed order
  • THEN the review is created with the submitted rating, text, and image URLs and the line can no longer be reviewed

Scenario: second review of the same line is rejected

  • WHEN a customer submits a second review for an already reviewed order line
  • THEN the request is rejected and exactly one review row exists for that line

Scenario: unreviewable line is rejected

  • WHEN a customer reviews a line from another customer's order or from an order that is not completed
  • THEN the request is rejected without creating a review

Requirement: Bilingual review content shape

Review content and merchant replies SHALL be stored as {en, zh} localized JSONB content. A submission MAY populate only the shopper's or merchant's active locale, and every display SHALL fall back to the other locale when the active locale is empty.

Scenario: single-locale submission renders everywhere

  • WHEN a shopper submits review text in only one locale
  • THEN both mall locales display the review through the non-empty locale fallback

Requirement: Single merchant reply per review

Only a shop user of the review's own shop SHALL reply to a review, at most once. The reply SHALL be written with a guarded update that succeeds only while no reply exists, and a second or cross-shop reply attempt SHALL be rejected.

Scenario: first reply succeeds

  • WHEN a merchant of the reviewed product's shop replies to a review
  • THEN the reply is stored with its audit timestamp and appears with the review

Scenario: second reply is rejected

  • WHEN the same merchant submits another reply to a review that already has one
  • THEN the request is rejected and the existing reply is unchanged

Requirement: Platform moderation hides or deletes reviews

Platform admins SHALL hide or delete any review. Hiding SHALL be a soft delete recorded through a guarded status transition that validates the prior visible state, and deletion SHALL remove the row. Hidden and deleted reviews SHALL be absent from storefront listings and rating summaries, while admin listings SHALL still show hidden reviews with their state.

Scenario: hidden review leaves the storefront

  • WHEN a platform admin hides a visible review
  • THEN it disappears from the product's public review list and no longer contributes to the rating summary

Scenario: hide transition validates prior state

  • WHEN a platform admin hides a review that is already hidden
  • THEN the guarded transition changes nothing and reports the conflict

Requirement: Visible-only paginated review listing

A product's review list SHALL be publicly readable and paginated, containing only visible reviews with the reviewer's display name, rating, content, image URLs, creation time, and any merchant reply. Pagination totals SHALL count only visible reviews, and a customer's pending-review listing SHALL show only their own completed order lines without a review.

Scenario: totals count only visible reviews

  • WHEN a product has visible and hidden reviews and the public list is requested
  • THEN only visible reviews are returned and total excludes the hidden ones

Scenario: pending-review listing shrinks after submission

  • WHEN a customer reviews one of their pending order lines
  • THEN that line disappears from the pending-review listing

Requirement: SQL rating summary aggregation

The product rating summary SHALL be computed with SQL aggregation over visible reviews only and SHALL report the review count, average rating, and per-star (1-5) distribution. A product without visible reviews SHALL report a zero count, zero average, and an empty distribution.

Scenario: summary reflects only visible reviews

  • WHEN a product's summary is requested after one of its reviews is hidden
  • THEN the count, average, and star distribution exclude the hidden review

Scenario: product without reviews

  • WHEN the summary is requested for a product with no visible reviews
  • THEN it reports a zero count and zero average