diff --git a/.dockerignore b/.dockerignore
new file mode 100644
index 0000000000000000000000000000000000000000..bf3da95c656cbb0223acf7e706ea4d1443b67bac
--- /dev/null
+++ b/.dockerignore
@@ -0,0 +1,2 @@
+plugins/*
+!plugins/*.vsix
diff --git a/.gitignore b/.gitignore
index ab6bef8bba52c3ab4cd8b7ac9576f8ea3831a5c6..5971bdf5e9fc93d6b5436aea6796ac367ec10cad 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,6 +1,9 @@
 out/
 .idea/
 
+recorder-out/*
+!recorder-out/webpack.config.js
+
 # Created by https://www.toptal.com/developers/gitignore/api/node,java
 # Edit at https://www.toptal.com/developers/gitignore?templates=node,java
 
diff --git a/Dockerfile b/Dockerfile
index 94d44a9511cd648766e00a1809720973a02baf05..1bd12ddd6139bd66fb5791fc7aea1117f56a33dc 100644
--- a/Dockerfile
+++ b/Dockerfile
@@ -4,25 +4,21 @@ USER root
 
 RUN apt update
 RUN apt upgrade -y
-RUN apt install strace -y
-RUN apt install rsyslog -y
 RUN apt install rsync -y
 
-COPY bash.bashrc .
-RUN cat bash.bashrc >> /etc/bash.bashrc
-COPY bash.conf /etc/rsyslog.d/
-
 COPY plugins /home/plugins
+COPY theia/plugin-storage/global-state.json /home/theia/.theia/plugin-storage/global-state.json
+RUN chown theia /home/theia/.theia -R
+RUN chown theia /home/plugins -R
+
 COPY server.js /home/theia/src-gen/backend/server.js
 
 COPY start.sh .
 
-COPY plugins/deadlock-extension/out deadlock/
-COPY plugins/deadlock-extension/package* deadlock/
-COPY .gitignore_recorder deadlock/recorder/.gitignore
-RUN cd deadlock/ && npm install && cd -
-
-
-ENTRYPOINT ["bash", "start.sh"]
+COPY recorder-out/dist/main.js deadlock/recorder.js
+COPY .gitignore_recorder deadlock/.gitignore
 
+RUN chmod 500 deadlock/ -R
+RUN chmod 500 start.sh
 
+ENTRYPOINT ["bash", "start.sh"]
\ No newline at end of file
diff --git a/README.md b/README.md
new file mode 100644
index 0000000000000000000000000000000000000000..e7c632eba45b938ab22b23ae3dd68e8af1fd597f
--- /dev/null
+++ b/README.md
@@ -0,0 +1,8 @@
+
+
+
+
+## With lerna ?
+
+Cannot work for now because `vsce` does not support npm link:  
+https://github.com/microsoft/vscode-vsce/issues/203
\ No newline at end of file
diff --git a/bash.bashrc b/bash.bashrc
deleted file mode 100644
index 33ee15f34f18e373d5d9b77e4887ada9f4c20257..0000000000000000000000000000000000000000
--- a/bash.bashrc
+++ /dev/null
@@ -1 +0,0 @@
-export PROMPT_COMMAND='RETRN_VAL=$?;logger -p local6.debug "$(whoami) [$$]: $(history 1 | sed "s/^[ ]*[0-9]\+[ ]*//" ) [$RETRN_VAL]"'
diff --git a/build-plugins.sh b/build-plugins.sh
index d18f136e7aae8fe4c7a5fc68b9ce090fbd7dc03f..cd83b8d510ef3fd03ded8ae9eb1e2f59d67cafb1 100755
--- a/build-plugins.sh
+++ b/build-plugins.sh
@@ -6,6 +6,7 @@ for dir in plugins/*/; do
     echo "Building $dir"
     cd $dir
     npm install
-    npm run compile
+    vsce package
+    cp *.vsix ../
     cd -
 done
diff --git a/build-recorder.sh b/build-recorder.sh
new file mode 100755
index 0000000000000000000000000000000000000000..7ee6bf8c76ad0b312680317b918b4330e9f8e798
--- /dev/null
+++ b/build-recorder.sh
@@ -0,0 +1,15 @@
+#!/bin/sh
+
+# You must build deadlock-extension first /!\
+
+set -e
+
+OUTPUT_DIR='recorder-out'
+
+cp -r ./plugins/deadlock-extension/out/* $OUTPUT_DIR
+cp ./plugins/deadlock-extension/packa* $OUTPUT_DIR
+cd $OUTPUT_DIR
+npm install
+npx webpack
+
+
diff --git a/build.sh b/build.sh
new file mode 100755
index 0000000000000000000000000000000000000000..d726478612c46b392bcb1ca67c8c693bdd1d3c5d
--- /dev/null
+++ b/build.sh
@@ -0,0 +1,18 @@
+#!/bin/sh
+
+TAG=${1:-latest}
+
+echo '====================================================='
+echo '================= BUILDING PLUGINS =================='
+echo '====================================================='
+./build-plugins.sh
+echo '====================================================='
+echo '================= BUILDING RECORDER ================='
+echo '====================================================='
+./build-recorder.sh
+
+echo '====================================================='
+echo '=============== BUILDING DOCKER IMAGE ==============='
+echo '====================================================='
+
+docker build . -t registry.e-biz.fr/deadlock-public/deadlock-theia:$TAG
diff --git a/plugins/deadlock-coding-0.0.1.vsix b/plugins/deadlock-coding-0.0.1.vsix
new file mode 100644
index 0000000000000000000000000000000000000000..ac256001c2e3c42bd5f9dd7749375fcb0bbe15ae
Binary files /dev/null and b/plugins/deadlock-coding-0.0.1.vsix differ
diff --git a/plugins/deadlock-extension/deadlock-coding-0.0.1.vsix b/plugins/deadlock-extension/deadlock-coding-0.0.1.vsix
new file mode 100644
index 0000000000000000000000000000000000000000..ac256001c2e3c42bd5f9dd7749375fcb0bbe15ae
Binary files /dev/null and b/plugins/deadlock-extension/deadlock-coding-0.0.1.vsix differ
diff --git a/plugins/deadlock-extension/package-lock.json b/plugins/deadlock-extension/package-lock.json
index 6f5594763143cb0e156080e59294deea259835b5..7acbadb1558a407383dbb527dd5712678a33072b 100644
--- a/plugins/deadlock-extension/package-lock.json
+++ b/plugins/deadlock-extension/package-lock.json
@@ -49,12 +49,38 @@
 			"integrity": "sha512-rr+OQyAjxze7GgWrSaJwydHStIhHq2lvY3BOC2Mj7KnzI7XK0Uw1TOOdI9lDoajEbSWLiYgoo4f1R51erQfhPQ==",
 			"dev": true
 		},
+		"@types/eslint": {
+			"version": "7.2.5",
+			"resolved": "https://registry.npmjs.org/@types/eslint/-/eslint-7.2.5.tgz",
+			"integrity": "sha512-Dc6ar9x16BdaR3NSxSF7T4IjL9gxxViJq8RmFd+2UAyA+K6ck2W+gUwfgpG/y9TPyUuBL35109bbULpEynvltA==",
+			"dev": true,
+			"requires": {
+				"@types/estree": "*",
+				"@types/json-schema": "*"
+			}
+		},
+		"@types/eslint-scope": {
+			"version": "3.7.0",
+			"resolved": "https://registry.npmjs.org/@types/eslint-scope/-/eslint-scope-3.7.0.tgz",
+			"integrity": "sha512-O/ql2+rrCUe2W2rs7wMR+GqPRcgB6UiqN5RhrR5xruFlY7l9YLMn0ZkDzjoHLeiFkR8MCQZVudUuuvQ2BLC9Qw==",
+			"dev": true,
+			"requires": {
+				"@types/eslint": "*",
+				"@types/estree": "*"
+			}
+		},
 		"@types/eslint-visitor-keys": {
 			"version": "1.0.0",
 			"resolved": "https://registry.npmjs.org/@types/eslint-visitor-keys/-/eslint-visitor-keys-1.0.0.tgz",
 			"integrity": "sha512-OCutwjDZ4aFS6PB1UZ988C4YgwlBHJd6wCeQqaLdmadZ/7e+w79+hbMUFC1QXDNCmdyoRfAFdm0RypzwR+Qpag==",
 			"dev": true
 		},
+		"@types/estree": {
+			"version": "0.0.45",
+			"resolved": "https://registry.npmjs.org/@types/estree/-/estree-0.0.45.tgz",
+			"integrity": "sha512-jnqIUKDUqJbDIUxm0Uj7bnlMnRm1T/eZ9N+AVMqhPgzrba2GhGG5o/jCTwmdPK709nEZsGoMzXEDUjcXHa3W0g==",
+			"dev": true
+		},
 		"@types/json-schema": {
 			"version": "7.0.4",
 			"resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.4.tgz",
@@ -164,6 +190,208 @@
 				}
 			}
 		},
+		"@webassemblyjs/ast": {
+			"version": "1.9.0",
+			"resolved": "https://registry.npmjs.org/@webassemblyjs/ast/-/ast-1.9.0.tgz",
+			"integrity": "sha512-C6wW5L+b7ogSDVqymbkkvuW9kruN//YisMED04xzeBBqjHa2FYnmvOlS6Xj68xWQRgWvI9cIglsjFowH/RJyEA==",
+			"dev": true,
+			"requires": {
+				"@webassemblyjs/helper-module-context": "1.9.0",
+				"@webassemblyjs/helper-wasm-bytecode": "1.9.0",
+				"@webassemblyjs/wast-parser": "1.9.0"
+			}
+		},
+		"@webassemblyjs/floating-point-hex-parser": {
+			"version": "1.9.0",
+			"resolved": "https://registry.npmjs.org/@webassemblyjs/floating-point-hex-parser/-/floating-point-hex-parser-1.9.0.tgz",
+			"integrity": "sha512-TG5qcFsS8QB4g4MhrxK5TqfdNe7Ey/7YL/xN+36rRjl/BlGE/NcBvJcqsRgCP6Z92mRE+7N50pRIi8SmKUbcQA==",
+			"dev": true
+		},
+		"@webassemblyjs/helper-api-error": {
+			"version": "1.9.0",
+			"resolved": "https://registry.npmjs.org/@webassemblyjs/helper-api-error/-/helper-api-error-1.9.0.tgz",
+			"integrity": "sha512-NcMLjoFMXpsASZFxJ5h2HZRcEhDkvnNFOAKneP5RbKRzaWJN36NC4jqQHKwStIhGXu5mUWlUUk7ygdtrO8lbmw==",
+			"dev": true
+		},
+		"@webassemblyjs/helper-buffer": {
+			"version": "1.9.0",
+			"resolved": "https://registry.npmjs.org/@webassemblyjs/helper-buffer/-/helper-buffer-1.9.0.tgz",
+			"integrity": "sha512-qZol43oqhq6yBPx7YM3m9Bv7WMV9Eevj6kMi6InKOuZxhw+q9hOkvq5e/PpKSiLfyetpaBnogSbNCfBwyB00CA==",
+			"dev": true
+		},
+		"@webassemblyjs/helper-code-frame": {
+			"version": "1.9.0",
+			"resolved": "https://registry.npmjs.org/@webassemblyjs/helper-code-frame/-/helper-code-frame-1.9.0.tgz",
+			"integrity": "sha512-ERCYdJBkD9Vu4vtjUYe8LZruWuNIToYq/ME22igL+2vj2dQ2OOujIZr3MEFvfEaqKoVqpsFKAGsRdBSBjrIvZA==",
+			"dev": true,
+			"requires": {
+				"@webassemblyjs/wast-printer": "1.9.0"
+			}
+		},
+		"@webassemblyjs/helper-fsm": {
+			"version": "1.9.0",
+			"resolved": "https://registry.npmjs.org/@webassemblyjs/helper-fsm/-/helper-fsm-1.9.0.tgz",
+			"integrity": "sha512-OPRowhGbshCb5PxJ8LocpdX9Kl0uB4XsAjl6jH/dWKlk/mzsANvhwbiULsaiqT5GZGT9qinTICdj6PLuM5gslw==",
+			"dev": true
+		},
+		"@webassemblyjs/helper-module-context": {
+			"version": "1.9.0",
+			"resolved": "https://registry.npmjs.org/@webassemblyjs/helper-module-context/-/helper-module-context-1.9.0.tgz",
+			"integrity": "sha512-MJCW8iGC08tMk2enck1aPW+BE5Cw8/7ph/VGZxwyvGbJwjktKkDK7vy7gAmMDx88D7mhDTCNKAW5tED+gZ0W8g==",
+			"dev": true,
+			"requires": {
+				"@webassemblyjs/ast": "1.9.0"
+			}
+		},
+		"@webassemblyjs/helper-wasm-bytecode": {
+			"version": "1.9.0",
+			"resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-bytecode/-/helper-wasm-bytecode-1.9.0.tgz",
+			"integrity": "sha512-R7FStIzyNcd7xKxCZH5lE0Bqy+hGTwS3LJjuv1ZVxd9O7eHCedSdrId/hMOd20I+v8wDXEn+bjfKDLzTepoaUw==",
+			"dev": true
+		},
+		"@webassemblyjs/helper-wasm-section": {
+			"version": "1.9.0",
+			"resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-section/-/helper-wasm-section-1.9.0.tgz",
+			"integrity": "sha512-XnMB8l3ek4tvrKUUku+IVaXNHz2YsJyOOmz+MMkZvh8h1uSJpSen6vYnw3IoQ7WwEuAhL8Efjms1ZWjqh2agvw==",
+			"dev": true,
+			"requires": {
+				"@webassemblyjs/ast": "1.9.0",
+				"@webassemblyjs/helper-buffer": "1.9.0",
+				"@webassemblyjs/helper-wasm-bytecode": "1.9.0",
+				"@webassemblyjs/wasm-gen": "1.9.0"
+			}
+		},
+		"@webassemblyjs/ieee754": {
+			"version": "1.9.0",
+			"resolved": "https://registry.npmjs.org/@webassemblyjs/ieee754/-/ieee754-1.9.0.tgz",
+			"integrity": "sha512-dcX8JuYU/gvymzIHc9DgxTzUUTLexWwt8uCTWP3otys596io0L5aW02Gb1RjYpx2+0Jus1h4ZFqjla7umFniTg==",
+			"dev": true,
+			"requires": {
+				"@xtuc/ieee754": "^1.2.0"
+			}
+		},
+		"@webassemblyjs/leb128": {
+			"version": "1.9.0",
+			"resolved": "https://registry.npmjs.org/@webassemblyjs/leb128/-/leb128-1.9.0.tgz",
+			"integrity": "sha512-ENVzM5VwV1ojs9jam6vPys97B/S65YQtv/aanqnU7D8aSoHFX8GyhGg0CMfyKNIHBuAVjy3tlzd5QMMINa7wpw==",
+			"dev": true,
+			"requires": {
+				"@xtuc/long": "4.2.2"
+			}
+		},
+		"@webassemblyjs/utf8": {
+			"version": "1.9.0",
+			"resolved": "https://registry.npmjs.org/@webassemblyjs/utf8/-/utf8-1.9.0.tgz",
+			"integrity": "sha512-GZbQlWtopBTP0u7cHrEx+73yZKrQoBMpwkGEIqlacljhXCkVM1kMQge/Mf+csMJAjEdSwhOyLAS0AoR3AG5P8w==",
+			"dev": true
+		},
+		"@webassemblyjs/wasm-edit": {
+			"version": "1.9.0",
+			"resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-edit/-/wasm-edit-1.9.0.tgz",
+			"integrity": "sha512-FgHzBm80uwz5M8WKnMTn6j/sVbqilPdQXTWraSjBwFXSYGirpkSWE2R9Qvz9tNiTKQvoKILpCuTjBKzOIm0nxw==",
+			"dev": true,
+			"requires": {
+				"@webassemblyjs/ast": "1.9.0",
+				"@webassemblyjs/helper-buffer": "1.9.0",
+				"@webassemblyjs/helper-wasm-bytecode": "1.9.0",
+				"@webassemblyjs/helper-wasm-section": "1.9.0",
+				"@webassemblyjs/wasm-gen": "1.9.0",
+				"@webassemblyjs/wasm-opt": "1.9.0",
+				"@webassemblyjs/wasm-parser": "1.9.0",
+				"@webassemblyjs/wast-printer": "1.9.0"
+			}
+		},
+		"@webassemblyjs/wasm-gen": {
+			"version": "1.9.0",
+			"resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-gen/-/wasm-gen-1.9.0.tgz",
+			"integrity": "sha512-cPE3o44YzOOHvlsb4+E9qSqjc9Qf9Na1OO/BHFy4OI91XDE14MjFN4lTMezzaIWdPqHnsTodGGNP+iRSYfGkjA==",
+			"dev": true,
+			"requires": {
+				"@webassemblyjs/ast": "1.9.0",
+				"@webassemblyjs/helper-wasm-bytecode": "1.9.0",
+				"@webassemblyjs/ieee754": "1.9.0",
+				"@webassemblyjs/leb128": "1.9.0",
+				"@webassemblyjs/utf8": "1.9.0"
+			}
+		},
+		"@webassemblyjs/wasm-opt": {
+			"version": "1.9.0",
+			"resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-opt/-/wasm-opt-1.9.0.tgz",
+			"integrity": "sha512-Qkjgm6Anhm+OMbIL0iokO7meajkzQD71ioelnfPEj6r4eOFuqm4YC3VBPqXjFyyNwowzbMD+hizmprP/Fwkl2A==",
+			"dev": true,
+			"requires": {
+				"@webassemblyjs/ast": "1.9.0",
+				"@webassemblyjs/helper-buffer": "1.9.0",
+				"@webassemblyjs/wasm-gen": "1.9.0",
+				"@webassemblyjs/wasm-parser": "1.9.0"
+			}
+		},
+		"@webassemblyjs/wasm-parser": {
+			"version": "1.9.0",
+			"resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-parser/-/wasm-parser-1.9.0.tgz",
+			"integrity": "sha512-9+wkMowR2AmdSWQzsPEjFU7njh8HTO5MqO8vjwEHuM+AMHioNqSBONRdr0NQQ3dVQrzp0s8lTcYqzUdb7YgELA==",
+			"dev": true,
+			"requires": {
+				"@webassemblyjs/ast": "1.9.0",
+				"@webassemblyjs/helper-api-error": "1.9.0",
+				"@webassemblyjs/helper-wasm-bytecode": "1.9.0",
+				"@webassemblyjs/ieee754": "1.9.0",
+				"@webassemblyjs/leb128": "1.9.0",
+				"@webassemblyjs/utf8": "1.9.0"
+			}
+		},
+		"@webassemblyjs/wast-parser": {
+			"version": "1.9.0",
+			"resolved": "https://registry.npmjs.org/@webassemblyjs/wast-parser/-/wast-parser-1.9.0.tgz",
+			"integrity": "sha512-qsqSAP3QQ3LyZjNC/0jBJ/ToSxfYJ8kYyuiGvtn/8MK89VrNEfwj7BPQzJVHi0jGTRK2dGdJ5PRqhtjzoww+bw==",
+			"dev": true,
+			"requires": {
+				"@webassemblyjs/ast": "1.9.0",
+				"@webassemblyjs/floating-point-hex-parser": "1.9.0",
+				"@webassemblyjs/helper-api-error": "1.9.0",
+				"@webassemblyjs/helper-code-frame": "1.9.0",
+				"@webassemblyjs/helper-fsm": "1.9.0",
+				"@xtuc/long": "4.2.2"
+			}
+		},
+		"@webassemblyjs/wast-printer": {
+			"version": "1.9.0",
+			"resolved": "https://registry.npmjs.org/@webassemblyjs/wast-printer/-/wast-printer-1.9.0.tgz",
+			"integrity": "sha512-2J0nE95rHXHyQ24cWjMKJ1tqB/ds8z/cyeOZxJhcb+rW+SQASVjuznUSmdz5GpVJTzU8JkhYut0D3siFDD6wsA==",
+			"dev": true,
+			"requires": {
+				"@webassemblyjs/ast": "1.9.0",
+				"@webassemblyjs/wast-parser": "1.9.0",
+				"@xtuc/long": "4.2.2"
+			}
+		},
+		"@webpack-cli/info": {
+			"version": "1.1.0",
+			"resolved": "https://registry.npmjs.org/@webpack-cli/info/-/info-1.1.0.tgz",
+			"integrity": "sha512-uNWSdaYHc+f3LdIZNwhdhkjjLDDl3jP2+XBqAq9H8DjrJUvlOKdP8TNruy1yEaDfgpAIgbSAN7pye4FEHg9tYQ==",
+			"dev": true,
+			"requires": {
+				"envinfo": "^7.7.3"
+			}
+		},
+		"@webpack-cli/serve": {
+			"version": "1.1.0",
+			"resolved": "https://registry.npmjs.org/@webpack-cli/serve/-/serve-1.1.0.tgz",
+			"integrity": "sha512-7RfnMXCpJ/NThrhq4gYQYILB18xWyoQcBey81oIyVbmgbc6m5ZHHyFK+DyH7pLHJf0p14MxL4mTsoPAgBSTpIg==",
+			"dev": true
+		},
+		"@xtuc/ieee754": {
+			"version": "1.2.0",
+			"resolved": "https://registry.npmjs.org/@xtuc/ieee754/-/ieee754-1.2.0.tgz",
+			"integrity": "sha512-DX8nKgqcGwsc0eJSqYt5lwP4DH5FlHnmuWWBRy7X0NcaGR0ZtuyeESgMwTYVEtxmsNGY+qit4QYT/MIYTOTPeA==",
+			"dev": true
+		},
+		"@xtuc/long": {
+			"version": "4.2.2",
+			"resolved": "https://registry.npmjs.org/@xtuc/long/-/long-4.2.2.tgz",
+			"integrity": "sha512-NuHqBY1PB/D8xU6s/thBgOAiAP7HOYDQ32+BFZILJ8ivkUkAHQnWfn6WhL79Owj1qmUnoN/YPhktdIoucipkAQ==",
+			"dev": true
+		},
 		"acorn": {
 			"version": "7.2.0",
 			"resolved": "https://registry.npmjs.org/acorn/-/acorn-7.2.0.tgz",
@@ -188,6 +416,18 @@
 				"uri-js": "^4.2.2"
 			}
 		},
+		"ajv-keywords": {
+			"version": "3.5.2",
+			"resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz",
+			"integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==",
+			"dev": true
+		},
+		"ansi-colors": {
+			"version": "4.1.1",
+			"resolved": "https://registry.npmjs.org/ansi-colors/-/ansi-colors-4.1.1.tgz",
+			"integrity": "sha512-JoX0apGbHaUJBNl6yF+p6JAFYZ666/hhCGKN5t9QFjbJQKUU/g8MNbFDbvfrgKXvI1QpZplPOnwIo99lX/AAmA==",
+			"dev": true
+		},
 		"ansi-escapes": {
 			"version": "4.3.1",
 			"resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-4.3.1.tgz",
@@ -235,6 +475,12 @@
 				"sprintf-js": "~1.0.2"
 			}
 		},
+		"array-back": {
+			"version": "4.0.1",
+			"resolved": "https://registry.npmjs.org/array-back/-/array-back-4.0.1.tgz",
+			"integrity": "sha512-Z/JnaVEXv+A9xabHzN43FiiiWEE7gPCRXMrVmRm00tWbjZRul1iHm7ECzlyNq1p4a4ATXz+G9FJ3GqGOkOV3fg==",
+			"dev": true
+		},
 		"astral-regex": {
 			"version": "1.0.0",
 			"resolved": "https://registry.npmjs.org/astral-regex/-/astral-regex-1.0.0.tgz",
@@ -267,6 +513,19 @@
 				"concat-map": "0.0.1"
 			}
 		},
+		"browserslist": {
+			"version": "4.14.7",
+			"resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.14.7.tgz",
+			"integrity": "sha512-BSVRLCeG3Xt/j/1cCGj1019Wbty0H+Yvu2AOuZSuoaUWn3RatbL33Cxk+Q4jRMRAbOm0p7SLravLjpnT6s0vzQ==",
+			"dev": true,
+			"requires": {
+				"caniuse-lite": "^1.0.30001157",
+				"colorette": "^1.2.1",
+				"electron-to-chromium": "^1.3.591",
+				"escalade": "^3.1.1",
+				"node-releases": "^1.1.66"
+			}
+		},
 		"buffer-from": {
 			"version": "1.1.1",
 			"resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.1.tgz",
@@ -279,6 +538,12 @@
 			"integrity": "sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==",
 			"dev": true
 		},
+		"caniuse-lite": {
+			"version": "1.0.30001159",
+			"resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001159.tgz",
+			"integrity": "sha512-w9Ph56jOsS8RL20K9cLND3u/+5WASWdhC/PPrf+V3/HsM3uHOavWOR1Xzakbv4Puo/srmPHudkmCRWM7Aq+/UA==",
+			"dev": true
+		},
 		"chalk": {
 			"version": "2.4.2",
 			"resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz",
@@ -296,6 +561,15 @@
 			"integrity": "sha512-mT8iDcrh03qDGRRmoA2hmBJnxpllMR+0/0qlzjqZES6NdiWDcZkCNAk4rPFZ9Q85r27unkiNNg8ZOiwZXBHwcA==",
 			"dev": true
 		},
+		"chrome-trace-event": {
+			"version": "1.0.2",
+			"resolved": "https://registry.npmjs.org/chrome-trace-event/-/chrome-trace-event-1.0.2.tgz",
+			"integrity": "sha512-9e/zx1jw7B4CO+c/RXoCsfg/x1AfUBioy4owYH0bJprEYAx5hRFLRhWBqHAG57D0ZM4H7vxbP7bPe0VwhQRYDQ==",
+			"dev": true,
+			"requires": {
+				"tslib": "^1.9.0"
+			}
+		},
 		"cli-cursor": {
 			"version": "3.1.0",
 			"resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-3.1.0.tgz",
@@ -326,6 +600,30 @@
 			"integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=",
 			"dev": true
 		},
+		"colorette": {
+			"version": "1.2.1",
+			"resolved": "https://registry.npmjs.org/colorette/-/colorette-1.2.1.tgz",
+			"integrity": "sha512-puCDz0CzydiSYOrnXpz/PKd69zRrribezjtE9yd4zvytoRc8+RY/KJPvtPFKZS3E3wP6neGyMe0vOTlHO5L3Pw==",
+			"dev": true
+		},
+		"command-line-usage": {
+			"version": "6.1.1",
+			"resolved": "https://registry.npmjs.org/command-line-usage/-/command-line-usage-6.1.1.tgz",
+			"integrity": "sha512-F59pEuAR9o1SF/bD0dQBDluhpT4jJQNWUHEuVBqpDmCUo6gPjCi+m9fCWnWZVR/oG6cMTUms4h+3NPl74wGXvA==",
+			"dev": true,
+			"requires": {
+				"array-back": "^4.0.1",
+				"chalk": "^2.4.2",
+				"table-layout": "^1.0.1",
+				"typical": "^5.2.0"
+			}
+		},
+		"commander": {
+			"version": "2.20.3",
+			"resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz",
+			"integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==",
+			"dev": true
+		},
 		"concat-map": {
 			"version": "0.0.1",
 			"resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz",
@@ -356,6 +654,12 @@
 				"ms": "^2.1.1"
 			}
 		},
+		"deep-extend": {
+			"version": "0.6.0",
+			"resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz",
+			"integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==",
+			"dev": true
+		},
 		"deep-is": {
 			"version": "0.1.3",
 			"resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.3.tgz",
@@ -377,12 +681,58 @@
 				"esutils": "^2.0.2"
 			}
 		},
+		"electron-to-chromium": {
+			"version": "1.3.601",
+			"resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.601.tgz",
+			"integrity": "sha512-ctRyXD9y0mZu8pgeNwBUhLP3Guyr5YuqkfLKYmpTwYx7o9JtCEJme9JVX4xBXPr5ZNvr/iBXUvHLFEVJQThATg==",
+			"dev": true
+		},
 		"emoji-regex": {
 			"version": "8.0.0",
 			"resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz",
 			"integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==",
 			"dev": true
 		},
+		"end-of-stream": {
+			"version": "1.4.4",
+			"resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz",
+			"integrity": "sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==",
+			"dev": true,
+			"requires": {
+				"once": "^1.4.0"
+			}
+		},
+		"enhanced-resolve": {
+			"version": "5.3.1",
+			"resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.3.1.tgz",
+			"integrity": "sha512-G1XD3MRGrGfNcf6Hg0LVZG7GIKcYkbfHa5QMxt1HDUTdYoXH0JR1xXyg+MaKLF73E9A27uWNVxvFivNRYeUB6w==",
+			"dev": true,
+			"requires": {
+				"graceful-fs": "^4.2.4",
+				"tapable": "^2.0.0"
+			}
+		},
+		"enquirer": {
+			"version": "2.3.6",
+			"resolved": "https://registry.npmjs.org/enquirer/-/enquirer-2.3.6.tgz",
+			"integrity": "sha512-yjNnPr315/FjS4zIsUxYguYUPP2e1NK4d7E7ZOLiyYCcbFBiTMyID+2wvm2w6+pZ/odMA7cRkjhsPbltwBOrLg==",
+			"dev": true,
+			"requires": {
+				"ansi-colors": "^4.1.1"
+			}
+		},
+		"envinfo": {
+			"version": "7.7.3",
+			"resolved": "https://registry.npmjs.org/envinfo/-/envinfo-7.7.3.tgz",
+			"integrity": "sha512-46+j5QxbPWza0PB1i15nZx0xQ4I/EfQxg9J8Had3b408SV63nEtor2e+oiY63amTo9KTuh2a3XLObNwduxYwwA==",
+			"dev": true
+		},
+		"escalade": {
+			"version": "3.1.1",
+			"resolved": "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz",
+			"integrity": "sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==",
+			"dev": true
+		},
 		"escape-string-regexp": {
 			"version": "1.0.5",
 			"resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz",
@@ -571,6 +921,29 @@
 			"integrity": "sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==",
 			"dev": true
 		},
+		"events": {
+			"version": "3.2.0",
+			"resolved": "https://registry.npmjs.org/events/-/events-3.2.0.tgz",
+			"integrity": "sha512-/46HWwbfCX2xTawVfkKLGxMifJYQBWMwY1mjywRtb4c9x8l5NP3KoJtnIOiL1hfdRkIuYhETxQlo62IF8tcnlg==",
+			"dev": true
+		},
+		"execa": {
+			"version": "4.1.0",
+			"resolved": "https://registry.npmjs.org/execa/-/execa-4.1.0.tgz",
+			"integrity": "sha512-j5W0//W7f8UxAn8hXVnwG8tLwdiUy4FJLcSupCg6maBYZDpyBvTApK7KyuI4bKj8KOh1r2YH+6ucuYtJv1bTZA==",
+			"dev": true,
+			"requires": {
+				"cross-spawn": "^7.0.0",
+				"get-stream": "^5.0.0",
+				"human-signals": "^1.1.1",
+				"is-stream": "^2.0.0",
+				"merge-stream": "^2.0.0",
+				"npm-run-path": "^4.0.0",
+				"onetime": "^5.1.0",
+				"signal-exit": "^3.0.2",
+				"strip-final-newline": "^2.0.0"
+			}
+		},
 		"external-editor": {
 			"version": "3.1.0",
 			"resolved": "https://registry.npmjs.org/external-editor/-/external-editor-3.1.0.tgz",
@@ -618,6 +991,16 @@
 				"flat-cache": "^2.0.1"
 			}
 		},
+		"find-up": {
+			"version": "4.1.0",
+			"resolved": "https://registry.npmjs.org/find-up/-/find-up-4.1.0.tgz",
+			"integrity": "sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==",
+			"dev": true,
+			"requires": {
+				"locate-path": "^5.0.0",
+				"path-exists": "^4.0.0"
+			}
+		},
 		"flat-cache": {
 			"version": "2.0.1",
 			"resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-2.0.1.tgz",
@@ -641,12 +1024,27 @@
 			"integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=",
 			"dev": true
 		},
+		"function-bind": {
+			"version": "1.1.1",
+			"resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz",
+			"integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==",
+			"dev": true
+		},
 		"functional-red-black-tree": {
 			"version": "1.0.1",
 			"resolved": "https://registry.npmjs.org/functional-red-black-tree/-/functional-red-black-tree-1.0.1.tgz",
 			"integrity": "sha1-GwqzvVU7Kg1jmdKcDj6gslIHgyc=",
 			"dev": true
 		},
+		"get-stream": {
+			"version": "5.2.0",
+			"resolved": "https://registry.npmjs.org/get-stream/-/get-stream-5.2.0.tgz",
+			"integrity": "sha512-nBF+F1rAZVCu/p7rjzgA+Yb4lfYXrpl7a6VmJrU8wF9I1CKvP/QwPNZHnOlwbTkY6dvtFIzFMSyQXbLoTQPRpA==",
+			"dev": true,
+			"requires": {
+				"pump": "^3.0.0"
+			}
+		},
 		"glob": {
 			"version": "7.1.6",
 			"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.6.tgz",
@@ -670,6 +1068,12 @@
 				"is-glob": "^4.0.1"
 			}
 		},
+		"glob-to-regexp": {
+			"version": "0.4.1",
+			"resolved": "https://registry.npmjs.org/glob-to-regexp/-/glob-to-regexp-0.4.1.tgz",
+			"integrity": "sha512-lkX1HJXwyMcprw/5YUZc2s7DrpAiHB21/V+E1rHUrVNokkvB6bqMzT0VfV6/86ZNabt1k14YOIaT7nDvOX3Iiw==",
+			"dev": true
+		},
 		"globals": {
 			"version": "12.4.0",
 			"resolved": "https://registry.npmjs.org/globals/-/globals-12.4.0.tgz",
@@ -679,12 +1083,33 @@
 				"type-fest": "^0.8.1"
 			}
 		},
+		"graceful-fs": {
+			"version": "4.2.4",
+			"resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.4.tgz",
+			"integrity": "sha512-WjKPNJF79dtJAVniUlGGWHYGz2jWxT6VhN/4m1NdkbZ2nOsEF+cI1Edgql5zCRhs/VsQYRvrXctxktVXZUkixw==",
+			"dev": true
+		},
+		"has": {
+			"version": "1.0.3",
+			"resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz",
+			"integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==",
+			"dev": true,
+			"requires": {
+				"function-bind": "^1.1.1"
+			}
+		},
 		"has-flag": {
 			"version": "3.0.0",
 			"resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz",
 			"integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=",
 			"dev": true
 		},
+		"human-signals": {
+			"version": "1.1.1",
+			"resolved": "https://registry.npmjs.org/human-signals/-/human-signals-1.1.1.tgz",
+			"integrity": "sha512-SEQu7vl8KjNL2eoGBLF3+wAjpsNfA9XMlXAYj/3EdaNfAlxKthD1xjEQfGOUhllCGGJVNY34bRr6lPINhNjyZw==",
+			"dev": true
+		},
 		"iconv-lite": {
 			"version": "0.4.24",
 			"resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz",
@@ -710,6 +1135,16 @@
 				"resolve-from": "^4.0.0"
 			}
 		},
+		"import-local": {
+			"version": "3.0.2",
+			"resolved": "https://registry.npmjs.org/import-local/-/import-local-3.0.2.tgz",
+			"integrity": "sha512-vjL3+w0oulAVZ0hBHnxa/Nm5TAurf9YLQJDhqRZyqb+VKGOB6LU8t9H1Nr5CIo16vh9XfJTOoHwU0B71S557gA==",
+			"dev": true,
+			"requires": {
+				"pkg-dir": "^4.2.0",
+				"resolve-cwd": "^3.0.0"
+			}
+		},
 		"imurmurhash": {
 			"version": "0.1.4",
 			"resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz",
@@ -805,6 +1240,21 @@
 				}
 			}
 		},
+		"interpret": {
+			"version": "2.2.0",
+			"resolved": "https://registry.npmjs.org/interpret/-/interpret-2.2.0.tgz",
+			"integrity": "sha512-Ju0Bz/cEia55xDwUWEa8+olFpCiQoypjnQySseKtmjNrnps3P+xfpUmGr90T7yjlVJmOtybRvPXhKMbHr+fWnw==",
+			"dev": true
+		},
+		"is-core-module": {
+			"version": "2.1.0",
+			"resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.1.0.tgz",
+			"integrity": "sha512-YcV7BgVMRFRua2FqQzKtTDMz8iCuLEyGKjr70q8Zm1yy2qKcurbFEd79PAdHV77oL3NrAaOVQIbMmiHQCHB7ZA==",
+			"dev": true,
+			"requires": {
+				"has": "^1.0.3"
+			}
+		},
 		"is-extglob": {
 			"version": "2.1.1",
 			"resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz",
@@ -826,12 +1276,46 @@
 				"is-extglob": "^2.1.1"
 			}
 		},
+		"is-stream": {
+			"version": "2.0.0",
+			"resolved": "https://registry.npmjs.org/is-stream/-/is-stream-2.0.0.tgz",
+			"integrity": "sha512-XCoy+WlUr7d1+Z8GgSuXmpuUFC9fOhRXglJMx+dwLKTkL44Cjd4W1Z5P+BQZpr+cR93aGP4S/s7Ftw6Nd/kiEw==",
+			"dev": true
+		},
 		"isexe": {
 			"version": "2.0.0",
 			"resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz",
 			"integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=",
 			"dev": true
 		},
+		"jest-worker": {
+			"version": "26.6.2",
+			"resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-26.6.2.tgz",
+			"integrity": "sha512-KWYVV1c4i+jbMpaBC+U++4Va0cp8OisU185o73T1vo99hqi7w8tSJfUXYswwqqrjzwxa6KpRK54WhPvwf5w6PQ==",
+			"dev": true,
+			"requires": {
+				"@types/node": "*",
+				"merge-stream": "^2.0.0",
+				"supports-color": "^7.0.0"
+			},
+			"dependencies": {
+				"has-flag": {
+					"version": "4.0.0",
+					"resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz",
+					"integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==",
+					"dev": true
+				},
+				"supports-color": {
+					"version": "7.2.0",
+					"resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz",
+					"integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==",
+					"dev": true,
+					"requires": {
+						"has-flag": "^4.0.0"
+					}
+				}
+			}
+		},
 		"js-sha256": {
 			"version": "0.9.0",
 			"resolved": "https://registry.npmjs.org/js-sha256/-/js-sha256-0.9.0.tgz",
@@ -853,6 +1337,12 @@
 				"esprima": "^4.0.0"
 			}
 		},
+		"json-parse-better-errors": {
+			"version": "1.0.2",
+			"resolved": "https://registry.npmjs.org/json-parse-better-errors/-/json-parse-better-errors-1.0.2.tgz",
+			"integrity": "sha512-mrqyZKfX5EhL7hvqcV6WG1yYjnjeuYDzDhhcAAUrq8Po85NBQBJP+ZDUT75qZQ98IkUoBqdkExkukOU7Ts2wrw==",
+			"dev": true
+		},
 		"json-schema-traverse": {
 			"version": "0.4.1",
 			"resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz",
@@ -874,6 +1364,12 @@
 				"js-sha256": "0.9.0"
 			}
 		},
+		"leven": {
+			"version": "3.1.0",
+			"resolved": "https://registry.npmjs.org/leven/-/leven-3.1.0.tgz",
+			"integrity": "sha512-qsda+H8jTaUaN/x5vzW2rzc+8Rw4TAQ/4KjB46IwK5VH+IlVeeeje/EoZRpiXvIqjFgK84QffqPztGI3VBLG1A==",
+			"dev": true
+		},
 		"levn": {
 			"version": "0.4.1",
 			"resolved": "https://registry.npmjs.org/levn/-/levn-0.4.1.tgz",
@@ -884,6 +1380,21 @@
 				"type-check": "~0.4.0"
 			}
 		},
+		"loader-runner": {
+			"version": "4.1.0",
+			"resolved": "https://registry.npmjs.org/loader-runner/-/loader-runner-4.1.0.tgz",
+			"integrity": "sha512-oR4lB4WvwFoC70ocraKhn5nkKSs23t57h9udUgw8o0iH8hMXeEoRuUgfcvgUwAJ1ZpRqBvcou4N2SMvM1DwMrA==",
+			"dev": true
+		},
+		"locate-path": {
+			"version": "5.0.0",
+			"resolved": "https://registry.npmjs.org/locate-path/-/locate-path-5.0.0.tgz",
+			"integrity": "sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==",
+			"dev": true,
+			"requires": {
+				"p-locate": "^4.1.0"
+			}
+		},
 		"lodash": {
 			"version": "4.17.15",
 			"resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.15.tgz",
@@ -901,6 +1412,27 @@
 			"resolved": "https://registry.npmjs.org/marked/-/marked-1.1.1.tgz",
 			"integrity": "sha512-mJzT8D2yPxoPh7h0UXkB+dBj4FykPJ2OIfxAWeIHrvoHDkFxukV/29QxoFQoPM6RLEwhIFdJpmKBlqVM3s2ZIw=="
 		},
+		"merge-stream": {
+			"version": "2.0.0",
+			"resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-2.0.0.tgz",
+			"integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==",
+			"dev": true
+		},
+		"mime-db": {
+			"version": "1.44.0",
+			"resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.44.0.tgz",
+			"integrity": "sha512-/NOTfLrsPBVeH7YtFPgsVWveuL+4SjjYxaQ1xtM1KMFj7HdxlBlxeyNLzhyJVx7r4rZGJAZ/6lkKCitSc/Nmpg==",
+			"dev": true
+		},
+		"mime-types": {
+			"version": "2.1.27",
+			"resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.27.tgz",
+			"integrity": "sha512-JIhqnCasI9yD+SsmkquHBxTSEuZdQX5BuQnS2Vc7puQQQ+8yiP5AY5uWhpdv4YL4VM5c6iliiYWPgJ/nJQLp7w==",
+			"dev": true,
+			"requires": {
+				"mime-db": "1.44.0"
+			}
+		},
 		"mimic-fn": {
 			"version": "2.1.0",
 			"resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-2.1.0.tgz",
@@ -948,6 +1480,27 @@
 			"integrity": "sha1-Sr6/7tdUHywnrPspvbvRXI1bpPc=",
 			"dev": true
 		},
+		"neo-async": {
+			"version": "2.6.2",
+			"resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.6.2.tgz",
+			"integrity": "sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==",
+			"dev": true
+		},
+		"node-releases": {
+			"version": "1.1.67",
+			"resolved": "https://registry.npmjs.org/node-releases/-/node-releases-1.1.67.tgz",
+			"integrity": "sha512-V5QF9noGFl3EymEwUYzO+3NTDpGfQB4ve6Qfnzf3UNydMhjQRVPR1DZTuvWiLzaFJYw2fmDwAfnRNEVb64hSIg==",
+			"dev": true
+		},
+		"npm-run-path": {
+			"version": "4.0.1",
+			"resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-4.0.1.tgz",
+			"integrity": "sha512-S48WzZW777zhNIrn7gxOlISNAqi9ZC/uQFnRdbeIHhZhCA6UqpkOT8T1G7BvfdgP4Er8gF4sUbaS0i7QvIfCWw==",
+			"dev": true,
+			"requires": {
+				"path-key": "^3.0.0"
+			}
+		},
 		"once": {
 			"version": "1.4.0",
 			"resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz",
@@ -986,6 +1539,41 @@
 			"integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=",
 			"dev": true
 		},
+		"p-limit": {
+			"version": "3.0.2",
+			"resolved": "https://registry.npmjs.org/p-limit/-/p-limit-3.0.2.tgz",
+			"integrity": "sha512-iwqZSOoWIW+Ew4kAGUlN16J4M7OB3ysMLSZtnhmqx7njIHFPlxWBX8xo3lVTyFVq6mI/lL9qt2IsN1sHwaxJkg==",
+			"dev": true,
+			"requires": {
+				"p-try": "^2.0.0"
+			}
+		},
+		"p-locate": {
+			"version": "4.1.0",
+			"resolved": "https://registry.npmjs.org/p-locate/-/p-locate-4.1.0.tgz",
+			"integrity": "sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A==",
+			"dev": true,
+			"requires": {
+				"p-limit": "^2.2.0"
+			},
+			"dependencies": {
+				"p-limit": {
+					"version": "2.3.0",
+					"resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.3.0.tgz",
+					"integrity": "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==",
+					"dev": true,
+					"requires": {
+						"p-try": "^2.0.0"
+					}
+				}
+			}
+		},
+		"p-try": {
+			"version": "2.2.0",
+			"resolved": "https://registry.npmjs.org/p-try/-/p-try-2.2.0.tgz",
+			"integrity": "sha512-R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ==",
+			"dev": true
+		},
 		"parent-module": {
 			"version": "1.0.1",
 			"resolved": "https://registry.npmjs.org/parent-module/-/parent-module-1.0.1.tgz",
@@ -995,6 +1583,12 @@
 				"callsites": "^3.0.0"
 			}
 		},
+		"path-exists": {
+			"version": "4.0.0",
+			"resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz",
+			"integrity": "sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==",
+			"dev": true
+		},
 		"path-is-absolute": {
 			"version": "1.0.1",
 			"resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz",
@@ -1007,6 +1601,21 @@
 			"integrity": "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==",
 			"dev": true
 		},
+		"path-parse": {
+			"version": "1.0.6",
+			"resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.6.tgz",
+			"integrity": "sha512-GSmOT2EbHrINBf9SR7CDELwlJ8AENk3Qn7OikK4nFYAu3Ote2+JYNVvkpAEQm3/TLNEJFD/xZJjzyxg3KBWOzw==",
+			"dev": true
+		},
+		"pkg-dir": {
+			"version": "4.2.0",
+			"resolved": "https://registry.npmjs.org/pkg-dir/-/pkg-dir-4.2.0.tgz",
+			"integrity": "sha512-HRDzbaKjC+AOWVXxAU/x54COGeIv9eb+6CkDSQoNTt4XyWoIJvuPsXizxu/Fr23EiekbtZwmh1IcIG/l/a10GQ==",
+			"dev": true,
+			"requires": {
+				"find-up": "^4.0.0"
+			}
+		},
 		"prelude-ls": {
 			"version": "1.2.1",
 			"resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.2.1.tgz",
@@ -1019,18 +1628,79 @@
 			"integrity": "sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA==",
 			"dev": true
 		},
+		"pump": {
+			"version": "3.0.0",
+			"resolved": "https://registry.npmjs.org/pump/-/pump-3.0.0.tgz",
+			"integrity": "sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww==",
+			"dev": true,
+			"requires": {
+				"end-of-stream": "^1.1.0",
+				"once": "^1.3.1"
+			}
+		},
 		"punycode": {
 			"version": "2.1.1",
 			"resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz",
 			"integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==",
 			"dev": true
 		},
+		"randombytes": {
+			"version": "2.1.0",
+			"resolved": "https://registry.npmjs.org/randombytes/-/randombytes-2.1.0.tgz",
+			"integrity": "sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ==",
+			"dev": true,
+			"requires": {
+				"safe-buffer": "^5.1.0"
+			}
+		},
+		"rechoir": {
+			"version": "0.7.0",
+			"resolved": "https://registry.npmjs.org/rechoir/-/rechoir-0.7.0.tgz",
+			"integrity": "sha512-ADsDEH2bvbjltXEP+hTIAmeFekTFK0V2BTxMkok6qILyAJEXV0AFfoWcAq4yfll5VdIMd/RVXq0lR+wQi5ZU3Q==",
+			"dev": true,
+			"requires": {
+				"resolve": "^1.9.0"
+			}
+		},
+		"reduce-flatten": {
+			"version": "2.0.0",
+			"resolved": "https://registry.npmjs.org/reduce-flatten/-/reduce-flatten-2.0.0.tgz",
+			"integrity": "sha512-EJ4UNY/U1t2P/2k6oqotuX2Cc3T6nxJwsM0N0asT7dhrtH1ltUxDn4NalSYmPE2rCkVpcf/X6R0wDwcFpzhd4w==",
+			"dev": true
+		},
 		"regexpp": {
 			"version": "3.1.0",
 			"resolved": "https://registry.npmjs.org/regexpp/-/regexpp-3.1.0.tgz",
 			"integrity": "sha512-ZOIzd8yVsQQA7j8GCSlPGXwg5PfmA1mrq0JP4nGhh54LaKN3xdai/vHUDu74pKwV8OxseMS65u2NImosQcSD0Q==",
 			"dev": true
 		},
+		"resolve": {
+			"version": "1.19.0",
+			"resolved": "https://registry.npmjs.org/resolve/-/resolve-1.19.0.tgz",
+			"integrity": "sha512-rArEXAgsBG4UgRGcynxWIWKFvh/XZCcS8UJdHhwy91zwAvCZIbcs+vAbflgBnNjYMs/i/i+/Ux6IZhML1yPvxg==",
+			"dev": true,
+			"requires": {
+				"is-core-module": "^2.1.0",
+				"path-parse": "^1.0.6"
+			}
+		},
+		"resolve-cwd": {
+			"version": "3.0.0",
+			"resolved": "https://registry.npmjs.org/resolve-cwd/-/resolve-cwd-3.0.0.tgz",
+			"integrity": "sha512-OrZaX2Mb+rJCpH/6CpSqt9xFVpN++x01XnN2ie9g6P5/3xelLAkXWVADpdz1IHD/KFfEXyE6V0U01OQ3UO2rEg==",
+			"dev": true,
+			"requires": {
+				"resolve-from": "^5.0.0"
+			},
+			"dependencies": {
+				"resolve-from": {
+					"version": "5.0.0",
+					"resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-5.0.0.tgz",
+					"integrity": "sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw==",
+					"dev": true
+				}
+			}
+		},
 		"resolve-from": {
 			"version": "4.0.0",
 			"resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-4.0.0.tgz",
@@ -1071,12 +1741,58 @@
 				"tslib": "^1.9.0"
 			}
 		},
+		"safe-buffer": {
+			"version": "5.2.1",
+			"resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz",
+			"integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==",
+			"dev": true
+		},
 		"safer-buffer": {
 			"version": "2.1.2",
 			"resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz",
 			"integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==",
 			"dev": true
 		},
+		"schema-utils": {
+			"version": "3.0.0",
+			"resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.0.0.tgz",
+			"integrity": "sha512-6D82/xSzO094ajanoOSbe4YvXWMfn2A//8Y1+MUqFAJul5Bs+yn36xbK9OtNDcRVSBJ9jjeoXftM6CfztsjOAA==",
+			"dev": true,
+			"requires": {
+				"@types/json-schema": "^7.0.6",
+				"ajv": "^6.12.5",
+				"ajv-keywords": "^3.5.2"
+			},
+			"dependencies": {
+				"@types/json-schema": {
+					"version": "7.0.6",
+					"resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.6.tgz",
+					"integrity": "sha512-3c+yGKvVP5Y9TYBEibGNR+kLtijnj7mYrXRg+WpFb2X9xm04g/DXYkfg4hmzJQosc9snFNUPkbYIhu+KAm6jJw==",
+					"dev": true
+				},
+				"ajv": {
+					"version": "6.12.6",
+					"resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz",
+					"integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==",
+					"dev": true,
+					"requires": {
+						"fast-deep-equal": "^3.1.1",
+						"fast-json-stable-stringify": "^2.0.0",
+						"json-schema-traverse": "^0.4.1",
+						"uri-js": "^4.2.2"
+					}
+				}
+			}
+		},
+		"serialize-javascript": {
+			"version": "5.0.1",
+			"resolved": "https://registry.npmjs.org/serialize-javascript/-/serialize-javascript-5.0.1.tgz",
+			"integrity": "sha512-SaaNal9imEO737H2c05Og0/8LUXG7EnsZyMa8MzkmuHoELfT6txuj0cMqRj6zfPKnmQ1yasR4PCJc8x+M4JSPA==",
+			"dev": true,
+			"requires": {
+				"randombytes": "^2.1.0"
+			}
+		},
 		"shebang-command": {
 			"version": "2.0.0",
 			"resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz",
@@ -1127,6 +1843,12 @@
 				}
 			}
 		},
+		"source-list-map": {
+			"version": "2.0.1",
+			"resolved": "https://registry.npmjs.org/source-list-map/-/source-list-map-2.0.1.tgz",
+			"integrity": "sha512-qnQ7gVMxGNxsiL4lEuJwe/To8UnK7fAnmbGEEH8RpLouuKbeEm0lhbQVFIrNSuB+G7tVrAlVsZgETT5nljf+Iw==",
+			"dev": true
+		},
 		"source-map": {
 			"version": "0.6.1",
 			"resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz",
@@ -1169,6 +1891,12 @@
 				"ansi-regex": "^5.0.0"
 			}
 		},
+		"strip-final-newline": {
+			"version": "2.0.0",
+			"resolved": "https://registry.npmjs.org/strip-final-newline/-/strip-final-newline-2.0.0.tgz",
+			"integrity": "sha512-BrpvfNAE3dcvq7ll3xVumzjKjZQ5tI1sEUIKr3Uoks0XUl45St3FlatVqef9prk4jRDzhW6WZg+3bk93y6pLjA==",
+			"dev": true
+		},
 		"strip-json-comments": {
 			"version": "3.1.0",
 			"resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-3.1.0.tgz",
@@ -1236,6 +1964,57 @@
 				}
 			}
 		},
+		"table-layout": {
+			"version": "1.0.1",
+			"resolved": "https://registry.npmjs.org/table-layout/-/table-layout-1.0.1.tgz",
+			"integrity": "sha512-dEquqYNJiGwY7iPfZ3wbXDI944iqanTSchrACLL2nOB+1r+h1Nzu2eH+DuPPvWvm5Ry7iAPeFlgEtP5bIp5U7Q==",
+			"dev": true,
+			"requires": {
+				"array-back": "^4.0.1",
+				"deep-extend": "~0.6.0",
+				"typical": "^5.2.0",
+				"wordwrapjs": "^4.0.0"
+			}
+		},
+		"tapable": {
+			"version": "2.1.1",
+			"resolved": "https://registry.npmjs.org/tapable/-/tapable-2.1.1.tgz",
+			"integrity": "sha512-Wib1S8m2wdpLbmQz0RBEVosIyvb/ykfKXf3ZIDqvWoMg/zTNm6G/tDSuUM61J1kNCDXWJrLHGSFeMhAG+gAGpQ==",
+			"dev": true
+		},
+		"terser": {
+			"version": "5.5.0",
+			"resolved": "https://registry.npmjs.org/terser/-/terser-5.5.0.tgz",
+			"integrity": "sha512-eopt1Gf7/AQyPhpygdKePTzaet31TvQxXvrf7xYUvD/d8qkCJm4SKPDzu+GHK5ZaYTn8rvttfqaZc3swK21e5g==",
+			"dev": true,
+			"requires": {
+				"commander": "^2.20.0",
+				"source-map": "~0.7.2",
+				"source-map-support": "~0.5.19"
+			},
+			"dependencies": {
+				"source-map": {
+					"version": "0.7.3",
+					"resolved": "https://registry.npmjs.org/source-map/-/source-map-0.7.3.tgz",
+					"integrity": "sha512-CkCj6giN3S+n9qrYiBTX5gystlENnRW5jZeNLHpe6aue+SrHcG5VYwujhW9s4dY31mEGsxBDrHR6oI69fTXsaQ==",
+					"dev": true
+				}
+			}
+		},
+		"terser-webpack-plugin": {
+			"version": "5.0.3",
+			"resolved": "https://registry.npmjs.org/terser-webpack-plugin/-/terser-webpack-plugin-5.0.3.tgz",
+			"integrity": "sha512-zFdGk8Lh9ZJGPxxPE6jwysOlATWB8GMW8HcfGULWA/nPal+3VdATflQvSBSLQJRCmYZnfFJl6vkRTiwJGNgPiQ==",
+			"dev": true,
+			"requires": {
+				"jest-worker": "^26.6.1",
+				"p-limit": "^3.0.2",
+				"schema-utils": "^3.0.0",
+				"serialize-javascript": "^5.0.1",
+				"source-map": "^0.6.1",
+				"terser": "^5.3.8"
+			}
+		},
 		"text-table": {
 			"version": "0.2.0",
 			"resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz",
@@ -1297,6 +2076,12 @@
 			"integrity": "sha512-9OL+r0KVHqsYVH7K18IBR9hhC82YwLNlpSZfQDupGcfg8goB9p/s/9Okcy+ztnTeHR2U68xq21/igW9xpoGTgA==",
 			"dev": true
 		},
+		"typical": {
+			"version": "5.2.0",
+			"resolved": "https://registry.npmjs.org/typical/-/typical-5.2.0.tgz",
+			"integrity": "sha512-dvdQgNDNJo+8B2uBQoqdb11eUCE1JQXhvjC/CZtgvZseVd5TYMXnq0+vuUemXbd/Se29cTaUuPX3YIc2xgbvIg==",
+			"dev": true
+		},
 		"uri-js": {
 			"version": "4.2.2",
 			"resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.2.2.tgz",
@@ -1312,6 +2097,137 @@
 			"integrity": "sha512-usZBT3PW+LOjM25wbqIlZwPeJV+3OSz3M1k1Ws8snlW39dZyYL9lOGC5FgPVHfk0jKmjiDV8Z0mIbVQPiwFs7g==",
 			"dev": true
 		},
+		"watchpack": {
+			"version": "2.0.1",
+			"resolved": "https://registry.npmjs.org/watchpack/-/watchpack-2.0.1.tgz",
+			"integrity": "sha512-vO8AKGX22ZRo6PiOFM9dC0re8IcKh8Kd/aH2zeqUc6w4/jBGlTy2P7fTC6ekT0NjVeGjgU2dGC5rNstKkeLEQg==",
+			"dev": true,
+			"requires": {
+				"glob-to-regexp": "^0.4.1",
+				"graceful-fs": "^4.1.2"
+			}
+		},
+		"webpack": {
+			"version": "5.6.0",
+			"resolved": "https://registry.npmjs.org/webpack/-/webpack-5.6.0.tgz",
+			"integrity": "sha512-SIeFuBhuheKElRbd84O35UhKc0nxlgSwtzm2ksZ0BVhRJqxVJxEguT/pYhfiR0le/pxTa1VsCp7EOYyTsa6XOA==",
+			"dev": true,
+			"requires": {
+				"@types/eslint-scope": "^3.7.0",
+				"@types/estree": "^0.0.45",
+				"@webassemblyjs/ast": "1.9.0",
+				"@webassemblyjs/helper-module-context": "1.9.0",
+				"@webassemblyjs/wasm-edit": "1.9.0",
+				"@webassemblyjs/wasm-parser": "1.9.0",
+				"acorn": "^8.0.4",
+				"browserslist": "^4.14.5",
+				"chrome-trace-event": "^1.0.2",
+				"enhanced-resolve": "^5.3.1",
+				"eslint-scope": "^5.1.1",
+				"events": "^3.2.0",
+				"glob-to-regexp": "^0.4.1",
+				"graceful-fs": "^4.2.4",
+				"json-parse-better-errors": "^1.0.2",
+				"loader-runner": "^4.1.0",
+				"mime-types": "^2.1.27",
+				"neo-async": "^2.6.2",
+				"pkg-dir": "^4.2.0",
+				"schema-utils": "^3.0.0",
+				"tapable": "^2.0.0",
+				"terser-webpack-plugin": "^5.0.3",
+				"watchpack": "^2.0.0",
+				"webpack-sources": "^2.1.1"
+			},
+			"dependencies": {
+				"acorn": {
+					"version": "8.0.4",
+					"resolved": "https://registry.npmjs.org/acorn/-/acorn-8.0.4.tgz",
+					"integrity": "sha512-XNP0PqF1XD19ZlLKvB7cMmnZswW4C/03pRHgirB30uSJTaS3A3V1/P4sS3HPvFmjoriPCJQs+JDSbm4bL1TxGQ==",
+					"dev": true
+				},
+				"eslint-scope": {
+					"version": "5.1.1",
+					"resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-5.1.1.tgz",
+					"integrity": "sha512-2NxwbF/hZ0KpepYN0cNbo+FN6XoK7GaHlQhgx/hIZl6Va0bF45RQOOwhLIy8lQDbuCiadSLCBnH2CFYquit5bw==",
+					"dev": true,
+					"requires": {
+						"esrecurse": "^4.3.0",
+						"estraverse": "^4.1.1"
+					}
+				},
+				"esrecurse": {
+					"version": "4.3.0",
+					"resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.3.0.tgz",
+					"integrity": "sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==",
+					"dev": true,
+					"requires": {
+						"estraverse": "^5.2.0"
+					},
+					"dependencies": {
+						"estraverse": {
+							"version": "5.2.0",
+							"resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.2.0.tgz",
+							"integrity": "sha512-BxbNGGNm0RyRYvUdHpIwv9IWzeM9XClbOxwoATuFdOE7ZE6wHL+HQ5T8hoPM+zHvmKzzsEqhgy0GrQ5X13afiQ==",
+							"dev": true
+						}
+					}
+				}
+			}
+		},
+		"webpack-cli": {
+			"version": "4.2.0",
+			"resolved": "https://registry.npmjs.org/webpack-cli/-/webpack-cli-4.2.0.tgz",
+			"integrity": "sha512-EIl3k88vaF4fSxWSgtAQR+VwicfLMTZ9amQtqS4o+TDPW9HGaEpbFBbAZ4A3ZOT5SOnMxNOzROsSTPiE8tBJPA==",
+			"dev": true,
+			"requires": {
+				"@webpack-cli/info": "^1.1.0",
+				"@webpack-cli/serve": "^1.1.0",
+				"colorette": "^1.2.1",
+				"command-line-usage": "^6.1.0",
+				"commander": "^6.2.0",
+				"enquirer": "^2.3.6",
+				"execa": "^4.1.0",
+				"import-local": "^3.0.2",
+				"interpret": "^2.2.0",
+				"leven": "^3.1.0",
+				"rechoir": "^0.7.0",
+				"v8-compile-cache": "^2.2.0",
+				"webpack-merge": "^4.2.2"
+			},
+			"dependencies": {
+				"commander": {
+					"version": "6.2.0",
+					"resolved": "https://registry.npmjs.org/commander/-/commander-6.2.0.tgz",
+					"integrity": "sha512-zP4jEKbe8SHzKJYQmq8Y9gYjtO/POJLgIdKgV7B9qNmABVFVc+ctqSX6iXh4mCpJfRBOabiZ2YKPg8ciDw6C+Q==",
+					"dev": true
+				},
+				"v8-compile-cache": {
+					"version": "2.2.0",
+					"resolved": "https://registry.npmjs.org/v8-compile-cache/-/v8-compile-cache-2.2.0.tgz",
+					"integrity": "sha512-gTpR5XQNKFwOd4clxfnhaqvfqMpqEwr4tOtCyz4MtYZX2JYhfr1JvBFKdS+7K/9rfpZR3VLX+YWBbKoxCgS43Q==",
+					"dev": true
+				}
+			}
+		},
+		"webpack-merge": {
+			"version": "4.2.2",
+			"resolved": "https://registry.npmjs.org/webpack-merge/-/webpack-merge-4.2.2.tgz",
+			"integrity": "sha512-TUE1UGoTX2Cd42j3krGYqObZbOD+xF7u28WB7tfUordytSjbWTIjK/8V0amkBfTYN4/pB/GIDlJZZ657BGG19g==",
+			"dev": true,
+			"requires": {
+				"lodash": "^4.17.15"
+			}
+		},
+		"webpack-sources": {
+			"version": "2.2.0",
+			"resolved": "https://registry.npmjs.org/webpack-sources/-/webpack-sources-2.2.0.tgz",
+			"integrity": "sha512-bQsA24JLwcnWGArOKUxYKhX3Mz/nK1Xf6hxullKERyktjNMC4x8koOeaDNTA2fEJ09BdWLbM/iTW0ithREUP0w==",
+			"dev": true,
+			"requires": {
+				"source-list-map": "^2.0.1",
+				"source-map": "^0.6.1"
+			}
+		},
 		"which": {
 			"version": "2.0.2",
 			"resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz",
@@ -1327,6 +2243,16 @@
 			"integrity": "sha512-Hz/mrNwitNRh/HUAtM/VT/5VH+ygD6DV7mYKZAtHOrbs8U7lvPS6xf7EJKMF0uW1KJCl0H701g3ZGus+muE5vQ==",
 			"dev": true
 		},
+		"wordwrapjs": {
+			"version": "4.0.0",
+			"resolved": "https://registry.npmjs.org/wordwrapjs/-/wordwrapjs-4.0.0.tgz",
+			"integrity": "sha512-Svqw723a3R34KvsMgpjFBYCgNOSdcW3mQFK4wIfhGQhtaFVOJmdYoXgi63ne3dTlWgatVcUc7t4HtQ/+bUVIzQ==",
+			"dev": true,
+			"requires": {
+				"reduce-flatten": "^2.0.0",
+				"typical": "^5.0.0"
+			}
+		},
 		"wrappy": {
 			"version": "1.0.2",
 			"resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz",
diff --git a/plugins/deadlock-extension/package.json b/plugins/deadlock-extension/package.json
index f5cdf38ffa4afeadb3120f1893452e299d3594cd..18c7624d0a18905b6defcf3b28ca75a8d3f61a45 100644
--- a/plugins/deadlock-extension/package.json
+++ b/plugins/deadlock-extension/package.json
@@ -55,7 +55,7 @@
 	},
 	"scripts": {
 		"vscode:prepublish": "npm run compile",
-		"compile": "./compile.sh && tsc -p ./ && cp ./out/config.prod.js ./out/config.js",
+		"compile": "./compile.sh && tsc -p ./ && cp ./out/core/config.prod.js ./out/core/config.js",
 		"lint": "eslint . --ext .ts,.tsx",
 		"watch": "tsc -w -p ./"
 	},
@@ -73,7 +73,10 @@
 		"@typescript-eslint/eslint-plugin": "^3.0.2",
 		"@typescript-eslint/parser": "^3.0.2",
 		"eslint": "^7.1.0",
+		"terser-webpack-plugin": "^5.0.3",
 		"ts-node": "^9.0.0",
-		"typescript": "^3.9.4"
+		"typescript": "^3.9.4",
+		"webpack": "^5.6.0",
+		"webpack-cli": "^4.2.0"
 	}
 }
diff --git a/plugins/deadlock-extension/src/command.ts b/plugins/deadlock-extension/src/command.ts
deleted file mode 100644
index 87504e9f774b5b94857f86af2a1c1deec3d0fc83..0000000000000000000000000000000000000000
--- a/plugins/deadlock-extension/src/command.ts
+++ /dev/null
@@ -1,2 +0,0 @@
-
-export const OPEN_BRIEFING_COMMAND = {title: 'Open Briefing', command: 'deadlock.openBriefing'};
\ No newline at end of file
diff --git a/plugins/deadlock-extension/src/config.prod.ts b/plugins/deadlock-extension/src/core/config.prod.ts
similarity index 100%
rename from plugins/deadlock-extension/src/config.prod.ts
rename to plugins/deadlock-extension/src/core/config.prod.ts
diff --git a/plugins/deadlock-extension/src/config.ts b/plugins/deadlock-extension/src/core/config.ts
similarity index 100%
rename from plugins/deadlock-extension/src/config.ts
rename to plugins/deadlock-extension/src/core/config.ts
diff --git a/plugins/deadlock-extension/src/gitMission.ts b/plugins/deadlock-extension/src/core/gitMission.ts
similarity index 84%
rename from plugins/deadlock-extension/src/gitMission.ts
rename to plugins/deadlock-extension/src/core/gitMission.ts
index 87d95517577a19e4beb03a39767ace8a9178f6ab..07de02701cbfc4a1537cd224d02381dff8d4cbfa 100644
--- a/plugins/deadlock-extension/src/gitMission.ts
+++ b/plugins/deadlock-extension/src/core/gitMission.ts
@@ -1,6 +1,6 @@
 import simpleGit, { SimpleGit, SimpleGitOptions } from 'simple-git';
 import { PROJECT_SRC_PATH } from './config';
-import { UserConfig } from './userConfig';
+import UserConfig from './userConfig';
 
 const util = require('util');
 const exec = util.promisify(require('child_process').exec);
@@ -51,6 +51,8 @@ export default class GitMission {
 
             await this.git.init();
             await this.git.addRemote(DEFAULT_REMOTE, remotePath);
+            await this.git.addConfig('user.email', this.userConfig.getCurrentUserDetails().email);
+            await this.git.addConfig('user.name', `${this.userConfig.getCurrentUserDetails().lastName} ${this.userConfig.getCurrentUserDetails().firstName}`);
 
             return Promise.resolve(this);
         } catch (e) {
@@ -60,7 +62,7 @@ export default class GitMission {
     }
 
     private getRemotePath() {
-        return `ssh://git@${this.userConfig.getGiteaHost()}:${this.userConfig.getGiteaSshPort()}/${this.userConfig.getUsername()}/${this.userConfig.getMissionId()}`;
+        return `ssh://git@${this.userConfig.getGiteaHost()}:${this.userConfig.getGiteaSshPort()}/${this.userConfig.getRemoteGitUsername()}/${this.userConfig.getMissionId()}`;
     }
 
     async readRemote() {
@@ -85,9 +87,7 @@ export default class GitMission {
     }
 
     commit(message) {
-        return this.git.commit(message,
-            undefined,
-            { '--author': `${this.userConfig.getUsername()} "<${this.userConfig.getEmail()}>"` });
+        return this.git.commit(message);
     }
 
     push() {
diff --git a/plugins/deadlock-extension/src/userConfig.ts b/plugins/deadlock-extension/src/core/userConfig.ts
similarity index 72%
rename from plugins/deadlock-extension/src/userConfig.ts
rename to plugins/deadlock-extension/src/core/userConfig.ts
index 587330d647035ed05c992875567f718b5f31da3f..bf4ab4f4ce9969424394018d36e4d4eca7d2d492 100644
--- a/plugins/deadlock-extension/src/userConfig.ts
+++ b/plugins/deadlock-extension/src/core/userConfig.ts
@@ -16,7 +16,14 @@
  * }
  */
 
-export abstract class UserConfig {
+export interface UserDetails {
+    firstName: string;
+    lastName: string;
+    avatarUrl: string;
+    email: string;
+}
+
+export default abstract class UserConfig {
     private userConfigJson: any | undefined;
 
     getPaths(): Map<number, string> {
@@ -43,6 +50,10 @@ export abstract class UserConfig {
         return this.userConfigJson?.username;
     }
 
+    getRemoteGitUsername(): string {
+        return this.userConfigJson?.remoteGitUsername;
+    }
+
     getMissionId(): string {
         return this.userConfigJson?.missionId;
     }
@@ -51,6 +62,18 @@ export abstract class UserConfig {
         return this.userConfigJson?.email;
     }
 
+    isProfessor(): boolean {
+        return this.userConfigJson?.professor;
+    }
+
+    getCurrentUserDetails(): UserDetails {
+        return this.userConfigJson?.currentUserDetails;
+    }
+
+    getRemoteUserDetails(): UserDetails {
+        return this.userConfigJson?.remoteUserDetails;
+    }
+
     abstract async loadText(): Promise<string>;
 
     public async init() {
diff --git a/plugins/deadlock-extension/src/extension.ts b/plugins/deadlock-extension/src/extension.ts
index b26928e57a261e47f295992937e5c2975e3d4c0d..a85faff3ff1adc4137dac412cc5dc1cbd88157f8 100644
--- a/plugins/deadlock-extension/src/extension.ts
+++ b/plugins/deadlock-extension/src/extension.ts
@@ -1,16 +1,23 @@
 import * as vscode from 'vscode';
-import { DepNodeProvider } from './deadlockPanel';
+import { DepNodeProvider } from './theia/deadlockPanel';
 import BriefingView, { BRIEFING_ID } from './view/briefingView';
-import View from './view/view';
-import { OPEN_BRIEFING_COMMAND } from './command';
+import { OPEN_BRIEFING_COMMAND } from './theia/command';
+import UserConfigTheia from './theia/userConfigTheia';
 
-export function initViews(extensionPath: string) {
-  new BriefingView(extensionPath);
+export function initViews() {
+  new BriefingView();
 }
 
+export const userConfig = new UserConfigTheia();
+
 export async function activate(context: vscode.ExtensionContext) {
-  initViews(context.extensionPath);
-  View.getView(BRIEFING_ID).createOrShow();
+
+  await userConfig.init();
+
+  initViews();
+
+  // View.getView(BRIEFING_ID).createOrShow();
+  await vscode.commands.executeCommand(OPEN_BRIEFING_COMMAND.cmd);
 
   // @ts-ignore
   const deadlockPanelProvider = new DepNodeProvider(vscode.workspace.rootPath);
@@ -19,10 +26,10 @@ export async function activate(context: vscode.ExtensionContext) {
     deadlockPanelProvider
   );
 
-  context.subscriptions.push(
-    vscode.commands.registerCommand(OPEN_BRIEFING_COMMAND.command, () => {
-      View.getView(BRIEFING_ID).createOrShow();
-    })
-  );
+  // context.subscriptions.push(
+  //   vscode.commands.registerCommand(OPEN_BRIEFING_COMMAND.command, () => {
+  //     View.getView(BRIEFING_ID).createOrShow();
+  //   })
+  // );
 
 }
diff --git a/plugins/deadlock-extension/src/recorder/command-recorder.ts b/plugins/deadlock-extension/src/recorder/command-recorder.ts
index 23ade5a253281efedb4a450dea653f544620a930..6ec8d4de2dcd945ae60f86f2d8ef26b2296d8cab 100644
--- a/plugins/deadlock-extension/src/recorder/command-recorder.ts
+++ b/plugins/deadlock-extension/src/recorder/command-recorder.ts
@@ -1,4 +1,4 @@
-import GitMission from '../gitMission';
+import GitMission from '../core/gitMission';
 import { error, commitAndPushCode, CommitFrom } from './utils';
 const async = require("async");
 
diff --git a/plugins/deadlock-extension/src/recorder/recorder.ts b/plugins/deadlock-extension/src/recorder/index.ts
similarity index 62%
rename from plugins/deadlock-extension/src/recorder/recorder.ts
rename to plugins/deadlock-extension/src/recorder/index.ts
index 61a2d26e364e19cff116c92e5e9f083cdf70558e..9246d7c917a75cf455f0c6f4505e4e796c377015 100644
--- a/plugins/deadlock-extension/src/recorder/recorder.ts
+++ b/plugins/deadlock-extension/src/recorder/index.ts
@@ -1,13 +1,9 @@
 import CommandRecorder from "./command-recorder"
-import GitMission from "../gitMission";
+import GitMission from '../core/gitMission';
 import UserConfigNode from "./userConfigNode";
-import { PROJECT_SRC_PATH, PROJECT_THEIA_PATH } from '../config'
-import { pathContainsFiles, copyProjectSources, clearFilesExceptGit, log } from "./utils";
+import { PROJECT_SRC_PATH, PROJECT_THEIA_PATH } from '../core/config';
+import { copyProjectSources, clearFilesExceptGit, log } from "./utils";
 
-async function setupProject() {
-    await pathContainsFiles(PROJECT_THEIA_PATH);
-    await copyProjectSources(PROJECT_SRC_PATH, PROJECT_THEIA_PATH);
-}
 
 export default class Recorder {
 
@@ -28,10 +24,14 @@ export default class Recorder {
                 await gitMission.pull();
             }
             log('Setup user project..');
-            await setupProject();
 
-            log('Starting CommandRecorder..');
-            new CommandRecorder(gitMission).run();
+            if (!userConfig.isProfessor()) {
+                await copyProjectSources(PROJECT_SRC_PATH, PROJECT_THEIA_PATH, ['.git/']);
+                log('Starting CommandRecorder..');
+                new CommandRecorder(gitMission).run();
+            } else {
+                await copyProjectSources(PROJECT_SRC_PATH, PROJECT_THEIA_PATH);
+            }
         } catch (e) {
             console.error('Cannot setup user repo.');
             console.error(e);
diff --git a/plugins/deadlock-extension/src/recorder/package.json b/plugins/deadlock-extension/src/recorder/package.json
new file mode 100644
index 0000000000000000000000000000000000000000..3e8d60d9f770b499340fd375b4a7f628120e272e
--- /dev/null
+++ b/plugins/deadlock-extension/src/recorder/package.json
@@ -0,0 +1,14 @@
+{
+  "name": "deadlock-recorder",
+  "version": "1.0.0",
+  "description": "``` ts-node recorder.ts ```",
+  "main": "index.js",
+  "scripts": {
+    "test": "echo \"Error: no test specified\" && exit 1"
+  },
+  "author": "",
+  "license": "MIT",
+  "dependencies": {
+    "deadlock-coding": "^0.0.1"
+  }
+}
diff --git a/plugins/deadlock-extension/src/recorder/preStop.ts b/plugins/deadlock-extension/src/recorder/preStop.ts
index ce1fedcfad975212dc3b4e532550735abdffaa3f..98b321368ba4311d3caebcb4789c1e21dfe0b555 100644
--- a/plugins/deadlock-extension/src/recorder/preStop.ts
+++ b/plugins/deadlock-extension/src/recorder/preStop.ts
@@ -1,7 +1,8 @@
-import UserConfigNode from "./userConfigNode";
-import GitMission from "../gitMission";
+import UserConfigNode from './userConfigNode';
+import GitMission from '../core/gitMission'
+import { PROJECT_SRC_PATH, PROJECT_THEIA_PATH } from '../core/config'
+
 import { log, error, commitAndPushCode, CommitFrom } from "./utils";
-import { PROJECT_SRC_PATH, PROJECT_THEIA_PATH } from "../config.prod";
 const util = require("util");
 const exec = util.promisify(require("child_process").exec);
 
@@ -33,13 +34,16 @@ async function containsDiff() {
 (async () => {
   try {
     log("Container will die");
-    log("Save user code..");
 
     const userConfig = new UserConfigNode();
     await userConfig.init();
-    const gitMission = await new GitMission(userConfig).init();
-    if (await containsDiff()) {
+
+    if (!userConfig.isProfessor()) {
+      log("Save user code..");
+      const gitMission = await new GitMission(userConfig).init();
+      if (await containsDiff()) {
         await commitAndPushCode(gitMission, CommitFrom.Auto);
+      }
     }
   } catch (e) {
     error("Cannot push user code at the end..");
diff --git a/plugins/deadlock-extension/src/recorder/userConfigNode.ts b/plugins/deadlock-extension/src/recorder/userConfigNode.ts
index 0a643228fc652ecf348432e3d02f67429c083b55..ce449c84d90c606a7c1551cfe2eb3e891788cc62 100644
--- a/plugins/deadlock-extension/src/recorder/userConfigNode.ts
+++ b/plugins/deadlock-extension/src/recorder/userConfigNode.ts
@@ -1,5 +1,5 @@
-import { UserConfig } from "../userConfig";
-import { USER_CHALLENGE_PATH } from '../config'
+import UserConfig from '../core/userConfig';
+import { USER_CHALLENGE_PATH } from '../core/config';
 
 const fs = require('fs');
  
diff --git a/plugins/deadlock-extension/src/recorder/utils.ts b/plugins/deadlock-extension/src/recorder/utils.ts
index dfa63343229f247cbdc380b115774aac4cbdd704..f37d234b6cccf6cec42573655141764780f3c52c 100644
--- a/plugins/deadlock-extension/src/recorder/utils.ts
+++ b/plugins/deadlock-extension/src/recorder/utils.ts
@@ -1,7 +1,7 @@
-import GitMission from "../gitMission";
-import { PROJECT_SRC_PATH, PROJECT_THEIA_PATH } from "../config.prod";
-import { execSync } from "child_process";
+import GitMission from '../core/gitMission';
+import { PROJECT_SRC_PATH, PROJECT_THEIA_PATH } from '../core/config';
 import { format } from 'date-fns';
+import { execSync } from "child_process";
 
 const util = require('util');
 const unlink = util.promisify(require('fs').unlink);
@@ -27,8 +27,9 @@ export const error = (message, args?) => {
     }
 }
 
-export async function copyProjectSources(srcPath: string, theiaPath: string) {
-    return exec(`rsync -a ${srcPath}/* ${theiaPath} --exclude .git/ && chown -R theia:theia /home/project`);
+export async function copyProjectSources(srcPath: string, theiaPath: string, excludes: Array<string> = []) {
+    const excludeCmd = excludes.map((current) => `--exclude ${current}`).join(' ');
+    return exec(`rsync -a ${srcPath}/ ${theiaPath} ${excludeCmd} && chown -R theia:theia /home/project`);
 }
 
 export async function pathContainsFiles(path: string) {
diff --git a/plugins/deadlock-extension/src/theia/command.ts b/plugins/deadlock-extension/src/theia/command.ts
new file mode 100644
index 0000000000000000000000000000000000000000..72ec485011d6183ba5f8a86ea1d01c2bd242c603
--- /dev/null
+++ b/plugins/deadlock-extension/src/theia/command.ts
@@ -0,0 +1,21 @@
+
+import { Command as VscodeComand } from 'vscode';
+export class Command {
+	constructor(private _title: string, private _command: string) {
+	}
+
+	get title() {
+		return this._title;
+	}
+
+	get cmd() {
+		return this._command;
+	}
+
+	asVsCodeCommand(): VscodeComand {
+		return { title: this.title, command: this.cmd }
+
+	}
+}
+
+export const OPEN_BRIEFING_COMMAND = new Command('Open Briefing', 'deadlock.openBriefing');
\ No newline at end of file
diff --git a/plugins/deadlock-extension/src/deadlockPanel.ts b/plugins/deadlock-extension/src/theia/deadlockPanel.ts
similarity index 97%
rename from plugins/deadlock-extension/src/deadlockPanel.ts
rename to plugins/deadlock-extension/src/theia/deadlockPanel.ts
index 6b968f6c3ef8f91a5a3ee0c801bcc87a8d901bcb..d4a5f752125a191492db1ed4d86d7dc62fbc920c 100644
--- a/plugins/deadlock-extension/src/deadlockPanel.ts
+++ b/plugins/deadlock-extension/src/theia/deadlockPanel.ts
@@ -37,7 +37,7 @@ export class DepNodeProvider implements vscode.TreeDataProvider<Action> {
 					'Briefing',
 					TreeItemCollapsibleState.None,
 					'document',
-					OPEN_BRIEFING_COMMAND),
+					OPEN_BRIEFING_COMMAND.asVsCodeCommand()),
 			]);
 		}
 
diff --git a/plugins/deadlock-extension/src/userConfigTheia.ts b/plugins/deadlock-extension/src/theia/userConfigTheia.ts
similarity index 75%
rename from plugins/deadlock-extension/src/userConfigTheia.ts
rename to plugins/deadlock-extension/src/theia/userConfigTheia.ts
index 409fddea8352a0f3be6db696100197b2f066a643..332bfb5a30d9213821d32504cf91cb5eafddb88c 100644
--- a/plugins/deadlock-extension/src/userConfigTheia.ts
+++ b/plugins/deadlock-extension/src/theia/userConfigTheia.ts
@@ -1,7 +1,7 @@
-import { UserConfig } from "./userConfig";
+import UserConfig from '../core/userConfig'
 import * as vscode from 'vscode';
 
-import { USER_CHALLENGE_PATH } from './config'
+import { USER_CHALLENGE_PATH } from '../core/config';
 
 export default class UserConfigTheia extends UserConfig {
     async loadText(): Promise<string> {
diff --git a/plugins/deadlock-extension/src/view/briefingView.ts b/plugins/deadlock-extension/src/view/briefingView.ts
index a4d5fb5ca24b9eabea9e62e11344292965326287..f65c871128f58310b530f728efc46d9b5adc07bc 100644
--- a/plugins/deadlock-extension/src/view/briefingView.ts
+++ b/plugins/deadlock-extension/src/view/briefingView.ts
@@ -6,50 +6,65 @@ import * as path from "path";
 // eslint-disable-next-line @typescript-eslint/no-var-requires
 const marked = require("marked");
 
-import { USER_CHALLENGE_PATH, DOCS_PATH, BRIEFING_FILE_NAME } from "../config";
+import { DOCS_PATH, BRIEFING_FILE_NAME } from "../core/config";
+import { WebviewBase } from "./webviewBase";
+import { OPEN_BRIEFING_COMMAND } from "../theia/command";
+
+import { userConfig } from "../extension";
+import { setInterval } from "timers";
 
 export const BRIEFING_ID = "brefingView";
-export default class BriefingView extends View {
+export default class BriefingView extends WebviewBase {
   private briefingContent: string | undefined;
-  private userChallengeConfig: any | undefined;
-  
+
   private errorLoadingBriefing: boolean = false;
-  private errorLoadingUserConfig: boolean = false;
 
-  constructor(extensionPath: string) {
-    super(BRIEFING_ID, extensionPath, "Briefing", "Briefing");
+  private loadingBriefing: boolean = false;
+
+  constructor() {
+    super(BRIEFING_ID, "Briefing", OPEN_BRIEFING_COMMAND);
   }
 
-  load() {
-    if (vscode.workspace) {
-      vscode.workspace
-        .openTextDocument(
-          vscode.Uri.parse(path.join(DOCS_PATH, BRIEFING_FILE_NAME))
-        ).then((document) => {
-          this.briefingContent = document.getText();
-          this.update();
-        }, (error) => {
-          console.error('Cannot load briefing', error); 
-          this.errorLoadingBriefing = true;
-          this.update();
-        });
-
-      vscode.workspace
-        .openTextDocument(vscode.Uri.parse(USER_CHALLENGE_PATH))
-        .then((userConfig) => {
-          this.userChallengeConfig = JSON.parse(userConfig.getText());
-          this.update();
-        }, (error) => {
-          console.error('Cannot load user_challenge config', error); 
-          this.errorLoadingUserConfig = true;
-          this.update();
-        });
-    }
+  load(): void {
+    const intervalId = setInterval(() => {
+      if (vscode.workspace && !this.loadingBriefing) {
+        this.loadingBriefing = true;
+        clearInterval(intervalId);
+
+        vscode.workspace
+          .openTextDocument(
+            vscode.Uri.parse(path.join(DOCS_PATH, BRIEFING_FILE_NAME))
+          )
+          .then(
+            (document) => {
+              this.briefingContent = document.getText();
+              this.show();
+            },
+            (error) => {
+              console.error("Cannot load briefing", error);
+              this.errorLoadingBriefing = true;
+            }
+          );
+      }
+    }, 500);
   }
 
   render() {
     let output = "";
 
+    if (userConfig.isProfessor()) {
+      output += `
+        <h2>Professeur</h2>
+        Bonjour ${userConfig.getCurrentUserDetails().lastName} ${
+        userConfig.getCurrentUserDetails().firstName
+      } vous êtes actuellement entrain de relire le code de <b>${
+        userConfig.getRemoteUserDetails().lastName
+      } ${userConfig.getRemoteUserDetails().firstName}</b>.<br />
+        Vous pouvez consulter chaque exécution de son code dans l'onglet à gauche de GitLens. Chaque commit sur <b>master</b> représente une exécution.
+        <br />
+      `;
+    }
+
     if (this.briefingContent) {
       output += `<h1>Mission Goal 🕶</h1>${marked(this.briefingContent)}`;
     } else if (this.errorLoadingBriefing) {
@@ -60,10 +75,8 @@ export default class BriefingView extends View {
 
     output += "<br/>";
 
-    if (this.userChallengeConfig) {
+    if (userConfig.getUsername()) {
       output += this.renderUserChallengeConfig();
-    } else if (this.errorLoadingUserConfig) {
-      output += "Cannot load user config."
     } else {
       output += "Loading help..";
     }
@@ -75,11 +88,12 @@ export default class BriefingView extends View {
     let adresses = "";
 
     let pathsLength = 0;
-    for (const key in this.userChallengeConfig?.paths) {
+    const paths = userConfig.getPaths();
+    for (const key in paths) {
       if (key !== "3000") {
         pathsLength++;
-        const path = this.userChallengeConfig?.paths[key];
-        adresses += `<li>${key} binded on <a href="https://${this.userChallengeConfig?.host}/${path}/">${path}</a></li>`;
+        const path = paths[key];
+        adresses += `<li>${key} binded on <a href="https://${userConfig.getHost()}/${path}/">${path}</a></li>`;
       }
     }
 
diff --git a/plugins/deadlock-extension/src/view/view.ts b/plugins/deadlock-extension/src/view/view.ts
index 32e34c4add87fef7ff2f639536da133ba31bf593..4bc8ed7408c8ece5731d1c1f20998d42ace8ada4 100644
--- a/plugins/deadlock-extension/src/view/view.ts
+++ b/plugins/deadlock-extension/src/view/view.ts
@@ -11,6 +11,9 @@ function getNonce() {
   return text;
 }
 
+/**
+ * @deprecated use #webviewBase instead of
+ */
 export default abstract class View {
 
   private static views: Map<string, View> = new Map();
@@ -21,7 +24,7 @@ export default abstract class View {
 
   constructor(
     id: string,
-    private readonly extensionPath: string,
+    private readonly context: vscode.ExtensionContext,
     public readonly panelName: string,
     public readonly title: string
   ) {
@@ -33,6 +36,11 @@ export default abstract class View {
     }
     View.views.set(id, this);
     this.load();
+    context.subscriptions.push(this);
+  }
+
+  static getViews(): Map<string, View> {
+    return this.views;
   }
 
   static getView(id: string): View {
diff --git a/plugins/deadlock-extension/src/view/webviewBase.ts b/plugins/deadlock-extension/src/view/webviewBase.ts
new file mode 100644
index 0000000000000000000000000000000000000000..c1b9ad4a07106f4195ebd79d5604094a25bd2d1e
--- /dev/null
+++ b/plugins/deadlock-extension/src/view/webviewBase.ts
@@ -0,0 +1,136 @@
+"use strict";
+import {
+  commands,
+  Disposable,
+  Uri,
+  ViewColumn,
+  Webview,
+  WebviewPanel,
+  WebviewPanelOnDidChangeViewStateEvent,
+  window,
+  workspace,
+} from "vscode";
+import { Command } from "../theia/command";
+
+const emptyCommands: Disposable[] = [
+  {
+    dispose: function () {
+      /* noop */
+    },
+  },
+];
+
+export abstract class WebviewBase implements Disposable {
+  protected disposable: Disposable;
+  private _disposablePanel: Disposable | undefined;
+  private _panel: WebviewPanel | undefined;
+
+  constructor(private id: string, private title:string, command: Command, private readonly _column?: ViewColumn) {
+    this.disposable = Disposable.from(
+      commands.registerCommand(command.cmd, this.onShowCommand, this)
+    );
+    this.load();
+  }
+
+  registerCommands(): Disposable[] {
+    return emptyCommands;
+  }
+
+  renderHead?(): string | Promise<string>;
+  renderBody?(): string | Promise<string>;
+  renderEndOfBody?(): string | Promise<string>;
+
+  dispose() {
+    this.disposable.dispose();
+    this._disposablePanel?.dispose();
+  }
+
+  protected onShowCommand() {
+    void this.show(this._column);
+  }
+
+  private onPanelDisposed() {
+    this._disposablePanel?.dispose();
+    this._panel = undefined;
+  }
+
+  private onViewStateChanged(e: WebviewPanelOnDidChangeViewStateEvent) {
+    console.log(
+      `Webview(${this.id}).onViewStateChanged`,
+      `active=${e.webviewPanel.active}, visible=${e.webviewPanel.visible}`
+    );
+  }
+
+  get visible() {
+    return this._panel?.visible ?? false;
+  }
+
+  hide() {
+    this._panel?.dispose();
+  }
+
+  setTitle(title: string) {
+    if (this._panel == null) return;
+
+    this._panel.title = title;
+  }
+
+  onMessageReceive(message) {
+    switch (message.command) {
+      case "alert":
+        window.showErrorMessage(message.text);
+        return;
+    }
+  }
+
+  async show(column: ViewColumn = ViewColumn.Beside): Promise<void> {
+    if (this._panel == null) {
+      this._panel = window.createWebviewPanel(
+        this.id,
+        this.title,
+        { viewColumn: column, preserveFocus: false },
+        {
+          retainContextWhenHidden: true,
+          enableFindWidget: true,
+          enableCommandUris: true,
+          enableScripts: true,
+        }
+      );
+
+    //   this._panel.iconPath = Uri.file(
+        // Container.context.asAbsolutePath("images/gitlens-icon.png")
+    //   );
+      this._disposablePanel = Disposable.from(
+        this._panel,
+        this._panel.onDidDispose(this.onPanelDisposed, this),
+        this._panel.onDidChangeViewState(this.onViewStateChanged, this),
+        this._panel.webview.onDidReceiveMessage(this.onMessageReceive, this),
+        ...this.registerCommands()
+      );
+
+      this._panel.webview.html = await this.getHtml(this._panel.webview);
+    } else {
+      const html = await this.getHtml(this._panel.webview);
+
+      // Reset the html to get the webview to reload
+      this._panel.webview.html = "";
+      this._panel.webview.html = html;
+
+      this._panel.reveal(this._panel.viewColumn ?? ViewColumn.Active, false);
+    }
+  }
+
+  /**
+   * Must return the content displayed within the webViewPanel
+   */
+  abstract render(): string;
+  /**
+   * Method called at the end of first render
+   */
+  abstract load(): void;
+
+  private async getHtml(webview: Webview): Promise<string> {
+	  return this.render();
+  }
+
+}
diff --git a/plugins/deadlock-extension/tsconfig.json b/plugins/deadlock-extension/tsconfig.json
index e3c9e49731d1c56267ed380f995a7f7e0d95b06e..45ea4863817c56fa21e1f40ba11c6c29935fb8a0 100644
--- a/plugins/deadlock-extension/tsconfig.json
+++ b/plugins/deadlock-extension/tsconfig.json
@@ -4,7 +4,7 @@
 		"target": "es2019",
 		"lib": ["ES2019"],
 		"outDir": "out",
-		"sourceMap": true,
+		"sourceMap": false,
 		"strict": true,
 		"rootDir": "src",
 		"noImplicitAny": false,
diff --git a/plugins/gitlens-10.2.3.vsix b/plugins/gitlens-10.2.3.vsix
new file mode 100644
index 0000000000000000000000000000000000000000..248629ac5c2accb40160dfc108b9026f43869ed2
Binary files /dev/null and b/plugins/gitlens-10.2.3.vsix differ
diff --git a/recorder-out/webpack.config.js b/recorder-out/webpack.config.js
new file mode 100644
index 0000000000000000000000000000000000000000..f0e0d44599b0aba4f08e50ace4233d4bc1a3849c
--- /dev/null
+++ b/recorder-out/webpack.config.js
@@ -0,0 +1,15 @@
+const path = require('path');
+const TerserPlugin = require("terser-webpack-plugin");
+
+module.exports = {
+  entry: './recorder/index.js',
+  target: 'node',
+  output: {
+    filename: 'main.js',
+    path: path.resolve(__dirname, 'dist'),
+  },
+  optimization: {
+    minimize: true,
+    minimizer: [new TerserPlugin()],
+  },
+};
\ No newline at end of file
diff --git a/start.sh b/start.sh
index bc195975bcc51aa07e3eab0cb0127fa8de0f5228..37d853aa2cf2043a02e1c0f9eb82906251010b3e 100755
--- a/start.sh
+++ b/start.sh
@@ -1,15 +1,12 @@
 #!/bin/sh
 
-# starting service as ROOT
-service rsyslog restart
-
 # setup ssh key for root user
 # must be installed by the API first within /tmp/.ssh
 mkdir ~/.ssh
 cp /tmp/.ssh/* ~/.ssh/
 
 # start command recorder
-node deadlock/recorder/recorder.js &
+node deadlock/recorder.js &
 
 # starting theia as THEIA
 su theia --command "yarn theia start /home/project --hostname=0.0.0.0 --plugins=local-dir:/home/plugins"
\ No newline at end of file
diff --git a/theia/plugin-storage/global-state.json b/theia/plugin-storage/global-state.json
new file mode 100644
index 0000000000000000000000000000000000000000..099573d9a63f720c94d7bae1b9f54d005a77d5bc
--- /dev/null
+++ b/theia/plugin-storage/global-state.json
@@ -0,0 +1 @@
+{"eamodio.gitlens":{"gitlensVersion":"10.2.3"}}
\ No newline at end of file