hot fix #3 dev day #70

This commit is contained in:
Tomas Dvorak
2025-10-24 18:15:36 +02:00
parent 80f833b926
commit 36f0f454ce
42 changed files with 124 additions and 127 deletions
+3 -4
View File
@@ -51,6 +51,7 @@ import { getArticles } from '../services/articles';
import { getCachedYouTube } from '../services/youtube';
import { getZoneramaManifestWithFallbacks } from '../services/zonerama';
import { getMyNewsletterToken } from '../services/public/newsletter';
import { API_URL } from '../services/api';
type NavLink = { label: string; to?: string; items?: { label: string; to: string }[]; external?: boolean };
@@ -327,8 +328,7 @@ const Navbar: React.FC<{ fullWidth?: boolean }> = ({ fullWidth = false }) => {
if (!url) return;
// Normalize relative upload paths to API origin so favicon resolves on all pages
try {
const apiUrl = process.env.REACT_APP_API_URL || 'http://localhost:8080/api/v1';
const apiOrigin = new URL(apiUrl).origin;
const apiOrigin = new URL(API_URL, typeof window !== 'undefined' ? window.location.origin : 'http://localhost:3000').origin;
if (/^\/.+/.test(url) && !/^https?:\/\//i.test(url)) {
// If starts with /uploads or any absolute path, prefix API origin
url = apiOrigin + url;
@@ -420,8 +420,7 @@ const Navbar: React.FC<{ fullWidth?: boolean }> = ({ fullWidth = false }) => {
try {
if (/^https?:\/\//i.test(path)) return path;
if (path.startsWith('/cache') || path.startsWith('/uploads') || path.startsWith('/api/')) {
const base = process.env.REACT_APP_API_BASE_URL || process.env.REACT_APP_API_URL || 'http://localhost:8080/api/v1';
const origin = new URL(base).origin;
const origin = new URL(API_URL, typeof window !== 'undefined' ? window.location.origin : 'http://localhost:3000').origin;
return new URL(path, origin).toString();
}
return path;
@@ -1,5 +1,6 @@
import React, { useEffect, useState } from 'react';
import { assetUrl } from '../../utils/url';
import { API_URL } from '../../services/api';
interface Sponsor {
id: number | string;
@@ -18,9 +19,8 @@ const resolveBackendUrl = (path: string) => {
try {
if (/^https?:\/\//i.test(path)) return path;
if (path.startsWith('/cache') || path.startsWith('/uploads') || path.startsWith('/api/')) {
const base = process.env.REACT_APP_API_BASE_URL || process.env.REACT_APP_API_URL || 'http://localhost:8080/api/v1';
const b = new URL(base);
const abs = new URL(path, `${b.protocol}//${b.host}`);
const origin = new URL(API_URL, typeof window !== 'undefined' ? window.location.origin : 'http://localhost:3000').origin;
const abs = new URL(path, origin);
return abs.toString();
}
return path;
@@ -42,7 +42,7 @@ const SponsorsSection: React.FC<SponsorsSectionProps> = ({
const fetchSponsors = async () => {
try {
// Try API first
const apiRes = await fetch(`${process.env.REACT_APP_API_BASE_URL || process.env.REACT_APP_API_URL || 'http://localhost:8080/api/v1'}/public/sponsors`);
const apiRes = await fetch(`${API_URL}/public/sponsors`);
if (apiRes.ok) {
const data = await apiRes.json();
if (!cancelled && Array.isArray(data)) {
@@ -1,4 +1,5 @@
import React, { useEffect, useState } from 'react';
import { API_URL } from '../../services/api';
import { Link as RouterLink } from 'react-router-dom';
import {
Box,
@@ -33,9 +34,8 @@ const resolveBackendUrl = (path: string) => {
try {
if (/^https?:\/\//i.test(path)) return path;
if (path.startsWith('/cache') || path.startsWith('/uploads') || path.startsWith('/api/')) {
const base = process.env.REACT_APP_API_BASE_URL || process.env.REACT_APP_API_URL || 'http://localhost:8080/api/v1';
const b = new URL(base);
const abs = new URL(path, `${b.protocol}//${b.host}`);
const origin = new URL(API_URL, typeof window !== 'undefined' ? window.location.origin : 'http://localhost:3000').origin;
const abs = new URL(path, origin);
return abs.toString();
}
return path;
@@ -1,5 +1,6 @@
import { Box, Grid, GridItem, Heading, Image, Button, HStack, Text, VStack, Badge } from '@chakra-ui/react';
import React, { useEffect, useState } from 'react';
import { API_URL } from '../../services/api';
import { Link as RouterLink } from 'react-router-dom';
import { Calendar, Image as ImageIcon } from 'lucide-react';
@@ -22,9 +23,8 @@ const resolveBackendUrl = (path: string) => {
try {
if (/^https?:\/\//i.test(path)) return path;
if (path.startsWith('/cache') || path.startsWith('/uploads') || path.startsWith('/api/')) {
const base = (process.env.REACT_APP_API_BASE_URL || process.env.REACT_APP_API_URL || 'http://localhost:8080/api/v1');
const b = new URL(base);
const abs = new URL(path, `${b.protocol}//${b.host}`);
const origin = new URL(API_URL, typeof window !== 'undefined' ? window.location.origin : 'http://localhost:3000').origin;
const abs = new URL(path, origin);
return abs.toString();
}
return path;
@@ -39,8 +39,7 @@ const PhotosSection: React.FC<{ zoneramaUrl?: string | null }> = ({ zoneramaUrl
let active = true;
(async () => {
try {
const apiUrl = process.env.REACT_APP_API_URL || 'http://localhost:8080/api/v1';
const response = await fetch(`${apiUrl}/gallery/albums`);
const response = await fetch(`${API_URL}/gallery/albums`);
if (response.ok) {
const data = await response.json();
+4 -6
View File
@@ -6,15 +6,14 @@ import { trackNavigation } from '../../utils/umami';
import { useClubTheme } from '../../contexts/ClubThemeContext';
import { usePublicSettings } from '../../hooks/usePublicSettings';
import { assetUrl } from '../../utils/url';
import { API_URL } from '../../services/api';
const resolveBackendUrl = (path: string) => {
try {
if (/^https?:\/\//i.test(path)) return path;
if (path.startsWith('/cache') || path.startsWith('/uploads')) {
const base = process.env.REACT_APP_API_BASE_URL || process.env.REACT_APP_API_URL || 'http://localhost:8080/api/v1';
const u = new URL(base);
u.pathname = path;
return u.toString();
const origin = new URL(API_URL, typeof window !== 'undefined' ? window.location.origin : 'http://localhost:3000').origin;
return new URL(path, origin).toString();
}
return path;
} catch {
@@ -59,8 +58,7 @@ const Footer: React.FC = () => {
} catch {}
// Fetch sponsors
try {
const apiUrl = process.env.REACT_APP_API_BASE_URL || process.env.REACT_APP_API_URL || 'http://localhost:8080/api/v1';
const sponsorsRes = await fetch(`${apiUrl}/public/sponsors`);
const sponsorsRes = await fetch(`${API_URL}/public/sponsors`);
if (sponsorsRes.ok) {
const data = await sponsorsRes.json();
if (!cancelled && Array.isArray(data)) {
@@ -3,7 +3,7 @@ import React, { useState } from 'react';
import { useLocation } from 'react-router-dom';
import { FaCalendarAlt, FaFutbol, FaExclamationTriangle, FaMapMarkerAlt } from 'react-icons/fa';
import { useQuery } from '@tanstack/react-query';
import { api } from '../../services/api';
import { api, API_URL } from '../../services/api';
import { useSettings } from '@/hooks/useSettings';
import { Widget } from './Widget';
import { format, parse, isToday, isTomorrow, isAfter } from 'date-fns';
@@ -46,8 +46,7 @@ export const MatchesWidget = () => {
const resolveUrl = (path: string) => {
try {
if (/^https?:\/\//i.test(path)) return path;
const apiUrl = process.env.REACT_APP_API_URL || 'http://localhost:8080/api/v1';
const origin = new URL(apiUrl).origin;
const origin = new URL(API_URL, typeof window !== 'undefined' ? window.location.origin : 'http://localhost:3000').origin;
return origin + path;
} catch {
return path;
@@ -109,8 +108,7 @@ export const MatchesWidget = () => {
}
const chosen = candidate || orig;
if (typeof chosen === 'string' && chosen.startsWith('/')) {
const apiUrl = process.env.REACT_APP_API_URL || 'http://localhost:8080/api/v1';
const origin = new URL(apiUrl).origin;
const origin = new URL(API_URL, typeof window !== 'undefined' ? window.location.origin : 'http://localhost:3000').origin;
return origin + chosen;
}
return chosen || (assetUrl('/dist/img/logo-club-empty.svg') as string);
@@ -122,8 +120,7 @@ export const MatchesWidget = () => {
queryKey: ['upcomingMatchesCache'],
queryFn: async () => {
// Build absolute origin from API URL env (which may include /api/v1)
const apiUrl = process.env.REACT_APP_API_URL || 'http://localhost:8080/api/v1';
const origin = new URL(apiUrl).origin;
const origin = new URL(API_URL, typeof window !== 'undefined' ? window.location.origin : 'http://localhost:3000').origin;
const url = `${origin}/cache/prefetch/facr_club_info.json`;
const res = await fetch(url, { headers: { 'Cache-Control': 'no-cache' } });