From f45de71d88d4834fde6199c004ce3dde9e2eb854 Mon Sep 17 00:00:00 2001
From: "leojoseph.r" <58416454+rleojoseph@users.noreply.github.com>
Date: Wed, 18 Oct 2023 13:22:55 +0900
Subject: [PATCH] [MINI-6324] Create interfaces to share Cookie info to MiniApp
(#276)
* Cookies from Host app
* Sample app changes
* Theme changed
* Update Helper class
* Updated Readme and Changelog
---
js-miniapp-bridge/src/common-bridge.ts | 27 ++
js-miniapp-bridge/src/index.ts | 2 +
js-miniapp-bridge/src/types/cookie-info.ts | 5 +
js-miniapp-sample/package.json | 2 +-
js-miniapp-sample/src/pages/cookie-manager.js | 356 ++++++++++++++++++
js-miniapp-sample/src/pages/helper.js | 4 +-
js-miniapp-sample/src/routes.js | 26 +-
js-miniapp-sample/src/theme.js | 4 +-
js-miniapp-sdk/CHANGELOG.md | 4 +
js-miniapp-sdk/README.md | 38 ++
js-miniapp-sdk/src/index.ts | 2 +
js-miniapp-sdk/src/miniapp.ts | 2 +
js-miniapp-sdk/src/modules/cookie-manager.ts | 30 ++
13 files changed, 485 insertions(+), 17 deletions(-)
create mode 100644 js-miniapp-bridge/src/types/cookie-info.ts
create mode 100644 js-miniapp-sample/src/pages/cookie-manager.js
create mode 100644 js-miniapp-sdk/src/modules/cookie-manager.ts
diff --git a/js-miniapp-bridge/src/common-bridge.ts b/js-miniapp-bridge/src/common-bridge.ts
index 239926c0b..c90aee48a 100644
--- a/js-miniapp-bridge/src/common-bridge.ts
+++ b/js-miniapp-bridge/src/common-bridge.ts
@@ -31,6 +31,7 @@ import { ProductInfo, PurchasedProductInfo } from './types/in-app-purchase';
import { HostThemeColor } from './types/host-color-scheme';
import { MAAnalyticsInfo } from './types/analytics/analytics';
import { UniversalBridgeInfo } from './types/universal-bridge';
+import { CookieInfo } from './types/cookie-info';
/** @internal */
const mabMessageQueue: Callback[] = [];
@@ -801,6 +802,32 @@ export class MiniAppBridge {
);
});
}
+
+ getAllCookies() {
+ return new Promise<[CookieInfo]>((resolve, reject) => {
+ return this.executor.exec(
+ 'getAllCookies',
+ null,
+ response => {
+ resolve(JSON.parse(response) as [CookieInfo]);
+ },
+ error => reject(parseMiniAppError(error))
+ );
+ });
+ }
+
+ getCookies(cookieNameList: string[]) {
+ return new Promise<[CookieInfo]>((resolve, reject) => {
+ return this.executor.exec(
+ 'getCookies',
+ { cookieList: cookieNameList },
+ response => {
+ resolve(JSON.parse(response) as [CookieInfo]);
+ },
+ error => reject(parseMiniAppError(error))
+ );
+ });
+ }
}
/**
diff --git a/js-miniapp-bridge/src/index.ts b/js-miniapp-bridge/src/index.ts
index 5a66566b9..0b67129c7 100644
--- a/js-miniapp-bridge/src/index.ts
+++ b/js-miniapp-bridge/src/index.ts
@@ -62,6 +62,7 @@ import {
PurchasedProductInfo,
ProductPrice,
} from './types/in-app-purchase';
+import { CookieInfo } from './types/cookie-info';
export {
MiniAppBridge,
@@ -111,4 +112,5 @@ export {
MAAnalyticsActionType,
MAAnalyticsEventType,
UniversalBridgeInfo,
+ CookieInfo,
};
diff --git a/js-miniapp-bridge/src/types/cookie-info.ts b/js-miniapp-bridge/src/types/cookie-info.ts
new file mode 100644
index 000000000..f7445c378
--- /dev/null
+++ b/js-miniapp-bridge/src/types/cookie-info.ts
@@ -0,0 +1,5 @@
+/** CookieInfo type. */
+export interface CookieInfo {
+ name?: string;
+ value?: string;
+}
diff --git a/js-miniapp-sample/package.json b/js-miniapp-sample/package.json
index 23636eca0..a3badd48f 100644
--- a/js-miniapp-sample/package.json
+++ b/js-miniapp-sample/package.json
@@ -25,7 +25,7 @@
"format": "prettier --config ./prettier.config.js --write 'src/**/*.js'",
"prettify": "prettier --config ./prettier.config.js --check src/**/*.js",
"lint": "eslint src/ --fix-dry-run",
- "start": "react-scripts start",
+ "start": "react-scripts --openssl-legacy-provider start",
"build": "react-scripts build && npm run zip",
"dockerBuild": "cd ci && make build",
"eject": "react-scripts eject",
diff --git a/js-miniapp-sample/src/pages/cookie-manager.js b/js-miniapp-sample/src/pages/cookie-manager.js
new file mode 100644
index 000000000..9822915d7
--- /dev/null
+++ b/js-miniapp-sample/src/pages/cookie-manager.js
@@ -0,0 +1,356 @@
+import React, { useReducer, useState } from 'react';
+
+import MiniApp from 'js-miniapp-sdk';
+
+import {
+ Button,
+ CardContent,
+ CardActions,
+ makeStyles,
+ Typography,
+ ListItem,
+ ListItemText,
+ Container,
+ TextField,
+} from '@material-ui/core';
+import { red, green } from '@material-ui/core/colors';
+import GreyCard from '../components/GreyCard';
+import Tab from '@material-ui/core/Tab';
+import TabContext from '@material-ui/lab/TabContext';
+import TabList from '@material-ui/lab/TabList';
+import TabPanel from '@material-ui/lab/TabPanel';
+
+const useStyles = makeStyles((theme) => ({
+ card: {
+ width: '100%',
+ height: 'auto',
+ display: 'grid',
+ },
+ content: {
+ height: 'auto',
+ justifyContent: 'center',
+ display: 'flex',
+ flexDirection: 'column',
+ alignItems: 'center',
+ fontSize: 18,
+ color: theme.color.primary,
+ fontWeight: 'bold',
+ wordBreak: 'break-word',
+ },
+ actions: {
+ justifyContent: 'center',
+ },
+ scrollable: {
+ overflowY: 'auto',
+ width: '100%',
+ paddingTop: 20,
+ paddingBottom: 20,
+ },
+ root: {
+ background: theme.color.secondary,
+ height: '90%',
+ width: '100%',
+ },
+ wrapper: {
+ position: 'relative',
+ marginTop: 10,
+ },
+ buttonSuccess: {
+ backgroundColor: green[500],
+ '&:hover': {
+ backgroundColor: green[700],
+ },
+ },
+ buttonFailure: {
+ backgroundColor: red[500],
+ '&:hover': {
+ backgroundColor: red[700],
+ },
+ },
+ buttonProgress: {
+ position: 'absolute',
+ top: 'calc(50% - 10px)',
+ left: 'calc(50% - 10px)',
+ },
+ error: {
+ color: red[500],
+ marginTop: 10,
+ },
+ success: {
+ color: green[500],
+ marginTop: 20,
+ },
+ rootUserGroup: {
+ alignItems: 'center',
+ },
+ formInput: {
+ width: '90%',
+ marginTop: 10,
+ },
+ rootCardActions: {
+ justifyContent: 'center',
+ },
+ caseSelector: {
+ marginTop: 5,
+ },
+ button: {
+ marginBottom: 15,
+ },
+ dataFormsWrapper: {
+ display: 'flex',
+ flexDirection: 'column',
+ justifyContent: 'center',
+ alignItems: 'center',
+ },
+ paper: {
+ width: '100%',
+ paddingBottom: 10,
+ marginBottom: 20,
+ '&:last-child': {
+ marginBottom: 0,
+ },
+ },
+ red: {
+ color: red[500],
+ },
+ displayInlineBlock: {
+ display: 'inline-block',
+ },
+ listItemStyle: {
+ overflowWrap: 'anywhere',
+ },
+ wrapperContainer: {
+ height: '100%',
+ display: 'flex',
+ flexDirection: 'column',
+ paddingLeft: 0,
+ },
+ label: {
+ display: 'block',
+ fontSize: 12,
+ width: '100%',
+ color: theme.color.primary,
+ },
+}));
+
+export const initialState = {
+ isLoading: false,
+ isError: false,
+ error: null,
+};
+
+type State = {
+ isLoading: ?boolean,
+ isError: ?boolean,
+};
+
+type Action = {
+ type: string,
+ miniAppError: MiniAppError,
+ cookieInfo: CookieInfo[],
+};
+
+export const dataFetchReducer = (state: State, action: Action) => {
+ switch (action.type) {
+ case 'COOKIE_FETCH_INIT':
+ return {
+ isLoading: true,
+ isError: false,
+ error: null,
+ cookieInfo: null,
+ };
+ case 'COOKIE_FETCH_SUCCESS':
+ return {
+ ...state,
+ isLoading: false,
+ isError: false,
+ error: null,
+ cookieInfo: action.cookieInfo,
+ };
+ case 'COOKIE_FETCH_FAILURE':
+ return {
+ ...state,
+ isLoading: false,
+ isError: false,
+ error: null,
+ cookieInfo: null,
+ };
+
+ default:
+ throw Error('Unknown action type');
+ }
+};
+
+function CookieManagerComponent() {
+ const classes = useStyles();
+ const [state, dispatch] = useReducer(dataFetchReducer, initialState);
+ let [infoInputName, setInfoInputName] = useState();
+ let [infoInputName1, setInfoInputName1] = useState();
+
+ const clearInfoSendInput = () => {
+ setInfoInputName('');
+ setInfoInputName1('');
+ dispatch({
+ type: 'COOKIE_FETCH_INIT',
+ miniAppError: null,
+ inputError: null,
+ });
+ };
+
+ function getAllCookies() {
+ MiniApp.cookieManager
+ .getAllCookies()
+ .then((response) => {
+ dispatch({
+ type: 'COOKIE_FETCH_SUCCESS',
+ miniAppError: null,
+ cookieInfo: response,
+ });
+ console.log('getAllCookies SUCCESS: ', response);
+ })
+ .catch((error) => {
+ console.log('getAllCookies ERROR: ', error);
+ });
+ }
+
+ function getCookies() {
+ MiniApp.cookieManager
+ .getCookies([infoInputName, infoInputName1])
+ .then((response) => {
+ dispatch({
+ type: 'COOKIE_FETCH_SUCCESS',
+ miniAppError: null,
+ cookieInfo: response,
+ });
+ })
+ .catch((error) => {
+ console.log('getCookies ERROR: ', error);
+ });
+ }
+
+ function ShowCookieDetails() {
+ return (
+
+ {state.cookieInfo &&
+ state.cookieInfo.map((cookie) => (
+
+
+
+ {cookie.value && cookie.value !== '' && (
+ {'Value: ' + cookie.value}
+ )}
+
+
+ }
+ />
+
+ ))}
+
+ );
+ }
+
+ function GetAllCookiesTab() {
+ return (
+
+
+ {!state.isLoading && state.cookieInfo && (
+ {ShowCookieDetails()}
+ )}
+
+
+
+
+
+ );
+ }
+
+ function GetSpecificCookiesTab() {
+ return (
+
+
+ setInfoInputName(e.target.value)}
+ />
+ setInfoInputName1(e.target.value)}
+ />
+
+
+
+
+
+
+
+ {!state.isLoading && state.cookieInfo && (
+ {ShowCookieDetails()}
+ )}
+
+
+ );
+ }
+
+ const [tabValue, setTabValue] = React.useState('1');
+
+ const handleTabChange = (event: Event, newValue: string) => {
+ dispatch({
+ type: 'COOKIE_FETCH_INIT',
+ miniAppError: null,
+ inputError: null,
+ });
+ setTabValue(newValue);
+ };
+
+ return (
+
+
+
+
+
+
+ {GetAllCookiesTab()}
+ {GetSpecificCookiesTab()}
+
+
+ );
+}
+
+export default CookieManagerComponent;
diff --git a/js-miniapp-sample/src/pages/helper.js b/js-miniapp-sample/src/pages/helper.js
index 337b26953..024183c87 100644
--- a/js-miniapp-sample/src/pages/helper.js
+++ b/js-miniapp-sample/src/pages/helper.js
@@ -20,5 +20,7 @@ export function sendAnalytics(
elementType: elementType,
data: data,
};
- return MiniApp.miniappUtils.sendAnalytics(analyticsInfo);
+ if (MiniApp.miniappUtils) {
+ MiniApp.miniappUtils.sendAnalytics(analyticsInfo);
+ }
}
diff --git a/js-miniapp-sample/src/routes.js b/js-miniapp-sample/src/routes.js
index b51912ec4..ab47168db 100644
--- a/js-miniapp-sample/src/routes.js
+++ b/js-miniapp-sample/src/routes.js
@@ -19,9 +19,9 @@ import PhotoCamera from '@material-ui/icons/PhotoCamera';
import SecurityIcon from '@material-ui/icons/Security';
import SendIcon from '@material-ui/icons/SendSharp';
import ShareIcon from '@material-ui/icons/Share';
-import ShoppingCartIcon from '@material-ui/icons/ShoppingCart';
import StorageIcon from '@material-ui/icons/Storage';
import VpnKeyIcon from '@material-ui/icons/VpnKey';
+import ArtTrackIcon from '@material-ui/icons/ArtTrack';
import Ads from './pages/ads';
import { CloseConfirmAlert } from './pages/app-close-alert';
@@ -32,7 +32,6 @@ import EventListener from './pages/event-listener';
import FileDownload from './pages/file-download';
import FileUploader from './pages/file-upload';
import GifPage from './pages/gifs';
-import { PurchaseProductComponent } from './pages/in-app-purchase';
import Landing from './pages/landing';
import LocalStorage from './pages/local-storage';
import Media from './pages/media';
@@ -45,6 +44,7 @@ import UserDetails from './pages/user-details';
import UuidFetcher from './pages/uuid-sdk';
import WebLocation from './pages/web-location';
import WindowActions from './pages/window-actions';
+import CookieManagerComponent from './pages/cookie-manager';
//default root location when using ios
const iosHomeNavLink = { navLink: '/index.html', label: 'Home' };
@@ -103,14 +103,14 @@ const universalBridgeNavLink = {
navLink: '/universal-bridge',
label: 'Universal Bridge',
};
-const inAppPurchaseNavLink = {
- navLink: '/in-app-purchase',
- label: 'Purchase',
-};
const colorThemeNavLink = {
navLink: '/color-theme',
label: 'Color Theme',
};
+const cookieManagerNavLink = {
+ navLink: '/cookies',
+ label: 'Cookie Manager',
+};
const navLinks = [
iosHomeNavLink,
@@ -136,8 +136,8 @@ const navLinks = [
secureStorageNavLink,
closeAlertNavLink,
universalBridgeNavLink,
- inAppPurchaseNavLink,
colorThemeNavLink,
+ cookieManagerNavLink,
];
const homeItem = [
@@ -264,18 +264,18 @@ const appItems = [
navLink: universalBridgeNavLink.navLink,
element: ,
},
- {
- icon: ,
- label: inAppPurchaseNavLink.label,
- navLink: inAppPurchaseNavLink.navLink,
- element: ,
- },
{
icon: ,
label: colorThemeNavLink.label,
navLink: colorThemeNavLink.navLink,
element: ,
},
+ {
+ icon: ,
+ label: cookieManagerNavLink.label,
+ navLink: cookieManagerNavLink.navLink,
+ element: ,
+ },
];
const navItems: Object[] = homeItem.concat(
diff --git a/js-miniapp-sample/src/theme.js b/js-miniapp-sample/src/theme.js
index ff7b4fbfc..57d88b45a 100644
--- a/js-miniapp-sample/src/theme.js
+++ b/js-miniapp-sample/src/theme.js
@@ -4,12 +4,12 @@ import { grey } from '@material-ui/core/colors';
export default createTheme({
palette: {
primary: {
- main: '#bf0000',
+ main: '#000000',
},
secondary: grey,
},
color: {
- primary: '#bf0000',
+ primary: '#000000',
secondary: 'lightgrey',
},
});
diff --git a/js-miniapp-sdk/CHANGELOG.md b/js-miniapp-sdk/CHANGELOG.md
index 31ca60aba..a0939d39b 100644
--- a/js-miniapp-sdk/CHANGELOG.md
+++ b/js-miniapp-sdk/CHANGELOG.md
@@ -1,5 +1,9 @@
## CHANGELOG
+### 1.18.0 (2023-10-13)
+- **Feature:** Added new interface `getAllCookies()` to get `CookieInfo` which contains `name` and `value` of the cookie
+- **Feature:** Added new interface `getCookies(cookieNameList:)` that requests for certain cookies to host application that will get `CookieInfo` which contains `name` and `value` of the cookie
+
### 1.18.0 (2023-07-25)
- **Feature:** Added new interface `getHostAppThemeColors()` to get `HostThemeColor` which contains primary & secondary color set by the Host app
- **Feature:** Added new interface `isDarkMode()`. Interface to know if the Hostapp/Device is set to use the Dark
diff --git a/js-miniapp-sdk/README.md b/js-miniapp-sdk/README.md
index bf6e2c708..39dd67afa 100644
--- a/js-miniapp-sdk/README.md
+++ b/js-miniapp-sdk/README.md
@@ -144,6 +144,7 @@ Here is the example of manifest. You can also see [it](https://github.com/rakute
- [Host app theme colors](#host-theme-colors)
- [isDarkMode](#dark-mode)
- [Send Analytics](#send-analytics)
+- [Get Cookies](#get-cookies)
### Retrieve a unique ID
@@ -1189,6 +1190,43 @@ import MiniApp from 'js-miniapp-sdk';
MiniApp.miniappUtils.sendAnalytics(analyticsInfo);
```
+
+
+## Get Cookies from host application Available from v1.19.0
+
+You can use the following interface to get all Cookies from Host app using the following interface
+
+```javascript
+import MiniApp from 'js-miniapp-sdk';
+
+ MiniApp.cookieManager
+ .getAllCookies()
+ .then((response) => {
+ // Response will be [CookieInfo]
+ console.log(response);
+ })
+ .catch((error) => {
+ console.log(error);
+ });
+
+```
+
+You can also request the host app to provide specific cookies by sharing the list of keys as `string[]`
+
+```javascript
+import MiniApp from 'js-miniapp-sdk';
+
+ MiniApp.cookieManager
+ .getCookies(['user-token', `user-last-session`])
+ .then((response) => {
+ // Response will be [CookieInfo]
+ console.log(response);
+ })
+ .catch((error) => {
+ console.log(error);
+ });
+
+```
## Advanced Usage
diff --git a/js-miniapp-sdk/src/index.ts b/js-miniapp-sdk/src/index.ts
index 002d8b0d9..a84bf4aba 100644
--- a/js-miniapp-sdk/src/index.ts
+++ b/js-miniapp-sdk/src/index.ts
@@ -46,6 +46,7 @@ import {
MAAnalyticsActionType,
MAAnalyticsEventType,
UniversalBridgeInfo,
+ CookieInfo,
} from '../../js-miniapp-bridge/src';
import { MiniApp } from './miniapp';
@@ -104,4 +105,5 @@ export {
MAAnalyticsActionType,
MAAnalyticsEventType,
UniversalBridgeInfo,
+ CookieInfo,
};
diff --git a/js-miniapp-sdk/src/miniapp.ts b/js-miniapp-sdk/src/miniapp.ts
index 42b99807e..62fceb9d2 100644
--- a/js-miniapp-sdk/src/miniapp.ts
+++ b/js-miniapp-sdk/src/miniapp.ts
@@ -21,6 +21,7 @@ import { SecureStorageService } from './modules/secure-storage';
import { UniversalBridge } from './modules/universal-bridge';
import { MiniAppUtils } from './modules/utils';
import { Purchases } from './modules/in-app-purchase';
+import { CookieManager } from './modules/cookie-manager';
/**
* A module layer for webapps and mobile native interaction.
@@ -170,6 +171,7 @@ export class MiniApp implements MiniAppFeatures, Ad, Platform {
universalBridge = new UniversalBridge();
miniappUtils = new MiniAppUtils();
purchaseService = new Purchases();
+ cookieManager = new CookieManager();
private requestPermission(permissionType: DevicePermission): Promise {
return getBridge().requestPermission(permissionType);
diff --git a/js-miniapp-sdk/src/modules/cookie-manager.ts b/js-miniapp-sdk/src/modules/cookie-manager.ts
new file mode 100644
index 000000000..93ae5a595
--- /dev/null
+++ b/js-miniapp-sdk/src/modules/cookie-manager.ts
@@ -0,0 +1,30 @@
+import { CookieInfo } from '../../../js-miniapp-bridge/src';
+import { getBridge } from '../sdkbridge';
+
+/**
+ * Interfaces to retrieve Cookies from Host app
+ */
+export interface CookieProvider {
+ /**
+ * Fetches all cookies from host app.
+ * @returns List of Cookies with name and value details
+ */
+ getAllCookies(): Promise<[CookieInfo]>;
+
+ /**
+ * Fetches the cookies for the provided name list
+ * @returns List of Cookies with name and value details
+ */
+ getCookies(cookieNameList: string[]): Promise<[CookieInfo]>;
+}
+
+/** @internal */
+export class CookieManager implements CookieProvider {
+ getAllCookies(): Promise<[CookieInfo]> {
+ return getBridge().getAllCookies();
+ }
+
+ getCookies(cookieNameList: string[]): Promise<[CookieInfo]> {
+ return getBridge().getCookies(cookieNameList);
+ }
+}