create-snapify-app 0.0.0-stage → 1.1.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (614) hide show
  1. package/LICENSE.md +24 -0
  2. package/README.md +55 -2
  3. package/bin/create-snapify-app.mjs +174 -0
  4. package/lib/args.mjs +59 -0
  5. package/lib/copy.mjs +44 -0
  6. package/lib/env.mjs +84 -0
  7. package/lib/prompt.mjs +63 -0
  8. package/package.json +35 -4
  9. package/template/.env.example +79 -0
  10. package/template/.github/workflows/ci.yml +23 -0
  11. package/template/.github/workflows/deploy.yml +26 -0
  12. package/template/.github/workflows/ping.yml +8 -0
  13. package/template/.github/workflows/release.yml +67 -0
  14. package/template/.snapify-install.json +5 -0
  15. package/template/CHANGELOG.md +28 -0
  16. package/template/LICENSE +14 -0
  17. package/template/README.md +287 -0
  18. package/template/administrator.html +23 -0
  19. package/template/apps/client/src/App.tsx +765 -0
  20. package/template/apps/client/src/auth.css +400 -0
  21. package/template/apps/client/src/lib/api.ts +22 -0
  22. package/template/apps/client/src/main.tsx +20 -0
  23. package/template/apps/community/src/App.tsx +592 -0
  24. package/template/apps/community/src/main.tsx +20 -0
  25. package/template/apps/community/src/styles.css +24 -0
  26. package/template/apps/developers/src/App.tsx +643 -0
  27. package/template/apps/developers/src/main.tsx +17 -0
  28. package/template/apps/developers/src/pages.tsx +1587 -0
  29. package/template/apps/developers/src/styles.css +98 -0
  30. package/template/apps/developers/src/ui.tsx +179 -0
  31. package/template/apps/landing/src/App.tsx +598 -0
  32. package/template/apps/landing/src/LegalPages.tsx +158 -0
  33. package/template/apps/landing/src/OrderPage.tsx +381 -0
  34. package/template/apps/landing/src/SeoPages.tsx +923 -0
  35. package/template/apps/landing/src/copy.ts +195 -0
  36. package/template/apps/landing/src/main.tsx +20 -0
  37. package/template/apps/landing/src/styles.css +803 -0
  38. package/template/apps/landing/src/types.ts +19 -0
  39. package/template/apps/marketplace/src/App.tsx +1229 -0
  40. package/template/apps/marketplace/src/developer/DeveloperApp.tsx +1266 -0
  41. package/template/apps/marketplace/src/main.tsx +20 -0
  42. package/template/apps/marketplace/src/styles.css +1001 -0
  43. package/template/apps/shared/AuthContext.tsx +65 -0
  44. package/template/apps/shared/Logo.tsx +33 -0
  45. package/template/apps/shared/api.ts +47 -0
  46. package/template/apps/shared/ui.tsx +128 -0
  47. package/template/apps/superadmin/src/App.tsx +1264 -0
  48. package/template/apps/superadmin/src/lib/api.ts +20 -0
  49. package/template/apps/superadmin/src/lib/hooks.ts +20 -0
  50. package/template/apps/superadmin/src/main.tsx +16 -0
  51. package/template/apps/superadmin/src/pages/ClientsPage.tsx +185 -0
  52. package/template/apps/superadmin/src/pages/InvoicesPage.tsx +157 -0
  53. package/template/apps/superadmin/src/pages/NewsletterPage.tsx +212 -0
  54. package/template/apps/superadmin/src/pages/OrdersPage.tsx +195 -0
  55. package/template/apps/superadmin/src/pages/PaymentsPage.tsx +150 -0
  56. package/template/apps/superadmin/src/pages/PayoutsPage.tsx +133 -0
  57. package/template/apps/superadmin/src/pages/PublishersPage.tsx +151 -0
  58. package/template/apps/superadmin/src/pages/SeoControlPage.tsx +692 -0
  59. package/template/apps/superadmin/src/pages/SettingsPage.tsx +199 -0
  60. package/template/apps/superadmin/src/pages/SystemPage.tsx +109 -0
  61. package/template/apps/superadmin/src/pages/TicketsPage.tsx +201 -0
  62. package/template/apps/superadmin/src/pages/UsersPage.tsx +167 -0
  63. package/template/client.html +21 -0
  64. package/template/community/hamdiayari/akhbar/README.md +23 -0
  65. package/template/community/hamdiayari/akhbar/screenshot.jpg +0 -0
  66. package/template/community/hamdiayari/akhbar/snapify.theme.json +76 -0
  67. package/template/community/hamdiayari/akhbar/src/Brand.tsx +26 -0
  68. package/template/community/hamdiayari/akhbar/src/Footer.tsx +182 -0
  69. package/template/community/hamdiayari/akhbar/src/Header.tsx +191 -0
  70. package/template/community/hamdiayari/akhbar/src/Layout.tsx +49 -0
  71. package/template/community/hamdiayari/akhbar/src/Social.tsx +33 -0
  72. package/template/community/hamdiayari/akhbar/src/Ticker.tsx +86 -0
  73. package/template/community/hamdiayari/akhbar/src/Views.tsx +285 -0
  74. package/template/community/hamdiayari/akhbar/src/blocks/CollectionBlocks.tsx +672 -0
  75. package/template/community/hamdiayari/akhbar/src/blocks/ContentBlocks.tsx +305 -0
  76. package/template/community/hamdiayari/akhbar/src/blocks/ConversionBlocks.tsx +569 -0
  77. package/template/community/hamdiayari/akhbar/src/blocks/HeaderBlocks.tsx +287 -0
  78. package/template/community/hamdiayari/akhbar/src/index.tsx +51 -0
  79. package/template/community/hamdiayari/akhbar/src/kit.tsx +357 -0
  80. package/template/community/hamdiayari/akhbar/src/site.ts +96 -0
  81. package/template/community/hamdiayari/akhbar/src/styles.css +566 -0
  82. package/template/community/hamdiayari/akhbar-actualites/README.md +28 -0
  83. package/template/community/hamdiayari/akhbar-actualites/screenshot.jpg +0 -0
  84. package/template/community/hamdiayari/akhbar-actualites/snapify.module.json +107 -0
  85. package/template/community/hamdiayari/akhbar-actualites/src/admin/AudiencePage.tsx +185 -0
  86. package/template/community/hamdiayari/akhbar-actualites/src/admin/index.tsx +11 -0
  87. package/template/community/hamdiayari/akhbar-actualites/src/public/Archive.tsx +142 -0
  88. package/template/community/hamdiayari/akhbar-actualites/src/public/cards.tsx +152 -0
  89. package/template/community/hamdiayari/akhbar-actualites/src/public/index.tsx +71 -0
  90. package/template/community/hamdiayari/akhbar-actualites/src/public/posts.ts +103 -0
  91. package/template/community/hamdiayari/akhbar-actualites/src/public/styles.css +568 -0
  92. package/template/community/hamdiayari/akhbar-actualites/src/public/widgets.tsx +226 -0
  93. package/template/community/hamdiayari/akhbar-actualites/src/server.ts +119 -0
  94. package/template/community/hamdiayari/akhbar-actualites/src/types.ts +25 -0
  95. package/template/community/hamdiayari/akhbar-urgent/README.md +36 -0
  96. package/template/community/hamdiayari/akhbar-urgent/screenshot.jpg +0 -0
  97. package/template/community/hamdiayari/akhbar-urgent/snapify.module.json +64 -0
  98. package/template/community/hamdiayari/akhbar-urgent/src/admin/FlashesPage.tsx +229 -0
  99. package/template/community/hamdiayari/akhbar-urgent/src/admin/index.tsx +11 -0
  100. package/template/community/hamdiayari/akhbar-urgent/src/public/Ticker.tsx +81 -0
  101. package/template/community/hamdiayari/akhbar-urgent/src/public/index.tsx +63 -0
  102. package/template/community/hamdiayari/akhbar-urgent/src/public/styles.css +142 -0
  103. package/template/community/hamdiayari/akhbar-urgent/src/server.ts +101 -0
  104. package/template/community/hamdiayari/akhbar-urgent/src/types.ts +35 -0
  105. package/template/community.html +21 -0
  106. package/template/developers.html +24 -0
  107. package/template/docker-compose.db.yml +24 -0
  108. package/template/docs/BACKOFFICE_SNAPIFY.md +130 -0
  109. package/template/docs/CI_CD.md +66 -0
  110. package/template/docs/MODULES.md +346 -0
  111. package/template/docs/PLATFORM_DEPLOY.md +54 -0
  112. package/template/docs/logo.svg +10 -0
  113. package/template/drizzle/0000_init.sql +147 -0
  114. package/template/drizzle/0001_page_project.sql +5 -0
  115. package/template/drizzle/0002_modules.sql +23 -0
  116. package/template/drizzle/0003_themes.sql +4 -0
  117. package/template/drizzle/0004_security.sql +82 -0
  118. package/template/drizzle/0005_module_records.sql +16 -0
  119. package/template/drizzle/0006_avatars.sql +4 -0
  120. package/template/drizzle/0007_platform.sql +264 -0
  121. package/template/drizzle/0008_mp_validation.sql +3 -0
  122. package/template/drizzle/0009_saas_ops.sql +77 -0
  123. package/template/drizzle/0010_cms_chrome.sql +13 -0
  124. package/template/drizzle/0011_client_portal.sql +26 -0
  125. package/template/drizzle/meta/0000_snapshot.json +998 -0
  126. package/template/drizzle/meta/0001_snapshot.json +1004 -0
  127. package/template/drizzle/meta/_journal.json +90 -0
  128. package/template/drizzle.config.ts +16 -0
  129. package/template/ecosystem.snapify.cjs +24 -0
  130. package/template/for.html +1 -0
  131. package/template/index.html +29 -0
  132. package/template/landing.html +37 -0
  133. package/template/marketplace/catalog.json +373 -0
  134. package/template/marketplace/gallery/hamdiayari.preveris/01-home.jpg +0 -0
  135. package/template/marketplace/gallery/hamdiayari.recaptcha/01-reglages.jpg +0 -0
  136. package/template/marketplace/gallery/hamdiayari.recaptcha/02-logo.jpg +0 -0
  137. package/template/marketplace/gallery/novalabs.ai-articles/01-generer.jpg +0 -0
  138. package/template/marketplace/gallery/novalabs.ai-articles/02-fournisseur-ia.jpg +0 -0
  139. package/template/marketplace/gallery/novalabs.calendar/01-agenda-site.jpg +0 -0
  140. package/template/marketplace/gallery/novalabs.calendar/02-evenements-admin.jpg +0 -0
  141. package/template/marketplace/gallery/novalabs.calendar/03-reglages.jpg +0 -0
  142. package/template/marketplace/screenshots/hamdiayari.preveris-1.0.6.jpg +0 -0
  143. package/template/marketplace/screenshots/hamdiayari.recaptcha-1.0.0.jpg +0 -0
  144. package/template/marketplace/screenshots/hamdiayari.wp-seo-migrator-1.1.1.jpg +0 -0
  145. package/template/marketplace/screenshots/novalabs.ai-articles-1.0.1.jpg +0 -0
  146. package/template/marketplace/screenshots/novalabs.ai-chat-1.0.1.jpg +0 -0
  147. package/template/marketplace/screenshots/novalabs.calendar-1.0.1.jpg +0 -0
  148. package/template/marketplace/screenshots/novalabs.cart-1.0.0.jpg +0 -0
  149. package/template/marketplace/screenshots/novalabs.checkout-1.0.0.jpg +0 -0
  150. package/template/marketplace/screenshots/novalabs.customers-1.1.0.jpg +0 -0
  151. package/template/marketplace/screenshots/novalabs.dogga-1.0.0.jpg +0 -0
  152. package/template/marketplace/screenshots/novalabs.mahdia-1.0.0.jpg +0 -0
  153. package/template/marketplace/screenshots/novalabs.shop-1.0.0.jpg +0 -0
  154. package/template/marketplace/screenshots/novalabs.sidibou-1.0.0.jpg +0 -0
  155. package/template/marketplace/screenshots/novalabs.whatsapp-1.0.1.jpg +0 -0
  156. package/template/marketplace.html +21 -0
  157. package/template/metadata.json +7 -0
  158. package/template/modules/ai-articles/screenshot.jpg +0 -0
  159. package/template/modules/ai-articles/snapify.module.json +74 -0
  160. package/template/modules/ai-articles/src/admin/ArticlesPage.tsx +162 -0
  161. package/template/modules/ai-articles/src/admin/GeneratePage.tsx +118 -0
  162. package/template/modules/ai-articles/src/admin/index.tsx +12 -0
  163. package/template/modules/ai-articles/src/public/index.tsx +119 -0
  164. package/template/modules/ai-articles/src/server.ts +287 -0
  165. package/template/modules/ai-articles/src/types.ts +30 -0
  166. package/template/modules/ai-chat/screenshot.jpg +0 -0
  167. package/template/modules/ai-chat/snapify.module.json +217 -0
  168. package/template/modules/ai-chat/src/public.tsx +198 -0
  169. package/template/modules/ai-chat/src/server.ts +142 -0
  170. package/template/modules/ai-theme-studio/README.md +15 -0
  171. package/template/modules/ai-theme-studio/screenshot.jpg +0 -0
  172. package/template/modules/ai-theme-studio/snapify.module.json +175 -0
  173. package/template/modules/ai-theme-studio/src/admin/HistoryPage.tsx +91 -0
  174. package/template/modules/ai-theme-studio/src/admin/StudioPage.tsx +414 -0
  175. package/template/modules/ai-theme-studio/src/admin/index.tsx +11 -0
  176. package/template/modules/ai-theme-studio/src/lib/images.ts +240 -0
  177. package/template/modules/ai-theme-studio/src/lib/llm.ts +123 -0
  178. package/template/modules/ai-theme-studio/src/lib/normalize.ts +714 -0
  179. package/template/modules/ai-theme-studio/src/lib/prompts.ts +198 -0
  180. package/template/modules/ai-theme-studio/src/server.ts +137 -0
  181. package/template/modules/ai-theme-studio/src/types.ts +112 -0
  182. package/template/modules/calendar/screenshot.jpg +0 -0
  183. package/template/modules/calendar/snapify.module.json +45 -0
  184. package/template/modules/calendar/src/admin/EventsPage.tsx +217 -0
  185. package/template/modules/calendar/src/admin/index.tsx +11 -0
  186. package/template/modules/calendar/src/public/index.tsx +231 -0
  187. package/template/modules/calendar/src/server.ts +143 -0
  188. package/template/modules/calendar/src/types.ts +25 -0
  189. package/template/modules/cart/screenshot.jpg +0 -0
  190. package/template/modules/cart/snapify.module.json +90 -0
  191. package/template/modules/cart/src/admin/index.tsx +265 -0
  192. package/template/modules/cart/src/public/CartPage.tsx +198 -0
  193. package/template/modules/cart/src/public/index.tsx +261 -0
  194. package/template/modules/cart/src/public/useQuote.ts +67 -0
  195. package/template/modules/cart/src/server.ts +148 -0
  196. package/template/modules/cart/src/types.ts +31 -0
  197. package/template/modules/checkout/screenshot.jpg +0 -0
  198. package/template/modules/checkout/snapify.module.json +264 -0
  199. package/template/modules/checkout/src/admin/OrderDetailPage.tsx +304 -0
  200. package/template/modules/checkout/src/admin/badges.tsx +28 -0
  201. package/template/modules/checkout/src/admin/index.tsx +236 -0
  202. package/template/modules/checkout/src/public/CheckoutPage.tsx +461 -0
  203. package/template/modules/checkout/src/public/OrderPages.tsx +153 -0
  204. package/template/modules/checkout/src/public/index.tsx +23 -0
  205. package/template/modules/checkout/src/server.ts +383 -0
  206. package/template/modules/checkout/src/types.ts +70 -0
  207. package/template/modules/customers/screenshot.jpg +0 -0
  208. package/template/modules/customers/snapify.module.json +115 -0
  209. package/template/modules/customers/src/admin/CustomerDetailPage.tsx +274 -0
  210. package/template/modules/customers/src/admin/index.tsx +194 -0
  211. package/template/modules/customers/src/public/AccountPages.tsx +470 -0
  212. package/template/modules/customers/src/public/AddressForm.tsx +115 -0
  213. package/template/modules/customers/src/public/AuthPages.tsx +349 -0
  214. package/template/modules/customers/src/public/Avatar.tsx +29 -0
  215. package/template/modules/customers/src/public/ProfileSection.tsx +291 -0
  216. package/template/modules/customers/src/public/index.tsx +137 -0
  217. package/template/modules/customers/src/public/session.ts +51 -0
  218. package/template/modules/customers/src/server.ts +421 -0
  219. package/template/modules/customers/src/types.ts +53 -0
  220. package/template/modules/recaptcha/logo.jpg +0 -0
  221. package/template/modules/recaptcha/screenshot.jpg +0 -0
  222. package/template/modules/recaptcha/snapify.module.json +99 -0
  223. package/template/modules/recaptcha/src/public/index.tsx +94 -0
  224. package/template/modules/recaptcha/src/server.ts +65 -0
  225. package/template/modules/recaptcha/src/types.ts +18 -0
  226. package/template/modules/shop/screenshot.jpg +0 -0
  227. package/template/modules/shop/snapify.module.json +340 -0
  228. package/template/modules/shop/src/admin/CategoriesPage.tsx +224 -0
  229. package/template/modules/shop/src/admin/ProductEditor.tsx +313 -0
  230. package/template/modules/shop/src/admin/ProductsPage.tsx +307 -0
  231. package/template/modules/shop/src/admin/index.tsx +14 -0
  232. package/template/modules/shop/src/public/Catalog.tsx +244 -0
  233. package/template/modules/shop/src/public/NotFound.tsx +22 -0
  234. package/template/modules/shop/src/public/ProductPage.tsx +195 -0
  235. package/template/modules/shop/src/public/index.tsx +134 -0
  236. package/template/modules/shop/src/public/useFetch.ts +26 -0
  237. package/template/modules/shop/src/server.ts +493 -0
  238. package/template/modules/shop/src/shared.ts +41 -0
  239. package/template/modules/shop/src/types.ts +60 -0
  240. package/template/modules/whatsapp/screenshot.jpg +0 -0
  241. package/template/modules/whatsapp/snapify.module.json +121 -0
  242. package/template/modules/whatsapp/src/public.tsx +119 -0
  243. package/template/modules/wp-seo-migrator/ARCHITECTURE.md +113 -0
  244. package/template/modules/wp-seo-migrator/README.md +21 -0
  245. package/template/modules/wp-seo-migrator/fixtures/aioseo-sample.csv +3 -0
  246. package/template/modules/wp-seo-migrator/fixtures/sample-exporter.json +39 -0
  247. package/template/modules/wp-seo-migrator/fixtures/sample-page.html +12 -0
  248. package/template/modules/wp-seo-migrator/fixtures/sample.htaccess +3 -0
  249. package/template/modules/wp-seo-migrator/screenshot.jpg +0 -0
  250. package/template/modules/wp-seo-migrator/snapify.module.json +87 -0
  251. package/template/modules/wp-seo-migrator/src/admin/HistoryPage.tsx +64 -0
  252. package/template/modules/wp-seo-migrator/src/admin/WizardPage.tsx +788 -0
  253. package/template/modules/wp-seo-migrator/src/admin/i18n.ts +156 -0
  254. package/template/modules/wp-seo-migrator/src/admin/index.tsx +11 -0
  255. package/template/modules/wp-seo-migrator/src/connectors/CUSTOM_CONNECTOR.md +31 -0
  256. package/template/modules/wp-seo-migrator/src/connectors/csvSeoFactory.ts +106 -0
  257. package/template/modules/wp-seo-migrator/src/connectors/exporter.ts +96 -0
  258. package/template/modules/wp-seo-migrator/src/connectors/gscCsv.ts +53 -0
  259. package/template/modules/wp-seo-migrator/src/connectors/htaccess.ts +65 -0
  260. package/template/modules/wp-seo-migrator/src/connectors/htmlCrawler.ts +90 -0
  261. package/template/modules/wp-seo-migrator/src/connectors/index.ts +113 -0
  262. package/template/modules/wp-seo-migrator/src/connectors/pluginCsv.ts +77 -0
  263. package/template/modules/wp-seo-migrator/src/connectors/rankMathCsv.ts +77 -0
  264. package/template/modules/wp-seo-migrator/src/connectors/redirection.ts +62 -0
  265. package/template/modules/wp-seo-migrator/src/connectors/sitemap.ts +44 -0
  266. package/template/modules/wp-seo-migrator/src/connectors/utils.ts +111 -0
  267. package/template/modules/wp-seo-migrator/src/connectors/wxr.ts +103 -0
  268. package/template/modules/wp-seo-migrator/src/connectors/yoastCsv.ts +56 -0
  269. package/template/modules/wp-seo-migrator/src/pipeline/analyze.ts +158 -0
  270. package/template/modules/wp-seo-migrator/src/pipeline/htmlParse.ts +58 -0
  271. package/template/modules/wp-seo-migrator/src/pipeline/remoteAuto.ts +328 -0
  272. package/template/modules/wp-seo-migrator/src/server.ts +492 -0
  273. package/template/modules/wp-seo-migrator/src/types.ts +151 -0
  274. package/template/modules/wp-seo-migrator/tests/connectors-extra.test.ts +39 -0
  275. package/template/modules/wp-seo-migrator/tests/merge.test.ts +25 -0
  276. package/template/package-lock.json +6016 -0
  277. package/template/package.json +74 -0
  278. package/template/public/images/photos/caravane-chameaux-desert.webp +0 -0
  279. package/template/public/images/photos/hammamet-medina-plage.jpg +0 -0
  280. package/template/public/images/photos/maison-campagne-collines.webp +0 -0
  281. package/template/public/images/photos/maisons-troglodytes-desert.jpg +0 -0
  282. package/template/public/images/photos/panorama-ville.jpg +0 -0
  283. package/template/public/images/photos/preveris-accessibilite-erp.jpg +0 -0
  284. package/template/public/images/photos/preveris-collectivites.jpg +0 -0
  285. package/template/public/images/photos/preveris-etudes-plans.jpg +0 -0
  286. package/template/public/images/photos/preveris-hero-erp.jpg +0 -0
  287. package/template/public/images/photos/preveris-ssi-incendie.jpg +0 -0
  288. package/template/public/images/photos/preveris-suivi-hotel.jpg +0 -0
  289. package/template/public/images/photos/ruelle-bleue-medina.jpg +0 -0
  290. package/template/public/images/photos/sidi-bou-said-port.webp +0 -0
  291. package/template/public/images/photos/terrasse-blanche-mer-voilier.jpg +0 -0
  292. package/template/public/landing/hero-ai-cms.jpg +0 -0
  293. package/template/public/landing/shot-dogga.jpg +0 -0
  294. package/template/public/landing/shot-mahdia.jpg +0 -0
  295. package/template/public/landing/shot-sidibou.jpg +0 -0
  296. package/template/public/llms.txt +35 -0
  297. package/template/public/logo.svg +10 -0
  298. package/template/scripts/app-pack.ts +155 -0
  299. package/template/scripts/app-publish.ts +123 -0
  300. package/template/scripts/apply-ecommerce-home.ts +196 -0
  301. package/template/scripts/auto-deploy-poll.sh +13 -0
  302. package/template/scripts/db-backup.sh +16 -0
  303. package/template/scripts/db-restore.sh +11 -0
  304. package/template/scripts/deploy.sh +34 -0
  305. package/template/scripts/github-webhook-deploy.sh +7 -0
  306. package/template/scripts/install-new-modules.ts +96 -0
  307. package/template/scripts/refresh-demo-baseline.ts +9 -0
  308. package/template/scripts/reinstall-marketplace-packs.ts +51 -0
  309. package/template/scripts/restore-classic-home.ts +13 -0
  310. package/template/scripts/sdk-pack.ts +289 -0
  311. package/template/scripts/sdk-publish.ts +75 -0
  312. package/template/scripts/seed-demo-products.ts +120 -0
  313. package/template/scripts/seed-theme-content-packs.ts +42 -0
  314. package/template/scripts/snapify-module.ts +207 -0
  315. package/template/scripts/test-theme-switch.ts +24 -0
  316. package/template/sdk/admin.css +18 -0
  317. package/template/sdk/admin.ts +95 -0
  318. package/template/sdk/build.ts +249 -0
  319. package/template/sdk/commerce.ts +512 -0
  320. package/template/sdk/content.ts +76 -0
  321. package/template/sdk/icons.ts +101 -0
  322. package/template/sdk/image.ts +60 -0
  323. package/template/sdk/index.ts +500 -0
  324. package/template/sdk/package.ts +298 -0
  325. package/template/sdk/recaptcha.tsx +122 -0
  326. package/template/sdk/settings.ts +84 -0
  327. package/template/sdk/theme.css +29 -0
  328. package/template/sdk/theme.ts +100 -0
  329. package/template/sdk/ui/commerce.tsx +385 -0
  330. package/template/sdk/ui/orders.tsx +136 -0
  331. package/template/sdk-kit/CHANGELOG.md +17 -0
  332. package/template/sdk-kit/LICENSE.md +47 -0
  333. package/template/sdk-kit/README.md +81 -0
  334. package/template/sdk-kit/cli.ts +339 -0
  335. package/template/sdk-kit/create-snapify/README.md +28 -0
  336. package/template/sdk-kit/create-snapify/create-snapify.mjs +11 -0
  337. package/template/sdk-kit/create-snapify/package.template.json +16 -0
  338. package/template/sdk-kit/package.template.json +95 -0
  339. package/template/sdk-kit/templates/common/README.md.tpl +27 -0
  340. package/template/sdk-kit/templates/common/_gitignore +3 -0
  341. package/template/sdk-kit/templates/common/package.json.tpl +19 -0
  342. package/template/sdk-kit/templates/common/src/snapify-env.d.ts +2 -0
  343. package/template/sdk-kit/templates/common/tsconfig.json +15 -0
  344. package/template/sdk-kit/templates/module/snapify.module.json.tpl +33 -0
  345. package/template/sdk-kit/templates/module/src/admin.tsx +53 -0
  346. package/template/sdk-kit/templates/module/src/public.tsx +49 -0
  347. package/template/sdk-kit/templates/module/src/server.ts +30 -0
  348. package/template/sdk-kit/templates/module/src/types.ts +19 -0
  349. package/template/sdk-kit/templates/theme/snapify.theme.json.tpl +22 -0
  350. package/template/sdk-kit/templates/theme/src/Footer.tsx +40 -0
  351. package/template/sdk-kit/templates/theme/src/Header.tsx +47 -0
  352. package/template/sdk-kit/templates/theme/src/Views.tsx +36 -0
  353. package/template/sdk-kit/templates/theme/src/blocks.tsx +93 -0
  354. package/template/sdk-kit/templates/theme/src/index.tsx +30 -0
  355. package/template/sdk-kit/templates/theme/src/site.tsx +59 -0
  356. package/template/sdk-kit/templates/theme/src/styles.css +71 -0
  357. package/template/server/client/routes.ts +252 -0
  358. package/template/server/cms/analyticsStore.ts +180 -0
  359. package/template/server/cms/auth.ts +155 -0
  360. package/template/server/cms/blockCatalog.ts +342 -0
  361. package/template/server/cms/blocks.ts +521 -0
  362. package/template/server/cms/contentMigration.ts +1119 -0
  363. package/template/server/cms/defaults.ts +303 -0
  364. package/template/server/cms/permissions.ts +154 -0
  365. package/template/server/cms/restoreClassicHome.ts +183 -0
  366. package/template/server/cms/revisions.ts +99 -0
  367. package/template/server/cms/scheduler.ts +78 -0
  368. package/template/server/cms/seed.ts +72 -0
  369. package/template/server/cms/seoAnalyzer.ts +213 -0
  370. package/template/server/cms/store.ts +122 -0
  371. package/template/server/cms/themeContent.ts +1386 -0
  372. package/template/server/cms/themePacks/sidibou-branding.json +1 -0
  373. package/template/server/cms/themePacks/sidibou-home.json +1 -0
  374. package/template/server/cms/themePacks/sidibou-menus.json +1 -0
  375. package/template/server/cms/types.ts +432 -0
  376. package/template/server/community/routes.ts +410 -0
  377. package/template/server/db/client.ts +43 -0
  378. package/template/server/db/repository.ts +389 -0
  379. package/template/server/db/schema.ts +726 -0
  380. package/template/server/demo/cmsReset.ts +196 -0
  381. package/template/server/developers/sdk.ts +85 -0
  382. package/template/server/geoip.ts +15 -0
  383. package/template/server/http.ts +53 -0
  384. package/template/server/mail.ts +216 -0
  385. package/template/server/marketplace/catalog.ts +74 -0
  386. package/template/server/marketplace/packageValidate.ts +475 -0
  387. package/template/server/marketplace/payments.ts +193 -0
  388. package/template/server/marketplace/routes.ts +850 -0
  389. package/template/server/marketplace/signing.ts +116 -0
  390. package/template/server/marketplace/syncOfficial.ts +282 -0
  391. package/template/server/media/images.ts +63 -0
  392. package/template/server/middleware/adminAuth.ts +134 -0
  393. package/template/server/modules/legacy.ts +44 -0
  394. package/template/server/modules/manager.ts +1122 -0
  395. package/template/server/modules/marketplace.ts +178 -0
  396. package/template/server/modules/outbound.ts +178 -0
  397. package/template/server/modules/purchases.ts +149 -0
  398. package/template/server/modules/records.ts +168 -0
  399. package/template/server/modules/themeHtml.ts +32 -0
  400. package/template/server/modules/trust.ts +16 -0
  401. package/template/server/modules/types.ts +147 -0
  402. package/template/server/platform/auth.ts +223 -0
  403. package/template/server/platform/clientWelcome.ts +168 -0
  404. package/template/server/platform/clients.ts +139 -0
  405. package/template/server/platform/dailyImprove.ts +356 -0
  406. package/template/server/platform/flouci.ts +126 -0
  407. package/template/server/platform/host.ts +69 -0
  408. package/template/server/platform/hostingProviders.ts +143 -0
  409. package/template/server/platform/licenseOrders.ts +291 -0
  410. package/template/server/platform/money.ts +42 -0
  411. package/template/server/platform/passwords.ts +41 -0
  412. package/template/server/platform/region.ts +86 -0
  413. package/template/server/platform/routes.ts +225 -0
  414. package/template/server/platform/seed.ts +82 -0
  415. package/template/server/platform/settings.ts +72 -0
  416. package/template/server/routes/adminAccount.ts +403 -0
  417. package/template/server/routes/adminCms.ts +808 -0
  418. package/template/server/routes/adminSystem.ts +243 -0
  419. package/template/server/routes/adminUsers.ts +449 -0
  420. package/template/server/routes/googleOAuth.ts +327 -0
  421. package/template/server/routes/modules.ts +323 -0
  422. package/template/server/routes/publicCms.ts +313 -0
  423. package/template/server/routes/seoPublic.ts +158 -0
  424. package/template/server/security/accounts.ts +121 -0
  425. package/template/server/security/audit.ts +143 -0
  426. package/template/server/security/authTokens.ts +74 -0
  427. package/template/server/security/ip.ts +68 -0
  428. package/template/server/security/rateLimit.ts +85 -0
  429. package/template/server/security/retention.ts +46 -0
  430. package/template/server/security/secrets.ts +44 -0
  431. package/template/server/security/sessions.ts +140 -0
  432. package/template/server/security/totp.ts +101 -0
  433. package/template/server/superadmin/analytics.ts +109 -0
  434. package/template/server/superadmin/auth.ts +92 -0
  435. package/template/server/superadmin/backlinksCatalog.ts +210 -0
  436. package/template/server/superadmin/frSeoContent.ts +165 -0
  437. package/template/server/superadmin/landingSeo.ts +675 -0
  438. package/template/server/superadmin/ops.ts +238 -0
  439. package/template/server/superadmin/routes.ts +1095 -0
  440. package/template/server/superadmin/tnSeoContent.ts +130 -0
  441. package/template/server.ts +522 -0
  442. package/template/src/App.tsx +263 -0
  443. package/template/src/admin/AdminApp.tsx +162 -0
  444. package/template/src/admin/account/AuthLayout.tsx +57 -0
  445. package/template/src/admin/account/SecurityForms.tsx +276 -0
  446. package/template/src/admin/admin.css +127 -0
  447. package/template/src/admin/context/AuthContext.tsx +147 -0
  448. package/template/src/admin/context/SiteContext.tsx +50 -0
  449. package/template/src/admin/editor/BlockLibrary.tsx +173 -0
  450. package/template/src/admin/editor/BlocksPanel.tsx +396 -0
  451. package/template/src/admin/editor/EditorBits.tsx +106 -0
  452. package/template/src/admin/editor/PreviewFrame.tsx +145 -0
  453. package/template/src/admin/editor/RichTextEditor.tsx +276 -0
  454. package/template/src/admin/editor/SeoPanel.tsx +349 -0
  455. package/template/src/admin/editor/StyleEditor.tsx +114 -0
  456. package/template/src/admin/editor/blockSchemas.ts +699 -0
  457. package/template/src/admin/editor/fields.tsx +486 -0
  458. package/template/src/admin/layout/AdminShell.tsx +418 -0
  459. package/template/src/admin/layout/nav.ts +95 -0
  460. package/template/src/admin/lib/api.ts +408 -0
  461. package/template/src/admin/lib/audit.ts +141 -0
  462. package/template/src/admin/lib/format.ts +84 -0
  463. package/template/src/admin/lib/hooks.ts +125 -0
  464. package/template/src/admin/main.tsx +16 -0
  465. package/template/src/admin/modules/InstallDialog.tsx +160 -0
  466. package/template/src/admin/modules/SettingsForm.tsx +145 -0
  467. package/template/src/admin/modules/kit.tsx +127 -0
  468. package/template/src/admin/modules/labels.tsx +226 -0
  469. package/template/src/admin/pages/AccountSetupPage.tsx +62 -0
  470. package/template/src/admin/pages/AnalyticsPage.tsx +206 -0
  471. package/template/src/admin/pages/BrandingPage.tsx +154 -0
  472. package/template/src/admin/pages/DashboardPage.tsx +239 -0
  473. package/template/src/admin/pages/EngagementPage.tsx +168 -0
  474. package/template/src/admin/pages/FormsPage.tsx +435 -0
  475. package/template/src/admin/pages/GeneralPage.tsx +120 -0
  476. package/template/src/admin/pages/LoginPage.tsx +249 -0
  477. package/template/src/admin/pages/MaintenancePage.tsx +125 -0
  478. package/template/src/admin/pages/MarketplacePage.tsx +426 -0
  479. package/template/src/admin/pages/MediaPage.tsx +251 -0
  480. package/template/src/admin/pages/MenusPage.tsx +446 -0
  481. package/template/src/admin/pages/ModuleAdminPage.tsx +113 -0
  482. package/template/src/admin/pages/ModuleDetailPage.tsx +293 -0
  483. package/template/src/admin/pages/ModulesPage.tsx +135 -0
  484. package/template/src/admin/pages/NewsletterPage.tsx +193 -0
  485. package/template/src/admin/pages/PageEditorPage.tsx +322 -0
  486. package/template/src/admin/pages/PagesListPage.tsx +277 -0
  487. package/template/src/admin/pages/PostEditorPage.tsx +292 -0
  488. package/template/src/admin/pages/PostsListPage.tsx +187 -0
  489. package/template/src/admin/pages/ProfilePage.tsx +489 -0
  490. package/template/src/admin/pages/ResetPasswordPage.tsx +110 -0
  491. package/template/src/admin/pages/SeoPage.tsx +670 -0
  492. package/template/src/admin/pages/SettingsPage.tsx +189 -0
  493. package/template/src/admin/pages/ThemeCustomizePage.tsx +170 -0
  494. package/template/src/admin/pages/ThemesPage.tsx +292 -0
  495. package/template/src/admin/pages/UsersPage.tsx +57 -0
  496. package/template/src/admin/pages/WidgetsPage.tsx +200 -0
  497. package/template/src/admin/seo/GoogleSetup.tsx +529 -0
  498. package/template/src/admin/settings/EmailTab.tsx +293 -0
  499. package/template/src/admin/settings/OtherTabs.tsx +270 -0
  500. package/template/src/admin/settings/SecurityTab.tsx +172 -0
  501. package/template/src/admin/settings/controls.tsx +133 -0
  502. package/template/src/admin/ui/Pagination.tsx +170 -0
  503. package/template/src/admin/ui/SaveBar.tsx +77 -0
  504. package/template/src/admin/ui/TagInput.tsx +54 -0
  505. package/template/src/admin/ui/charts.tsx +108 -0
  506. package/template/src/admin/ui/media.tsx +265 -0
  507. package/template/src/admin/ui/overlays.tsx +239 -0
  508. package/template/src/admin/ui/primitives.tsx +544 -0
  509. package/template/src/admin/users/AuditTab.tsx +104 -0
  510. package/template/src/admin/users/RolesTab.tsx +368 -0
  511. package/template/src/admin/users/UsersTab.tsx +723 -0
  512. package/template/src/admin/users/shared.tsx +278 -0
  513. package/template/src/cms/icons.ts +7 -0
  514. package/template/src/components/CookieBanner.tsx +166 -0
  515. package/template/src/components/MaintenanceGate.tsx +66 -0
  516. package/template/src/components/SiteAnalytics.tsx +64 -0
  517. package/template/src/components/SnapifyLogo.tsx +44 -0
  518. package/template/src/components/cms/BlockRenderer.tsx +154 -0
  519. package/template/src/components/cms/WidgetArea.tsx +193 -0
  520. package/template/src/context/SiteConfigContext.tsx +130 -0
  521. package/template/src/demoBase.ts +23 -0
  522. package/template/src/index.css +90 -0
  523. package/template/src/main.tsx +16 -0
  524. package/template/src/modules/ModuleHost.tsx +197 -0
  525. package/template/src/preview.ts +63 -0
  526. package/template/src/runtime.ts +38 -0
  527. package/template/src/themes/ThemeHost.tsx +168 -0
  528. package/template/src/themes/fallback.tsx +71 -0
  529. package/template/src/types.ts +94 -0
  530. package/template/src/views/BlogPostView.tsx +68 -0
  531. package/template/src/views/CmsPageView.tsx +34 -0
  532. package/template/start-pm2.sh +3 -0
  533. package/template/superadmin.html +20 -0
  534. package/template/themes/ai-canvas/screenshot.jpg +0 -0
  535. package/template/themes/ai-canvas/snapify.theme.json +96 -0
  536. package/template/themes/ai-canvas/src/CeeSimulator.tsx +247 -0
  537. package/template/themes/ai-canvas/src/Footer.tsx +190 -0
  538. package/template/themes/ai-canvas/src/Header.tsx +324 -0
  539. package/template/themes/ai-canvas/src/Layout.tsx +56 -0
  540. package/template/themes/ai-canvas/src/NotFound.tsx +58 -0
  541. package/template/themes/ai-canvas/src/Post.tsx +26 -0
  542. package/template/themes/ai-canvas/src/SnapifyLogo.tsx +44 -0
  543. package/template/themes/ai-canvas/src/blocks/CollectionBlocks.tsx +711 -0
  544. package/template/themes/ai-canvas/src/blocks/ContentBlocks.tsx +318 -0
  545. package/template/themes/ai-canvas/src/blocks/ConversionBlocks.tsx +559 -0
  546. package/template/themes/ai-canvas/src/blocks/HeaderBlocks.tsx +341 -0
  547. package/template/themes/ai-canvas/src/index.tsx +54 -0
  548. package/template/themes/ai-canvas/src/kit.tsx +398 -0
  549. package/template/themes/ai-canvas/src/site.ts +29 -0
  550. package/template/themes/ai-canvas/src/styles.css +317 -0
  551. package/template/themes/dogga/screenshot.jpg +0 -0
  552. package/template/themes/dogga/snapify.theme.json +55 -0
  553. package/template/themes/dogga/src/Brand.tsx +41 -0
  554. package/template/themes/dogga/src/Footer.tsx +202 -0
  555. package/template/themes/dogga/src/Header.tsx +239 -0
  556. package/template/themes/dogga/src/Layout.tsx +43 -0
  557. package/template/themes/dogga/src/Views.tsx +71 -0
  558. package/template/themes/dogga/src/blocks/CollectionBlocks.tsx +674 -0
  559. package/template/themes/dogga/src/blocks/ContentBlocks.tsx +307 -0
  560. package/template/themes/dogga/src/blocks/ConversionBlocks.tsx +571 -0
  561. package/template/themes/dogga/src/blocks/HeaderBlocks.tsx +289 -0
  562. package/template/themes/dogga/src/index.tsx +53 -0
  563. package/template/themes/dogga/src/kit.tsx +362 -0
  564. package/template/themes/dogga/src/site.ts +56 -0
  565. package/template/themes/dogga/src/styles.css +396 -0
  566. package/template/themes/mahdia/screenshot.jpg +0 -0
  567. package/template/themes/mahdia/snapify.theme.json +65 -0
  568. package/template/themes/mahdia/src/Brand.tsx +39 -0
  569. package/template/themes/mahdia/src/Footer.tsx +210 -0
  570. package/template/themes/mahdia/src/Header.tsx +291 -0
  571. package/template/themes/mahdia/src/Layout.tsx +44 -0
  572. package/template/themes/mahdia/src/Views.tsx +79 -0
  573. package/template/themes/mahdia/src/blocks/CollectionBlocks.tsx +674 -0
  574. package/template/themes/mahdia/src/blocks/ContentBlocks.tsx +307 -0
  575. package/template/themes/mahdia/src/blocks/ConversionBlocks.tsx +571 -0
  576. package/template/themes/mahdia/src/blocks/HeaderBlocks.tsx +289 -0
  577. package/template/themes/mahdia/src/index.tsx +53 -0
  578. package/template/themes/mahdia/src/kit.tsx +362 -0
  579. package/template/themes/mahdia/src/site.ts +75 -0
  580. package/template/themes/mahdia/src/styles.css +446 -0
  581. package/template/themes/preveris/screenshot.jpg +0 -0
  582. package/template/themes/preveris/snapify.theme.json +126 -0
  583. package/template/themes/preveris/src/Brand.tsx +44 -0
  584. package/template/themes/preveris/src/Footer.tsx +202 -0
  585. package/template/themes/preveris/src/Header.tsx +239 -0
  586. package/template/themes/preveris/src/Layout.tsx +42 -0
  587. package/template/themes/preveris/src/Views.tsx +71 -0
  588. package/template/themes/preveris/src/blocks/CollectionBlocks.tsx +678 -0
  589. package/template/themes/preveris/src/blocks/ContentBlocks.tsx +307 -0
  590. package/template/themes/preveris/src/blocks/ConversionBlocks.tsx +571 -0
  591. package/template/themes/preveris/src/blocks/HeaderBlocks.tsx +299 -0
  592. package/template/themes/preveris/src/index.tsx +53 -0
  593. package/template/themes/preveris/src/kit.tsx +365 -0
  594. package/template/themes/preveris/src/site.ts +79 -0
  595. package/template/themes/preveris/src/styles.css +446 -0
  596. package/template/themes/sidibou/screenshot.jpg +0 -0
  597. package/template/themes/sidibou/snapify.theme.json +21 -0
  598. package/template/themes/sidibou/src/CeeSimulator.tsx +247 -0
  599. package/template/themes/sidibou/src/Footer.tsx +203 -0
  600. package/template/themes/sidibou/src/Header.tsx +324 -0
  601. package/template/themes/sidibou/src/Layout.tsx +53 -0
  602. package/template/themes/sidibou/src/NotFound.tsx +58 -0
  603. package/template/themes/sidibou/src/Post.tsx +26 -0
  604. package/template/themes/sidibou/src/SnapifyLogo.tsx +44 -0
  605. package/template/themes/sidibou/src/blocks/CollectionBlocks.tsx +711 -0
  606. package/template/themes/sidibou/src/blocks/ContentBlocks.tsx +318 -0
  607. package/template/themes/sidibou/src/blocks/ConversionBlocks.tsx +559 -0
  608. package/template/themes/sidibou/src/blocks/HeaderBlocks.tsx +341 -0
  609. package/template/themes/sidibou/src/index.tsx +54 -0
  610. package/template/themes/sidibou/src/kit.tsx +398 -0
  611. package/template/themes/sidibou/src/site.ts +28 -0
  612. package/template/themes/sidibou/src/styles.css +317 -0
  613. package/template/tsconfig.json +33 -0
  614. package/template/vite.config.ts +42 -0
@@ -0,0 +1 @@
1
+ {"fonts": {"body": "Poppins", "heading": "Poppins"}, "colors": {"navy": "#0B1528", "text": "#0B1528", "muted": "#64748B", "accent": "#0066EE", "border": "#E3E8EE", "primary": "#00C6BA", "background": "#F5F7FA", "primaryHover": "#00A89D"}, "logoUrl": "", "tagline": "Lorem ipsum dolor sit amet", "siteName": "Snapify"}
@@ -0,0 +1 @@
1
+ {"blocks" : [{"id": "b-3emyi5km", "data": {"media": "composition", "title": "Réduisez durablement la facture énergétique de vos", "layout": "split", "buttons": [{"id": "btn-ok1lspxu", "icon": "arrow", "link": "/contact/", "label": "Parler de votre projet", "variant": "primary"}, {"id": "btn-ibpgore6", "icon": "none", "link": "/realisations/", "label": "Voir nos réalisations", "variant": "secondary"}], "marquee": ["Intermarché", "Colorcon", "Carrefour Market", "CEDIM", "Contrôle COFRAC", "Fiches CEE", "Décret BACS", "Décret Tertiaire"], "badgeTag": "CEE", "chipText": "01 Conseil · 02 Ingénierie · 03 Suivi", "liveText": "Réponse d'un ingénieur sous {{delai}}", "parallax": true, "subtitle": "Industrie, tertiaire, résidentiel collectif : nous auditons, installons et mesurons les économies de vos installations. Preuves à l'appui, contrôle COFRAC à la clé.", "badgeText": "Travaux finançables par les CEE · montage de A à Z", "highlight": "", "mainImage": "/images/photos/ruelle-bleue-medina.jpg", "statLabel": "sur la consommation des groupes froids", "statValue": "jusqu'à -35 %", "trustItems": ["RGE Ventilation+", "RGE Qualisol", "SOCOTEC Cat. I"], "mainImageAlt": "Réseau électrique, éoliennes et panneaux solaires au coucher du soleil", "badgeCardText": "systématique après travaux", "rotatingWords": ["groupes froids.", "chaufferies.", "process industriels.", "bâtiments."], "badgeCardTitle": "Contrôle COFRAC", "secondaryImage": "/images/photos/hammamet-medina-plage.jpg", "secondaryCaption": "Nos équipes sur site", "secondaryImageAlt": "Ingénieure Snapify sur chantier"}, "type": "hero", "style": {"decor": "none", "overlay": 55, "background": "image", "paddingTop": "sm", "overlayTone": "light", "paddingBottom": "lg", "backgroundImage": "/images/photos/terrasse-blanche-mer-voilier.jpg"}}, {"id": "b-644ybmhv", "data": {"intro": "Grande distribution, industrie pharmaceutique, plateformes logistiques : des chantiers réels, en site exploité.", "limit": 4, "title": "Nos réalisations,", "filter": "all", "layout": "featured", "eyebrow": "Preuves de terrain", "highlight": "résultats mesurés.", "headerLink": "/realisations/", "showFilters": false, "headerLinkLabel": "Toutes nos réalisations"}, "type": "projects", "style": {"decor": "dots", "background": "surface"}}, {"id": "b-7b8128e5", "data": {"text": "", "image": "/images/photos/terrasse-blanche-mer-voilier.jpg", "title": "Vos travaux sont peut-être déjà financés.", "layout": "split", "buttons": [{"id": "btn-q24bhcpo", "icon": "arrow", "link": "/contact/", "label": "Étude d'éligibilité gratuite", "variant": "dark"}, {"id": "btn-1lq8wjmp", "icon": "phone", "link": "tel:{{telephoneLien}}", "label": "{{telephone}}", "variant": "glass"}], "eyebrow": "Éligibilité CEE", "variant": "gradient", "imageAlt": "Centrale solaire au coucher du soleil", "highlight": "Vérifions-le ensemble.", "imageCaption": "De l'étude au chantier"}, "type": "cta", "style": {"background": "white", "paddingTop": "sm", "paddingBottom": "sm"}}, {"id": "b-mec0nfvv", "data": {"items": [{"id": "c-3ldlxo4j", "icon": "trendingDown", "link": "/expertises/", "tags": [], "text": "Nous identifions vos postes les plus consommateurs (froid, chauffage, process) et engageons les actions au meilleur retour sur investissement.", "title": "Des factures énergétiques trop élevées", "linkLabel": "Voir les solutions"}, {"id": "c-qt4f29nj", "icon": "shieldAlert", "link": "/expertises/reglementation-cee/", "tags": [], "text": "Nous vous aidons à atteindre vos objectifs et à sécuriser votre conformité sans perturber vos exploitations.", "title": "Des obligations réglementaires (Décrets Tertiaire & BACS)", "linkLabel": "Comprendre les décrets"}, {"id": "c-semmag00", "icon": "wrench", "link": "/expertises/", "tags": [], "text": "Groupes froids, chaufferies fioul, réseaux mal isolés : nous modernisons vos équipements sans interrompre votre activité.", "title": "Des installations techniques vieillissantes", "linkLabel": "Nos technologies"}, {"id": "c-clr13fzf", "icon": "badgePercent", "link": "/expertises/reglementation-cee/", "tags": [], "text": "Nous montons et valorisons vos dossiers CEE pour réduire le reste à charge de vos travaux au strict minimum.", "title": "Un budget travaux à financer", "linkLabel": "Voir le montage CEE"}], "style": "hoverDark", "title": "Vos consommations sont un coût.", "columns": 2, "eyebrow": "Vos enjeux, nos réponses", "highlight": "Elles deviennent une obligation.", "textPrefix": "Réponse Snapify —"}, "type": "cards", "style": {"decor": "rings", "background": "white", "paddingTop": "sm"}}, {"id": "b-y2k47xwy", "data": {"items": [{"id": "sh-n1x4gxvz", "icon": "snowflake", "link": "/expertises/froid/", "text": "Varius turpis et commodo pharetra, est eros bibendum, elit nec luctus magna felis sollicitudin.", "chips": ["Dolor sit amet", "Aute irure in", "A odio nullam", "Tellus et risus vulputate (VEHICULA)"], "image": "/images/photos/panorama-ville.jpg", "title": "A odio & nullam", "buttonLabel": "Découvrir l'expertise"}, {"id": "sh-q66umy1s", "icon": "flame", "link": "/expertises/recuperation-de-chaleur/", "text": "Pretium tincidunt lacus nulla gravida orci a, odio nullam varius turpis et commodo.", "chips": ["Risus a elit / ETIAM", "Nisi aliquip ex", "Non proident sunt culpa qui"], "image": "/images/photos/ruelle-bleue-medina.jpg", "title": "Est laborum curabitur", "buttonLabel": "Découvrir l'expertise"}, {"id": "sh-j185xti7", "icon": "wind", "link": "/expertises/chauffage-traitement-air/", "text": "Sollicitudin mauris integer in mauris eu/nibh euismod gravida duis ac tellus et risus.", "chips": ["Dolore magna aliqua enim/ad (minim veniam/quis)", "Culpa qui"], "image": "/images/photos/maison-campagne-collines.webp", "title": "Luctus & magna felis", "buttonLabel": "Découvrir l'expertise"}, {"id": "sh-mf8jvzvi", "icon": "cpu", "link": "/expertises/gtb-gtc/", "text": "Et Risus vulputate Vehicula donec Lobortis/Risus a elit etiam tempor lorem ipsum dolor sit AMET.", "chips": ["EA / COMMODO consequat", "Id est laborum Curabitur PRETIUM"], "image": "/images/photos/maison-campagne-collines.webp", "title": "Duis AC / TELLUS", "buttonLabel": "Découvrir l'expertise"}, {"id": "sh-qls9jtrn", "icon": "shieldCheck", "link": "/expertises/isolation-technique/", "text": "Duis ac tellus et, risus vulputate vehicula donec lobortis risus a elit etiam.", "chips": ["Quis nostrud exercitation ullamco", "Qui officia deserunt mollit"], "image": "/images/photos/ruelle-bleue-medina.jpg", "title": "Euismod gravida", "buttonLabel": "Découvrir l'expertise"}, {"id": "sh-td24blxd", "icon": "fileCheck", "link": "/expertises/reglementation-cee/", "text": "In mauris, eu NIBH euismod gravida duis ac tellus et risus Vulputate vehicula donec.", "chips": ["Ut labore & Et DOLORE", "Nulla PARIATUR (Excepteur Sint & Occaecat Cupidatat)", "Varius turpis et COMMODO pharetra Est eros Bibendum"], "image": "/images/photos/terrasse-blanche-mer-voilier.jpg", "title": "Sollicitudin & mauris INTEGER", "buttonLabel": "Découvrir l'expertise"}], "title": "Froid, chaleur, pilotage, isolation :", "eyebrow": "Nos expertises", "interval": 6, "highlight": "agir sur chaque kWh.", "headerLink": "/expertises/", "headerLinkLabel": "Toutes les expertises"}, "type": "showcase", "style": {"decor": "diagonal", "borderTop": true, "background": "soft"}}, {"id": "b-bulde0sl", "data": {"align": "center", "title": "Estimez votre potentiel", "eyebrow": "Simulateur", "highlight": "en quelques clics."}, "type": "simulator", "style": {"decor": "grid", "background": "white", "paddingBottom": "md"}}, {"id": "b-u2fqhl44", "data": {"align": "center", "items": [{"id": "st-ohpa84ua", "num": "01", "text": "Turpis et commodo pharetra, est eros bibendum elit nec, luctus magna felis sollicitudin, mauris integer in mauris EU.", "title": "Curabitur & pretium tincidunt lacus", "deliverable": "Nibh-euismod gravida duis"}, {"id": "st-ql2rfwuo", "num": "02", "text": "Elit etiam tempor lorem ipsum dolor, sit amet consectetur, adipiscing elit sed do eiusmod (TEMPOR) incididunt ut labore et dolore magna aliqua ENIM.", "title": "Ac & tellus et-risus", "deliverable": "Ad minim veniam, quis nostrud & exercitation ullamco laboris NISI"}, {"id": "st-norgnjmh", "num": "03", "text": "Reprehenderit voluptate velit esse cillum fugiat nulla pariatur, excepteur sint occaecat cupidatat non proident sunt culpa, qui officia deserunt mollit anim.", "title": "Aliquip, ex & ea commodo consequat", "deliverable": "Id-est laborum curabitur & pretium tincidunt lacus nulla gravida orci"}, {"id": "st-0dob0abk", "num": "04", "text": "Bibendum elit nec luctus magna felis SOLLICITUDIN mauris integer in mauris eu, nibh euismod gravida duis ac tellus et risus vulputate.", "title": "A ODIO, nullam & varius", "deliverable": "Vehicula donec lobortis RISUS & a elit etiam"}], "style": "timeline", "title": "4 étapes,", "buttons": [{"id": "btn-f09q2tsv", "icon": "arrow", "link": "/contact/", "label": "Parler de votre projet", "variant": "primary"}, {"id": "btn-y8hxhyl1", "icon": "arrow", "link": "/notre-approche/", "label": "Découvrir notre approche complète", "variant": "link"}], "eyebrow": "Notre méthode", "highlight": "un livrable à chacune.", "deliverableLabel": "Document remis"}, "type": "steps", "style": {"decor": "dots", "borderTop": true, "background": "soft"}}, {"id": "b-3oedj5vd", "data": {"note": "Photos de chantiers Snapify et illustrations techniques d'installations réelles (Wikimedia Commons, licences CC BY / CC BY-SA / CC0).", "intro": "Le monde de l'énergie tel qu'il est vraiment : installations, réseaux et équipements photographiés sur le terrain.", "items": [{"id": "g-5xx2dhn8", "image": "/images/photos/terrasse-blanche-mer-voilier.jpg", "caption": "Centrale solaire au couchant"}, {"id": "g-46mk1p28", "image": "/images/photos/ruelle-bleue-medina.jpg", "caption": "Réseau, nucléaire & renouvelables"}, {"id": "g-u6tnf09w", "image": "/images/photos/sidi-bou-said-port.webp", "caption": "Éolien, solaire & réseau électrique"}, {"id": "g-t5ispwog", "image": "/images/photos/panorama-ville.jpg", "caption": "Meubles froids — grande distribution"}, {"id": "g-6gtcr4jp", "image": "/images/photos/terrasse-blanche-mer-voilier.jpg", "caption": "Réseaux & transition énergétique"}, {"id": "g-vfk1octh", "image": "/images/photos/caravane-chameaux-desert.webp", "caption": "Parc éolien en montagne"}, {"id": "g-2vnqaufo", "image": "/images/photos/maison-campagne-collines.webp", "caption": "Supervision GTB en exploitation"}, {"id": "g-ocax74j2", "image": "/images/photos/maisons-troglodytes-desert.jpg", "caption": "Ferme solaire & éolienne"}, {"id": "g-7nhjsscp", "image": "/images/photos/ruelle-bleue-medina.jpg", "caption": "Éolienne au coucher du soleil"}, {"id": "g-grmiir7z", "image": "/images/photos/hammamet-medina-plage.jpg", "caption": "Sobriété — relamping LED"}, {"id": "g-zxv2fb6s", "image": "/images/photos/maisons-troglodytes-desert.jpg", "caption": "Le mix énergétique en mutation"}, {"id": "g-w82kzu1i", "image": "/images/photos/caravane-chameaux-desert.webp", "caption": "Autoproduction solaire"}], "style": "polaroid", "title": "Des installations réelles,", "eyebrow": "Sur le terrain", "handNote": "faites défiler →", "highlight": "photographiées sur site."}, "type": "gallery", "style": {"background": "white", "paddingBottom": "md"}}, {"id": "b-bmb7y5uf", "data": {"text": "-40 % en 2030, -50 % en 2040, -60 % en 2050. GTB obligatoire au-delà de 290 kW, puis 70 kW en 2030.", "badge": "Échéance dans {{ans2030}}", "title": "Décret Tertiaire & BACS : votre site est-il prêt ?", "layout": "split", "buttons": [{"id": "btn-8jzb4xxp", "icon": "arrow", "link": "/expertises/reglementation-cee/", "label": "Vérifier ma conformité", "variant": "primary"}], "variant": "dark", "bigNumber": "-40%", "bigNumberLabel": "de consommation", "backgroundImage": "/images/photos/maisons-troglodytes-desert.jpg", "bigNumberStrong": "exigés en 2030"}, "type": "cta", "style": {"background": "white", "paddingTop": "sm", "paddingBottom": "sm"}}, {"id": "b-d7j25ro2", "data": {"items": [{"id": "p-imw467co", "icon": "factory", "link": "/secteurs/industrie/", "text": "Elit sed do, eiusmod, tempor incididunt, ut labore.", "image": "/images/photos/caravane-chameaux-desert.webp", "title": "Adipiscing", "bullets": ["Irure in reprehenderit voluptate velit esse cillum fugiat nulla pariatur excepteur sint occaecat cupidatat non.", "Proident sunt culpa qui officia deserunt mollit anim id est laborum curabitur pretium."], "linkLabel": "Découvrir le secteur"}, {"id": "p-ds1atha7", "icon": "building", "link": "/secteurs/tertiaire/", "text": "Vulputate vehicula, donec, lobortis risus, a.", "image": "/images/photos/panorama-ville.jpg", "title": "Risus", "bullets": ["Et dolore magna aliqua enim Ad Minim (veniam 2030 / 2040 / 2050 quis nostrud EXERCITATION).", "Ullamco laboris nisi aliquip ex ea Commodo CONSEQUAT (duis AUTE > 290 irure in > 70 reprehenderit)."], "linkLabel": "Découvrir le secteur"}, {"id": "p-yhttff27", "icon": "home", "link": "/secteurs/residentiel-collectif/", "text": "Pharetra est, eros bibendum elit nec luctus.", "image": "/images/photos/ruelle-bleue-medina.jpg", "title": "Et commodo", "bullets": ["Lobortis risus a elit etiam tempor lorem ipsum dolor sit amet.", "Consectetur adipiscing elit sed do eiusmod tempor incididunt ut labore et (dolore/magna)."], "linkLabel": "Découvrir le secteur"}], "title": "Industrie, tertiaire,", "eyebrow": "Secteurs", "highlight": "résidentiel collectif.", "headerLink": "/secteurs/", "headerLinkLabel": "Tous les secteurs"}, "type": "panels", "style": {"decor": "rings", "background": "white", "paddingTop": "sm"}}, {"id": "b-l71aevg2", "data": {"items": [{"id": "k-gwjtsfax", "hint": "Jusqu'à, sur groupes froids et régulations HP", "label": "de consommation électrique", "value": "35", "prefix": "-", "suffix": " %"}, {"id": "k-bws9ttwp", "hint": "Prise en charge administrative de A à Z", "label": "dossiers CEE sécurisés", "value": "100", "suffix": " %"}, {"id": "k-i66xzkj5", "hint": "Contact direct avec un ingénieur d'études", "label": "délai de réponse", "value": "48", "suffix": " h"}, {"id": "k-ci449729", "hint": "Interventions sur tout le territoire", "label": "déploiement national", "value": "France"}], "style": "cards", "title": "Des engagements", "countUp": true, "eyebrow": "Snapify en chiffres", "highlight": "vérifiés par des tiers."}, "type": "stats", "style": {"overlay": 85, "borderTop": true, "background": "image", "overlayTone": "light", "paddingBottom": "sm", "backgroundImage": "/images/photos/maisons-troglodytes-desert.jpg"}}, {"id": "b-wczmxjpv", "data": {"text": "Montage rigoureux des dossiers CEE, chantiers contrôlés par un organisme accrédité COFRAC, qualifications à jour : un partenaire fiable pour vos opérations.", "title": "Mandataires, délégataires, fournisseurs : travaillons ensemble.", "layout": "split", "buttons": [{"id": "btn-a74w2fck", "icon": "arrow", "link": "/contact/", "label": "Devenir partenaire", "variant": "secondary"}], "eyebrow": "Partenaires CEE", "variant": "light"}, "type": "cta", "style": {"background": "surface", "paddingTop": "none", "paddingBottom": "lg"}}, {"id": "b-4gewqacl", "data": {"cards": [{"id": "ck-zyxz6npw", "tag": "Qualifications Snapify", "icon": "shieldCheck", "entries": [{"id": "e-dp11i2uy", "text": "Traitement d'air haute performance", "title": "RGE Ventilation+"}, {"id": "e-i7tp9g3d", "text": "Solaire thermique & ECS", "title": "RGE Qualisol CESI"}, {"id": "e-gu2v1i84", "text": "Manipulation et mise en service froid", "title": "SOCOTEC Fluides Cat. I"}]}, {"id": "ck-fh3ygn5u", "tag": "Bureau d'études partenaire", "icon": "award", "entries": [{"id": "e-voizxpf0", "text": "Audit énergétique dans l'industrie", "title": "OPQIBI 1717"}, {"id": "e-h0v9fto8", "text": "Audit tertiaire et collectif", "title": "OPQIBI 1905"}, {"id": "e-1v7p5xm8", "text": "Bureau d'études partenaire", "title": "Leo Energy"}]}, {"id": "ck-5rqo4t2l", "tag": "Assurances & contrôle", "icon": "check", "entries": [{"id": "e-qm4on8og", "text": "Responsabilité Civile Professionnelle", "title": "MIC Insurance"}, {"id": "e-f5d9s3xg", "text": "Travaux et ouvrages techniques", "title": "Garantie décennale"}, {"id": "e-adi0haqp", "text": "Systématique post-travaux", "title": "Contrôle COFRAC"}]}], "title": "Qualifiés, assurés,", "eyebrow": "Garanties", "highlight": "contrôlés."}, "type": "checklist", "style": {"decor": "diagonal", "background": "white"}}, {"id": "b-b9oqxz6x", "data": {"intro": "Interventions, délais, financements : l'essentiel avant de lancer votre projet.", "items": [{"id": "q-e3uogguy", "answer": "<p>Snapify lobortis risus a elit etiam, tempor lorem ipsum (dolor sit, amet, consectetur, adipiscing) elit sed do eiusmod, tempor incididunt Ut.</p>", "question": "Tellus et risus vulputate vehicula-donec ?"}, {"id": "q-s2j4u7lr", "answer": "<p>Ad 4 minim : veniam quis nostrud, exercitation ullamco laboris nisi-aliquip, ex ea commodo consequat duis, aute irure IN reprehenderit voluptate velit esse. Cillum fugiat nulla pariatur excepteur sint occaecat cupidatat.</p>", "question": "Labore et dolore magna aliqua enim Snapify ?"}, {"id": "q-1e9jen0t", "answer": "<p>Id est laborum curabitur pretium tincidunt lacus nulla gravida orci a odio nullam varius. Snapify turpis et commodo pharetra est EROS, bibendum elit nec luctus magna felis sollicitudin mauris integer. In mauris eu nibh euismod gravida duis ac.</p>", "question": "Non proident sunt-culpa qui officia deserunt mollit ANIM ?"}, {"id": "q-983dqrnv", "answer": "<p>Elit etiam tempor lorem ipsum dolor sit 1 000 amet² consectetur adipiscing. Elit sed do eiusmod tempor incididunt ut labore 40 % et 2030, 50 % dolore 2040 magna 60 % aliqua 2050 enim ad minim veniam quis nostrud exercitation, ullamco laboris nisi aliquip ex ea commodo CONSEQUAT.</p>", "question": "Tellus et risus-vulputate vehicula donec lobortis risus a ?"}, {"id": "q-l8yx5i8m", "answer": "<p>Nulla pariatur excepteur sint occaecat cupidatat non proident sunt culpa 290 qui officia deserunt mollit anim id est laborum (CURABITUR) pretium tincidunt 1lacus nulla 2025. Gravida orci a odio 70 nullam varius 1turpis et 2030.</p>", "question": "Duis aute IRURE in-reprehenderit-voluptate velit esse cillum FUGIAT ?"}, {"id": "q-j5v3v8wl", "answer": "<p>Felis-sollicitudin mauris integer in mauris eu nibh euismod gravida duis ac tellus. Et risus vulputate vehicula donec lobortis risus 48 a elit.</p>", "question": "Commodo pharetra est, eros bibendum elit : nec luctus magna Snapify ?"}, {"id": "q-evacc5fc", "answer": "<p>Sit amet consectetur adipiscing elit sed do eiusmod 48 tempor incididunt.</p>", "question": "Etiam tempor lorem ipsum-dolor ?"}], "title": "Questions fréquentes", "layout": "split", "eyebrow": "FAQ", "contactLabel": "Une autre question ?", "showContactCard": true}, "type": "faq", "style": {"decor": "dots", "borderTop": true, "background": "surface"}}, {"id": "b-f5nr5ol7", "data": {"text": "Audit préliminaire, étude de dimensionnement ou montage CEE : un ingénieur Snapify analyse votre site et vous propose un plan d'action chiffré.", "badge": "Réponse sous {{delai}}", "title": "Un projet ?", "layout": "centered", "buttons": [{"id": "btn-esfr95x5", "icon": "arrow", "link": "/contact/", "label": "Parler de votre projet", "variant": "primary"}, {"id": "btn-rfy604bz", "icon": "phone", "link": "tel:{{telephoneLien}}", "label": "{{telephone}}", "variant": "secondary"}], "variant": "dark", "highlight": "Parlons-en."}, "type": "cta", "style": {"background": "white", "paddingTop": "md"}}], "title" : "Accueil", "seo" : {"slug": "accueil", "noindex": false, "nofollow": false, "seoTitle": "Snapify | Ingénierie & performance énergétique", "schemaType": "Organization", "twitterCard": "summary_large_image", "focusKeyphrase": "", "metaDescription": "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua."}}
@@ -0,0 +1 @@
1
+ [{"id" : "footer", "label" : "Pied de page", "items" : [{"id": "f-real", "path": "/realisations/", "label": "Réalisations & Chantiers"}, {"id": "f-approche", "path": "/notre-approche/", "label": "Notre approche (4 étapes)"}, {"id": "f-contact", "path": "/contact/", "label": "Lorem ipsum dolor", "highlight": true}, {"id": "f-legal", "path": "/mentions-legales/", "label": "Mentions légales"}, {"id": "f-privacy", "path": "/politique-de-confidentialite/", "label": "Politique de confidentialité"}, {"id": "f-cookies", "path": "/cookies/", "label": "Cookies"}]}, {"id" : "mobile", "label" : "Menu mobile", "items" : [{"id": "m-exp", "path": "/expertises/", "label": "Lorem", "children": [{"id": "m-exp-froid", "path": "/expertises/froid/", "label": "Froid commercial & industriel"}, {"id": "m-exp-recup", "path": "/expertises/recuperation-de-chaleur/", "label": "Récupération de chaleur"}, {"id": "m-exp-cvc", "path": "/expertises/chauffage-traitement-air/", "label": "Chauffage & traitement d'air"}, {"id": "m-exp-gtb", "path": "/expertises/gtb-gtc/", "label": "GTB / GTC & BACS"}, {"id": "m-exp-iso", "path": "/expertises/isolation-technique/", "label": "Isolation technique"}, {"id": "m-exp-cee", "path": "/expertises/reglementation-cee/", "label": "Réglementation & CEE"}]}, {"id": "m-sec", "path": "/secteurs/", "label": "Ipsum", "children": [{"id": "m-sec-ind", "path": "/secteurs/industrie/", "label": "Industrie"}, {"id": "m-sec-ter", "path": "/secteurs/tertiaire/", "label": "Tertiaire"}, {"id": "m-sec-res", "path": "/secteurs/residentiel-collectif/", "label": "Résidentiel collectif"}]}, {"id": "m-real", "path": "/realisations/", "label": "Réalisations"}, {"id": "m-approche", "path": "/notre-approche/", "label": "Notre approche"}, {"id": "m-contact", "path": "/contact/", "label": "Lorem ipsum dolor", "highlight": true}]}, {"id" : "primary", "label" : "Menu principal (desktop)", "items" : [{"id": "m-exp", "path": "/expertises/", "label": "Lorem", "children": [{"id": "m-exp-froid", "path": "/expertises/froid/", "label": "Froid commercial & industriel"}, {"id": "m-exp-recup", "path": "/expertises/recuperation-de-chaleur/", "label": "Récupération de chaleur"}, {"id": "m-exp-cvc", "path": "/expertises/chauffage-traitement-air/", "label": "Chauffage & traitement d'air"}, {"id": "m-exp-gtb", "path": "/expertises/gtb-gtc/", "label": "GTB / GTC & BACS"}, {"id": "m-exp-iso", "path": "/expertises/isolation-technique/", "label": "Isolation technique"}, {"id": "m-exp-cee", "path": "/expertises/reglementation-cee/", "label": "Réglementation & CEE"}]}, {"id": "m-sec", "path": "/secteurs/", "label": "Ipsum", "children": [{"id": "m-sec-ind", "path": "/secteurs/industrie/", "label": "Industrie"}, {"id": "m-sec-ter", "path": "/secteurs/tertiaire/", "label": "Tertiaire"}, {"id": "m-sec-res", "path": "/secteurs/residentiel-collectif/", "label": "Résidentiel collectif"}]}, {"id": "m-real", "path": "/realisations/", "label": "Réalisations"}, {"id": "m-approche", "path": "/notre-approche/", "label": "Notre approche"}, {"id": "m-contact", "path": "/contact/", "label": "Lorem ipsum dolor", "highlight": true}]}]
@@ -0,0 +1,432 @@
1
+ /**
2
+ * Snapify
3
+ * © 2026 NOVALABS WEB DESIGN — Tunisie
4
+ * Contact : contact@novalabs.tn · +216 24 734 647
5
+ * Tous droits réservés. Toute reproduction, modification ou diffusion sans autorisation écrite est interdite.
6
+ */
7
+ /** Modèle de données CMS Snapify — source unique pour le site et le backoffice */
8
+
9
+ import type { BlockKind, BlockStyle, ProjectMeta } from './blocks';
10
+ import type { RoleDefinition } from './permissions';
11
+
12
+ export type BlockType = BlockKind;
13
+
14
+ export interface CmsBlock {
15
+ id: string;
16
+ type: BlockType;
17
+ data: Record<string, unknown>;
18
+ style?: Partial<BlockStyle>;
19
+ }
20
+
21
+ export interface SeoMeta {
22
+ focusKeyphrase: string;
23
+ seoTitle: string;
24
+ metaDescription: string;
25
+ slug: string;
26
+ canonicalUrl?: string;
27
+ noindex: boolean;
28
+ nofollow: boolean;
29
+ ogTitle?: string;
30
+ ogDescription?: string;
31
+ ogImage?: string;
32
+ twitterCard: 'summary' | 'summary_large_image';
33
+ schemaType: 'WebPage' | 'Article' | 'Organization' | 'LocalBusiness';
34
+ breadcrumbsTitle?: string;
35
+ }
36
+
37
+ export type PageContentSource = 'react' | 'cms';
38
+ export type PageTemplate = 'default' | 'landing' | 'legal' | 'project';
39
+
40
+ export interface CmsPage {
41
+ id: string;
42
+ path: string;
43
+ title: string;
44
+ status: 'draft' | 'published' | 'scheduled';
45
+ publishedAt?: string;
46
+ scheduledAt?: string;
47
+ contentSource: PageContentSource;
48
+ template: PageTemplate;
49
+ blocks: CmsBlock[];
50
+ seo: SeoMeta;
51
+ /** Fiche réalisation (template `project`) : alimente les blocs « Réalisations ». */
52
+ project?: ProjectMeta;
53
+ updatedAt: string;
54
+ createdAt: string;
55
+ }
56
+
57
+ export interface MenuItem {
58
+ id: string;
59
+ label: string;
60
+ path: string;
61
+ children?: MenuItem[];
62
+ openInNewTab?: boolean;
63
+ highlight?: boolean;
64
+ }
65
+
66
+ export interface MenuConfig {
67
+ id: string;
68
+ label: string;
69
+ items: MenuItem[];
70
+ }
71
+
72
+ export type CoreWidgetKind = 'text' | 'html' | 'menu' | 'recent_posts' | 'search';
73
+
74
+ export interface WidgetInstance {
75
+ id: string;
76
+ kind: CoreWidgetKind | 'module';
77
+ title: string;
78
+ data: Record<string, unknown>;
79
+ }
80
+
81
+ export interface WidgetArea {
82
+ id: string;
83
+ label: string;
84
+ description?: string;
85
+ widgets: WidgetInstance[];
86
+ }
87
+
88
+ export interface BlockPattern {
89
+ id: string;
90
+ name: string;
91
+ description?: string;
92
+ blocks: CmsBlock[];
93
+ createdAt: string;
94
+ }
95
+
96
+ export interface ThemeBranding {
97
+ siteName: string;
98
+ tagline: string;
99
+ logoUrl: string;
100
+ logoDarkUrl?: string;
101
+ faviconUrl?: string;
102
+ colors: {
103
+ primary: string;
104
+ primaryHover: string;
105
+ accent: string;
106
+ navy: string;
107
+ background: string;
108
+ text: string;
109
+ muted: string;
110
+ border: string;
111
+ };
112
+ fonts: {
113
+ heading: string;
114
+ body: string;
115
+ };
116
+ }
117
+
118
+ export interface SiteGeneralInfo {
119
+ legalName: string;
120
+ baseline: string;
121
+ slogan: string;
122
+ phone: string;
123
+ phoneClean: string;
124
+ contactEmail: string;
125
+ slaHours: string;
126
+ address: string;
127
+ timezone: string;
128
+ locale: string;
129
+ }
130
+
131
+ export interface FloatingButtonConfig {
132
+ id: string;
133
+ label: string;
134
+ path: string;
135
+ style: 'primary' | 'outline' | 'ghost';
136
+ enabled: boolean;
137
+ }
138
+
139
+ export interface ContactFormField {
140
+ id: string;
141
+ name: string;
142
+ label: string;
143
+ type: 'text' | 'email' | 'tel' | 'select' | 'textarea' | 'checkbox';
144
+ required: boolean;
145
+ options?: string[];
146
+ placeholder?: string;
147
+ width?: 'full' | 'half';
148
+ }
149
+
150
+ export interface ContactFormConfig {
151
+ id: string;
152
+ name: string;
153
+ recipientEmails: string[];
154
+ successPath: string;
155
+ fields: ContactFormField[];
156
+ honeypotField?: string;
157
+ enabled: boolean;
158
+ }
159
+
160
+ export interface ContactSubmission {
161
+ id: string;
162
+ formId: string;
163
+ payload: Record<string, unknown>;
164
+ ip?: string;
165
+ userAgent?: string;
166
+ createdAt: string;
167
+ read: boolean;
168
+ }
169
+
170
+ export interface NewsletterConfig {
171
+ enabled: boolean;
172
+ provider: 'internal' | 'mailchimp' | 'brevo' | 'custom';
173
+ doubleOptIn: boolean;
174
+ welcomeEmailSubject?: string;
175
+ apiKeyEnvVar?: string;
176
+ listId?: string;
177
+ }
178
+
179
+ export interface NewsletterSubscriber {
180
+ id: string;
181
+ email: string;
182
+ status: 'pending' | 'active' | 'unsubscribed';
183
+ source?: string;
184
+ confirmToken?: string;
185
+ createdAt: string;
186
+ confirmedAt?: string;
187
+ }
188
+
189
+ export interface ContentRevision {
190
+ id: string;
191
+ entityType: 'page' | 'post';
192
+ entityId: string;
193
+ label: string;
194
+ snapshot: CmsPage | BlogPost;
195
+ createdAt: string;
196
+ authorEmail?: string;
197
+ }
198
+
199
+ export interface MaintenanceConfig {
200
+ enabled: boolean;
201
+ title: string;
202
+ message: string;
203
+ allowedIps: string[];
204
+ bypassSecret?: string;
205
+ }
206
+
207
+ export interface SeoGlobalSettings {
208
+ titleSeparator: string;
209
+ titleSuffix: string;
210
+ defaultOgImage?: string;
211
+ organizationName: string;
212
+ organizationLogo?: string;
213
+ socialProfiles: string[];
214
+ googleVerification?: string;
215
+ bingVerification?: string;
216
+ }
217
+
218
+ export interface SiteSettings {
219
+ publicUrl: string;
220
+ maintenance: MaintenanceConfig;
221
+ cookieBannerEnabled: boolean;
222
+ analyticsEnabled: boolean;
223
+ robotsTxtExtra?: string;
224
+ sitemapAuto: boolean;
225
+ seo: SeoGlobalSettings;
226
+ }
227
+
228
+ export interface GoogleIntegration {
229
+ connected: boolean;
230
+ searchConsoleProperty?: string;
231
+ analyticsPropertyId?: string;
232
+ /** Chiffré (secrets.ts) ; les anciennes valeurs en clair restent lisibles. */
233
+ oauthRefreshToken?: string;
234
+ /** Identifiants OAuth saisis dans l'administration (prioritaires sur GOOGLE_CLIENT_ID / GOOGLE_CLIENT_SECRET). */
235
+ oauthClientId?: string;
236
+ oauthClientSecretEnc?: string;
237
+ /** Compte Google ayant autorisé l'accès. */
238
+ accountEmail?: string;
239
+ lastSyncAt?: string;
240
+ }
241
+
242
+ export interface MediaAsset {
243
+ id: string;
244
+ filename: string;
245
+ url: string;
246
+ mimeType: string;
247
+ sizeBytes: number;
248
+ alt?: string;
249
+ createdAt: string;
250
+ }
251
+
252
+ export interface BlogPost {
253
+ id: string;
254
+ slug: string;
255
+ title: string;
256
+ excerpt: string;
257
+ coverImage?: string;
258
+ blocks: CmsBlock[];
259
+ seo: SeoMeta;
260
+ status: 'draft' | 'published' | 'scheduled';
261
+ publishedAt?: string;
262
+ scheduledAt?: string;
263
+ author?: string;
264
+ tags: string[];
265
+ updatedAt: string;
266
+ createdAt: string;
267
+ }
268
+
269
+ export interface RedirectRule {
270
+ from: string;
271
+ to: string;
272
+ permanent: boolean;
273
+ }
274
+
275
+ export interface AnalyticsEvent {
276
+ id: string;
277
+ kind: 'view' | 'leave';
278
+ sessionId: string;
279
+ path: string;
280
+ referrer?: string;
281
+ country?: string;
282
+ city?: string;
283
+ device: 'mobile' | 'tablet' | 'desktop' | 'unknown';
284
+ durationSec?: number;
285
+ ts: string;
286
+ }
287
+
288
+ export type UserStatus = 'active' | 'invited' | 'suspended';
289
+
290
+ export interface AdminUser {
291
+ id: string;
292
+ email: string;
293
+ passwordHash: string;
294
+ salt: string;
295
+ /** Identifiant d'un rôle de `CmsSnapshot.roles` (`superadmin` = tous les droits). */
296
+ role: string;
297
+ name: string;
298
+ status?: UserStatus;
299
+ title?: string;
300
+ phone?: string;
301
+ /** Photo de profil (/uploads/avatars/…). */
302
+ avatarUrl?: string;
303
+ /** Secret TOTP chiffré (voir server/security/secrets.ts). */
304
+ totpSecret?: string;
305
+ totpEnabled?: boolean;
306
+ /** Empreintes SHA-256 des codes de secours non utilisés. */
307
+ recoveryCodes?: string[];
308
+ mustChangePassword?: boolean;
309
+ passwordChangedAt?: string;
310
+ lastLoginAt?: string;
311
+ lastLoginIp?: string;
312
+ loginCount?: number;
313
+ invitedBy?: string;
314
+ createdAt?: string;
315
+ }
316
+
317
+ export interface SmtpSettings {
318
+ /** `false` = utilise la configuration SMTP_* du fichier .env si elle existe. */
319
+ enabled: boolean;
320
+ host: string;
321
+ port: number;
322
+ security: 'starttls' | 'ssl' | 'none';
323
+ username: string;
324
+ /** Mot de passe chiffré ; jamais renvoyé au navigateur. */
325
+ passwordEnc?: string;
326
+ fromName: string;
327
+ fromEmail: string;
328
+ replyTo: string;
329
+ timeoutSec: number;
330
+ allowSelfSigned: boolean;
331
+ }
332
+
333
+ export interface RateWindow {
334
+ max: number;
335
+ windowMinutes: number;
336
+ }
337
+
338
+ export interface SystemSettings {
339
+ smtp: SmtpSettings;
340
+ notifications: {
341
+ /** Prévient l'utilisateur par e-mail (nouvel appareil, mot de passe ou 2FA modifiés). */
342
+ securityAlerts: boolean;
343
+ /** Prévient les adresses ci-dessous à chaque création ou suppression de compte. */
344
+ accountChanges: boolean;
345
+ adminEmails: string[];
346
+ };
347
+ security: {
348
+ passwordMinLength: number;
349
+ requireUppercase: boolean;
350
+ requireNumber: boolean;
351
+ requireSymbol: boolean;
352
+ /** 0 = jamais. */
353
+ passwordExpiryDays: number;
354
+ sessionHours: number;
355
+ rememberDays: number;
356
+ /** Déconnexion après inactivité ; 0 = désactivé. */
357
+ idleMinutes: number;
358
+ maxLoginAttempts: number;
359
+ lockoutMinutes: number;
360
+ twoFactor: 'optional' | 'superadmins' | 'all';
361
+ /** Vide = administration accessible depuis toute adresse. IPv4, IPv6 ou plage CIDR IPv4. */
362
+ adminIpAllowlist: string[];
363
+ hsts: boolean;
364
+ };
365
+ limits: {
366
+ /** Requêtes par minute et par IP sur /api/public ; 0 = illimité. */
367
+ publicApiPerMinute: number;
368
+ /** Requêtes par minute et par utilisateur sur /api/admin ; 0 = illimité. */
369
+ adminApiPerMinute: number;
370
+ formSubmissions: RateWindow;
371
+ newsletter: RateWindow;
372
+ passwordReset: RateWindow;
373
+ };
374
+ uploads: {
375
+ maxSizeMb: number;
376
+ allowImages: boolean;
377
+ allowSvg: boolean;
378
+ allowVideo: boolean;
379
+ allowPdf: boolean;
380
+ };
381
+ privacy: {
382
+ analyticsRetentionDays: number;
383
+ /** 0 = conservés indéfiniment. */
384
+ submissionsRetentionDays: number;
385
+ auditRetentionDays: number;
386
+ mailLogRetentionDays: number;
387
+ storeSubmitterIp: boolean;
388
+ };
389
+ performance: {
390
+ publicCacheSeconds: number;
391
+ };
392
+ }
393
+
394
+ export interface CmsSnapshot {
395
+ version: number;
396
+ general: SiteGeneralInfo;
397
+ branding: ThemeBranding;
398
+ pages: CmsPage[];
399
+ posts: BlogPost[];
400
+ menus: MenuConfig[];
401
+ widgetAreas: WidgetArea[];
402
+ blockPatterns: BlockPattern[];
403
+ forms: ContactFormConfig[];
404
+ formSubmissions: ContactSubmission[];
405
+ floatingButtons: FloatingButtonConfig[];
406
+ newsletter: NewsletterConfig;
407
+ subscribers: NewsletterSubscriber[];
408
+ settings: SiteSettings;
409
+ google: GoogleIntegration;
410
+ media: MediaAsset[];
411
+ redirects: RedirectRule[];
412
+ /** Hérité : les événements sont désormais dans data/cms/analytics.jsonl */
413
+ analyticsEvents?: AnalyticsEvent[];
414
+ users: AdminUser[];
415
+ roles: RoleDefinition[];
416
+ system: SystemSettings;
417
+ }
418
+
419
+ export interface AnalyticsSummary {
420
+ days: number;
421
+ pageViews: number;
422
+ uniqueSessions: number;
423
+ avgTimeOnPageSec: number;
424
+ bounceRate: number;
425
+ activeNow: number;
426
+ timeseries: { date: string; views: number; sessions: number }[];
427
+ topPages: { path: string; views: number; avgTimeSec: number }[];
428
+ countries: { country: string; views: number }[];
429
+ devices: { device: string; views: number }[];
430
+ referrers: { source: string; views: number }[];
431
+ recent: AnalyticsEvent[];
432
+ }