From dd8773b4aad2e82d61ee91c862c83fe4840fd0fe Mon Sep 17 00:00:00 2001
From: jaombori <jovanni.auxilio@ombori.com>
Date: Wed, 18 Jan 2023 17:35:28 +0100
Subject: [PATCH] feat: screen app

---
 .gitignore               |  2 +
 DESCRIPTION.md           |  4 +-
 auth-cases.txt           |  8 ++++
 package.json             |  5 ++-
 src/app.tsx              | 97 +++++++++++++++++-----------------------
 src/format-remote-key.ts |  1 +
 src/index.tsx            | 11 +++--
 src/init.tsx             | 21 ++++++++-
 yarn.lock                | 50 ++++++++++++++++++++-
 9 files changed, 131 insertions(+), 68 deletions(-)
 create mode 100644 auth-cases.txt
 create mode 100644 src/format-remote-key.ts

diff --git a/.gitignore b/.gitignore
index 0657f90..2fb0037 100644
--- a/.gitignore
+++ b/.gitignore
@@ -26,3 +26,5 @@ src/settings
 npm-debug.log*
 yarn-debug.log*
 yarn-error.log*
+
+.env
diff --git a/DESCRIPTION.md b/DESCRIPTION.md
index ead6b27..0ddd72b 100644
--- a/DESCRIPTION.md
+++ b/DESCRIPTION.md
@@ -1,5 +1,5 @@
-# {{applicationName}} #
-by {{author}}
+# demo-session-creation-screen #
+by Vnx Test Parent
 
 A short description will be displayed in application list.
 
diff --git a/auth-cases.txt b/auth-cases.txt
new file mode 100644
index 0000000..70014f8
--- /dev/null
+++ b/auth-cases.txt
@@ -0,0 +1,8 @@
+Cases:
+1. [fresh] accessing the url, without sessionId
+2. [fresh] accessing the url, with invalid sessionId as hash param
+3. [fresh] accessing the url, with valid sessionId
+4. [existing cache] accessing the url without sessionId
+5. [existing cache] accessing the url with invalid sessionId
+6. [existing cache] accessing the url with valid sessionId
+7. [expiration] session should expire and just show gate status
diff --git a/package.json b/package.json
index b69d20f..e053ad3 100644
--- a/package.json
+++ b/package.json
@@ -5,7 +5,7 @@
   "homepage": "./",
   "scripts": {
     "bootstrap": "mkdirp src/settings && ncp default.settings.json src/settings/index.json",
-    "start": "yarn schema && cross-env REACT_APP_MESSAGING_URL=ws://localhost:8088 react-scripts start",
+    "start": "yarn schema && PORT=3001 react-scripts start",
     "schema": "mkdirp build && npx ts-schema src/schema.ts build && yarn analytics-schema",
     "analytics-schema": "npx tsc src/analytics-schema.ts --moduleResolution node --skipLibCheck --outFile /dev/stdout -m amd | node -e 'a={};eval(\"define=(_,d,c)=>{c(a,a,...d.slice(2).map(require));console.log(JSON.stringify(a.default))};\"+require(\"fs\").readFileSync(\"/dev/stdin\",\"utf8\"))' > build/analytics-schema.json",
     "prodbuild": "cross-env GENERATE_SOURCEMAP=false react-scripts build && ncp package.json build/",
@@ -33,6 +33,7 @@
   },
   "dependencies": {
     "@ombori/ga-messaging": "^2.90.2",
+    "@ombori/ga-react-qr-run": "^3.11.0",
     "@ombori/ga-settings": "^3.11.3",
     "@ombori/grid-reports": "^3.11.2",
     "@ombori/grid-signals-react": "^3.11.3",
@@ -59,4 +60,4 @@
     "rimraf": "^3.0.2"
   },
   "description": "demo-session-creation-screen"
-}
\ No newline at end of file
+}
diff --git a/src/app.tsx b/src/app.tsx
index 82342a1..a8c2306 100644
--- a/src/app.tsx
+++ b/src/app.tsx
@@ -1,43 +1,49 @@
-import React, { useEffect, useCallback, useState } from 'react';
+import React, { useEffect } from 'react';
 import { getInstance as gs } from '@ombori/grid-signals-react';
+import ShortUrlQrCode from '@ombori/ga-react-qr-run';
 import styled from 'styled-components';
 import { useSettings } from '@ombori/ga-settings';
-import { useHeartbeat } from '@ombori/ga-messaging';
-import logo from './logo.svg';
+import { formatRemoteKey } from './format-remote-key';
 
 import { Schema as Settings } from './schema';
 
+const MY_DEV_URL = 'http://localhost:3002';
+
 function App() {
-  useHeartbeat();
-  const [productCount, setProductCount] = useState(0);
   const settings = useSettings<Settings>();
 
-  const productName = settings?.productName;
-  const productPrice = settings?.productPrice;
-
-  useEffect(() => {
-    if (productName) {
-      gs().sendContentView({ title: productName });
-    }
-  }, [productName]);
-
   useEffect(() => {
     const startSessionSubscription = async () => {
-      const sessionState = await gs().subscribeSessionState((sessionState) => {
-        setProductCount(sessionState.CART['TEMPORARY-PRODUCT-ID-123']);
+      const spaceEventSubscription = await gs().subscribeSpaceEvent((spaceEvent) => {
+        switch(spaceEvent.eventType) {
+          case 'GWREMOTE_REQUEST': {
+            console.log("GWREMOTE_REQUEST:", spaceEvent);
+            const currentSessionId = gs().getInstanceProps().sessionId;
+            if (currentSessionId === spaceEvent.sessionId) {
+              gs().setState({
+                key: formatRemoteKey(spaceEvent.str1),
+                value: spaceEvent.str1,
+                expiryDuration: 10,
+              });
+            }
+          }
+        }
+      });
+
+      const spaceStateSubscription = await gs().subscribeSpaceState((spaceState) => {
+        console.log('spaceState:', spaceState);
       });
   
       return () => {
-        sessionState.stop();
+        spaceEventSubscription.stop();
+        spaceStateSubscription.stop();
       }
     }
 
     startSessionSubscription();
   }, []);
 
-  const onAddToCart = useCallback(() => {
-    gs().sendCartAdd({ productId: 'TEMPORARY-PRODUCT-ID-123', quantity: 1 })
-  }, []);
+  const currentSessionId = gs().getInstanceProps().sessionId;
 
   if (!settings) {
     return <Container>Loading gridapp settings...</Container>
@@ -45,16 +51,17 @@ function App() {
 
   return (
     <Container>
-      <ProductInfo>
-        <Logo src={logo} alt="logo" />
-        <p>Product name: {productName}</p>
-        <p>Product price: {productPrice}</p>
-        <Button onClick={onAddToCart}>Add to Cart</Button>
-      </ProductInfo>
-      <RealTimeInfo>
-        <p>Real Cart Subscription</p>
-        <p>{productName} count: {productCount}</p>
-      </RealTimeInfo>
+      <ShortUrlQrCode
+        url={`${MY_DEV_URL}#s=${currentSessionId}`}
+        size={112}
+      >
+        {(shortUrl) => (
+          <ShortUrlContainer>
+            <ShortUrl>{shortUrl.replace(/^https:\/\//, '')}</ShortUrl>
+          </ShortUrlContainer>
+        )}
+      </ShortUrlQrCode>
+      <div>{`${MY_DEV_URL}#s=${currentSessionId}`}</div>
     </Container>
   );
 }
@@ -65,7 +72,7 @@ const Container = styled.div`
   height: 100%;
   position: absolute;
   display: flex;
-  flex-direction: row;
+  flex-direction: column;
   width: 100%;
   color: white;
   align-items: center;
@@ -73,34 +80,10 @@ const Container = styled.div`
   font-size: calc(10px + 1.5vmin);
 `;
 
-const ProductInfo = styled.header`
-  display: flex;
-  flex-direction: column;
-  flex: 1;
-  padding-bottom: 64px;
-  border-right: solid 1px white;
-`;
-
-const Logo = styled.img`
-  height: 40vmin;
-  pointer-events: none;
-`;
+const ShortUrlContainer = styled.div`
 
-const Button = styled.button`
-  padding: 16px 32px;
-  margin-top: 24px;
-  align-self: center;
-  border-radius: 8px;
 `;
 
-const RealTimeInfo = styled.footer`
-  display: flex;
-  height: 100%;
-  flex: 1;
-  flex-direction: column;
-  pointer-events: none;
-  align-items: center;
-  justify-content: center;
-`;
+const ShortUrl = styled.div``;
 
 export default App;
diff --git a/src/format-remote-key.ts b/src/format-remote-key.ts
new file mode 100644
index 0000000..58561ab
--- /dev/null
+++ b/src/format-remote-key.ts
@@ -0,0 +1 @@
+export const formatRemoteKey = (clientId: string) => `GWREMOTE_${clientId}`.replace(/-/g, '').toUpperCase();
\ No newline at end of file
diff --git a/src/index.tsx b/src/index.tsx
index dff142f..23bc28e 100644
--- a/src/index.tsx
+++ b/src/index.tsx
@@ -1,11 +1,14 @@
 import React from 'react';
-import ReactDOM from 'react-dom';
+import ReactDOM from 'react-dom/client';
 import './index.css';
 import Init from './init';
 
-ReactDOM.render(
+
+const root = ReactDOM.createRoot(
+  document.getElementById('root') as HTMLElement
+);
+root.render(
   <React.StrictMode>
     <Init />
-  </React.StrictMode>,
-  document.getElementById('root'),
+  </React.StrictMode>
 );
diff --git a/src/init.tsx b/src/init.tsx
index 93ba6f1..42ecab0 100644
--- a/src/init.tsx
+++ b/src/init.tsx
@@ -2,8 +2,27 @@ import React from 'react';
 import { useGridSignals } from '@ombori/grid-signals-react';
 import App from './app';
 
+const {
+  REACT_APP_ACCESS_ID,
+  REACT_APP_ACCESS_TOKEN,
+  REACT_APP_SPACE_ID,
+  REACT_APP_TENANT_ID,
+} = process.env;
+
+console.log({
+  REACT_APP_ACCESS_ID,
+  REACT_APP_ACCESS_TOKEN,
+  REACT_APP_SPACE_ID,
+  REACT_APP_TENANT_ID,
+});
+
 const Init = () => {
-  const isSignalsReady = useGridSignals();
+  const isSignalsReady = useGridSignals({
+    accessId: REACT_APP_ACCESS_ID,
+    accessToken: REACT_APP_ACCESS_TOKEN,
+    spaceId: REACT_APP_SPACE_ID,
+    tenantId: REACT_APP_TENANT_ID,
+  });
 
   if (!isSignalsReady) {
     return <div className='init'>Initializing App...</div>
diff --git a/yarn.lock b/yarn.lock
index 8ab5af0..c5ad456 100644
--- a/yarn.lock
+++ b/yarn.lock
@@ -2484,6 +2484,19 @@
   resolved "https://registry.yarnpkg.com/@ombori/ga-messaging/-/ga-messaging-2.90.2.tgz#e3fb877b9519505146f9981fdacac3a44e7557d1"
   integrity sha512-OxgMS/pRh8PV3T9TIa1aOiLjWJs2FJ1t91TfRwg1T94FWjUIRVt0tVOVEYOK3UYbV747yS7/RzZNDG7w0c53vA==
 
+"@ombori/ga-react-qr-run@^3.11.0":
+  version "3.11.0"
+  resolved "https://registry.yarnpkg.com/@ombori/ga-react-qr-run/-/ga-react-qr-run-3.11.0.tgz#0a5c6beb63960ea048fcb87d5a14473c8c0fb538"
+  integrity sha512-DxleqGddB9q2fo6CN8QkxAuXpT1t8jQ4J4KF9ZrMgU92D4mUtRqCPwmR3EYDX+18bBAPyS+gZEko+rsmFcIhlw==
+  dependencies:
+    "@ombori/grid-signals" "3.11.0"
+    "@types/debug" "^4.1.7"
+    "@types/qrcode.react" "^1.0.2"
+    abort-controller "^3.0.0"
+    babel-plugin-module-resolver "^4.0.0"
+    debug "^4.3.3"
+    qrcode.react "^1.0.1"
+
 "@ombori/ga-settings@3.11.3", "@ombori/ga-settings@^3.11.3":
   version "3.11.3"
   resolved "https://registry.yarnpkg.com/@ombori/ga-settings/-/ga-settings-3.11.3.tgz#94028c35731e53dba3b28bb160e2dd8e2648aebf"
@@ -2879,6 +2892,13 @@
   dependencies:
     "@types/node" "*"
 
+"@types/debug@^4.1.7":
+  version "4.1.7"
+  resolved "https://registry.yarnpkg.com/@types/debug/-/debug-4.1.7.tgz#7cc0ea761509124709b8b2d1090d8f6c17aadb82"
+  integrity sha512-9AonUzyTjXXhEOa0DnqpzZi6VHlqKMswga9EXjpXnnqxwLtdvPPtlO8evrI5D9S6asFRCQ6v+wpiUKbw+vKqyg==
+  dependencies:
+    "@types/ms" "*"
+
 "@types/eslint-scope@^3.7.3":
   version "3.7.4"
   resolved "https://registry.yarnpkg.com/@types/eslint-scope/-/eslint-scope-3.7.4.tgz#37fc1223f0786c39627068a12e94d6e6fc61de16"
@@ -3016,6 +3036,11 @@
   resolved "https://registry.yarnpkg.com/@types/mime/-/mime-3.0.1.tgz#5f8f2bca0a5863cb69bc0b0acd88c96cb1d4ae10"
   integrity sha512-Y4XFY5VJAuw0FgAqPNd6NNoV44jbq9Bz2L7Rh/J6jLTiHBSBJa9fxqQIvkIld4GsoDOcCbvzOUAbLPsSKKg+uA==
 
+"@types/ms@*":
+  version "0.7.31"
+  resolved "https://registry.yarnpkg.com/@types/ms/-/ms-0.7.31.tgz#31b7ca6407128a3d2bbc27fe2d21b345397f6197"
+  integrity sha512-iiUgKzV9AuaEkZqkOLDIvlQiL6ltuZd9tGcW3gwpnX8JbuiuhFlEGmmFXEXkN50Cvq7Os88IY2v0dkDqXYWVgA==
+
 "@types/node@*":
   version "13.9.2"
   resolved "https://registry.yarnpkg.com/@types/node/-/node-13.9.2.tgz#ace1880c03594cc3e80206d96847157d8e7fa349"
@@ -3046,6 +3071,13 @@
   resolved "https://registry.yarnpkg.com/@types/q/-/q-1.5.2.tgz#690a1475b84f2a884fd07cd797c00f5f31356ea8"
   integrity sha512-ce5d3q03Ex0sy4R14722Rmt6MT07Ua+k4FwDfdcToYJcMKNtRVQvJ6JCAPdAmAnbRb6CsX6aYb9m96NGod9uTw==
 
+"@types/qrcode.react@^1.0.2":
+  version "1.0.2"
+  resolved "https://registry.yarnpkg.com/@types/qrcode.react/-/qrcode.react-1.0.2.tgz#f892432cc41b5dac52e3ca8873b717c8bfea6002"
+  integrity sha512-I9Oq5Cjlkgy3Tw7krCnCXLw2/zMhizkTere49OOcta23tkvH0xBTP0yInimTh0gstLRtb8Ki9NZVujE5UI6ffQ==
+  dependencies:
+    "@types/react" "*"
+
 "@types/qs@*":
   version "6.9.7"
   resolved "https://registry.yarnpkg.com/@types/qs/-/qs-6.9.7.tgz#63bb7d067db107cc1e457c303bc25d511febf6cb"
@@ -4813,7 +4845,7 @@ debug@2.6.9, debug@^2.6.0, debug@^2.6.9:
   dependencies:
     ms "2.0.0"
 
-debug@4, debug@^4.3.2, debug@^4.3.4:
+debug@4, debug@^4.3.2, debug@^4.3.3, debug@^4.3.4:
   version "4.3.4"
   resolved "https://registry.yarnpkg.com/debug/-/debug-4.3.4.tgz#1319f6579357f2338d3337d2cdd4914bb5dcc865"
   integrity sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ==
@@ -9109,7 +9141,7 @@ prompts@^2.4.2:
     kleur "^3.0.3"
     sisteransi "^1.0.5"
 
-prop-types@^15.8.1:
+prop-types@^15.6.0, prop-types@^15.8.1:
   version "15.8.1"
   resolved "https://registry.yarnpkg.com/prop-types/-/prop-types-15.8.1.tgz#67d87bf1a694f48435cf332c24af10214a3140b5"
   integrity sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==
@@ -9141,6 +9173,20 @@ q@^1.1.2:
   resolved "https://registry.yarnpkg.com/q/-/q-1.5.1.tgz#7e32f75b41381291d04611f1bf14109ac00651d7"
   integrity sha1-fjL3W0E4EpHQRhHxvxQQmsAGUdc=
 
+qr.js@0.0.0:
+  version "0.0.0"
+  resolved "https://registry.yarnpkg.com/qr.js/-/qr.js-0.0.0.tgz#cace86386f59a0db8050fa90d9b6b0e88a1e364f"
+  integrity sha512-c4iYnWb+k2E+vYpRimHqSu575b1/wKl4XFeJGpFmrJQz5I88v9aY2czh7s0w36srfCM1sXgC/xpoJz5dJfq+OQ==
+
+qrcode.react@^1.0.1:
+  version "1.0.1"
+  resolved "https://registry.yarnpkg.com/qrcode.react/-/qrcode.react-1.0.1.tgz#2834bb50e5e275ffe5af6906eff15391fe9e38a5"
+  integrity sha512-8d3Tackk8IRLXTo67Y+c1rpaiXjoz/Dd2HpcMdW//62/x8J1Nbho14Kh8x974t9prsLHN6XqVgcnRiBGFptQmg==
+  dependencies:
+    loose-envify "^1.4.0"
+    prop-types "^15.6.0"
+    qr.js "0.0.0"
+
 qs@6.11.0:
   version "6.11.0"
   resolved "https://registry.yarnpkg.com/qs/-/qs-6.11.0.tgz#fd0d963446f7a65e1367e01abd85429453f0c37a"