Fix ESLint errors for CI pipeline
- Prefix unused state variables with underscore - Remove unused 'name' parameter from Tooltip formatters - Add eslint-disable comments for JSX component props not recognized - Suppress react-hooks/exhaustive-deps for intentional effect deps - Suppress react-refresh/only-export-components for AuthContext Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
24
src/App.jsx
24
src/App.jsx
@ -22,7 +22,7 @@ const ApartmentDashboard = () => {
|
|||||||
const [selectedUnit, setSelectedUnit] = useState(null);
|
const [selectedUnit, setSelectedUnit] = useState(null);
|
||||||
const [loading, setLoading] = useState(false);
|
const [loading, setLoading] = useState(false);
|
||||||
const [error, setError] = useState(null);
|
const [error, setError] = useState(null);
|
||||||
const [lastUpdated, setLastUpdated] = useState(new Date());
|
const [_lastUpdated, setLastUpdated] = useState(new Date());
|
||||||
const [modalTimeRange, setModalTimeRange] = useState('month');
|
const [modalTimeRange, setModalTimeRange] = useState('month');
|
||||||
const [unitPriceHistory, setUnitPriceHistory] = useState([]);
|
const [unitPriceHistory, setUnitPriceHistory] = useState([]);
|
||||||
const [loadingPriceHistory, setLoadingPriceHistory] = useState(false);
|
const [loadingPriceHistory, setLoadingPriceHistory] = useState(false);
|
||||||
@ -58,10 +58,10 @@ const ApartmentDashboard = () => {
|
|||||||
const [planStats, setPlanStats] = useState([]);
|
const [planStats, setPlanStats] = useState([]);
|
||||||
|
|
||||||
// Enhanced data state (optional endpoints)
|
// Enhanced data state (optional endpoints)
|
||||||
const [bestDeals, setBestDeals] = useState([]);
|
const [_bestDeals, setBestDeals] = useState([]);
|
||||||
const [priceDrops, setPriceDrops] = useState([]);
|
const [priceDrops, setPriceDrops] = useState([]);
|
||||||
const [staleInventory, setStaleInventory] = useState([]);
|
const [_staleInventory, setStaleInventory] = useState([]);
|
||||||
const [marketInsights, setMarketInsights] = useState(null);
|
const [_marketInsights, setMarketInsights] = useState(null);
|
||||||
|
|
||||||
// Analytics data state
|
// Analytics data state
|
||||||
const [analyticsData, setAnalyticsData] = useState(null);
|
const [analyticsData, setAnalyticsData] = useState(null);
|
||||||
@ -305,7 +305,7 @@ const ApartmentDashboard = () => {
|
|||||||
return filtered;
|
return filtered;
|
||||||
};
|
};
|
||||||
|
|
||||||
const toggleWatchUnit = (unitCode) => {
|
const _toggleWatchUnit = (unitCode) => {
|
||||||
const newWatched = new Set(watchedUnits);
|
const newWatched = new Set(watchedUnits);
|
||||||
if (newWatched.has(unitCode)) {
|
if (newWatched.has(unitCode)) {
|
||||||
newWatched.delete(unitCode);
|
newWatched.delete(unitCode);
|
||||||
@ -367,6 +367,7 @@ const ApartmentDashboard = () => {
|
|||||||
if (location.pathname === '/analytics' && !analyticsData) {
|
if (location.pathname === '/analytics' && !analyticsData) {
|
||||||
fetchAnalytics();
|
fetchAnalytics();
|
||||||
}
|
}
|
||||||
|
// eslint-disable-next-line react-hooks/exhaustive-deps
|
||||||
}, [location.pathname]);
|
}, [location.pathname]);
|
||||||
|
|
||||||
// Calculate insights from available data
|
// Calculate insights from available data
|
||||||
@ -435,7 +436,8 @@ const ApartmentDashboard = () => {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
const MetricCard = ({ title, value, subtitle, icon: Icon, trend, color = "blue", highlight = false }) => (
|
// eslint-disable-next-line no-unused-vars
|
||||||
|
const MetricCard = ({ title, value, subtitle, icon: IconProp, trend, color = "blue", highlight = false }) => (
|
||||||
<div className={`bg-white rounded-lg shadow-md p-6 border-l-4 ${highlight ? 'ring-2 ring-yellow-400' : ''}`}
|
<div className={`bg-white rounded-lg shadow-md p-6 border-l-4 ${highlight ? 'ring-2 ring-yellow-400' : ''}`}
|
||||||
style={{borderLeftColor: color === 'blue' ? '#3B82F6' : color === 'green' ? '#10B981' : color === 'red' ? '#EF4444' : '#F59E0B'}}>
|
style={{borderLeftColor: color === 'blue' ? '#3B82F6' : color === 'green' ? '#10B981' : color === 'red' ? '#EF4444' : '#F59E0B'}}>
|
||||||
<div className="flex items-center justify-between">
|
<div className="flex items-center justify-between">
|
||||||
@ -451,7 +453,7 @@ const ApartmentDashboard = () => {
|
|||||||
{Math.abs(trend)}%
|
{Math.abs(trend)}%
|
||||||
</span>
|
</span>
|
||||||
)}
|
)}
|
||||||
<Icon className="w-8 h-8 text-gray-400" />
|
<IconProp className="w-8 h-8 text-gray-400" />
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@ -698,7 +700,7 @@ const ApartmentDashboard = () => {
|
|||||||
/>
|
/>
|
||||||
<YAxis tickFormatter={(value) => formatPrice(value)} domain={getAxisDomain(priceHistory.filter(d => d.avgPrice !== null), 'avgPrice')} />
|
<YAxis tickFormatter={(value) => formatPrice(value)} domain={getAxisDomain(priceHistory.filter(d => d.avgPrice !== null), 'avgPrice')} />
|
||||||
<Tooltip
|
<Tooltip
|
||||||
formatter={(value, name) => [formatPrice(value), 'Avg Price']}
|
formatter={(value) => [formatPrice(value), 'Avg Price']}
|
||||||
labelFormatter={(date) => formatDate(date)}
|
labelFormatter={(date) => formatDate(date)}
|
||||||
/>
|
/>
|
||||||
<Area type="monotone" dataKey="avgPrice" stroke="#8B0000" fill="#8B0000" fillOpacity={0.1} />
|
<Area type="monotone" dataKey="avgPrice" stroke="#8B0000" fill="#8B0000" fillOpacity={0.1} />
|
||||||
@ -718,7 +720,7 @@ const ApartmentDashboard = () => {
|
|||||||
/>
|
/>
|
||||||
<YAxis domain={getAxisDomain(priceHistory, 'unitCount')} />
|
<YAxis domain={getAxisDomain(priceHistory, 'unitCount')} />
|
||||||
<Tooltip
|
<Tooltip
|
||||||
formatter={(value, name) => [value, 'Available Units']}
|
formatter={(value) => [value, 'Available Units']}
|
||||||
labelFormatter={(date) => formatDate(date)}
|
labelFormatter={(date) => formatDate(date)}
|
||||||
/>
|
/>
|
||||||
<Area type="monotone" dataKey="unitCount" stroke="#3B82F6" fill="#3B82F6" fillOpacity={0.2} />
|
<Area type="monotone" dataKey="unitCount" stroke="#3B82F6" fill="#3B82F6" fillOpacity={0.2} />
|
||||||
@ -760,7 +762,7 @@ const ApartmentDashboard = () => {
|
|||||||
<CartesianGrid strokeDasharray="3 3" />
|
<CartesianGrid strokeDasharray="3 3" />
|
||||||
<XAxis dataKey="name" angle={-45} textAnchor="end" height={80} />
|
<XAxis dataKey="name" angle={-45} textAnchor="end" height={80} />
|
||||||
<YAxis tickFormatter={(value) => formatPrice(value)} domain={getAxisDomain(planStats, 'avgPrice')} />
|
<YAxis tickFormatter={(value) => formatPrice(value)} domain={getAxisDomain(planStats, 'avgPrice')} />
|
||||||
<Tooltip formatter={(value, name) => [formatPrice(value), 'Avg Price']} />
|
<Tooltip formatter={(value) => [formatPrice(value), 'Avg Price']} />
|
||||||
<Bar dataKey="avgPrice" fill="#8B0000" />
|
<Bar dataKey="avgPrice" fill="#8B0000" />
|
||||||
</BarChart>
|
</BarChart>
|
||||||
</ResponsiveContainer>
|
</ResponsiveContainer>
|
||||||
@ -1475,7 +1477,7 @@ const ApartmentDashboard = () => {
|
|||||||
/>
|
/>
|
||||||
<YAxis tickFormatter={(value) => formatPrice(value)} domain={['dataMin - 50', 'dataMax + 50']} />
|
<YAxis tickFormatter={(value) => formatPrice(value)} domain={['dataMin - 50', 'dataMax + 50']} />
|
||||||
<Tooltip
|
<Tooltip
|
||||||
formatter={(value, name) => [formatPrice(value), modalTimeRange === 'year' ? 'Weekly Avg' : 'Price']}
|
formatter={(value) => [formatPrice(value), modalTimeRange === 'year' ? 'Weekly Avg' : 'Price']}
|
||||||
labelFormatter={(date) => formatDate(date)}
|
labelFormatter={(date) => formatDate(date)}
|
||||||
/>
|
/>
|
||||||
<Line type="monotone" dataKey="price" stroke="#8B0000" strokeWidth={2} dot={modalTimeRange === 'month'} />
|
<Line type="monotone" dataKey="price" stroke="#8B0000" strokeWidth={2} dot={modalTimeRange === 'month'} />
|
||||||
|
|||||||
@ -1,7 +1,8 @@
|
|||||||
import React, { createContext, useState, useEffect, useCallback } from 'react';
|
import { createContext, useState, useEffect, useCallback } from 'react';
|
||||||
|
|
||||||
const API_BASE = 'https://apartments.maverickapplications.com/api';
|
const API_BASE = 'https://apartments.maverickapplications.com/api';
|
||||||
|
|
||||||
|
// eslint-disable-next-line react-refresh/only-export-components
|
||||||
export const AuthContext = createContext(null);
|
export const AuthContext = createContext(null);
|
||||||
|
|
||||||
export const AuthProvider = ({ children }) => {
|
export const AuthProvider = ({ children }) => {
|
||||||
|
|||||||
@ -24,7 +24,8 @@ import {
|
|||||||
const API_BASE = 'https://apartments.maverickapplications.com/api';
|
const API_BASE = 'https://apartments.maverickapplications.com/api';
|
||||||
|
|
||||||
// Stats card component
|
// Stats card component
|
||||||
const StatsCard = ({ title, value, subtitle, icon: Icon, color = 'violet', loading = false }) => {
|
// eslint-disable-next-line no-unused-vars
|
||||||
|
const StatsCard = ({ title, value, subtitle, icon: IconComponent, color = 'violet', loading = false }) => {
|
||||||
const colorClasses = {
|
const colorClasses = {
|
||||||
violet: 'bg-violet-100 text-violet-600',
|
violet: 'bg-violet-100 text-violet-600',
|
||||||
green: 'bg-green-100 text-green-600',
|
green: 'bg-green-100 text-green-600',
|
||||||
@ -46,7 +47,7 @@ const StatsCard = ({ title, value, subtitle, icon: Icon, color = 'violet', loadi
|
|||||||
{subtitle && <p className="text-sm text-gray-500 mt-1">{subtitle}</p>}
|
{subtitle && <p className="text-sm text-gray-500 mt-1">{subtitle}</p>}
|
||||||
</div>
|
</div>
|
||||||
<div className={`p-3 rounded-full ${colorClasses[color]}`}>
|
<div className={`p-3 rounded-full ${colorClasses[color]}`}>
|
||||||
<Icon className="w-6 h-6" />
|
<IconComponent className="w-6 h-6" />
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
Reference in New Issue
Block a user