Host module yang hilang
npm run build gagal dengan Failed to resolve import "@/routes/login", atau pesan serupa yang menyebut @/components/UserMenuContent atau @/types/ui. Module-module tersebut memang milik aplikasi Anda: Wayfinder menghasilkan sebagian berdasarkan route table aplikasi, sedangkan Laravel Vue starter kit menyediakan sisanya. Gunakan halaman ini ketika build tidak dapat me-resolve sebuah specifier, atau ketika menambahkan panel ke aplikasi yang bukan berasal dari starter kit.
Mulai dari sini
Installer dapat menyebutkan semua module yang hilang dan, jika dijalankan seperti ini, tidak mengubah aplikasi:
php artisan panel:install --no-panel --no-user --no-interaction WARN 1 thing(s) this package cannot do for your application:
1. The published components import these modules, which belong to your application and are
not there yet:
@/routes/two-factor
@/components/UserMenuContent
@/composables/useTwoFactorAuth
`@/routes/*` and `@/actions/*` are generated — run `php artisan wayfinder:generate`.
The rest come with a Laravel Vue starter kit.2
3
4
5
6
7
8
9
10
11
Pada kasus umum, dua command berikut sudah cukup:
php artisan wayfinder:generate
npm run build2
Membaca hasil pemeriksaan melalui PHP
PandaPanel\Support\Installer\FrontendRequirements adalah class yang digunakan installer, dan dapat dipanggil dari mana saja — tinker, test, maupun deployment check.
use PandaPanel\Support\Installer\FrontendRequirements;
FrontendRequirements::missingHostModules();
// ['@/routes/two-factor', '@/components/UserMenuContent']2
3
4
| Method | Signature | Mengembalikan |
|---|---|---|
missingHostModules | static missingHostModules(): array | list<string> — specifier @/… yang tidak ditemukan di disk |
npmPackages | static npmPackages(): array | list<string> — pasangan name@range dari dependencies milik package |
missingNpmPackages | static missingNpmPackages(): array | pasangan yang sama, dikurangi dependency yang sudah dideklarasikan aplikasi |
hasVite | static hasVite(): bool | apakah vite.config.ts atau vite.config.js tersedia |
missingInertia | static missingInertia(): array | list<string> — bagian Inertia yang hilang, dalam bentuk deskripsi |
layoutOverrides | static layoutOverrides(): array | list<array{file: string, line: int, code: string}> |
use PandaPanel\Support\Installer\FrontendRequirements;
FrontendRequirements::hasVite(); // false → the components are Vue and need a build
FrontendRequirements::missingInertia(); // ['an Inertia root view at resources/views/app.blade.php']
FrontendRequirements::missingNpmPackages();
// ['reka-ui@^2.0.0', 'vue-sonner@^2.0.0']
FrontendRequirements::layoutOverrides();
// [['file' => 'resources/js/app.ts', 'line' => 12, 'code' => 'page.default.layout = AppLayout;']]2
3
4
5
6
7
8
Sembilan belas host module
Daftar private HOST_MODULES di dalam FrontendRequirements, sesuai urutan deklarasinya. Dari luar class, baca melalui missingHostModules().
| Module | Berasal dari |
|---|---|
@/routes | Wayfinder |
@/routes/login | Wayfinder |
@/routes/register | Wayfinder |
@/routes/password | Wayfinder |
@/routes/two-factor | Wayfinder |
@/routes/verification | Wayfinder |
@/actions/App/Http/Controllers/Settings/ProfileController | Wayfinder |
@/actions/App/Http/Controllers/Settings/SecurityController | Wayfinder |
@/actions/Laravel/Passkeys/Http/Controllers/PasskeyRegistrationController | Wayfinder |
@/components/Heading | starter kit |
@/components/UserInfo | starter kit |
@/components/UserMenuContent | starter kit |
@/components/PasskeyItem | starter kit |
@/components/PasskeyRegister | starter kit |
@/components/TwoFactorRecoveryCodes | starter kit |
@/components/TwoFactorSetupModal | starter kit |
@/composables/useTwoFactorAuth | starter kit |
@/types | starter kit |
@/types/ui | starter kit — diimpor oleh broadcasting dan flash bridge panel |
Bentuk module yang hilang memberi tahu apa yang harus dilakukan. Jika seluruh @/routes/* dan @/actions/* hilang, Wayfinder belum dijalankan. Jika hanya beberapa component yang hilang, aplikasi kemungkinan bukan Laravel Vue starter kit dan file-file tersebut perlu Anda sediakan sendiri.
Cara module dicari
Specifier @/x berarti resources/js/x. Setiap nama dicoba dengan suffix berikut, secara berurutan:
.ts .vue .d.ts /index.ts /index.vue /index.d.tsPemeriksaan tidak mengandalkan extension tertentu karena module Wayfinder adalah .ts, component adalah .vue, dan starter kit dapat menyimpan module sebagai directory dengan index file.
Sengaja tidak ada bare match dalam daftar tersebut. File::exists() juga mengembalikan true untuk sebuah directory, sehingga bare entry pernah membuat module berbentuk directory terlihat valid padahal sebenarnya tidak ada file module yang dapat diimpor. Contohnya, @/types dapat terlihat terpenuhi hanya karena package membuat folder resources/js/types/, walaupun file yang diimpor tidak pernah ada. .d.ts disertakan karena starter kit dapat menulis shared types sebagai resources/js/types/index.d.ts, yang memang valid untuk @/types.
Karena itu, keberadaan directory dari ls resources/js/types bukan bukti bahwa module tersedia:
ls resources/js/types/index.d.ts resources/js/types/ui.ts 2>/dev/nullMemperbaiki module yang digenerate
php artisan wayfinder:generateWayfinder menulis resources/js/routes/** dan resources/js/actions/** berdasarkan route table dan controller milik aplikasi. Banyak project tidak melakukan commit terhadap output tersebut, sehingga fresh clone dan setiap CI job perlu menjalankan command ini sebelum npm run build.
Tiga module @/actions/* menunjuk controller yang disediakan starter kit: Settings\ProfileController, Settings\SecurityController, dan — dari laravel/passkeys — PasskeyRegistrationController. Aplikasi yang tidak memiliki controller tersebut juga tidak akan menghasilkan module action terkait. Screen profile, security, dan passkey milik panel adalah bagian yang mengimpornya.
Menyediakan module lainnya secara manual
Jika aplikasi bukan starter kit, component yang dibutuhkan harus tersedia. Repository package ini memiliki stand-in minimal untuk masing-masing module di frontend/host/, hanya untuk kebutuhan type-check dan build package itu sendiri. Tidak ada file di sana yang dipublikasikan atau dapat diakses aplikasi, tetapi setiap stand-in mendeklarasikan props, emits, dan exports yang benar-benar digunakan komponen panel, sehingga dapat dijadikan spesifikasi kontraknya.
// resources/js/types/ui.ts — the flash toast the panel's middleware writes
export interface FlashToast {
type: 'success' | 'error' | 'warning' | 'info';
message: string;
url?: string | null;
urlLabel?: string | null;
}2
3
4
5
6
7
// resources/js/composables/useTwoFactorAuth.ts
import type { Ref } from 'vue';
export function useTwoFactorAuth(): {
hasSetupData: Ref<boolean>;
clearTwoFactorAuthData: () => void;
};2
3
4
5
6
7
<!-- resources/js/components/Heading.vue -->
<script setup lang="ts">
defineProps<{
title: string;
description?: string;
variant?: 'default' | 'small';
}>();
</script>2
3
4
5
6
7
8
Ikuti surface contract-nya, bukan styling-nya. Styling tetap milik aplikasi Anda.
Sisi lain dari error build yang sama
Pesan Failed to resolve import yang sama juga dapat berarti npm dependency hilang. Cara membedakannya adalah bentuk specifier: @/… adalah host module, sedangkan nama lain adalah package dependency.
use PandaPanel\Support\Installer\FrontendRequirements;
FrontendRequirements::missingNpmPackages();2
3
npm install @inertiajs/vue3@^3.0.0 reka-ui@^2.0.0 vue-sonner@^2.0.0
npm run build2
npmPackages() membaca block dependencies dari package.json milik package ini, bukan menyalin daftar package ke dalam PHP. Menjaga daftar kedua akan cepat stale saat sebuah component menambahkan import baru. missingNpmPackages() membandingkan daftar tersebut terhadap package.json aplikasi, membaca dependencies dan devDependencies, karena yang penting adalah project mendeklarasikan dependency tersebut. Transitive dependency yang kebetulan ada di node_modules hari ini dapat hilang ketika package lain di-upgrade besok.
Aplikasi yang sama sekali tidak memiliki package.json dianggap kehilangan seluruh daftar dependency.
Catatan
- Host module yang hilang menyebabkan
npm run buildgagal dengan pesan module specifier. Pesan itu benar, tetapi tidak menjelaskan konteks package; karena itu installer memeriksa dan menyebutkan module yang hilang satu per satu. package.jsondi-export-ignoreoleh.gitattributes. Karena itu, instalasi Composer dari dist archive tidak memiliki salinan file tersebut divendor/chocoalano/panel, dannpmPackages()— yang memang membaca file itu — mengembalikan daftar kosong. Laporan dependency npm dari installer hanya lengkap ketika package diinstal dari source; daftar lengkap tersedia di Frontend requirements.- Directory bukan module. Keberadaan
resources/js/types/tidak memenuhi@/types; harus ada.ts,.d.ts, atau index file yang dapat di-resolve. missingNpmPackages()membacapackage.json, bukannode_modules, secara sengaja.- Tidak ada file dari
frontend/hostyang dikirim. Directory tersebut di-export-ignore, dan import@/…dalam published file selalu di-resolve terhadapresources/jsmilik aplikasi. - Account menu item adalah tanggung jawab aplikasi untuk dirender.
panel.shell.userMenuItemsdikirim melalui response;UserMenuContent.vueadalah component milik host, sehingga package tidak menggambar item tersebut sendiri. - Sebuah test menghasilkan daftar module dari import di published tree lalu membandingkannya dengan
FrontendRequirements, sehingga module baru yang dipakai code tetapi belum masuk daftar akan gagal di repository package, bukan baru gagal pada build aplikasi pengguna.