Temporary Wishlist Management
Description
The Temporary Wishlist Management system provides comprehensive CRUD operations for temporary wishlists with complex nested data structures, enabling users to create, organize, and manage product collections, categories, search queries, and AI-generated viewpoints before converting them to official wishlists. This system operates without affecting subscription quotas, allowing users to experiment with different product combinations and collaborate within groups.
Key features include:
- Complex Nested Data Management: Simultaneous creation of wishlists with products, categories, search queries, and viewpoints
- Quota-Free Operations: Create and modify wishlists without consuming subscription resources
- Group Collaboration: Real-time collaboration within user groups with ownership validation
- Advanced Validation: Comprehensive validation including emoji restrictions, input type enums, and mall compatibility
- Automatic Slug Generation: URL-safe slug generation with automatic updates on name changes
- Duplicate Detection: Intelligent filtering of duplicate items during updates
- Transaction Safety: All operations wrapped in database transactions for data integrity
- CSV Integration: Seamless integration with CSV import/export functionality
- Import History Tracking: Complete audit trail of all import operations with detailed error reporting
Activity Diagram
---
config:
theme: base
layout: dagre
flowchart:
curve: linear
htmlLabels: true
themeVariables:
edgeLabelBackground: "transparent"
---
flowchart TD
Start([User Initiates Wishlist Operation])
Start --> Step1[
<div style='text-align: center'>
<span style='display: inline-block; background-color: #4CAF50 !important; color:white; width: 28px; height: 28px; line-height: 28px; border-radius: 50%; font-weight: bold'>1</span>
<p style='margin-top: 8px'>Authenticate & Validate Group</p>
</div>
]
Step1 --> Step2[
<div style='text-align: center'>
<span style='display: inline-block; background-color: #2196F3 !important; color:white; width: 28px; height: 28px; line-height: 28px; border-radius: 50%; font-weight: bold'>2</span>
<p style='margin-top: 8px'>Validate Complex Nested Data</p>
</div>
]
Step2 --> Decision{Operation Type}
Decision -->|Create| Step3[
<div style='text-align: center'>
<span style='display: inline-block; background-color: #FF9800 !important; color:white; width: 28px; height: 28px; line-height: 28px; border-radius: 50%; font-weight: bold'>3</span>
<p style='margin-top: 8px'>Create with Nested Data</p>
</div>
]
Decision -->|Read| Step4[
<div style='text-align: center'>
<span style='display: inline-block; background-color: #9C27B0 !important; color:white; width: 28px; height: 28px; line-height: 28px; border-radius: 50%; font-weight: bold'>4</span>
<p style='margin-top: 8px'>Retrieve with Pagination</p>
</div>
]
Decision -->|Update| Step5[
<div style='text-align: center'>
<span style='display: inline-block; background-color: #607D8B !important; color:white; width: 28px; height: 28px; line-height: 28px; border-radius: 50%; font-weight: bold'>5</span>
<p style='margin-top: 8px'>Update with Duplicate Detection</p>
</div>
]
Decision -->|Show| Step6[
<div style='text-align: center'>
<span style='display: inline-block; background-color: #795548 !important; color:white; width: 28px; height: 28px; line-height: 28px; border-radius: 50%; font-weight: bold'>6</span>
<p style='margin-top: 8px'>Show with Ownership Check</p>
</div>
]
Decision -->|Import History| Step7[
<div style='text-align: center'>
<span style='display: inline-block; background-color: #E91E63 !important; color:white; width: 28px; height: 28px; line-height: 28px; border-radius: 50%; font-weight: bold'>7</span>
<p style='margin-top: 8px'>Manage Import Operations</p>
</div>
]
Step3 --> End([Operation Complete])
Step4 --> End
Step5 --> End
Step6 --> End
Step7 --> End
%% Styling
style Start fill:#e8f5e8,stroke:#4caf50,stroke-width:2px
style End fill:#ffe8e8,stroke:#f44336,stroke-width:2px
style Decision fill:#fff3e0,stroke:#ff9800,stroke-width:2px
style Step1 fill:transparent,stroke:transparent,stroke-width:1px
style Step2 fill:transparent,stroke:transparent,stroke-width:1px
style Step3 fill:transparent,stroke:transparent,stroke-width:1px
style Step4 fill:transparent,stroke:transparent,stroke-width:1px
style Step5 fill:transparent,stroke:transparent,stroke-width:1px
style Step6 fill:transparent,stroke:transparent,stroke-width:1px
style Step7 fill:transparent,stroke:transparent,stroke-width:1px
Database Related Tables & Fields
Database: gb_console
erDiagram
users ||--o{ temp_wishlist_to_groups : "creates"
groups ||--o{ temp_wishlist_to_groups : "belongs_to"
temp_wishlist_to_groups ||--o{ temp_wishlist_products : "has"
temp_wishlist_to_groups ||--o{ temp_wishlist_categories : "has"
temp_wishlist_to_groups ||--o{ temp_wishlist_search_queries : "has"
temp_wishlist_to_groups ||--o{ temp_wl_cat_vps : "has"
users ||--o{ temp_wl_cat_vps : "creates"
groups ||--o{ temp_wl_cat_vps : "belongs_to"
temp_wl_cat_vps ||--o{ temp_wl_cat_vp_details : "has"
temp_wl_cat_vp_details ||--o{ temp_wl_spec_vps : "has"
users ||--o{ import_histories : "creates"
import_histories ||--o{ import_errors : "has"
users {
bigint id PK
}
groups {
bigint id PK
}
temp_wishlist_to_groups {
bigint id PK
bigint user_id FK
bigint group_id FK
string name "Name of the wishlist"
string slug "Slug of the wishlist"
tinyint status "1: Temporary Save, 2: CSV Import Draft"
}
temp_wishlist_products {
bigint id PK
bigint temp_wishlist_to_group_id FK
string input "The input of the product"
string input_type "The type of the input: jan, asin, rakuten_id"
string product_url "The url of the product"
bigint mall_id FK
string pair_id "Unique identifier for product pairs"
}
temp_wishlist_categories {
bigint id PK
bigint temp_wishlist_to_group_id FK
string category_id "The id of the category in the mall"
bigint mall_id FK
string category_url "URL of the category"
}
temp_wishlist_search_queries {
bigint id PK
bigint temp_wishlist_to_group_id FK
string keyword "The keyword to search"
bigint mall_id FK
}
temp_wl_cat_vps {
bigint id PK
bigint temp_wishlist_to_group_id FK "Nullable, for linking to wishlist"
bigint user_id FK
bigint group_id FK
string name "Category viewpoint name (max 200 chars)"
string slug "Unique slug for the viewpoint"
}
temp_wl_cat_vp_details {
bigint id PK
bigint temp_wl_cat_vp_id FK
text detail "AI-generated category detail"
}
temp_wl_spec_vps {
bigint id PK
bigint temp_wl_cat_vp_detail_id FK
string name "Specific viewpoint name (max 100 chars)"
text description "Detailed description of the viewpoint"
}
import_histories {
bigint id PK
string file_name "The name of the file"
bigint created_by FK "User who created the import"
string temp_wishlist_id "The ID of the temp wishlist"
string temp_wishlist_name "The name of the temp wishlist"
string error "The error message"
tinyint status "0: Pending, 1: Success, 2: Error"
}
import_errors {
bigint id PK
bigint import_history_id FK
string header "The key of the error"
string value "The value of the error"
json error_messages "The error messages"
}
Case Documentation
Case 1: Create Temporary Wishlist with Nested Data
API: Create Temporary Wishlist
Sequence Diagram
sequenceDiagram
participant Client
participant TempWishlistController
participant TempWishlistService
participant TempWishlistRepository
participant TempProductService
participant TempCategoryService
participant TempSearchQueryService
participant TempViewpointService
participant Database
rect rgb(255, 255, 200)
Note over Client,Database: Authentication & Group Validation
Client->>TempWishlistController: POST /api/v1/temp-wishlist-to-group
TempWishlistController->>TempWishlistController: Check user authentication
TempWishlistController->>TempWishlistController: Validate group membership (isMemberOfGroup)
TempWishlistController->>TempWishlistController: Validate complex nested data structure
end
rect rgb(200, 230, 255)
Note over TempWishlistController,Database: Complex Validation Phase
TempWishlistController->>TempWishlistController: Validate wishlist name (max 50, no emoji)
TempWishlistController->>TempWishlistController: Validate products (input, input_type, mall compatibility)
TempWishlistController->>TempWishlistController: Validate categories (category_id, mall)
TempWishlistController->>TempWishlistController: Validate search queries (keyword, mall)
TempWishlistController->>TempWishlistController: Validate viewpoints (category_name, detail, viewpoints array)
end
rect rgb(200, 255, 200)
Note over TempWishlistController,Database: Happy Case - Transaction-Safe Creation
TempWishlistController->>TempWishlistService: create(validated_data)
TempWishlistService->>Database: BEGIN TRANSACTION
TempWishlistService->>TempWishlistService: Extract user and group from session
TempWishlistService->>TempWishlistRepository: Create main wishlist record
TempWishlistRepository->>Database: INSERT temp_wishlist_to_groups
Database-->>TempWishlistRepository: Created wishlist with auto-generated slug
alt Has Products
TempWishlistService->>TempProductService: mapDataFromRequest(products, malls)
TempProductService->>TempWishlistService: Mapped product data
TempWishlistService->>TempWishlistService: appendTempWishlistToGroupId(products)
TempWishlistService->>Database: INSERT temp_wishlist_products (bulk)
end
alt Has Categories
TempWishlistService->>TempCategoryService: mapDataFromRequest(categories, malls)
TempCategoryService->>TempWishlistService: Mapped category data
TempWishlistService->>TempWishlistService: appendTempWishlistToGroupId(categories)
TempWishlistService->>Database: INSERT temp_wishlist_categories (bulk)
end
alt Has Search Queries
TempWishlistService->>TempSearchQueryService: mapDataFromRequest(queries, malls)
TempSearchQueryService->>TempWishlistService: Mapped query data
TempWishlistService->>TempWishlistService: appendTempWishlistToGroupId(queries)
TempWishlistService->>Database: INSERT temp_wishlist_search_queries (bulk)
end
alt Has Viewpoints
TempWishlistService->>TempViewpointService: linkAndUpdateViewpoints(viewpoints, wishlist_id)
TempViewpointService->>TempViewpointService: createOrUpdateTempWishlistCategoryViewpoint(user, category_name)
TempViewpointService->>Database: INSERT/UPDATE temp_wl_cat_vps
TempViewpointService->>TempViewpointService: createOrUpdateTempWishlistCategoryViewpointDetail(viewpoint, detail)
alt Has Specific Viewpoints Array
TempViewpointService->>TempViewpointService: Process viewpoints array (create/update logic)
TempViewpointService->>Database: INSERT/UPDATE temp_wl_spec_vps (bulk operations)
end
TempViewpointService->>Database: UPDATE temp_wl_cat_vps SET temp_wishlist_to_group_id
end
TempWishlistService->>Database: COMMIT TRANSACTION
TempWishlistService->>TempWishlistRepository: refresh() - reload with relationships
TempWishlistService-->>TempWishlistController: Complete wishlist object
TempWishlistController-->>Client: 201 Created with TempWishlistToGroupResource
end
rect rgb(255, 200, 200)
Note over Client,Database: Error Handling with Rollback
alt Validation Error
TempWishlistController-->>Client: 422 Validation Error (detailed field errors)
else Group Access Denied
TempWishlistController-->>Client: 403 Forbidden
else Transaction Error
TempWishlistService->>Database: ROLLBACK TRANSACTION
TempWishlistService-->>TempWishlistController: Creation failed
TempWishlistController-->>Client: 400 Bad Request
end
end
Steps
Step 1: Authentication & Group Authorization
- Description: Verify user authentication and group membership using
isMemberOfGroup()method - Validation: User session, group access permissions, group member relationship
- Security: Ensure user belongs to a group and has permission to create wishlists
Step 2: Complex Nested Data Validation
- Description: Validate all nested data structures with comprehensive rules
- Rules:
- Name: max 50 characters, no emoji (WithoutEmojiRule)
- Products: input (max 255), input_type (enum: jan/asin/rakuten_id), mall compatibility
- Categories: category_id (max 255, no emoji), mall (enum: amazon/rakuten)
- Search Queries: keyword (max 255, no emoji), mall (enum)
- Viewpoints: category_name (max 200), category_detail (max 1000), viewpoints array
- Sanitization: Clean input data and prepare for database insertion
Step 3: Transaction-Safe Creation with Nested Data
- Description: Create wishlist and all related data in a single transaction
- Process:
- Begin database transaction
- Create main wishlist record with auto-generated slug
- Bulk insert products with mall mapping and pair_id generation
- Bulk insert categories with mall validation
- Bulk insert search queries with keyword processing
- Complex Viewpoint Creation (3-tier hierarchy):
- Tier 1: Create/update category viewpoint in
temp_wl_cat_vpswith user/group context - Tier 2: Create/update category detail in
temp_wl_cat_vp_detailswith rich description - Tier 3: Process specific viewpoints array:
- If empty existing viewpoints: bulk insert new viewpoints into
temp_wl_spec_vps - If existing viewpoints: smart update using ID-based mapping for performance
- If empty existing viewpoints: bulk insert new viewpoints into
- Linking: Update category viewpoint with
temp_wishlist_to_group_idfor association
- Tier 1: Create/update category viewpoint in
- Commit transaction or rollback on any error
- Response: Return complete wishlist with all nested relationships loaded
Error Handling
| Status Code | Error Message | Description |
|---|---|---|
| 422 | Validation errors | Invalid input data, emoji validation, enum violations, length constraints |
| 403 | "Access denied" | User not member of any group or insufficient permissions |
| 400 | "Creation failed" | Database transaction error, service layer failure |
Case 2: Retrieve Temporary Wishlists with Pagination
Sequence Diagram
sequenceDiagram
participant Client
participant TempWishlistController
participant TempWishlistRepository
participant Database
rect rgb(255, 255, 200)
Note over Client,Database: Authentication & Query Parameters
Client->>TempWishlistController: GET /api/v1/temp-wishlist-to-group?page=1&per_page=10
TempWishlistController->>TempWishlistController: Check user authentication
TempWishlistController->>TempWishlistController: Parse pagination parameters (page, per_page)
end
rect rgb(200, 255, 200)
Note over TempWishlistController,Database: Happy Case - Server-Side Pagination
TempWishlistController->>TempWishlistRepository: serverPaginationFilteringFor(request->all())
TempWishlistRepository->>Database: SELECT with user/group filters, pagination, ordering
Database-->>TempWishlistRepository: Paginated wishlist records with metadata
TempWishlistRepository-->>TempWishlistController: LengthAwarePaginator with wishlists
TempWishlistController->>TempWishlistController: Transform to TempWishlistToGroupResource::collection
TempWishlistController-->>Client: 200 OK with paginated collection + meta + links
end
rect rgb(255, 200, 200)
Note over Client,Database: Error Handling
alt No Access
TempWishlistController-->>Client: 403 Forbidden
else Database Error
Database-->>TempWishlistRepository: Query error
TempWishlistRepository-->>TempWishlistController: Exception
TempWishlistController-->>Client: 400 Bad Request
end
end
Steps
Step 1: Authentication & Parameter Processing
- Description: Verify user authentication and process query parameters
- Parameters:
page(integer),per_page(integer), additional filtering options - Authorization: Check user permissions for wishlist access
Step 2: Server-Side Pagination with Filtering
- Description: Execute optimized database query with pagination and filtering
- Features:
- User-specific filtering (only user's wishlists)
- Group-based filtering (group membership)
- Status filtering (TemporarySave, CsvImport)
- Ordering by creation date (newest first)
- Response: Paginated collection with metadata (current_page, total, per_page, etc.)
Step 3: Resource Transformation
- Description: Transform database models to API resources
- Includes: Basic wishlist info, status names, user/group relationships (when loaded)
- Response: Structured JSON with data, meta, and pagination links
Case 3: Show Specific Temporary Wishlist
Sequence Diagram
sequenceDiagram
participant Client
participant TempWishlistController
participant TempWishlistRepository
participant Database
rect rgb(255, 255, 200)
Note over Client,Database: Authentication & Ownership Validation
Client->>TempWishlistController: GET /api/v1/temp-wishlist-to-group/{slug}
TempWishlistController->>TempWishlistController: Check user authentication
TempWishlistController->>TempWishlistRepository: Find by slug (route model binding)
TempWishlistRepository->>Database: SELECT wishlist by slug
Database-->>TempWishlistRepository: Wishlist record or 404
TempWishlistController->>TempWishlistController: Verify ownership (user_id === logged_in_user.id)
end
rect rgb(200, 255, 200)
Note over TempWishlistController,Database: Happy Case - Return Wishlist Details
TempWishlistController->>TempWishlistController: Ownership verified
TempWishlistController->>TempWishlistController: Transform to TempWishlistToGroupResource
TempWishlistController-->>Client: 200 OK with detailed wishlist data
end
rect rgb(255, 200, 200)
Note over Client,Database: Error Handling
alt Wishlist Not Found
TempWishlistRepository-->>TempWishlistController: 404 from route model binding
TempWishlistController-->>Client: 404 Not Found
else Access Denied (Wrong Owner)
TempWishlistController->>TempWishlistController: user_id !== logged_in_user.id
TempWishlistController-->>Client: 404 Not Found (security: don't reveal existence)
else Database Error
Database-->>TempWishlistRepository: Query error
TempWishlistRepository-->>TempWishlistController: Exception
TempWishlistController-->>Client: 400 Bad Request
end
end
Steps
Step 1: Route Model Binding & Ownership Verification
- Description: Laravel automatically finds wishlist by slug, then verify user ownership
- Security: Only wishlist creator can view details (user_id check)
- Privacy: Return 404 instead of 403 to not reveal wishlist existence to unauthorized users
Step 2: Resource Transformation
- Description: Transform model to API resource with relationships
- Includes: All wishlist details, status information, user/group data when loaded
- Response: Complete wishlist object with formatted dates and status names
Case 4: Update Temporary Wishlist with Duplicate Detection
API: Update Temporary Wishlist
Sequence Diagram
sequenceDiagram
participant Client
participant TempWishlistController
participant TempWishlistService
participant TempWishlistRepository
participant TempProductService
participant TempCategoryService
participant TempSearchQueryService
participant TempViewpointService
participant Database
rect rgb(255, 255, 200)
Note over Client,Database: Authentication & Ownership Validation
Client->>TempWishlistController: PUT /api/v1/temp-wishlist-to-group/{id}
TempWishlistController->>TempWishlistController: Check user authentication
TempWishlistController->>TempWishlistRepository: Find by ID (route model binding)
TempWishlistController->>TempWishlistController: Verify ownership (user_id check)
TempWishlistController->>TempWishlistController: Validate updated data (same rules as create)
end
rect rgb(200, 230, 255)
Note over TempWishlistController,Database: Complex Update with Duplicate Detection
TempWishlistController->>TempWishlistService: update(wishlist, validated_data)
TempWishlistService->>Database: BEGIN TRANSACTION
TempWishlistService->>TempWishlistService: Initialize counts tracking (new/duplicate)
TempWishlistService->>TempWishlistRepository: Update main wishlist record
TempWishlistService->>TempWishlistRepository: Load existing relationships (products, categories, queries)
alt Has New Products
TempWishlistService->>TempProductService: mapDataFromRequest(products, malls)
TempProductService->>TempWishlistService: Mapped product data
TempWishlistService->>TempProductService: filterNewItems(mapped, existing)
TempProductService->>TempWishlistService: {items: new_items, stats: {new: X, duplicate: Y}}
TempWishlistService->>TempWishlistService: appendTempWishlistToGroupId(new_items)
TempWishlistService->>Database: INSERT only new products (bulk)
end
alt Has New Categories
TempWishlistService->>TempCategoryService: mapDataFromRequest + filterNewItems
TempWishlistService->>Database: INSERT only new categories (bulk)
end
alt Has New Search Queries
TempWishlistService->>TempSearchQueryService: mapDataFromRequest + filterNewItems
TempWishlistService->>Database: INSERT only new search queries (bulk)
end
alt Has Viewpoints
TempWishlistService->>TempViewpointService: linkAndUpdateViewpoints(viewpoints, wishlist_id)
TempViewpointService->>TempViewpointService: createOrUpdateTempWishlistCategoryViewpoint(user, category_name)
TempViewpointService->>Database: INSERT/UPDATE temp_wl_cat_vps
TempViewpointService->>TempViewpointService: createOrUpdateTempWishlistCategoryViewpointDetail(viewpoint, detail)
alt Has Specific Viewpoints Array
TempViewpointService->>TempViewpointService: Process viewpoints array (create/update logic)
TempViewpointService->>Database: INSERT/UPDATE temp_wl_spec_vps (bulk operations)
end
TempViewpointService->>Database: UPDATE temp_wl_cat_vps SET temp_wishlist_to_group_id
end
TempWishlistService->>Database: COMMIT TRANSACTION
TempWishlistService-->>TempWishlistController: {temp_wishlist: updated_object, counts: statistics}
end
rect rgb(200, 255, 200)
Note over TempWishlistController,Database: Happy Case - Return Updated Data
TempWishlistController->>TempWishlistController: Transform to TempWishlistToGroupResource
TempWishlistController-->>Client: 200 OK with updated wishlist + statistics
end
rect rgb(255, 200, 200)
Note over Client,Database: Error Handling
alt Wishlist Not Found
TempWishlistRepository-->>TempWishlistController: null
TempWishlistController-->>Client: 404 Not Found
else Access Denied
TempWishlistController-->>Client: 404 Not Found (security)
else Validation Error
TempWishlistController-->>Client: 422 Validation Error
else Transaction Error
TempWishlistService->>Database: ROLLBACK TRANSACTION
TempWishlistService-->>TempWishlistController: Update failed
TempWishlistController-->>Client: 400 Bad Request
end
end
Steps
Step 1: Ownership Verification & Data Validation
- Description: Verify user owns the wishlist and validate all update data
- Security: Prevent unauthorized modifications with user ID check
- Validation: Same comprehensive rules as creation (emoji, length, enums)
Step 2: Intelligent Duplicate Detection
- Description: Advanced logic to detect and filter duplicate items
- Process:
- Load existing relationships (products, categories, search queries)
- Map new data with mall compatibility checks
- Filter out duplicates using service-specific logic
- Track statistics (new items vs duplicates)
- Insert only new items to avoid database constraints
- Efficiency: Bulk operations for performance, minimal database queries
Step 3: Transaction-Safe Update with Statistics
- Description: Update all data atomically and return detailed statistics
- Response: Updated wishlist object + counts of new/duplicate items
- Rollback: Automatic rollback on any error to maintain data integrity
Case 5: Import History Management
API: Get Import Histories
Sequence Diagram
sequenceDiagram
participant Client
participant TempWishlistController
participant ImportHistoryRepository
participant Database
rect rgb(255, 255, 200)
Note over Client,Database: Authentication & Query Processing
Client->>TempWishlistController: GET /api/v1/temp-wishlist-to-group/import-history/list
TempWishlistController->>TempWishlistController: Check user authentication
TempWishlistController->>TempWishlistController: Parse pagination and filter parameters
end
rect rgb(200, 255, 200)
Note over TempWishlistController,Database: Happy Case - Retrieve Import History
TempWishlistController->>ImportHistoryRepository: serverPaginationFilteringFor(request->all())
ImportHistoryRepository->>Database: SELECT import_histories WHERE created_by = user_id
Database-->>ImportHistoryRepository: Paginated import history records
ImportHistoryRepository-->>TempWishlistController: LengthAwarePaginator with histories
TempWishlistController->>TempWishlistController: Transform to ImportHistoryResource::collection
TempWishlistController-->>Client: 200 OK with paginated import histories
end
rect rgb(255, 200, 200)
Note over Client,Database: Error Handling
alt Database Error
Database-->>ImportHistoryRepository: Query error
ImportHistoryRepository-->>TempWishlistController: Exception
TempWishlistController-->>Client: 400 Bad Request
end
end
Case 6: Find Specific Import History
API: Find Import History
Sequence Diagram
sequenceDiagram
participant Client
participant TempWishlistController
participant ImportHistoryRepository
participant Database
rect rgb(255, 255, 200)
Note over Client,Database: Authentication & History Lookup
Client->>TempWishlistController: GET /api/v1/temp-wishlist-to-group/import-history/{id}
TempWishlistController->>TempWishlistController: Check user authentication
TempWishlistController->>ImportHistoryRepository: findByIdAndErrorStatus(historyId)
ImportHistoryRepository->>Database: SELECT import_histories WHERE id = ? AND status = ERROR
Database-->>ImportHistoryRepository: Import history record or null
end
rect rgb(200, 255, 200)
Note over TempWishlistController,Database: Happy Case - Return History Details
ImportHistoryRepository-->>TempWishlistController: Import history with error details
TempWishlistController->>TempWishlistController: Transform to ImportHistoryResource
TempWishlistController-->>Client: 200 OK with detailed import history
end
rect rgb(255, 200, 200)
Note over Client,Database: Error Handling
alt History Not Found
ImportHistoryRepository-->>TempWishlistController: null
TempWishlistController-->>Client: 404 Not Found
else Database Error
Database-->>ImportHistoryRepository: Query error
ImportHistoryRepository-->>TempWishlistController: Exception
TempWishlistController-->>Client: 400 Bad Request
end
end
Case 7: Get Import Errors
API: Get Import Errors
Sequence Diagram
sequenceDiagram
participant Client
participant TempWishlistController
participant ImportErrorRepository
participant Database
rect rgb(255, 255, 200)
Note over Client,Database: Authentication & Error Retrieval
Client->>TempWishlistController: GET /api/v1/temp-wishlist-to-group/import-history/{id}/import-error/list
TempWishlistController->>TempWishlistController: Check user authentication
TempWishlistController->>ImportErrorRepository: getAllByHistoryId(historyId)
ImportErrorRepository->>Database: SELECT import_errors WHERE import_history_id = ?
Database-->>ImportErrorRepository: All error records for the import
end
rect rgb(200, 255, 200)
Note over TempWishlistController,Database: Happy Case - Return Error Details
ImportErrorRepository-->>TempWishlistController: Collection of import errors
TempWishlistController->>TempWishlistController: Transform to ImportErrorResource::collection
TempWishlistController-->>Client: 200 OK with detailed error information
end
rect rgb(255, 200, 200)
Note over Client,Database: Error Handling
alt Database Error
Database-->>ImportErrorRepository: Query error
ImportErrorRepository-->>TempWishlistController: Exception
TempWishlistController-->>Client: 400 Bad Request
end
end
Business Logic Details
Complex Nested Data Structure
The system handles sophisticated nested data structures in a single request:
{
"name": "My Complex Wishlist",
"wishlist_products": [
{
"input": "B08N5WRWNW",
"input_type": "asin",
"pair_id": "unique-pair-123"
}
],
"wishlist_categories": [
{
"category_id": "electronics-smartphones",
"mall": "amazon"
}
],
"wishlist_search_queries": [
{
"keyword": "iPhone 13 Pro",
"mall": "rakuten"
}
],
"wishlist_viewpoints": {
"category_name": "Smartphones",
"category_detail": "High-end smartphones with advanced features",
"viewpoints": [
{
"id": "existing-viewpoint-id",
"name": "Performance",
"description": "Focus on processing power and speed"
}
]
}
}
Advanced Validation Rules
- WithoutEmojiRule: Custom validation rule preventing emoji characters in text fields
- Enum Validation: Strict validation for
InputType(jan, asin, rakuten_id) andMallSlug(amazon, rakuten) - Conditional Validation:
category_detailrequired whencategory_nameis provided - Array Validation: Complex validation for nested arrays with distinct ID requirements
- Length Constraints: Specific character limits for different field types
Automatic Slug Generation
- Observer Pattern:
TempWishlistToGroupObserverhandles slug generation automatically - Creation: Slug generated on model creation using
generate_slug()helper - Updates: Slug regenerated when name changes (dirty checking)
- Format:
twtg-{id}-{sanitized-name}for URL-safe identifiers - Uniqueness: Ensured through ID inclusion in slug format
Intelligent Duplicate Detection
- Service-Level Logic: Each service (Product, Category, SearchQuery) implements
filterNewItems() - Comparison Logic: Sophisticated comparison based on business rules (input+type, category_id+mall, keyword+mall)
- Statistics Tracking: Detailed counts of new vs duplicate items
- Performance: Efficient filtering to minimize database operations
Transaction Safety
- Database Transactions: All create/update operations wrapped in transactions
- Rollback Strategy: Automatic rollback on any error to maintain data integrity
- Nested Operations: Complex operations with multiple table inserts handled atomically
- Error Propagation: Proper exception handling with transaction cleanup
Status Management
- TemporarySave (1): Default status for manual creation and updates
- CsvImport (2): Special status for CSV-imported wishlists
- Status Names: Localized status names through enum
getName()method - Automatic Assignment: Status managed by system based on operation type
Import History Integration
- Complete Audit Trail: All import operations tracked with detailed metadata
- Error Management: Comprehensive error collection and reporting
- File Metadata: Original filename and processing details preserved
- User Association: Import history linked to authenticated user
- Status Tracking: Real-time status updates (Pending, Success, Error)
Security Features
- Group Membership:
isMemberOfGroup()validation for all operations - Ownership Validation: Strict user ID checking for access control
- Privacy Protection: 404 responses instead of 403 to hide resource existence
- Input Sanitization: Comprehensive validation and cleaning of all inputs
- Transaction Isolation: Database-level protection against concurrent modifications
Integration Points
Related APIs
- CSV Import/Export: Seamless integration with bulk data operations
- Product Management: Individual product CRUD operations
- Category Management: Category-specific operations and mall handling
- Search Query Management: Keyword management and search operations
- AI Viewpoint Generation: OpenAI integration for intelligent content
GET /api/v1/temp-viewpoint/category- Get category viewpoint by userGET /api/v1/temp-viewpoint/category/group- Get category viewpoint by groupPOST /api/v1/temp-viewpoint/category/generate- Generate AI category detailPOST /api/v1/temp-viewpoint/specific-viewpoint/generate- Generate specific viewpoints
- Official Wishlist Conversion: Migration to production wishlists
External Services
- Group Management: Verify user group membership and permissions
- User Authentication: Validate user sessions and extract user context
- Mall Configuration: Validate mall compatibility and mapping
- Slug Generation: URL-safe identifier generation with uniqueness
- Database: Primary data storage with transaction support
Data Flow
- Creation → Population: Create wishlist with all nested data in single operation
- Management → Enhancement: Add/update content with duplicate detection
- Validation → Security: Comprehensive validation and authorization
- Import → Integration: CSV import creates wishlists with full audit trail
- Conversion → Production: Seamless migration to official wishlist system
Complex Viewpoint Hierarchy System
The system implements a sophisticated 3-tier viewpoint hierarchy with OpenAI integration:
Tier 1: Category Viewpoints (temp_wl_cat_vps)
- Purpose: Top-level category definitions with AI-generated names
- Scope: User and group specific, can be linked to specific temp wishlists
- Auto-Slug: Automatic slug generation via
TempWishlistCategoryViewpointObserver - Linking: Can be linked to temp wishlists via
temp_wishlist_to_group_id
Tier 2: Category Details (temp_wl_cat_vp_details)
- Purpose: AI-generated detailed descriptions for categories
- OpenAI Integration: Generated via
OpenAIService->generateCategoryDetail() - Relationship: One-to-many with category viewpoints (latest detail used)
- Content: Rich text descriptions explaining the category context
Tier 3: Specific Viewpoints (temp_wl_spec_vps)
- Purpose: Granular AI-generated viewpoints for specific analysis angles
- OpenAI Integration: Generated via
OpenAIService->generateSpecificViewpoints() - Quantity: Configurable via
config('viewpoint.default_quantity') - Structure: Name + detailed description for each viewpoint
Viewpoint Management Logic
// Example of complex viewpoint data structure
{
"wishlist_viewpoints": {
"category_name": "Smartphones",
"category_detail": "High-end smartphones with advanced features",
"viewpoints": [
{
"id": "existing-viewpoint-id", // For updates
"name": "Performance",
"description": "Focus on processing power and speed"
},
{
"name": "Camera Quality",
"description": "Emphasis on photography capabilities"
}
]
}
}
TempViewpointService Integration
linkAndUpdateViewpoints(): Links viewpoints to temp wishlists during creation/update- Smart Updates: Detects existing viewpoints and updates only changed data
- Transaction Safety: All viewpoint operations wrapped in database transactions
- User Action Logging: Tracks AI generation usage for analytics
- Cleanup Logic: Automatic cleanup of orphaned viewpoint data
OpenAI Integration Workflow
- Category Detail Generation:
generateCategoryDetail()→ OpenAI API → Store intemp_wl_cat_vp_details - Specific Viewpoint Generation:
generateSpecificViewpoints()→ OpenAI API → Bulk insert intotemp_wl_spec_vps - Error Handling: Comprehensive retry mechanisms and error logging
- User Tracking: All AI operations logged via
UserActionLogRepository