Compare commits

...
Author SHA1 Message Date
Shivam Mishra 060a43b0ff fix: typo 2024-12-05 10:45:24 +05:30
Shivam Mishra 3e5e4ca80f feat: add story config 2024-12-05 10:38:38 +05:30
Shivam Mishra 298034b5e8 feat: multiple vite configs 2024-12-04 20:43:42 +05:30
Shivam Mishra 353d89ea7b feat: add netlify 2024-12-04 20:12:12 +05:30
8 changed files with 149 additions and 105 deletions
+4
View File
@@ -0,0 +1,4 @@
[[redirects]]
from = "/*"
to = "/"
status = 200
+3 -3
View File
@@ -15,9 +15,9 @@
"build:sdk": "BUILD_MODE=library vite build",
"prepare": "husky install",
"size": "size-limit",
"story:dev": "histoire dev",
"story:build": "histoire build",
"story:preview": "histoire preview"
"story:dev": "BUILD_MODE=story histoire dev",
"story:build": "BUILD_MODE=story histoire build",
"story:preview": "BUILD_MODE=story histoire preview"
},
"size-limit": [
{
+19
View File
@@ -0,0 +1,19 @@
import { defineConfig } from 'vite';
import path from 'path';
export default defineConfig({
resolve: {
alias: {
vue: 'vue/dist/vue.esm-bundler.js',
components: path.resolve('./app/javascript/dashboard/components'),
next: path.resolve('./app/javascript/dashboard/components-next'),
v3: path.resolve('./app/javascript/v3'),
dashboard: path.resolve('./app/javascript/dashboard'),
helpers: path.resolve('./app/javascript/shared/helpers'),
shared: path.resolve('./app/javascript/shared'),
survey: path.resolve('./app/javascript/survey'),
widget: path.resolve('./app/javascript/widget'),
assets: path.resolve('./app/javascript/dashboard/assets'),
},
},
});
+26
View File
@@ -0,0 +1,26 @@
import { defineConfig } from 'vite';
import ruby from 'vite-plugin-ruby';
import vue from '@vitejs/plugin-vue';
import baseConfig from './vite.config.base';
import { mergeConfig } from 'vite';
const vueOptions = {
template: {
compilerOptions: {
isCustomElement: tag => ['ninja-keys'].includes(tag),
},
},
};
const defaultConfig = defineConfig({
plugins: [ruby(), vue(vueOptions)],
build: {
rollupOptions: {
output: {
inlineDynamicImports: false,
},
},
},
});
export default mergeConfig(baseConfig, defaultConfig);
+29
View File
@@ -0,0 +1,29 @@
import { defineConfig } from 'vite';
import path from 'path';
import baseConfig from './vite.config.base';
import { mergeConfig } from 'vite';
const libraryConfig = defineConfig({
plugins: [],
build: {
rollupOptions: {
output: {
dir: 'public/packs',
entryFileNames: chunkInfo => {
if (chunkInfo.name === 'sdk') {
return 'js/sdk.js';
}
return '[name].js';
},
inlineDynamicImports: true, // Disable code-splitting for SDK
},
},
lib: {
entry: path.resolve(__dirname, './app/javascript/entrypoints/sdk.js'),
formats: ['iife'], // IIFE format for single file
name: 'sdk',
},
},
});
export default mergeConfig(baseConfig, libraryConfig);
+18
View File
@@ -0,0 +1,18 @@
import { defineConfig } from 'vite';
import vue from '@vitejs/plugin-vue';
import baseConfig from './vite.config.base';
import { mergeConfig } from 'vite';
const vueOptions = {
template: {
compilerOptions: {
isCustomElement: tag => ['ninja-keys'].includes(tag),
},
},
};
const testConfig = defineConfig({
plugins: [vue(vueOptions)],
});
export default mergeConfig(baseConfig, testConfig);
+41
View File
@@ -0,0 +1,41 @@
import { defineConfig } from 'vite';
import vue from '@vitejs/plugin-vue';
import baseConfig from './vite.config.base';
import { mergeConfig } from 'vite';
const vueOptions = {
template: {
compilerOptions: {
isCustomElement: tag => ['ninja-keys'].includes(tag),
},
},
};
const testConfig = defineConfig({
plugins: [vue(vueOptions)],
test: {
environment: 'jsdom',
include: ['app/**/*.{test,spec}.?(c|m)[jt]s?(x)'],
coverage: {
reporter: ['lcov', 'text'],
include: ['app/**/*.js', 'app/**/*.vue'],
exclude: [
'app/**/*.@(spec|stories|routes).js',
'**/specs/**/*',
'**/i18n/**/*',
],
},
globals: true,
outputFile: 'coverage/sonar-report.xml',
server: {
deps: {
inline: ['tinykeys', '@material/mwc-icon'],
},
},
setupFiles: ['fake-indexeddb/auto', 'vitest.setup.js'],
mockReset: true,
clearMocks: true,
},
});
export default mergeConfig(baseConfig, testConfig);
+9 -102
View File
@@ -1,111 +1,18 @@
/// <reference types="vitest" />
/**
What's going on with library mode?
Glad you asked, here's a quick rundown:
1. vite-plugin-ruby will automatically bring all the entrypoints like dashbord and widget as input to vite.
2. vite needs to be in library mode to build the SDK as a single file. (UMD) format and set `inlineDynamicImports` to true.
3. But when setting `inlineDynamicImports` to true, vite will not be able to handle mutliple entrypoints.
This puts us in a deadlock, now there are two ways around this, either add another separate build pipeline to
the app using vanilla rollup or rspack or something. The second option is to remove sdk building from the main pipeline
and build it separately using Vite itself, toggled by an ENV variable.
`BUILD_MODE=library bin/vite build` should build only the SDK and save it to `public/packs/js/sdk.js`
`bin/vite build` will build the rest of the app as usual. But exclude the SDK.
We need to edit the `asset:precompile` rake task to include the SDK in the precompile list.
*/
import { defineConfig } from 'vite';
import ruby from 'vite-plugin-ruby';
import path from 'path';
import vue from '@vitejs/plugin-vue';
const isLibraryMode = process.env.BUILD_MODE === 'library';
const isTestMode = process.env.TEST === 'true';
const isStoryMode = process.env.BUILD_MODE === 'story';
const vueOptions = {
template: {
compilerOptions: {
isCustomElement: tag => ['ninja-keys'].includes(tag),
},
},
};
let plugins = [ruby(), vue(vueOptions)];
let config;
if (isLibraryMode) {
plugins = [];
config = import('./vite.config.lib');
} else if (isTestMode) {
plugins = [vue(vueOptions)];
config = import('./vite.config.test');
} else if (isStoryMode) {
config = import('./vite.config.story');
} else {
config = import('./vite.config.dev');
}
export default defineConfig({
plugins: plugins,
build: {
rollupOptions: {
output: {
// [NOTE] when not in library mode, no new keys will be addedd or overwritten
// setting dir: isLibraryMode ? 'public/packs' : undefined will not work
...(isLibraryMode
? {
dir: 'public/packs',
entryFileNames: chunkInfo => {
if (chunkInfo.name === 'sdk') {
return 'js/sdk.js';
}
return '[name].js';
},
}
: {}),
inlineDynamicImports: isLibraryMode, // Disable code-splitting for SDK
},
},
lib: isLibraryMode
? {
entry: path.resolve(__dirname, './app/javascript/entrypoints/sdk.js'),
formats: ['iife'], // IIFE format for single file
name: 'sdk',
}
: undefined,
},
resolve: {
alias: {
vue: 'vue/dist/vue.esm-bundler.js',
components: path.resolve('./app/javascript/dashboard/components'),
next: path.resolve('./app/javascript/dashboard/components-next'),
v3: path.resolve('./app/javascript/v3'),
dashboard: path.resolve('./app/javascript/dashboard'),
helpers: path.resolve('./app/javascript/shared/helpers'),
shared: path.resolve('./app/javascript/shared'),
survey: path.resolve('./app/javascript/survey'),
widget: path.resolve('./app/javascript/widget'),
assets: path.resolve('./app/javascript/dashboard/assets'),
},
},
test: {
environment: 'jsdom',
include: ['app/**/*.{test,spec}.?(c|m)[jt]s?(x)'],
coverage: {
reporter: ['lcov', 'text'],
include: ['app/**/*.js', 'app/**/*.vue'],
exclude: [
'app/**/*.@(spec|stories|routes).js',
'**/specs/**/*',
'**/i18n/**/*',
],
},
globals: true,
outputFile: 'coverage/sonar-report.xml',
server: {
deps: {
inline: ['tinykeys', '@material/mwc-icon'],
},
},
setupFiles: ['fake-indexeddb/auto', 'vitest.setup.js'],
mockReset: true,
clearMocks: true,
},
});
export default config;