Add pre-commit hooks for linting and formatting
Set up pre-commit framework with ruff (backend) and ESLint/Prettier/tsc (frontend) hooks to catch issues locally before CI. Auto-format all frontend files with Prettier to comply with the new check. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -36,15 +36,17 @@ export const createGame = (data: CreateGameInput) =>
|
||||
export const updateGame = (id: number, data: UpdateGameInput) =>
|
||||
api.put<Game>(`/games/${id}`, data)
|
||||
|
||||
export const deleteGame = (id: number) =>
|
||||
api.del(`/games/${id}`)
|
||||
export const deleteGame = (id: number) => api.del(`/games/${id}`)
|
||||
|
||||
// Routes
|
||||
export const createRoute = (gameId: number, data: CreateRouteInput) =>
|
||||
api.post<Route>(`/games/${gameId}/routes`, data)
|
||||
|
||||
export const updateRoute = (gameId: number, routeId: number, data: UpdateRouteInput) =>
|
||||
api.put<Route>(`/games/${gameId}/routes/${routeId}`, data)
|
||||
export const updateRoute = (
|
||||
gameId: number,
|
||||
routeId: number,
|
||||
data: UpdateRouteInput
|
||||
) => api.put<Route>(`/games/${gameId}/routes/${routeId}`, data)
|
||||
|
||||
export const deleteRoute = (gameId: number, routeId: number) =>
|
||||
api.del(`/games/${gameId}/routes/${routeId}`)
|
||||
@@ -53,7 +55,12 @@ export const reorderRoutes = (gameId: number, routes: RouteReorderItem[]) =>
|
||||
api.put<Route[]>(`/games/${gameId}/routes/reorder`, { routes })
|
||||
|
||||
// Pokemon
|
||||
export const listPokemon = (search?: string, limit = 50, offset = 0, type?: string) => {
|
||||
export const listPokemon = (
|
||||
search?: string,
|
||||
limit = 50,
|
||||
offset = 0,
|
||||
type?: string
|
||||
) => {
|
||||
const params = new URLSearchParams()
|
||||
if (search) params.set('search', search)
|
||||
if (type) params.set('type', type)
|
||||
@@ -68,11 +75,17 @@ export const createPokemon = (data: CreatePokemonInput) =>
|
||||
export const updatePokemon = (id: number, data: UpdatePokemonInput) =>
|
||||
api.put<Pokemon>(`/pokemon/${id}`, data)
|
||||
|
||||
export const deletePokemon = (id: number) =>
|
||||
api.del(`/pokemon/${id}`)
|
||||
export const deletePokemon = (id: number) => api.del(`/pokemon/${id}`)
|
||||
|
||||
export const bulkImportPokemon = (items: Array<{ pokeapiId: number; nationalDex: number; name: string; types: string[]; spriteUrl?: string | null }>) =>
|
||||
api.post<BulkImportResult>('/pokemon/bulk-import', items)
|
||||
export const bulkImportPokemon = (
|
||||
items: Array<{
|
||||
pokeapiId: number
|
||||
nationalDex: number
|
||||
name: string
|
||||
types: string[]
|
||||
spriteUrl?: string | null
|
||||
}>
|
||||
) => api.post<BulkImportResult>('/pokemon/bulk-import', items)
|
||||
|
||||
export const bulkImportEvolutions = (items: unknown[]) =>
|
||||
api.post<BulkImportResult>('/evolutions/bulk-import', items)
|
||||
@@ -84,7 +97,12 @@ export const bulkImportBosses = (gameId: number, items: unknown[]) =>
|
||||
api.post<BulkImportResult>(`/games/${gameId}/bosses/bulk-import`, items)
|
||||
|
||||
// Evolutions
|
||||
export const listEvolutions = (search?: string, limit = 50, offset = 0, trigger?: string) => {
|
||||
export const listEvolutions = (
|
||||
search?: string,
|
||||
limit = 50,
|
||||
offset = 0,
|
||||
trigger?: string
|
||||
) => {
|
||||
const params = new URLSearchParams()
|
||||
if (search) params.set('search', search)
|
||||
if (trigger) params.set('trigger', trigger)
|
||||
@@ -99,8 +117,7 @@ export const createEvolution = (data: CreateEvolutionInput) =>
|
||||
export const updateEvolution = (id: number, data: UpdateEvolutionInput) =>
|
||||
api.put<EvolutionAdmin>(`/evolutions/${id}`, data)
|
||||
|
||||
export const deleteEvolution = (id: number) =>
|
||||
api.del(`/evolutions/${id}`)
|
||||
export const deleteEvolution = (id: number) => api.del(`/evolutions/${id}`)
|
||||
|
||||
// Export
|
||||
export const exportGames = () =>
|
||||
@@ -119,11 +136,20 @@ export const exportEvolutions = () =>
|
||||
api.get<Record<string, unknown>[]>('/export/evolutions')
|
||||
|
||||
// Route Encounters
|
||||
export const addRouteEncounter = (routeId: number, data: CreateRouteEncounterInput) =>
|
||||
api.post<RouteEncounterDetail>(`/routes/${routeId}/pokemon`, data)
|
||||
export const addRouteEncounter = (
|
||||
routeId: number,
|
||||
data: CreateRouteEncounterInput
|
||||
) => api.post<RouteEncounterDetail>(`/routes/${routeId}/pokemon`, data)
|
||||
|
||||
export const updateRouteEncounter = (routeId: number, encounterId: number, data: UpdateRouteEncounterInput) =>
|
||||
api.put<RouteEncounterDetail>(`/routes/${routeId}/pokemon/${encounterId}`, data)
|
||||
export const updateRouteEncounter = (
|
||||
routeId: number,
|
||||
encounterId: number,
|
||||
data: UpdateRouteEncounterInput
|
||||
) =>
|
||||
api.put<RouteEncounterDetail>(
|
||||
`/routes/${routeId}/pokemon/${encounterId}`,
|
||||
data
|
||||
)
|
||||
|
||||
export const removeRouteEncounter = (routeId: number, encounterId: number) =>
|
||||
api.del(`/routes/${routeId}/pokemon/${encounterId}`)
|
||||
@@ -132,8 +158,11 @@ export const removeRouteEncounter = (routeId: number, encounterId: number) =>
|
||||
export const createBossBattle = (gameId: number, data: CreateBossBattleInput) =>
|
||||
api.post<BossBattle>(`/games/${gameId}/bosses`, data)
|
||||
|
||||
export const updateBossBattle = (gameId: number, bossId: number, data: UpdateBossBattleInput) =>
|
||||
api.put<BossBattle>(`/games/${gameId}/bosses/${bossId}`, data)
|
||||
export const updateBossBattle = (
|
||||
gameId: number,
|
||||
bossId: number,
|
||||
data: UpdateBossBattleInput
|
||||
) => api.put<BossBattle>(`/games/${gameId}/bosses/${bossId}`, data)
|
||||
|
||||
export const deleteBossBattle = (gameId: number, bossId: number) =>
|
||||
api.del(`/games/${gameId}/bosses/${bossId}`)
|
||||
@@ -141,15 +170,17 @@ export const deleteBossBattle = (gameId: number, bossId: number) =>
|
||||
export const reorderBosses = (gameId: number, bosses: BossReorderItem[]) =>
|
||||
api.put<BossBattle[]>(`/games/${gameId}/bosses/reorder`, { bosses })
|
||||
|
||||
export const setBossTeam = (gameId: number, bossId: number, team: BossPokemonInput[]) =>
|
||||
api.put<BossBattle>(`/games/${gameId}/bosses/${bossId}/pokemon`, team)
|
||||
export const setBossTeam = (
|
||||
gameId: number,
|
||||
bossId: number,
|
||||
team: BossPokemonInput[]
|
||||
) => api.put<BossBattle>(`/games/${gameId}/bosses/${bossId}/pokemon`, team)
|
||||
|
||||
// Genlockes
|
||||
export const updateGenlocke = (id: number, data: UpdateGenlockeInput) =>
|
||||
api.patch<Genlocke>(`/genlockes/${id}`, data)
|
||||
|
||||
export const deleteGenlocke = (id: number) =>
|
||||
api.del(`/genlockes/${id}`)
|
||||
export const deleteGenlocke = (id: number) => api.del(`/genlockes/${id}`)
|
||||
|
||||
export const addGenlockeLeg = (genlockeId: number, data: AddGenlockeLegInput) =>
|
||||
api.post<Genlocke>(`/genlockes/${genlockeId}/legs`, data)
|
||||
|
||||
@@ -1,7 +1,14 @@
|
||||
import { api } from './client'
|
||||
import type { BossBattle, BossResult, CreateBossResultInput } from '../types/game'
|
||||
import type {
|
||||
BossBattle,
|
||||
BossResult,
|
||||
CreateBossResultInput,
|
||||
} from '../types/game'
|
||||
|
||||
export function getGameBosses(gameId: number, all?: boolean): Promise<BossBattle[]> {
|
||||
export function getGameBosses(
|
||||
gameId: number,
|
||||
all?: boolean
|
||||
): Promise<BossBattle[]> {
|
||||
const params = all ? '?all=true' : ''
|
||||
return api.get(`/games/${gameId}/bosses${params}`)
|
||||
}
|
||||
@@ -10,10 +17,16 @@ export function getBossResults(runId: number): Promise<BossResult[]> {
|
||||
return api.get(`/runs/${runId}/boss-results`)
|
||||
}
|
||||
|
||||
export function createBossResult(runId: number, data: CreateBossResultInput): Promise<BossResult> {
|
||||
export function createBossResult(
|
||||
runId: number,
|
||||
data: CreateBossResultInput
|
||||
): Promise<BossResult> {
|
||||
return api.post(`/runs/${runId}/boss-results`, data)
|
||||
}
|
||||
|
||||
export function deleteBossResult(runId: number, resultId: number): Promise<void> {
|
||||
export function deleteBossResult(
|
||||
runId: number,
|
||||
resultId: number
|
||||
): Promise<void> {
|
||||
return api.del(`/runs/${runId}/boss-results/${resultId}`)
|
||||
}
|
||||
|
||||
@@ -10,10 +10,7 @@ export class ApiError extends Error {
|
||||
}
|
||||
}
|
||||
|
||||
async function request<T>(
|
||||
path: string,
|
||||
options?: RequestInit,
|
||||
): Promise<T> {
|
||||
async function request<T>(path: string, options?: RequestInit): Promise<T> {
|
||||
const res = await fetch(`${API_BASE}/api/v1${path}`, {
|
||||
...options,
|
||||
headers: {
|
||||
@@ -52,6 +49,5 @@ export const api = {
|
||||
body: JSON.stringify(body),
|
||||
}),
|
||||
|
||||
del: <T = void>(path: string) =>
|
||||
request<T>(path, { method: 'DELETE' }),
|
||||
del: <T = void>(path: string) => request<T>(path, { method: 'DELETE' }),
|
||||
}
|
||||
|
||||
@@ -9,14 +9,14 @@ import type {
|
||||
|
||||
export function createEncounter(
|
||||
runId: number,
|
||||
data: CreateEncounterInput,
|
||||
data: CreateEncounterInput
|
||||
): Promise<EncounterDetail> {
|
||||
return api.post(`/runs/${runId}/encounters`, data)
|
||||
}
|
||||
|
||||
export function updateEncounter(
|
||||
id: number,
|
||||
data: UpdateEncounterInput,
|
||||
data: UpdateEncounterInput
|
||||
): Promise<EncounterDetail> {
|
||||
return api.patch(`/encounters/${id}`, data)
|
||||
}
|
||||
@@ -25,7 +25,10 @@ export function deleteEncounter(id: number): Promise<void> {
|
||||
return api.del(`/encounters/${id}`)
|
||||
}
|
||||
|
||||
export function fetchEvolutions(pokemonId: number, region?: string): Promise<Evolution[]> {
|
||||
export function fetchEvolutions(
|
||||
pokemonId: number,
|
||||
region?: string
|
||||
): Promise<Evolution[]> {
|
||||
const params = region ? `?region=${encodeURIComponent(region)}` : ''
|
||||
return api.get(`/pokemon/${pokemonId}/evolutions${params}`)
|
||||
}
|
||||
@@ -34,6 +37,8 @@ export function fetchForms(pokemonId: number): Promise<Pokemon[]> {
|
||||
return api.get(`/pokemon/${pokemonId}/forms`)
|
||||
}
|
||||
|
||||
export function bulkRandomizeEncounters(runId: number): Promise<{ created: unknown[]; skippedRoutes: number }> {
|
||||
export function bulkRandomizeEncounters(
|
||||
runId: number
|
||||
): Promise<{ created: unknown[]; skippedRoutes: number }> {
|
||||
return api.post(`/runs/${runId}/encounters/bulk-randomize`, {})
|
||||
}
|
||||
|
||||
@@ -19,7 +19,10 @@ export function getGameRoutes(gameId: number): Promise<Route[]> {
|
||||
return api.get(`/games/${gameId}/routes?flat=true`)
|
||||
}
|
||||
|
||||
export function getRoutePokemon(routeId: number, gameId?: number): Promise<RouteEncounterDetail[]> {
|
||||
export function getRoutePokemon(
|
||||
routeId: number,
|
||||
gameId?: number
|
||||
): Promise<RouteEncounterDetail[]> {
|
||||
const params = gameId != null ? `?game_id=${gameId}` : ''
|
||||
return api.get(`/routes/${routeId}/pokemon${params}`)
|
||||
}
|
||||
|
||||
@@ -1,5 +1,15 @@
|
||||
import { api } from './client'
|
||||
import type { Genlocke, GenlockeListItem, GenlockeDetail, GenlockeGraveyard, GenlockeLineage, CreateGenlockeInput, Region, SurvivorEncounter, AdvanceLegInput } from '../types/game'
|
||||
import type {
|
||||
Genlocke,
|
||||
GenlockeListItem,
|
||||
GenlockeDetail,
|
||||
GenlockeGraveyard,
|
||||
GenlockeLineage,
|
||||
CreateGenlockeInput,
|
||||
Region,
|
||||
SurvivorEncounter,
|
||||
AdvanceLegInput,
|
||||
} from '../types/game'
|
||||
|
||||
export function getGenlockes(): Promise<GenlockeListItem[]> {
|
||||
return api.get('/genlockes')
|
||||
@@ -25,10 +35,20 @@ export function getGenlockeLineages(id: number): Promise<GenlockeLineage> {
|
||||
return api.get(`/genlockes/${id}/lineages`)
|
||||
}
|
||||
|
||||
export function getLegSurvivors(genlockeId: number, legOrder: number): Promise<SurvivorEncounter[]> {
|
||||
export function getLegSurvivors(
|
||||
genlockeId: number,
|
||||
legOrder: number
|
||||
): Promise<SurvivorEncounter[]> {
|
||||
return api.get(`/genlockes/${genlockeId}/legs/${legOrder}/survivors`)
|
||||
}
|
||||
|
||||
export function advanceLeg(genlockeId: number, legOrder: number, data?: AdvanceLegInput): Promise<Genlocke> {
|
||||
return api.post(`/genlockes/${genlockeId}/legs/${legOrder}/advance`, data ?? {})
|
||||
export function advanceLeg(
|
||||
genlockeId: number,
|
||||
legOrder: number,
|
||||
data?: AdvanceLegInput
|
||||
): Promise<Genlocke> {
|
||||
return api.post(
|
||||
`/genlockes/${genlockeId}/legs/${legOrder}/advance`,
|
||||
data ?? {}
|
||||
)
|
||||
}
|
||||
|
||||
@@ -10,10 +10,14 @@ export function fetchPokemonFamilies(): Promise<{ families: number[][] }> {
|
||||
return api.get('/pokemon/families')
|
||||
}
|
||||
|
||||
export function fetchPokemonEncounterLocations(pokemonId: number): Promise<PokemonEncounterLocation[]> {
|
||||
export function fetchPokemonEncounterLocations(
|
||||
pokemonId: number
|
||||
): Promise<PokemonEncounterLocation[]> {
|
||||
return api.get(`/pokemon/${pokemonId}/encounter-locations`)
|
||||
}
|
||||
|
||||
export function fetchPokemonEvolutionChain(pokemonId: number): Promise<EvolutionAdmin[]> {
|
||||
export function fetchPokemonEvolutionChain(
|
||||
pokemonId: number
|
||||
): Promise<EvolutionAdmin[]> {
|
||||
return api.get(`/pokemon/${pokemonId}/evolution-chain`)
|
||||
}
|
||||
|
||||
@@ -20,7 +20,7 @@ export function createRun(data: CreateRunInput): Promise<NuzlockeRun> {
|
||||
|
||||
export function updateRun(
|
||||
id: number,
|
||||
data: UpdateRunInput,
|
||||
data: UpdateRunInput
|
||||
): Promise<NuzlockeRun> {
|
||||
return api.patch(`/runs/${id}`, data)
|
||||
}
|
||||
@@ -33,7 +33,11 @@ export function getNamingCategories(): Promise<string[]> {
|
||||
return api.get('/runs/naming-categories')
|
||||
}
|
||||
|
||||
export function getNameSuggestions(runId: number, count = 10, pokemonId?: number): Promise<string[]> {
|
||||
export function getNameSuggestions(
|
||||
runId: number,
|
||||
count = 10,
|
||||
pokemonId?: number
|
||||
): Promise<string[]> {
|
||||
let url = `/runs/${runId}/name-suggestions?count=${count}`
|
||||
if (pokemonId != null) {
|
||||
url += `&pokemon_id=${pokemonId}`
|
||||
|
||||
Reference in New Issue
Block a user