Deploy Vue.js with Bantam CLI
Deploy Vue 3 applications and SPAs with zero configuration
Quick start:
# Build your Vue.js app
npm run build
# Deploy it
bantam deploy ./dist
Quick Start
Install dependencies
Ensure all Vue app dependencies are installed
npm install
Build your Vue app
Creates an optimized production build
npm run build
Deploy with Bantam
Your Vue app is now live!
bantam deploy ./dist
Framework Details
Build Configuration
Configure Vue build settings in vite.config.js
:
vite.config.js - Vue 3 with Vite:
import { defineConfig } from 'vite'
import vue from '@vitejs/plugin-vue'
export default defineConfig({
plugins: [vue()],
build: {
outDir: 'dist',
assetsDir: 'assets',
// Optimize chunk splitting
rollupOptions: {
output: {
manualChunks: {
'vue-vendor': ['vue', 'vue-router'],
}
}
}
}
})
vue.config.js - Vue CLI projects:
module.exports = {
publicPath: '/',
outputDir: 'dist',
assetsDir: 'static',
productionSourceMap: false,
css: {
extract: true,
sourceMap: false,
}
}
Router Configuration
Configure Vue Router for static hosting:
router/index.js - HTML5 History Mode:
import { createRouter, createWebHistory } from 'vue-router'
const router = createRouter({
history: createWebHistory(import.meta.env.BASE_URL),
routes: [
{ path: '/', component: Home },
{ path: '/about', component: About },
{ path: '/:pathMatch(.*)*', component: NotFound }
]
})
export default router
public/_redirects
file:/* /index.html 200
Environment Variables
Vue uses different prefixes depending on your build tool:
.env.production - Vite:
# Vite exposes VITE_ prefixed variables
VITE_APP_TITLE=My Vue App
VITE_API_ENDPOINT=https://api.example.com
VITE_PUBLIC_KEY=abc123
.env.production - Vue CLI:
# Vue CLI uses VUE_APP_ prefix
VUE_APP_TITLE=My Vue App
VUE_APP_API_ENDPOINT=https://api.example.com
VUE_APP_VERSION=1.0.0
Access in components:
// Vite
const apiUrl = import.meta.env.VITE_API_ENDPOINT
// Vue CLI
const apiUrl = process.env.VUE_APP_API_ENDPOINT
Asset Handling
Properly reference assets for production builds:
Import assets in components:
<template>
<!-- Static assets in public/ -->
<img src="/logo.png" alt="Logo">
<!-- Imported assets (recommended) -->
<img :src="logoUrl" alt="Logo">
<!-- Dynamic assets -->
<img :src="getImageUrl(imageName)" alt="Dynamic">
</template>
<script setup>
import logoUrl from '@/assets/logo.png'
const getImageUrl = (name) => {
return new URL(`../assets/${name}`, import.meta.url).href
}
</script>
Advanced Usage
Custom Domain
Deploy directly to your own domain
bantam deploy ./dist --domain myapp.com
Permanent Deployment
Keep your site online forever (requires login)
bantam deploy ./dist --permanent
Custom Expiry
Set how long your deployment stays online
bantam deploy ./dist --expiry-days 7
Custom Subdomain
Choose your own subdomain on bantam.site
bantam deploy ./dist --subdomain my-project
CI/CD Integration
Add Bantam to your continuous deployment pipeline:
# GitHub Actions example
- name: Deploy to Bantam
run: |
npm install -g @bantamhq/cli
bantam login --token ${{ secrets.BANTAM_TOKEN }}
bantam deploy ./dist --domain myapp.com --permanent
Common Issues & Solutions
Quick fixes for deployment challenges
01.Blank page after deployment
Common causes and solutions:
- Wrong
publicPath
orbase
setting - Missing
_redirects
file for client routing - Console errors - check browser DevTools
// vite.config.js
export default defineConfig({
base: '/', // Must match deployment path
})
// vue.config.js
module.exports = {
publicPath: '/', // Must match deployment path
}
02.Build fails with module errors
Resolve common module issues:
# Clear cache and reinstall
rm -rf node_modules package-lock.json
npm install
# For Vite projects
npm run build -- --debug
# For Vue CLI projects
vue-cli-service build --modern
03.How to handle dynamic routes?
For dynamic routes in Vue Router:
// Generate static pages for dynamic routes
// vite.config.js with vite-plugin-pages
import Pages from 'vite-plugin-pages'
export default defineConfig({
plugins: [
vue(),
Pages({
extendRoute(route) {
if (route.path === '/posts/:id') {
// Return array of params for static generation
return [
{ params: { id: '1' } },
{ params: { id: '2' } },
]
}
}
})
]
})
04.Large bundle size warnings
Optimize your Vue bundle:
// Analyze bundle size
npm run build -- --report
// vite.config.js optimizations
export default defineConfig({
build: {
rollupOptions: {
output: {
manualChunks(id) {
if (id.includes('node_modules')) {
if (id.includes('vue')) return 'vue-vendor'
if (id.includes('lodash')) return 'lodash'
return 'vendor'
}
}
}
},
// Tree-shake unused CSS
cssCodeSplit: true,
}
})
05.Composition API vs Options API for static sites?
Both work fine for static deployments. Composition API with <script setup>
often results in smaller bundles:
<!-- Composition API (recommended) -->
<script setup>
import { ref, computed } from 'vue'
const count = ref(0)
const doubled = computed(() => count.value * 2)
</script>
<!-- Options API (still valid) -->
<script>
export default {
data() {
return { count: 0 }
},
computed: {
doubled() {
return this.count * 2
}
}
}
</script>