vite.config.mts 5.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194
  1. import { defineConfig, loadEnv } from "vite";
  2. import react from "@vitejs/plugin-react";
  3. import svgrPlugin from "vite-plugin-svgr";
  4. import { ViteEjsPlugin } from "vite-plugin-ejs";
  5. import { VitePWA } from "vite-plugin-pwa";
  6. import checker from "vite-plugin-checker";
  7. // To load .env.local variables
  8. const envVars = loadEnv("", `../`);
  9. // https://vitejs.dev/config/
  10. export default defineConfig({
  11. server: {
  12. port: Number(envVars.VITE_APP_PORT || 3000),
  13. // open the browser
  14. open: true,
  15. },
  16. // We need to specify the envDir since now there are no
  17. //more located in parallel with the vite.config.ts file but in parent dir
  18. envDir: "../",
  19. build: {
  20. outDir: "build",
  21. rollupOptions: {
  22. output: {
  23. // Creating separate chunk for locales except for en and percentages.json so they
  24. // can be cached at runtime and not merged with
  25. // app precache. en.json and percentages.json are needed for first load
  26. // or fallback hence not clubbing with locales so first load followed by offline mode works fine. This is how CRA used to work too.
  27. manualChunks(id) {
  28. if (
  29. id.includes("packages/excalidraw/locales") &&
  30. id.match(/en.json|percentages.json/) === null
  31. ) {
  32. const index = id.indexOf("locales/");
  33. // Taking the substring after "locales/"
  34. return `locales/${id.substring(index + 8)}`;
  35. }
  36. },
  37. },
  38. },
  39. sourcemap: true,
  40. },
  41. plugins: [
  42. react(),
  43. checker({
  44. typescript: true,
  45. eslint:
  46. envVars.VITE_APP_ENABLE_ESLINT === "false"
  47. ? undefined
  48. : { lintCommand: 'eslint "./**/*.{js,ts,tsx}"' },
  49. overlay: {
  50. initialIsOpen: envVars.VITE_APP_COLLAPSE_OVERLAY === "false",
  51. badgeStyle: "margin-bottom: 4rem; margin-left: 1rem",
  52. },
  53. }),
  54. svgrPlugin(),
  55. ViteEjsPlugin(),
  56. VitePWA({
  57. registerType: "autoUpdate",
  58. devOptions: {
  59. /* set this flag to true to enable in Development mode */
  60. enabled: false,
  61. },
  62. workbox: {
  63. // Don't push fonts and locales to app precache
  64. globIgnores: ["fonts.css", "**/locales/**", "service-worker.js"],
  65. runtimeCaching: [
  66. {
  67. urlPattern: new RegExp("/.+.(ttf|woff2|otf)"),
  68. handler: "CacheFirst",
  69. options: {
  70. cacheName: "fonts",
  71. expiration: {
  72. maxEntries: 50,
  73. maxAgeSeconds: 60 * 60 * 24 * 90, // <== 90 days
  74. },
  75. },
  76. },
  77. {
  78. urlPattern: new RegExp("fonts.css"),
  79. handler: "StaleWhileRevalidate",
  80. options: {
  81. cacheName: "fonts",
  82. expiration: {
  83. maxEntries: 50,
  84. },
  85. },
  86. },
  87. {
  88. urlPattern: new RegExp("locales/[^/]+.js"),
  89. handler: "CacheFirst",
  90. options: {
  91. cacheName: "locales",
  92. expiration: {
  93. maxEntries: 50,
  94. maxAgeSeconds: 60 * 60 * 24 * 30, // <== 30 days
  95. },
  96. },
  97. },
  98. ],
  99. },
  100. manifest: {
  101. short_name: "Excalidraw",
  102. name: "Excalidraw",
  103. description:
  104. "Excalidraw is a whiteboard tool that lets you easily sketch diagrams that have a hand-drawn feel to them.",
  105. icons: [
  106. {
  107. src: "android-chrome-192x192.png",
  108. sizes: "192x192",
  109. type: "image/png",
  110. },
  111. {
  112. src: "apple-touch-icon.png",
  113. type: "image/png",
  114. sizes: "180x180",
  115. },
  116. {
  117. src: "favicon-32x32.png",
  118. sizes: "32x32",
  119. type: "image/png",
  120. },
  121. {
  122. src: "favicon-16x16.png",
  123. sizes: "16x16",
  124. type: "image/png",
  125. },
  126. ],
  127. start_url: "/",
  128. display: "standalone",
  129. theme_color: "#121212",
  130. background_color: "#ffffff",
  131. file_handlers: [
  132. {
  133. action: "/",
  134. accept: {
  135. "application/vnd.excalidraw+json": [".excalidraw"],
  136. },
  137. },
  138. ],
  139. share_target: {
  140. action: "/web-share-target",
  141. method: "POST",
  142. enctype: "multipart/form-data",
  143. params: {
  144. files: [
  145. {
  146. name: "file",
  147. accept: [
  148. "application/vnd.excalidraw+json",
  149. "application/json",
  150. ".excalidraw",
  151. ],
  152. },
  153. ],
  154. },
  155. },
  156. screenshots: [
  157. {
  158. src: "/screenshots/virtual-whiteboard.png",
  159. type: "image/png",
  160. sizes: "462x945",
  161. },
  162. {
  163. src: "/screenshots/wireframe.png",
  164. type: "image/png",
  165. sizes: "462x945",
  166. },
  167. {
  168. src: "/screenshots/illustration.png",
  169. type: "image/png",
  170. sizes: "462x945",
  171. },
  172. {
  173. src: "/screenshots/shapes.png",
  174. type: "image/png",
  175. sizes: "462x945",
  176. },
  177. {
  178. src: "/screenshots/collaboration.png",
  179. type: "image/png",
  180. sizes: "462x945",
  181. },
  182. {
  183. src: "/screenshots/export.png",
  184. type: "image/png",
  185. sizes: "462x945",
  186. },
  187. ],
  188. },
  189. }),
  190. ],
  191. publicDir: "../public",
  192. });