diff --git a/.gitignore b/.gitignore index 77cb7b9..e8f8e2f 100644 --- a/.gitignore +++ b/.gitignore @@ -1,13 +1,22 @@ **/node_modules -config.json .DS_Store *.iml *.swp -dist +.npm + +# Test cache +cache cypress/screenshots cypress/videos -cache -.npm -.DS_Store -src/manifest.webmanifest -.cache \ No newline at end of file + +# Built files +.cache +dist + +# Config specific files +config.json +config.*.json +!config.sample.json + +# PWA Generated file +src/manifest.webmanifest \ No newline at end of file diff --git a/README.md b/README.md index 5b23231..da971e1 100644 --- a/README.md +++ b/README.md @@ -71,6 +71,22 @@ Serve, watch files & rebuild on change with this command: npm run watch ``` +### Multiple config.json + +You can have as many `config.*.json` as you need. + +Watch on a custom config file: + +```bash +CONFIG_PATH='config.customName.json' npm run watch +``` + +Build with a custom config file: + +```bash +CONFIG_PATH='config.customName.json' npm run build +``` + ## Mandatory modules By default, a Hubl includes only individual chat modules. @@ -86,9 +102,14 @@ On `config.json`: "clientLogo": "/images/logo.webp", "authority": "http://localhost:8000/", "endpoints": { - "skills": "http://server.url/skills/", - "users": "http://server.url/users/", - "uploads": "http://server.url/upload/" + "get": { + "skills": "http://server.url/skills/", + "users": "http://server.url/users/" + }, + "post": { + "users": "http://server.url/users/", + "uploads": "http://server.url/upload/" + } } } ``` @@ -99,9 +120,9 @@ Where: * `clientLogo` is an URL to an image file * `xmppWebsocket` is your [Prosody](https://prosody.im/) with [appropriate modules](https://git.startinblox.com/infra/prosody-modules/) configured on. * `authority` is the OpenID Provider. Usually, if you use `djangoldp-account` it's the same as your djangoldp server. -* `endpoints.users` is the API endpoints for Users on your djangoldp server. (djangoldp-account) -* `endpoints.skills` is the API endpoints for Skills on your djangoldp server. (djangoldp-skill) -* `endpoints.uploads` is the API endpoints for Uploads on your djangoldp server. (djangoldp-upload) +* `endpoints.*.users` is the API endpoints for Users on your djangoldp server. (djangoldp-account) +* `endpoints.*.skills` is the API endpoints for Skills on your djangoldp server. (djangoldp-skill) +* `endpoints.*.uploads` is the API endpoints for Uploads on your djangoldp server. (djangoldp-upload) ### Communities @@ -157,7 +178,12 @@ On `config.json`: ```json "endpoints": { - "circle": "http://server.url/circles/" + "get": { + "circle": "http://server.url/circles/" + }, + "post": { + "circle": "http://server.url/circles/" + }, } ``` @@ -171,7 +197,9 @@ On `config.json`: ```json "endpoints": { - "dashboard": "http://server.url/dashboard/" + "get": { + "dashboard": "http://server.url/dashboard/" + } } ``` @@ -187,9 +215,9 @@ On `config.json`: ```json "endpoints": { - "joboffers": "http://server.url/job-offers/", - "skills": "http://server.url/skills/", - "uploads": "http://server.url/upload/" + "get": { + "joboffers": "http://server.url/job-offers/" + } } ``` @@ -203,10 +231,12 @@ On `config.json`: ```json "endpoints": { - "projects": "http://server.url/projects/", - "customers": "http://server.url/customers/", - "businessproviders": "http://server.url/businessproviders/", - "skills": "http://server.url/skills/" + "get": { + "projects": "http://server.url/projects/" + }, + "post": { + "projects": "http://server.url/projects/" + } } ``` @@ -219,12 +249,7 @@ On Server: `djangoldp_skill`, `djangoldp_upload` packages On `config.json`: ```json - "publicDirectory": true, - "endpoints": { - "groups": "http://server.url/groups/", - "skills": "http://server.url/skills/", - "uploads": "http://server.url/upload/" - } + "publicDirectory": true ``` ## Optional community modules @@ -241,9 +266,14 @@ On `config.json`: ```json "endpoints": { - "events":"http://server.url/events/", - "typeevents":"http://server.url/typeevents/", - "uploads": "http://server.url/upload/" + "get": { + "events":"http://server.url/events/", + "typeevents":"http://server.url/typeevents/" + }, + "post": { + "events":"http://server.url/events/", + "typeevents":"http://server.url/typeevents/" + } } ``` @@ -259,10 +289,16 @@ On `config.json`: ```json "endpoints": { - "resources":"http://server.url/resources/", - "resourceskeywords":"http://server.url/keywords/", - "resourcestypes":"http://server.url/types/", - "uploads": "http://server.url/upload/" + "get": { + "resources":"http://server.url/resources/", + "resourceskeywords":"http://server.url/keywords/", + "resourcestypes":"http://server.url/types/" + }, + "post": { + "resources":"http://server.url/resources/", + "resourceskeywords":"http://server.url/keywords/", + "resourcestypes":"http://server.url/types/" + } } ``` @@ -276,7 +312,12 @@ On `config.json`: ```json "endpoints": { - "polls":"http://server.url/polls/" + "get": { + "polls":"http://server.url/polls/" + }, + "post": { + "polls":"http://server.url/polls/" + } } ``` @@ -316,4 +357,4 @@ Did you properly created subscriptions on your DjangoLDP's server? You can quick ## Built With -* [Sib-Core](https://git.startinblox.com/framework/sib-core/) - A SOLID-Compliant framework +* [Sib-Core](https://git.startinblox.com/framework/sib-core/) - A SOLID-Compliant framework diff --git a/config.sample.json b/config.sample.json index 7f2fcb5..a3368b7 100644 --- a/config.sample.json +++ b/config.sample.json @@ -6,13 +6,11 @@ "endpoints": { "get": { "skills": "http://localhost:8000/skills/", - "users": "http://localhost:8000/users/", - "groups": "http://localhost:8000/groups/" + "users": "http://localhost:8000/users/" }, "post": { - "skills": "http://localhost:8000/skills/", "users": "http://localhost:8000/users/", - "groups": "http://localhost:8000/groups/" + "upload": "http://localhost:8000/upload/" } } } \ No newline at end of file diff --git a/internal/assets.js b/internal/assets.js index ef756d9..1097807 100644 --- a/internal/assets.js +++ b/internal/assets.js @@ -2,7 +2,7 @@ const HTMLAsset = require('parcel-bundler/lib/assets/HTMLAsset') function shouldIgnore (file) { // Ignore img(src="${...}") on pug & keep the components folder pristine - return /\${.+}/.test(file) || /components/.test(file); + return /\${.+}/.test(file) || /components/.test(file) || /\/lib\/solid-/.test(file); } class SkipStartinbloxWidgetAsset extends HTMLAsset { diff --git a/internal/parcel.js b/internal/parcel.js index 80161f3..610965e 100644 --- a/internal/parcel.js +++ b/internal/parcel.js @@ -26,12 +26,14 @@ const options = { }; (async function() { - if(!fs.existsSync("config.json")) throw "[Error] (Mandatory) Missing config.json file"; + let configPath = process.env.CONFIG_PATH || 'config.json'; + if(!fs.existsSync(configPath)) throw `[Error] (Mandatory) Missing ${configPath} file`; + console.log(`Using ${configPath} config file`); - let config = JSON.parse(fs.readFileSync('config.json')); + let config = JSON.parse(fs.readFileSync(configPath)); - if(!config.clientName) throw "[Error] (Mandatory) Missing clientName on config.json"; - if(!config.clientLogo) throw "[Error] (Mandatory) Missing clientLogo on config.json"; + if(!config.clientName) throw `[Error] (Mandatory) Missing clientName on ${configPath}`; + if(!config.clientLogo) throw `[Error] (Mandatory) Missing clientLogo on ${configPath}`; let manifest = { "lang": "fr", diff --git a/src/pug.config.js b/src/pug.config.js index 7b44602..c6f8a25 100644 --- a/src/pug.config.js +++ b/src/pug.config.js @@ -1,4 +1,5 @@ -const config = require("../config.json"); +let configPath = process.env.CONFIG_PATH || 'config.json'; +const config = require(`../${configPath}`); module.exports = { locals: config diff --git a/src/sw.js b/src/sw.js index 63a77b7..881a4a5 100644 --- a/src/sw.js +++ b/src/sw.js @@ -30,84 +30,86 @@ self.addEventListener('activate', function (e) { self.clients.claim(); }); -self.addEventListener('fetch', function (event) { - let requestURL = new URL(event.request.url); - if (requestURL.origin == location.origin) { - // Static asset, cache then network - event.respondWith( - caches.open(CACHE_NAME).then(function (cache) { - return cache.match(event.request).then(function (response) { - var fetchPromise = fetch(event.request).then(function (networkResponse) { - cache.put(event.request, networkResponse.clone()); - return networkResponse; +if(process.env.NODE_ENV === 'production'){ + self.addEventListener('fetch', function (event) { + let requestURL = new URL(event.request.url); + if (requestURL.origin == location.origin) { + // Static asset, cache then network + event.respondWith( + caches.open(CACHE_NAME).then(function (cache) { + return cache.match(event.request).then(function (response) { + var fetchPromise = fetch(event.request).then(function (networkResponse) { + cache.put(event.request, networkResponse.clone()); + return networkResponse; + }); + return response || fetchPromise; }); - return response || fetchPromise; - }); - }), - ); - } else { - if ( - event.request.method == 'POST' || - event.request.method == 'PUT' - ) { - // disabled: lead to cors errors - // // POST/PUT to api, rewrite the cache - // event.respondWith( - // caches.open(CACHE_NAME + '-api').then(function (cache) { - // return fetch(event.request).then(function (response) { - // cache.put(event.request, response.clone()); - // return response; - // }) - // })); - // api: no cache - event.respondWith(fetch(event.request)); - } else if ( - /matomo/.test(requestURL.origin) || - /sentry/.test(requestURL.origin) || - /jabber/.test(requestURL.origin) || - /xmpp/.test(requestURL.origin) - ) { - // analytics, always distant - event.respondWith(fetch(event.request)); + }), + ); } else { if ( - /unpkg/.test(requestURL.origin) || - /skypack/.test(requestURL.origin) || - /jspm/.test(requestURL.origin) || - /jsdeliver/.test(requestURL.origin) || - /cdn/.test(requestURL.origin) || - /googleapis/.test(requestURL.origin) + event.request.method == 'POST' || + event.request.method == 'PUT' ) { - // cdn: cache then network - event.respondWith( - caches.open(CACHE_NAME + '-cdn').then(function (cache) { - return cache.match(event.request).then(function (response) { - var fetchPromise = fetch(event.request).then(function (networkResponse) { - cache.put(event.request, networkResponse.clone()); - return networkResponse; - }); - return response || fetchPromise; - }); - }), - ); - } else { // disabled: lead to cors errors - // // api: distant then cache + // // POST/PUT to api, rewrite the cache // event.respondWith( - // fetch(event.request) - // .then((response) => { - // caches.open(CACHE_NAME + '-api').then(function (cache) { + // caches.open(CACHE_NAME + '-api').then(function (cache) { + // return fetch(event.request).then(function (response) { // cache.put(event.request, response.clone()); // return response; - // }); - // }) - // .catch(() => { - // return caches.match(event.request); - // }) - // ); + // }) + // })); // api: no cache event.respondWith(fetch(event.request)); + } else if ( + /matomo/.test(requestURL.origin) || + /sentry/.test(requestURL.origin) || + /jabber/.test(requestURL.origin) || + /xmpp/.test(requestURL.origin) + ) { + // analytics, always distant + event.respondWith(fetch(event.request)); + } else { + if ( + /unpkg/.test(requestURL.origin) || + /skypack/.test(requestURL.origin) || + /jspm/.test(requestURL.origin) || + /jsdeliver/.test(requestURL.origin) || + /cdn/.test(requestURL.origin) || + /googleapis/.test(requestURL.origin) + ) { + // cdn: cache then network + event.respondWith( + caches.open(CACHE_NAME + '-cdn').then(function (cache) { + return cache.match(event.request).then(function (response) { + var fetchPromise = fetch(event.request).then(function (networkResponse) { + cache.put(event.request, networkResponse.clone()); + return networkResponse; + }); + return response || fetchPromise; + }); + }), + ); + } else { + // disabled: lead to cors errors + // // api: distant then cache + // event.respondWith( + // fetch(event.request) + // .then((response) => { + // caches.open(CACHE_NAME + '-api').then(function (cache) { + // cache.put(event.request, response.clone()); + // return response; + // }); + // }) + // .catch(() => { + // return caches.match(event.request); + // }) + // ); + // api: no cache + event.respondWith(fetch(event.request)); + } } } - } -}); \ No newline at end of file + }); +} \ No newline at end of file