AnyaSelf Docs

Wardrobe Service

CRUD for items, outfits, image uploads, discover feed, and collections.

The wardrobe service is the centralized persistence and feed engine for AnyaSelf. It manages wardrobe items, outfit compositions, image uploads to GCS, the discovery feed with engagement tracking, and user collections.

Endpoints

Items

MethodPathDescription
POST/api/v1/households/{id}/wardrobe/itemsCreate a new wardrobe item
GET/api/v1/households/{id}/wardrobe/itemsList items (filter: owner, category, season, occasion)
GET/api/v1/households/{id}/wardrobe/items/{itemId}Get item detail
PATCH/api/v1/households/{id}/wardrobe/items/{itemId}Update item fields
DELETE/api/v1/households/{id}/wardrobe/items/{itemId}Delete an item

Create Item Request:

{
  "ownerMemberId": "mem_123",
  "category": "BOTTOM",
  "brand": "Acne Studios",
  "colors": ["Black", "Charcoal"],
  "season": ["FALL", "WINTER"],
  "occasion": ["CASUAL"],
  "tags": ["denim", "relaxed"],
  "purchaseMeta": {
    "store": "Acne Studios",
    "price": 250,
    "currency": "USD"
  }
}

Image Lifecycle

MethodPathDescription
POST/api/v1/households/{id}/wardrobe/items/{itemId}/upload-urlGenerate a signed GCS upload URL
POST/api/v1/households/{id}/wardrobe/items/{itemId}/images/{imageId}/confirmConfirm image was uploaded to GCS
POST/api/v1/households/{id}/wardrobe/items/{itemId}/curateTrigger outfit curation (detect garment slices)

The image lifecycle follows an async pattern:

  1. Client requests a signed upload URL
  2. Client uploads directly to GCS using the signed URL
  3. Client confirms the upload, transitioning the image from PENDINGUPLOADED
  4. Optional: trigger curation to detect garment regions

Outfits

MethodPathDescription
POST/api/v1/households/{id}/wardrobe/outfitsCreate an outfit from item references
GET/api/v1/households/{id}/wardrobe/outfitsList outfits (filter: owner)
DELETE/api/v1/households/{id}/wardrobe/outfits/{outfitId}Delete an outfit
// POST /households/{id}/wardrobe/outfits
{
  "ownerMemberId": "mem_123",
  "name": "Spring Casual",
  "occasion": "CASUAL",
  "season": "SPRING",
  "itemIds": ["item_1", "item_2", "item_3"]
}

Discover Feed

MethodPathDescription
GET/api/v1/households/{id}/wardrobe/feedPaginated feed (params: limit, cursor, source, occasion, likedOnly)
POST/api/v1/households/{id}/wardrobe/feed/{itemId}/likeLike/unlike a feed item
POST/api/v1/households/{id}/wardrobe/feed/{itemId}/saveSave/unsave to a collection
POST/api/v1/households/{id}/wardrobe/feed/{itemId}/impressionRecord a feed impression

Collections

MethodPathDescription
GET/api/v1/households/{id}/wardrobe/feed/collectionsList feed collections
POST/api/v1/households/{id}/wardrobe/feed/collectionsCreate a named collection

Configuration

VariableDefaultDescription
PERSISTENCE_BACKENDinmemoryfirestore or inmemory
WARDROBE_STORAGE_BACKENDstubgcs or stub (stub returns fake URLs)
GCS_BUCKETanyaself-wardrobe-devGCS bucket for image storage
WARDROBE_EMBEDDINGS_BACKENDdeterministichttp, deterministic, or none
EVENT_BUS_BACKENDinmemoryEvent bus for wardrobe domain events
MEMBERSHIP_PROVIDER_BACKENDnonefirestore or none

Domain Events

The wardrobe emits typed domain events via the internal event bus:

EventTrigger
wardrobe.item.createdNew item added
wardrobe.item.updatedItem fields modified
wardrobe.item.deletedItem removed
wardrobe.image.uploadedImage upload confirmed
wardrobe.embedding.readyEmbedding vector computed
wardrobe.feed.engagement.updatedLike/save/impression recorded
wardrobe.feed.collection.updatedCollection created or modified

On this page