mirror of
https://github.com/Dvorinka/MyClubServer.git
synced 2026-06-04 02:32:57 +00:00
dev day #65
This commit is contained in:
@@ -0,0 +1,92 @@
|
||||
# Blog Match Link Fix - October 2025
|
||||
|
||||
## Problem
|
||||
React Error #310 (Maximum update depth exceeded) - infinite render loop caused by backend returning `map[string]interface{}` instead of Article structs. Each map created new object references, triggering infinite re-renders in React useEffect hooks.
|
||||
|
||||
## Root Cause
|
||||
Previous attempt to add match link data to article JSON responses used helper functions that returned maps instead of structs. This broke React's referential equality checks.
|
||||
|
||||
## Solution
|
||||
|
||||
### 1. Added MatchLink Field to Article Model
|
||||
**File**: `internal/models/models.go`
|
||||
|
||||
```go
|
||||
type Article struct {
|
||||
// ... existing fields ...
|
||||
|
||||
// Match link (loaded separately, not stored in this table)
|
||||
MatchLink *ArticleMatchLink `gorm:"-" json:"match_link,omitempty"`
|
||||
}
|
||||
```
|
||||
|
||||
The `gorm:"-"` tag prevents GORM from treating it as a database column, and `omitempty` keeps it out of JSON if nil.
|
||||
|
||||
### 2. Updated Backend Controllers
|
||||
**File**: `internal/controllers/base_controller.go`
|
||||
|
||||
#### GetArticle (single article by ID)
|
||||
- Loads match link after fetching article
|
||||
- Sets `art.MatchLink` if found
|
||||
|
||||
#### GetArticles (paginated list)
|
||||
- Batch loads all match links for returned articles in single query
|
||||
- Maps match links to articles by ID for O(1) lookup
|
||||
- Efficient: one extra query regardless of result set size
|
||||
|
||||
#### GetArticleBySlug (single article by slug)
|
||||
- Same as GetArticle - loads match link if exists
|
||||
|
||||
### 3. Simplified Frontend
|
||||
**File**: `frontend/src/pages/admin/ArticlesAdminPage.tsx`
|
||||
|
||||
- **Removed**: Redundant useEffect that fetched match link separately
|
||||
- **Kept**: openEdit() function that extracts match_link from article data
|
||||
- **Result**: Fewer API calls, no infinite loops
|
||||
|
||||
## Benefits
|
||||
|
||||
1. **No Infinite Loops**: Article structs maintain referential equality
|
||||
2. **Complete Data**: Article JSON now includes both competition AND match data
|
||||
3. **Better Performance**: Batch loading for lists (N+1 → 2 queries)
|
||||
4. **Backward Compatible**: Match link is optional (`omitempty`)
|
||||
5. **Cleaner Code**: No complex map transformations
|
||||
|
||||
## Album Link Reuse
|
||||
|
||||
The album link reuse feature was **already implemented** (lines 400-415 in ArticlesAdminPage.tsx). When photos are selected in the Obsah tab, both the album link AND photos are automatically populated in the Media tab.
|
||||
|
||||
**Enhancement made**: Improved UI feedback with green background and clear status messages when album is loaded.
|
||||
|
||||
## Article JSON Structure
|
||||
|
||||
Articles now include:
|
||||
|
||||
```json
|
||||
{
|
||||
"id": 123,
|
||||
"title": "Match Report",
|
||||
"category_name": "A třída",
|
||||
"gallery_album_url": "https://eu.zonerama.com/...",
|
||||
"youtube_video_id": "abc123",
|
||||
"match_link": {
|
||||
"external_match_id": "match-abc-123",
|
||||
"title": "Home Team vs Away Team"
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Testing
|
||||
|
||||
Test that:
|
||||
1. ✅ No React infinite loop errors
|
||||
2. ✅ Match link appears in article JSON responses
|
||||
3. ✅ Match link displays correctly in admin UI
|
||||
4. ✅ Album link persists between Obsah and Media tabs
|
||||
5. ✅ All article endpoints work (GetArticle, GetArticles, GetArticleBySlug)
|
||||
|
||||
## Files Modified
|
||||
|
||||
- `internal/models/models.go` - Added MatchLink field
|
||||
- `internal/controllers/base_controller.go` - Load match links in 3 endpoints
|
||||
- `frontend/src/pages/admin/ArticlesAdminPage.tsx` - Removed redundant fetch, improved UI
|
||||
Reference in New Issue
Block a user