cloudcommerce 2.3.4 → 2.4.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.
- package/CHANGELOG.md +9 -0
- package/ecomplus-stores/barradoce/functions/many/package.json +3 -3
- package/ecomplus-stores/barradoce/functions/ssr/package.json +6 -6
- package/ecomplus-stores/barradoce/functions/with-apps/package.json +3 -3
- package/ecomplus-stores/barradoce/package.json +2 -2
- package/package.json +2 -2
- package/packages/api/package.json +1 -1
- package/packages/apps/affiliate-program/package.json +1 -1
- package/packages/apps/correios/package.json +1 -1
- package/packages/apps/custom-payment/package.json +1 -1
- package/packages/apps/custom-shipping/package.json +1 -1
- package/packages/apps/datafrete/package.json +1 -1
- package/packages/apps/discounts/package.json +1 -1
- package/packages/apps/emails/package.json +1 -1
- package/packages/apps/fb-conversions/package.json +1 -1
- package/packages/apps/flash-courier/package.json +1 -1
- package/packages/apps/frenet/package.json +1 -1
- package/packages/apps/galaxpay/package.json +1 -1
- package/packages/apps/google-analytics/package.json +1 -1
- package/packages/apps/jadlog/package.json +1 -1
- package/packages/apps/loyalty-points/package.json +1 -1
- package/packages/apps/mandae/package.json +1 -1
- package/packages/apps/melhor-envio/package.json +1 -1
- package/packages/apps/mercadopago/package.json +1 -1
- package/packages/apps/pagarme/package.json +1 -1
- package/packages/apps/pagarme-v5/package.json +1 -1
- package/packages/apps/paghiper/package.json +1 -1
- package/packages/apps/pix/package.json +1 -1
- package/packages/apps/tiny-erp/package.json +1 -1
- package/packages/apps/webhooks/package.json +1 -1
- package/packages/cli/package.json +1 -1
- package/packages/config/package.json +1 -1
- package/packages/emails/package.json +1 -1
- package/packages/eslint/package.json +1 -1
- package/packages/eslint/storefront.eslintrc.cjs +1 -0
- package/packages/events/package.json +1 -1
- package/packages/feeds/package.json +1 -1
- package/packages/firebase/package.json +1 -1
- package/packages/i18n/package.json +1 -1
- package/packages/modules/package.json +1 -1
- package/packages/passport/package.json +1 -1
- package/packages/ssr/package.json +1 -1
- package/packages/storefront/client.d.ts +1 -0
- package/packages/storefront/package.json +2 -1
- package/packages/storefront/src/decap-cms/gen-preview-container.ts +64 -17
- package/packages/storefront/src/decap-cms/get-cms-config.ts +2 -2
- package/packages/storefront/src/decap-cms/preview/indexeddb.ts +51 -0
- package/packages/storefront/src/decap-cms/preview/webcontainer.ts +146 -0
- package/packages/storefront/src/env.d.ts +1 -0
- package/packages/storefront/src/lib/scripts/decap-cms.ts +51 -37
- package/packages/storefront/src/lib/ssr-context.ts +5 -0
- package/packages/test-base/package.json +1 -1
- package/packages/types/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -2,6 +2,15 @@
|
|
|
2
2
|
|
|
3
3
|
All notable changes to this project will be documented in this file. See [standard-version](https://github.com/conventional-changelog/standard-version) for commit guidelines.
|
|
4
4
|
|
|
5
|
+
### [2.4.1](https://github.com/ecomplus/cloud-commerce/compare/v2.4.0...v2.4.1) (2024-02-10)
|
|
6
|
+
|
|
7
|
+
## [2.4.0](https://github.com/ecomplus/cloud-commerce/compare/v2.3.4...v2.4.0) (2024-02-10)
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
### Features
|
|
11
|
+
|
|
12
|
+
* **storefront:** Getting startep with new `scripts/decap-cms` ([bac0d21](https://github.com/ecomplus/cloud-commerce/commit/bac0d21fd1bd03abe53b283bda92c1c36b08098f)), closes [#320](https://github.com/ecomplus/cloud-commerce/issues/320)
|
|
13
|
+
|
|
5
14
|
### [2.3.4](https://github.com/ecomplus/cloud-commerce/compare/v2.3.3...v2.3.4) (2024-02-09)
|
|
6
15
|
|
|
7
16
|
### [2.3.3](https://github.com/ecomplus/cloud-commerce/compare/v2.3.2...v2.3.3) (2024-02-09)
|
|
@@ -15,8 +15,8 @@
|
|
|
15
15
|
},
|
|
16
16
|
"main": "index.js",
|
|
17
17
|
"dependencies": {
|
|
18
|
-
"@cloudcommerce/feeds": "^2.3.
|
|
19
|
-
"@cloudcommerce/firebase": "^2.3.
|
|
20
|
-
"@cloudcommerce/passport": "^2.3.
|
|
18
|
+
"@cloudcommerce/feeds": "^2.3.4",
|
|
19
|
+
"@cloudcommerce/firebase": "^2.3.4",
|
|
20
|
+
"@cloudcommerce/passport": "^2.3.4"
|
|
21
21
|
}
|
|
22
22
|
}
|
|
@@ -18,15 +18,15 @@
|
|
|
18
18
|
},
|
|
19
19
|
"main": "index.js",
|
|
20
20
|
"dependencies": {
|
|
21
|
-
"@cloudcommerce/api": "^2.3.
|
|
22
|
-
"@cloudcommerce/firebase": "^2.3.
|
|
23
|
-
"@cloudcommerce/ssr": "^2.3.
|
|
21
|
+
"@cloudcommerce/api": "^2.3.4",
|
|
22
|
+
"@cloudcommerce/firebase": "^2.3.4",
|
|
23
|
+
"@cloudcommerce/ssr": "^2.3.4",
|
|
24
24
|
"@headlessui/vue": "^1.7.18"
|
|
25
25
|
},
|
|
26
26
|
"devDependencies": {
|
|
27
|
-
"@cloudcommerce/i18n": "^2.3.
|
|
28
|
-
"@cloudcommerce/storefront": "^2.3.
|
|
29
|
-
"@cloudcommerce/types": "^2.3.
|
|
27
|
+
"@cloudcommerce/i18n": "^2.3.4",
|
|
28
|
+
"@cloudcommerce/storefront": "^2.3.4",
|
|
29
|
+
"@cloudcommerce/types": "^2.3.4",
|
|
30
30
|
"@iconify-json/mingcute": "^1.1.16",
|
|
31
31
|
"photoswipe": "^5.4.3"
|
|
32
32
|
}
|
|
@@ -15,8 +15,8 @@
|
|
|
15
15
|
},
|
|
16
16
|
"main": "index.js",
|
|
17
17
|
"dependencies": {
|
|
18
|
-
"@cloudcommerce/events": "^2.3.
|
|
19
|
-
"@cloudcommerce/firebase": "^2.3.
|
|
20
|
-
"@cloudcommerce/modules": "^2.3.
|
|
18
|
+
"@cloudcommerce/events": "^2.3.4",
|
|
19
|
+
"@cloudcommerce/firebase": "^2.3.4",
|
|
20
|
+
"@cloudcommerce/modules": "^2.3.4"
|
|
21
21
|
}
|
|
22
22
|
}
|
|
@@ -26,10 +26,10 @@
|
|
|
26
26
|
"url": "https://github.com/ecomplus/cloud-commerce/issues"
|
|
27
27
|
},
|
|
28
28
|
"dependencies": {
|
|
29
|
-
"@cloudcommerce/cli": "^2.3.
|
|
29
|
+
"@cloudcommerce/cli": "^2.3.4"
|
|
30
30
|
},
|
|
31
31
|
"devDependencies": {
|
|
32
|
-
"@cloudcommerce/eslint": "^2.3.
|
|
32
|
+
"@cloudcommerce/eslint": "^2.3.4",
|
|
33
33
|
"husky": "^9.0.10",
|
|
34
34
|
"lint-staged": "^15.2.2"
|
|
35
35
|
}
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "cloudcommerce",
|
|
3
3
|
"type": "module",
|
|
4
|
-
"version": "2.
|
|
4
|
+
"version": "2.4.1",
|
|
5
5
|
"description": "Open fair-code headless commerce platform: API-first, microservices based, event driven and cloud native",
|
|
6
6
|
"main": "packages/api/lib/index.js",
|
|
7
7
|
"author": "E-Com Club Softwares para E-commerce <ti@e-com.club>",
|
|
@@ -36,7 +36,7 @@
|
|
|
36
36
|
"vite": "^5.0.11",
|
|
37
37
|
"vitest": "^1.2.2",
|
|
38
38
|
"zx": "^7.2.3",
|
|
39
|
-
"@cloudcommerce/eslint": "2.
|
|
39
|
+
"@cloudcommerce/eslint": "2.4.1"
|
|
40
40
|
},
|
|
41
41
|
"scripts": {
|
|
42
42
|
"fix-install": "bash scripts/pre-install.sh && pnpm i",
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@cloudcommerce/storefront",
|
|
3
3
|
"type": "module",
|
|
4
|
-
"version": "2.
|
|
4
|
+
"version": "2.4.1",
|
|
5
5
|
"description": "E-Com Plus Cloud Commerce storefront with Astro",
|
|
6
6
|
"bin": {
|
|
7
7
|
"storefront": "./scripts/build-prod.sh"
|
|
@@ -65,6 +65,7 @@
|
|
|
65
65
|
"devDependencies": {
|
|
66
66
|
"@cloudcommerce/eslint": "workspace:*",
|
|
67
67
|
"@cloudcommerce/types": "workspace:*",
|
|
68
|
+
"@types/react": "^18.2.55",
|
|
68
69
|
"@webcontainer/api": "^1.1.9"
|
|
69
70
|
}
|
|
70
71
|
}
|
|
@@ -1,14 +1,42 @@
|
|
|
1
|
-
import type
|
|
1
|
+
import type NReact from 'react';
|
|
2
|
+
import afetch from '../helpers/afetch';
|
|
3
|
+
import { initWebcontainer } from './preview/webcontainer';
|
|
2
4
|
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
5
|
+
const getRepoCommits = async (repo: string, ghToken?: string) => {
|
|
6
|
+
const headers: Record<string, string> = {
|
|
7
|
+
Accept: 'application/vnd.github+json',
|
|
8
|
+
'X-GitHub-Api-Version': '2022-11-28',
|
|
9
|
+
};
|
|
10
|
+
if (ghToken) {
|
|
11
|
+
headers.Authorization = `Bearer ${ghToken}`;
|
|
12
|
+
}
|
|
13
|
+
const res = await afetch(`https://api.github.com/repos/${repo}/commits`, {
|
|
14
|
+
headers,
|
|
15
|
+
});
|
|
16
|
+
if (res.ok) {
|
|
17
|
+
return res.json();
|
|
18
|
+
}
|
|
19
|
+
const err: any = new Error('Failed reading repository commits on GitHub API');
|
|
20
|
+
err.res = res;
|
|
21
|
+
err.text = await res.text();
|
|
22
|
+
throw new Error(err);
|
|
23
|
+
};
|
|
24
|
+
|
|
25
|
+
export const genPreviewContainer = ({
|
|
26
|
+
React,
|
|
27
|
+
WebContainer,
|
|
28
|
+
cmsConfig,
|
|
29
|
+
ghToken,
|
|
30
|
+
}: {
|
|
31
|
+
React: typeof NReact,
|
|
6
32
|
WebContainer: any,
|
|
33
|
+
cmsConfig: Record<string, any>,
|
|
34
|
+
ghToken?: string,
|
|
7
35
|
}) => {
|
|
8
|
-
const
|
|
9
|
-
|
|
36
|
+
const { repo } = cmsConfig.backend;
|
|
37
|
+
const cliTextareaId = 'webcontainerCli';
|
|
10
38
|
// https://github.com/decaporg/decap-cms/issues/2183#issuecomment-997373169
|
|
11
|
-
return
|
|
39
|
+
return class Prevew extends React.Component {
|
|
12
40
|
render() {
|
|
13
41
|
const { entry } = (this as any).props;
|
|
14
42
|
console.log({ entry });
|
|
@@ -17,16 +45,35 @@ export const genPreviewContainer = async ({ createClass, h, WebContainer }: {
|
|
|
17
45
|
const isLocal = host.startsWith('localhost') || host.startsWith('127.0.0.');
|
|
18
46
|
const src = `${isLocal ? 'http' : 'https'}://${host}/~preview/${slug}`;
|
|
19
47
|
const html = `
|
|
20
|
-
<
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
48
|
+
<textarea id="${cliTextareaId}"></textarea>
|
|
49
|
+
<code>${src}</code>`;
|
|
50
|
+
return React.createElement('div', {
|
|
51
|
+
dangerouslySetInnerHTML: { __html: html },
|
|
52
|
+
});
|
|
53
|
+
}
|
|
54
|
+
componentDidMount() {
|
|
55
|
+
let commitSha: string | undefined;
|
|
56
|
+
(async () => {
|
|
57
|
+
try {
|
|
58
|
+
const commits = await getRepoCommits(repo, ghToken);
|
|
59
|
+
commitSha = commits[0]?.sha;
|
|
60
|
+
} catch (err) {
|
|
61
|
+
console.error(err);
|
|
62
|
+
}
|
|
63
|
+
})();
|
|
64
|
+
const iframe = document.getElementById('preview-pane') as HTMLIFrameElement;
|
|
65
|
+
const cliTextarea = iframe.contentWindow!.document
|
|
66
|
+
.getElementById(cliTextareaId) as HTMLTextAreaElement;
|
|
67
|
+
initWebcontainer({
|
|
68
|
+
repo,
|
|
69
|
+
ghToken,
|
|
70
|
+
WebContainer,
|
|
71
|
+
cliTextarea,
|
|
72
|
+
}).then(({ startDevServer }) => {
|
|
73
|
+
startDevServer(commitSha);
|
|
74
|
+
});
|
|
75
|
+
}
|
|
76
|
+
};
|
|
30
77
|
};
|
|
31
78
|
|
|
32
79
|
export default genPreviewContainer;
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
let db: IDBDatabase;
|
|
2
|
+
const storeName = 'repo';
|
|
3
|
+
|
|
4
|
+
export const startingDb = new Promise<IDBDatabase>((resolve, reject) => {
|
|
5
|
+
const openRequest = indexedDB.open('ecomplus', 2);
|
|
6
|
+
openRequest.onerror = () => {
|
|
7
|
+
reject(new Error('Why didn\'t you allow my web app to use IndexedDB?!'));
|
|
8
|
+
};
|
|
9
|
+
openRequest.onsuccess = (ev) => {
|
|
10
|
+
db = (ev.target as any).result;
|
|
11
|
+
resolve(db!);
|
|
12
|
+
};
|
|
13
|
+
openRequest.onupgradeneeded = (ev) => {
|
|
14
|
+
db = (ev.target as any).result;
|
|
15
|
+
db!.createObjectStore(storeName, { keyPath: 'sha' });
|
|
16
|
+
resolve(db!);
|
|
17
|
+
};
|
|
18
|
+
});
|
|
19
|
+
|
|
20
|
+
export class RepoDatabase {
|
|
21
|
+
objectKey = '';
|
|
22
|
+
data: any;
|
|
23
|
+
constructor(repo: string) {
|
|
24
|
+
this.objectKey = repo;
|
|
25
|
+
}
|
|
26
|
+
async put(sha: string, zip: any) {
|
|
27
|
+
await startingDb;
|
|
28
|
+
const data = this.data || {};
|
|
29
|
+
data.sha = sha;
|
|
30
|
+
data.zip = zip;
|
|
31
|
+
const tx = db.transaction([storeName], 'readwrite');
|
|
32
|
+
const objectStore = tx.objectStore(storeName);
|
|
33
|
+
console.log({ data });
|
|
34
|
+
objectStore.put(data, this.objectKey);
|
|
35
|
+
}
|
|
36
|
+
async get(sha: string) {
|
|
37
|
+
await startingDb;
|
|
38
|
+
const tx = db.transaction([storeName]);
|
|
39
|
+
const objectStore = tx.objectStore(storeName);
|
|
40
|
+
const request = objectStore.get(this.objectKey);
|
|
41
|
+
return new Promise((resolve, reject) => {
|
|
42
|
+
request.onerror = (error) => {
|
|
43
|
+
reject(error);
|
|
44
|
+
};
|
|
45
|
+
request.onsuccess = (ev) => {
|
|
46
|
+
this.data = (ev.target as any).result;
|
|
47
|
+
resolve(sha === this.data?.sha ? this.data.zip : null);
|
|
48
|
+
};
|
|
49
|
+
});
|
|
50
|
+
}
|
|
51
|
+
}
|
|
@@ -0,0 +1,146 @@
|
|
|
1
|
+
import type { WebContainer as IWebContainer } from '@webcontainer/api';
|
|
2
|
+
import { RepoDatabase } from './indexeddb';
|
|
3
|
+
|
|
4
|
+
export const genContainerFiles = ({ repo, ghToken }: {
|
|
5
|
+
repo: string,
|
|
6
|
+
ghToken?: string,
|
|
7
|
+
}) => ({
|
|
8
|
+
'git.js': {
|
|
9
|
+
file: {
|
|
10
|
+
contents: `
|
|
11
|
+
import { join } from 'path';
|
|
12
|
+
import { clone } from 'isomorphic-git';
|
|
13
|
+
import * as http from 'isomorphic-git/http/node/index.cjs';
|
|
14
|
+
import fs from 'node:fs';
|
|
15
|
+
const exe = async () => {
|
|
16
|
+
const dir = join(process.cwd(), 'store');
|
|
17
|
+
const gitOptions = {
|
|
18
|
+
fs,
|
|
19
|
+
http,
|
|
20
|
+
dir,
|
|
21
|
+
url: 'https://github.com/${repo}.git',
|
|
22
|
+
singleBranch: true,
|
|
23
|
+
depth: 1,
|
|
24
|
+
};
|
|
25
|
+
${(ghToken
|
|
26
|
+
? `
|
|
27
|
+
gitOptions.oauth2format = 'github';
|
|
28
|
+
gitOptions.token = '${ghToken}';`
|
|
29
|
+
: '')}
|
|
30
|
+
await clone(gitOptions);
|
|
31
|
+
};
|
|
32
|
+
exe();
|
|
33
|
+
`,
|
|
34
|
+
},
|
|
35
|
+
},
|
|
36
|
+
'unzipper.js': {
|
|
37
|
+
file: {
|
|
38
|
+
contents: `
|
|
39
|
+
import AdmZip from 'adm-zip';
|
|
40
|
+
const unzipDirectory = async (inputFilePath, outputDirectory) => {
|
|
41
|
+
const zip = new AdmZip(inputFilePath);
|
|
42
|
+
return new Promise((resolve, reject) => {
|
|
43
|
+
zip.extractAllToAsync(outputDirectory, true, (error) => {
|
|
44
|
+
if (error) {
|
|
45
|
+
console.error(error);
|
|
46
|
+
reject(error);
|
|
47
|
+
} else {
|
|
48
|
+
resolve();
|
|
49
|
+
}
|
|
50
|
+
});
|
|
51
|
+
});
|
|
52
|
+
};
|
|
53
|
+
await unzipDirectory('store.zip', 'store');
|
|
54
|
+
`,
|
|
55
|
+
},
|
|
56
|
+
},
|
|
57
|
+
'zipper.js': {
|
|
58
|
+
file: {
|
|
59
|
+
contents: `
|
|
60
|
+
import AdmZip from 'adm-zip';
|
|
61
|
+
const zipDirectory = async (sourceDir, outputFilePath) => {
|
|
62
|
+
const zip = new AdmZip();
|
|
63
|
+
zip.addLocalFolder(sourceDir);
|
|
64
|
+
await zip.writeZipPromise(outputFilePath);
|
|
65
|
+
};
|
|
66
|
+
await zipDirectory('./store', './store.zip');
|
|
67
|
+
`,
|
|
68
|
+
},
|
|
69
|
+
},
|
|
70
|
+
'package.json': {
|
|
71
|
+
file: {
|
|
72
|
+
contents: `
|
|
73
|
+
{
|
|
74
|
+
"name": "git-app",
|
|
75
|
+
"version": "1.0.0",
|
|
76
|
+
"type": "module",
|
|
77
|
+
"private": true,
|
|
78
|
+
"description": "",
|
|
79
|
+
"main": "index.js",
|
|
80
|
+
"author": "",
|
|
81
|
+
"license": "ISC",
|
|
82
|
+
"scripts": {
|
|
83
|
+
"start": "nodemon --watch './' index.js",
|
|
84
|
+
"git": "node git.js",
|
|
85
|
+
"unzipper": "node unzipper.js",
|
|
86
|
+
"zipper": "node zipper.js"
|
|
87
|
+
},
|
|
88
|
+
"dependencies": {
|
|
89
|
+
"dotenv": "^16.3.1",
|
|
90
|
+
"adm-zip": "^0.5.10",
|
|
91
|
+
"axios": "^1.6.2",
|
|
92
|
+
"isomorphic-git": "^1.25.2"
|
|
93
|
+
}
|
|
94
|
+
}`,
|
|
95
|
+
},
|
|
96
|
+
},
|
|
97
|
+
});
|
|
98
|
+
|
|
99
|
+
export const initWebcontainer = async ({
|
|
100
|
+
repo,
|
|
101
|
+
ghToken,
|
|
102
|
+
WebContainer,
|
|
103
|
+
cliTextarea,
|
|
104
|
+
}: {
|
|
105
|
+
repo: string,
|
|
106
|
+
ghToken?: string,
|
|
107
|
+
WebContainer: Record<string, any>,
|
|
108
|
+
cliTextarea: HTMLTextAreaElement,
|
|
109
|
+
}) => {
|
|
110
|
+
const webcontainerInstance: IWebContainer = await WebContainer.boot();
|
|
111
|
+
const files = genContainerFiles({ repo, ghToken });
|
|
112
|
+
await webcontainerInstance.mount(files);
|
|
113
|
+
const exec = async (command: string, args: string[]) => {
|
|
114
|
+
const cliArgs = args.reduce((acc, opt) => `${acc} ${opt}`, '');
|
|
115
|
+
const cli = `$ ${command}${cliArgs}\n`;
|
|
116
|
+
cliTextarea.value += cli;
|
|
117
|
+
const cmd = await webcontainerInstance.spawn(command, args);
|
|
118
|
+
cmd.output.pipeTo(new WritableStream({
|
|
119
|
+
write(stdout) {
|
|
120
|
+
console.debug?.('webcontainer', { stdout });
|
|
121
|
+
},
|
|
122
|
+
}));
|
|
123
|
+
if (await cmd.exit !== 0) {
|
|
124
|
+
throw new Error(`${command} failed`);
|
|
125
|
+
}
|
|
126
|
+
};
|
|
127
|
+
await exec('npm', ['install']);
|
|
128
|
+
const startDevServer = async (commitSha?: string) => {
|
|
129
|
+
const repoDatabase = new RepoDatabase(repo);
|
|
130
|
+
const storedRepoZip = commitSha ? await repoDatabase.get(commitSha) : null;
|
|
131
|
+
if (!storedRepoZip) {
|
|
132
|
+
await exec('npm', ['run', 'git']);
|
|
133
|
+
await exec('npm', ['--prefix', 'store', 'i']);
|
|
134
|
+
if (commitSha) {
|
|
135
|
+
await exec('npm', ['run', 'zipper']);
|
|
136
|
+
const repoZip = await webcontainerInstance.fs.readFile('./store.zip');
|
|
137
|
+
repoDatabase.put(commitSha, repoZip);
|
|
138
|
+
}
|
|
139
|
+
}
|
|
140
|
+
};
|
|
141
|
+
return {
|
|
142
|
+
webcontainerInstance,
|
|
143
|
+
webcontainerExec: exec,
|
|
144
|
+
startDevServer,
|
|
145
|
+
};
|
|
146
|
+
};
|
|
@@ -4,47 +4,42 @@ import getCmsConfig from '../../decap-cms/get-cms-config';
|
|
|
4
4
|
import genPreviewContainer from '../../decap-cms/gen-preview-container';
|
|
5
5
|
|
|
6
6
|
let cmsConfig: Record<string, any> = getCmsConfig();
|
|
7
|
+
let ghToken: string | undefined;
|
|
7
8
|
const initCmsWithPreview = () => {
|
|
8
|
-
const {
|
|
9
|
-
|
|
10
|
-
initCMS,
|
|
11
|
-
createClass,
|
|
12
|
-
h,
|
|
13
|
-
} = window as any as {
|
|
9
|
+
const { React, CMS, WebContainer } = window as any as {
|
|
10
|
+
React: any,
|
|
14
11
|
CMS: Record<string, any>,
|
|
15
|
-
|
|
16
|
-
createClass: any,
|
|
17
|
-
h: any,
|
|
12
|
+
WebContainer: any,
|
|
18
13
|
};
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
.catch((err) => {
|
|
28
|
-
console.error(err);
|
|
29
|
-
// eslint-disable-next-line
|
|
30
|
-
window.alert('Failed importing WebContainer for live preview');
|
|
31
|
-
});
|
|
14
|
+
CMS.init({ config: cmsConfig });
|
|
15
|
+
const Preview = genPreviewContainer({
|
|
16
|
+
React,
|
|
17
|
+
WebContainer,
|
|
18
|
+
cmsConfig,
|
|
19
|
+
ghToken,
|
|
20
|
+
});
|
|
21
|
+
CMS.registerPreviewTemplate('general', Preview);
|
|
32
22
|
};
|
|
33
23
|
|
|
34
24
|
const authAndInitCms = async () => {
|
|
35
|
-
if (import.meta.env.DEV) {
|
|
36
|
-
cmsConfig.local_backend = true;
|
|
37
|
-
cmsConfig.backend = { name: 'git-gateway' };
|
|
38
|
-
initCmsWithPreview();
|
|
39
|
-
return;
|
|
40
|
-
}
|
|
41
25
|
const {
|
|
42
26
|
location,
|
|
43
27
|
sessionStorage,
|
|
44
28
|
ECOM_STORE_ID,
|
|
29
|
+
GIT_REPO,
|
|
45
30
|
CMS_SSO_URL = 'https://app.e-com.plus/pages/login?api_version=2',
|
|
46
31
|
} = window;
|
|
47
|
-
|
|
32
|
+
if (import.meta.env.DEV) {
|
|
33
|
+
cmsConfig.local_backend = true;
|
|
34
|
+
cmsConfig.backend = {
|
|
35
|
+
repo: GIT_REPO || 'ecomplus/store',
|
|
36
|
+
name: 'git-gateway',
|
|
37
|
+
};
|
|
38
|
+
initCmsWithPreview();
|
|
39
|
+
return;
|
|
40
|
+
}
|
|
41
|
+
const storageKey = '__cms_token';
|
|
42
|
+
let token = sessionStorage.getItem(storageKey);
|
|
48
43
|
const searchParams = new URLSearchParams(location.search);
|
|
49
44
|
const ssoToken = searchParams.get('sso_token') || searchParams.get('access_token');
|
|
50
45
|
if (!cmsConfig.backend?.base_url) {
|
|
@@ -56,8 +51,8 @@ const authAndInitCms = async () => {
|
|
|
56
51
|
return;
|
|
57
52
|
}
|
|
58
53
|
cmsConfig.backend = {
|
|
59
|
-
repo: '_owner/_name',
|
|
60
|
-
api_root:
|
|
54
|
+
repo: GIT_REPO || '_owner/_name',
|
|
55
|
+
api_root: `https://ecomplus.app/api/${ECOM_STORE_ID}/git/github/`,
|
|
61
56
|
name: 'github',
|
|
62
57
|
base_url: `https://${location.hostname}`,
|
|
63
58
|
auth_endpoint: location.pathname, // self
|
|
@@ -89,8 +84,10 @@ const authAndInitCms = async () => {
|
|
|
89
84
|
: installations[0];
|
|
90
85
|
if (installation?.gh_token && installation.gh_token.charAt(0) !== '*') {
|
|
91
86
|
// Consume GitHub REST API directly
|
|
92
|
-
token = installation.gh_token;
|
|
87
|
+
token = installation.gh_token as string;
|
|
88
|
+
ghToken = token;
|
|
93
89
|
delete cmsConfig.backend.api_root;
|
|
90
|
+
cmsConfig.backend.repo = installation.repository;
|
|
94
91
|
cmsConfig.backend.name = 'github';
|
|
95
92
|
}
|
|
96
93
|
}
|
|
@@ -98,6 +95,7 @@ const authAndInitCms = async () => {
|
|
|
98
95
|
}
|
|
99
96
|
}
|
|
100
97
|
if (token) {
|
|
98
|
+
sessionStorage.removeItem(storageKey);
|
|
101
99
|
if (!window.opener) initCmsWithPreview();
|
|
102
100
|
// Ref.: https://github.com/decaporg/decap-cms/blob/e93c94f1ce707719dfb7750af82b17c38b461831/packages/decap-cms-lib-auth/src/netlify-auth.js#L46
|
|
103
101
|
// E.g.: https://github.com/Herohtar/netlify-cms-oauth-firebase/blob/master/functions/index.js#L9-L25
|
|
@@ -122,7 +120,7 @@ const authAndInitCms = async () => {
|
|
|
122
120
|
);
|
|
123
121
|
const provider = cmsConfig.backend.name;
|
|
124
122
|
if (provider && provider !== 'git-gateway') {
|
|
125
|
-
sessionStorage.setItem(
|
|
123
|
+
sessionStorage.setItem(storageKey, ssoToken);
|
|
126
124
|
}
|
|
127
125
|
}
|
|
128
126
|
initCmsWithPreview();
|
|
@@ -134,8 +132,24 @@ if (!import.meta.env.SSR) {
|
|
|
134
132
|
cmsConfig = deepmerge(cmsConfig, window.CMS_CUSTOM_CONFIG);
|
|
135
133
|
}
|
|
136
134
|
(window as any).CMS_MANUAL_INIT = true;
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
135
|
+
/* eslint-disable import/no-unresolved */
|
|
136
|
+
Promise.all([
|
|
137
|
+
// @ts-ignore
|
|
138
|
+
import(/* @vite-ignore */ 'https://esm.sh/react@^18'),
|
|
139
|
+
// @ts-ignore
|
|
140
|
+
import(/* @vite-ignore */ 'https://esm.sh/decap-cms-app@^3'),
|
|
141
|
+
// @ts-ignore
|
|
142
|
+
import(/* @vite-ignore */ 'https://esm.sh/@webcontainer/api@^1'),
|
|
143
|
+
])
|
|
144
|
+
.then(([React, { default: CMS }, { WebContainer }]) => {
|
|
145
|
+
(window as any).React = React;
|
|
146
|
+
(window as any).CMS = CMS;
|
|
147
|
+
(window as any).WebContainer = WebContainer;
|
|
148
|
+
authAndInitCms();
|
|
149
|
+
})
|
|
150
|
+
.catch((err) => {
|
|
151
|
+
console.error(err);
|
|
152
|
+
// eslint-disable-next-line
|
|
153
|
+
window.alert('Failed importing Decap CMS app or preview dependencies');
|
|
154
|
+
});
|
|
141
155
|
}
|
|
@@ -267,6 +267,11 @@ const loadRouteContext = async (
|
|
|
267
267
|
} else {
|
|
268
268
|
setResponseCache(Astro, 120, 180);
|
|
269
269
|
}
|
|
270
|
+
if (isPreview || urlPath.startsWith('/admin/')) {
|
|
271
|
+
// https://webcontainers.io/guides/configuring-headers#configuring-headers
|
|
272
|
+
Astro.response.headers.set('Cross-Origin-Embedder-Policy', 'require-corp');
|
|
273
|
+
Astro.response.headers.set('Cross-Origin-Opener-Policy', 'same-origin');
|
|
274
|
+
}
|
|
270
275
|
const routeContext = {
|
|
271
276
|
...config,
|
|
272
277
|
isHomepage,
|