Skip to content

Commit 0168c3f

Browse files
committed
chore(example): add shared worker with lazy and style-loader
1 parent 7866fc0 commit 0168c3f

17 files changed

+692
-0
lines changed
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
## Start Up
2+
3+
Make sure the root directory is running `yarn install && yarn build`.
4+
5+
```bash
6+
cd examples/reactant-share-sharedworker
7+
yarn install
8+
yarn start
9+
```
10+
11+
open `http://localhost:7000/` & `chrome://inspect/#workers`.
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
<!doctype html>
2+
<html>
3+
<head>
4+
</head>
5+
<body>
6+
<div id="app"></div>
7+
<script src="detached-window.bundle.js"></script>
8+
</body>
9+
</html>
Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
declare const __DEV__: boolean;
2+
3+
interface Window {
4+
__REDUX_DEVTOOLS_EXTENSION_COMPOSE__: any;
5+
app: any;
6+
}
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
<!doctype html>
2+
<html>
3+
<head>
4+
</head>
5+
<body>
6+
<div id="app"></div>
7+
<script src="iframe.bundle.js"></script>
8+
</body>
9+
</html>
Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
<!DOCTYPE html>
2+
<html lang="en">
3+
<head>
4+
<meta charset="UTF-8">
5+
<meta name="viewport" content="width=device-width, initial-scale=1.0">
6+
<title>Index</title>
7+
<script>
8+
window.__worker__ = new SharedWorker('worker.bundle.js');
9+
</script>
10+
</head>
11+
<body>
12+
<div id="app"></div>
13+
<script async src="index.bundle.js"></script>
14+
</body>
15+
</html>
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
{
2+
"name": "reactant-share-sharedworker-lazy",
3+
"version": "1.0.0",
4+
"description": "",
5+
"main": "index.js",
6+
"scripts": {
7+
"start": "webpack-dev-server"
8+
},
9+
"keywords": [],
10+
"author": "",
11+
"license": "MIT",
12+
"devDependencies": {
13+
"copy-webpack-plugin": "^11.0.0",
14+
"node-polyfill-webpack-plugin": "^2.0.1",
15+
"ts-loader": "^9.4.1",
16+
"typescript": "^4.8.4",
17+
"webpack": "^5.74.0",
18+
"webpack-cli": "^4.10.0",
19+
"webpack-dev-server": "^4.11.1"
20+
},
21+
"dependencies": {
22+
"css-loader": "^6.7.3",
23+
"html-inline-script-webpack-plugin": "^3.1.0",
24+
"html-webpack-plugin": "^5.5.0",
25+
"localforage": "^1.10.0",
26+
"react": "^17.0.2",
27+
"style-loader": "^3.3.1"
28+
}
29+
}
Lines changed: 145 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,145 @@
1+
/* eslint-disable jsx-a11y/anchor-is-valid */
2+
// @ts-nocheck
3+
import React, { useState, FunctionComponent } from 'react';
4+
import { Switch, Route } from 'reactant-web';
5+
import {
6+
ViewModule,
7+
injectable,
8+
useConnector,
9+
Router,
10+
PortDetector,
11+
ClientTransport as IClientTransport,
12+
ServerTransport as IServerTransport,
13+
Transport,
14+
} from 'reactant-share';
15+
import { TodoListView } from './todoList.view';
16+
import { CounterView } from './counter.view';
17+
// @ts-ignore
18+
import style from './style.css';
19+
20+
const Link: FunctionComponent<{ active: boolean; onClick: () => any }> = ({
21+
active,
22+
children,
23+
onClick,
24+
}) => {
25+
return (
26+
<div onClick={onClick} style={{ color: active ? 'red' : 'black' }}>
27+
{children}
28+
</div>
29+
);
30+
};
31+
32+
interface ClientTransport extends IClientTransport {
33+
test(n: number): Promise<string>;
34+
}
35+
36+
@injectable({
37+
name: 'appView',
38+
})
39+
export class AppView extends ViewModule {
40+
type = '';
41+
42+
push?: (path: string) => void;
43+
44+
setType?: React.Dispatch<React.SetStateAction<string>>;
45+
46+
constructor(
47+
private todoListView: TodoListView,
48+
private counterView: CounterView,
49+
private portDetector: PortDetector,
50+
private router: Router
51+
) {
52+
super();
53+
54+
this.portDetector.onServer(
55+
(transport: Transport<IServerTransport, ClientTransport>) => {
56+
transport.listen(
57+
'test',
58+
async (n) => `response '${n}' from server port`
59+
);
60+
}
61+
);
62+
this.portDetector.onClient(
63+
(transport: Transport<ClientTransport, IServerTransport>) => {
64+
this.type = 'Client';
65+
transport.emit('test', 42).then((response) => {
66+
console.log(response);
67+
});
68+
}
69+
);
70+
}
71+
72+
load() {
73+
import(/* webpackChunkName: "lazyModule" */ './lazyModule').then(
74+
({ fn }) => {
75+
fn();
76+
}
77+
);
78+
}
79+
80+
component() {
81+
const [type, setType] = useState(this.type);
82+
const currentPath = useConnector(() => this.router?.currentPath);
83+
this.setType = setType;
84+
return (
85+
<>
86+
<ul>
87+
<li>
88+
<Link
89+
active={currentPath === '/'}
90+
onClick={() => this.router.push('/')}
91+
>
92+
Home
93+
</Link>
94+
</li>
95+
<li>
96+
<Link
97+
active={currentPath === this.counterView.path}
98+
onClick={() => this.router.push(this.counterView.path)}
99+
>
100+
{this.counterView.name}
101+
</Link>
102+
</li>
103+
<li>
104+
<Link
105+
active={currentPath === this.todoListView.path}
106+
onClick={() => this.router.push(this.todoListView.path)}
107+
>
108+
{this.todoListView.name}
109+
</Link>
110+
</li>
111+
<li>
112+
<Link
113+
active={currentPath === '/iframe'}
114+
onClick={() => this.router.push('/iframe')}
115+
>
116+
iFrame mode
117+
</Link>
118+
</li>
119+
</ul>
120+
121+
<Switch>
122+
<Route exact path="/">
123+
<h2
124+
style={{ color: type === 'Server' ? 'red' : 'green' }}
125+
className={style.use().locals.button}
126+
>
127+
{`This app is a ${type}`}
128+
</h2>
129+
</Route>
130+
<Route
131+
path={this.counterView.path}
132+
component={this.counterView.component}
133+
/>
134+
<Route
135+
path={this.todoListView.path}
136+
component={this.todoListView.component}
137+
/>
138+
<Route path="/iframe">
139+
<iframe title="iFrame mode" src="./iframe.html" />
140+
</Route>
141+
</Switch>
142+
</>
143+
);
144+
}
145+
}
Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,51 @@
1+
// @ts-nocheck
2+
import React from 'react';
3+
import {
4+
ViewModule,
5+
injectable,
6+
useConnector,
7+
action,
8+
state,
9+
spawn,
10+
} from 'reactant-share';
11+
12+
@injectable({
13+
name: 'counterView',
14+
})
15+
export class CounterView extends ViewModule {
16+
constructor() {
17+
super();
18+
}
19+
20+
name = 'counter';
21+
22+
path = '/counter';
23+
24+
@state
25+
count = 0;
26+
27+
@action
28+
increase() {
29+
this.count += 1;
30+
}
31+
32+
@action
33+
decrease() {
34+
this.count -= 1;
35+
}
36+
37+
component(this: CounterView) {
38+
const count = useConnector(() => this.count);
39+
return (
40+
<>
41+
<button type="button" onClick={() => spawn(this, 'decrease', [])}>
42+
-
43+
</button>
44+
<div>{count}</div>
45+
<button type="button" onClick={() => spawn(this, 'increase', [])}>
46+
+
47+
</button>
48+
</>
49+
);
50+
}
51+
}
Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
// @ts-nocheck
2+
import { render } from 'reactant-web';
3+
import { createSharedApp } from 'reactant-share';
4+
import { TodoListView } from './todoList.view';
5+
6+
createSharedApp({
7+
modules: [
8+
{
9+
provide: 'TodoListViewOptions',
10+
useValue: {
11+
isDetachedWindow: true,
12+
},
13+
},
14+
],
15+
main: TodoListView,
16+
render,
17+
share: {
18+
name: 'SharedWorkerApp',
19+
type: 'SharedWorker',
20+
port: 'client',
21+
workerURL: 'worker.bundle.js',
22+
enablePatchesFilter: true,
23+
},
24+
}).then((app) => {
25+
console.log(app, '====');
26+
(window as any).app = app;
27+
app.bootstrap(document.getElementById('app'));
28+
});
Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
// @ts-nocheck
2+
import { render } from 'reactant-web';
3+
import {
4+
createSharedApp,
5+
RouterOptions,
6+
createHashHistory,
7+
IRouterOptions,
8+
} from 'reactant-share';
9+
import { CounterView } from './counter.view';
10+
11+
createSharedApp({
12+
modules: [
13+
{
14+
provide: RouterOptions,
15+
useValue: {
16+
createHistory: () => createHashHistory(),
17+
} as IRouterOptions,
18+
},
19+
],
20+
main: CounterView,
21+
render,
22+
share: {
23+
name: 'SharedWorkerApp',
24+
port: 'client',
25+
type: 'SharedWorker',
26+
workerURL: 'worker.bundle.js',
27+
portName:
28+
globalThis.location.pathname === '/index.html' ? 'other' : 'default',
29+
},
30+
}).then((app) => {
31+
console.log(app, '====');
32+
(window as any).app = app;
33+
app.bootstrap(document.getElementById('app'));
34+
});

0 commit comments

Comments
 (0)