Files
pantry/app/scripts/verify-pwa.js
Pantry Lead Agent 9bdbe9a420
Some checks failed
Deploy to Coolify / Deploy to Test (pull_request) Has been cancelled
Pull Request Checks / Validate PR (pull_request) Has been cancelled
Deploy to Coolify / Deploy to Production (pull_request) Has been cancelled
Deploy to Coolify / Code Quality (pull_request) Has been cancelled
Deploy to Coolify / Run Tests (pull_request) Has been cancelled
Deploy to Coolify / Deploy to Development (pull_request) Has been cancelled
feat: add PWA offline testing documentation and verification (#36)
- Create comprehensive PWA_TESTING.md guide
- Add automated verify-pwa script
- Document all test categories:
  - PWA manifest & installation
  - Service worker functionality
  - Offline mode
  - Cross-platform testing
  - Performance testing
  - Storage management
- Include platform-specific test cases
- Add troubleshooting section
- Create success criteria checklist
- Verify all PWA components present

Testing script checks:
- All icon assets exist
- Screenshots present
- Nuxt config valid
- Composables available
- Components present
- Offline page exists

All automated checks pass 

Closes #36
2026-02-25 00:11:21 +00:00

142 lines
4.6 KiB
JavaScript
Raw Permalink Blame History

This file contains invisible Unicode characters
This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
#!/usr/bin/env node
/**
* Verify PWA Configuration
*
* Checks that all PWA assets and configuration are present and valid.
*/
import { readFile, access } from 'fs/promises';
import { join, dirname } from 'path';
import { fileURLToPath } from 'url';
const __dirname = dirname(fileURLToPath(import.meta.url));
const publicDir = join(__dirname, '..', 'public');
const configPath = join(__dirname, '..', 'nuxt.config.ts');
let errors = [];
let warnings = [];
async function checkFileExists(path, description) {
try {
await access(path);
console.log(`${description}`);
return true;
} catch {
errors.push(`${description} - File not found: ${path}`);
return false;
}
}
async function verifyPWA() {
console.log('🔍 Verifying PWA Configuration...\n');
// Check icons
console.log('Icons:');
await checkFileExists(join(publicDir, 'icon.svg'), 'Source icon (SVG)');
await checkFileExists(join(publicDir, 'icon-192x192.png'), 'Icon 192x192');
await checkFileExists(join(publicDir, 'icon-512x512.png'), 'Icon 512x512');
await checkFileExists(join(publicDir, 'icon-192x192-maskable.png'), 'Maskable icon 192x192');
await checkFileExists(join(publicDir, 'icon-512x512-maskable.png'), 'Maskable icon 512x512');
await checkFileExists(join(publicDir, 'favicon.ico'), 'Favicon');
await checkFileExists(join(publicDir, 'apple-touch-icon.png'), 'Apple touch icon');
// Check screenshots
console.log('\nScreenshots:');
await checkFileExists(join(publicDir, 'screenshot-mobile.png'), 'Mobile screenshot');
await checkFileExists(join(publicDir, 'screenshot-desktop.png'), 'Desktop screenshot');
// Check Nuxt config
console.log('\nConfiguration:');
const configExists = await checkFileExists(configPath, 'Nuxt config file');
if (configExists) {
const config = await readFile(configPath, 'utf-8');
// Check for required PWA configuration
if (config.includes('@vite-pwa/nuxt')) {
console.log('✓ @vite-pwa/nuxt module configured');
} else {
errors.push('✗ @vite-pwa/nuxt module not found in config');
}
if (config.includes('registerType')) {
console.log('✓ Service worker registration configured');
} else {
warnings.push('⚠ Service worker registration type not set');
}
if (config.includes('manifest')) {
console.log('✓ PWA manifest configured');
} else {
errors.push('✗ PWA manifest configuration missing');
}
if (config.includes('workbox')) {
console.log('✓ Workbox configured');
} else {
warnings.push('⚠ Workbox configuration missing');
}
// Check for important manifest fields
if (config.includes('theme_color')) {
console.log('✓ Theme color configured');
} else {
warnings.push('⚠ Theme color not configured');
}
if (config.includes('display')) {
console.log('✓ Display mode configured');
} else {
warnings.push('⚠ Display mode not configured');
}
}
// Check composables
console.log('\nComposables:');
await checkFileExists(join(__dirname, '..', 'composables', 'usePWAInstall.ts'), 'usePWAInstall composable');
await checkFileExists(join(__dirname, '..', 'composables', 'useOnlineStatus.ts'), 'useOnlineStatus composable');
// Check components
console.log('\nComponents:');
await checkFileExists(join(__dirname, '..', 'components', 'InstallPrompt.vue'), 'InstallPrompt component');
await checkFileExists(join(__dirname, '..', 'components', 'OfflineBanner.vue'), 'OfflineBanner component');
// Check pages
console.log('\nPages:');
await checkFileExists(join(__dirname, '..', 'pages', 'offline.vue'), 'Offline fallback page');
// Print summary
console.log('\n' + '='.repeat(60));
if (errors.length === 0 && warnings.length === 0) {
console.log('✅ PWA configuration is valid!');
console.log('\nNext steps:');
console.log('1. Run `npm run dev` and test in browser');
console.log('2. Check DevTools → Application → Manifest');
console.log('3. Test offline functionality');
console.log('4. Run Lighthouse PWA audit');
return 0;
}
if (warnings.length > 0) {
console.log('\n⚠ Warnings:');
warnings.forEach(w => console.log(w));
}
if (errors.length > 0) {
console.log('\n❌ Errors:');
errors.forEach(e => console.log(e));
console.log('\nPWA configuration is incomplete. Please fix the errors above.');
return 1;
}
console.log('\n✅ PWA configuration is mostly valid (with warnings).');
return 0;
}
verifyPWA()
.then(code => process.exit(code))
.catch(error => {
console.error('\n❌ Verification failed:', error.message);
process.exit(1);
});