@brightlayer-ui/react-native-template-authentication-typescript 3.0.1-alpha.0 → 4.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (40) hide show
  1. package/CHANGELOG.md +22 -9
  2. package/README.md +10 -8
  3. package/package.json +2 -2
  4. package/template/.prettierrc.js +0 -2
  5. package/template/App.tsx +37 -9
  6. package/template/Gemfile +11 -2
  7. package/template/android/app/build.gradle +15 -14
  8. package/template/android/app/src/main/AndroidManifest.xml +2 -1
  9. package/template/android/app/src/main/java/com/example/MainApplication.kt +4 -11
  10. package/template/android/app/src/main/res/drawable/rn_edit_text_material.xml +2 -1
  11. package/template/android/build.gradle +6 -6
  12. package/template/android/gradle/wrapper/gradle-wrapper.jar +0 -0
  13. package/template/android/gradle/wrapper/gradle-wrapper.properties +1 -1
  14. package/template/android/gradle.properties +1 -3
  15. package/template/android/gradlew +13 -11
  16. package/template/android/gradlew.bat +19 -12
  17. package/template/android/settings.gradle +3 -1
  18. package/template/babel.config.js +1 -1
  19. package/template/ios/Podfile +3 -27
  20. package/template/ios/Podfile.lock +2234 -662
  21. package/template/ios/example/AppDelegate.swift +48 -0
  22. package/template/ios/example/Info.plist +16 -26
  23. package/template/ios/example/PrivacyInfo.xcprivacy +37 -0
  24. package/template/ios/example.xcodeproj/project.pbxproj +26 -268
  25. package/template/ios/exampleTests/Info.plist +31 -18
  26. package/template/okta.config.js +10 -0
  27. package/template/package.json +55 -46
  28. package/template/src/components/UserMenuComponent.tsx +40 -5
  29. package/template/src/contexts/RegistrationContext.tsx +26 -0
  30. package/template/src/navigation/index.tsx +56 -61
  31. package/template/src/navigation/navigation-drawer.tsx +8 -9
  32. package/template/src/screens/ChangePassword.tsx +20 -4
  33. package/template/src/screens/OktaLogin.tsx +58 -0
  34. package/template/translations/i18n.ts +5 -5
  35. package/template/yarn.lock +8616 -0
  36. package/template/_gitignore +0 -64
  37. package/template/ios/example/AppDelegate.h +0 -6
  38. package/template/ios/example/AppDelegate.mm +0 -31
  39. package/template/ios/example/main.m +0 -10
  40. package/template/ios/exampleTests/exampleTests.m +0 -66
@@ -2,23 +2,36 @@
2
2
  <!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
3
3
  <plist version="1.0">
4
4
  <dict>
5
- <key>CFBundleDevelopmentRegion</key>
6
- <string>en</string>
7
- <key>CFBundleExecutable</key>
8
- <string>$(EXECUTABLE_NAME)</string>
9
- <key>CFBundleIdentifier</key>
10
- <string>$(PRODUCT_BUNDLE_IDENTIFIER)</string>
11
- <key>CFBundleInfoDictionaryVersion</key>
12
- <string>6.0</string>
13
- <key>CFBundleName</key>
14
- <string>$(PRODUCT_NAME)</string>
15
- <key>CFBundlePackageType</key>
16
- <string>BNDL</string>
17
- <key>CFBundleShortVersionString</key>
18
- <string>1.0</string>
19
- <key>CFBundleSignature</key>
20
- <string>????</string>
21
- <key>CFBundleVersion</key>
22
- <string>1</string>
5
+ <key>NSPrivacyAccessedAPITypes</key>
6
+ <array>
7
+ <dict>
8
+ <key>NSPrivacyAccessedAPIType</key>
9
+ <string>NSPrivacyAccessedAPICategoryFileTimestamp</string>
10
+ <key>NSPrivacyAccessedAPITypeReasons</key>
11
+ <array>
12
+ <string>C617.1</string>
13
+ </array>
14
+ </dict>
15
+ <dict>
16
+ <key>NSPrivacyAccessedAPIType</key>
17
+ <string>NSPrivacyAccessedAPICategoryUserDefaults</string>
18
+ <key>NSPrivacyAccessedAPITypeReasons</key>
19
+ <array>
20
+ <string>CA92.1</string>
21
+ </array>
22
+ </dict>
23
+ <dict>
24
+ <key>NSPrivacyAccessedAPIType</key>
25
+ <string>NSPrivacyAccessedAPICategorySystemBootTime</string>
26
+ <key>NSPrivacyAccessedAPITypeReasons</key>
27
+ <array>
28
+ <string>35F9.1</string>
29
+ </array>
30
+ </dict>
31
+ </array>
32
+ <key>NSPrivacyCollectedDataTypes</key>
33
+ <array/>
34
+ <key>NSPrivacyTracking</key>
35
+ <false/>
23
36
  </dict>
24
37
  </plist>
@@ -0,0 +1,10 @@
1
+ export default {
2
+ oidc: {
3
+ clientId: process.env.OKTA_CLIENT_ID,
4
+ redirectUri: process.env.OKTA_REDIRECT_URI,
5
+ endSessionRedirectUri: process.env.OKTA_LOGOUT_REDIRECT_URI,
6
+ discoveryUri: process.env.OKTA_ISSUER,
7
+ scopes: ['openid', 'profile', 'offline_access', 'groups'],
8
+ requireHardwareBackedKeyStore: false,
9
+ },
10
+ };
@@ -16,63 +16,72 @@
16
16
  },
17
17
  "dependencies": {
18
18
  "@brightlayer-ui/colors": "^4.0.0",
19
- "@brightlayer-ui/react-native-components": "^8.0.2",
20
- "@brightlayer-ui/react-native-themes": "^7.0.0",
21
- "@brightlayer-ui/react-native-vector-icons": "^2.2.0",
22
- "@react-native-async-storage/async-storage": "^1.22.3",
19
+ "@brightlayer-ui/icons-svg": "^1.15.0",
20
+ "@brightlayer-ui/react-native-auth-workflow": "^8.0.0",
21
+ "@brightlayer-ui/react-native-components": "^9.0.0",
22
+ "@brightlayer-ui/react-native-themes": "^8.0.0",
23
+ "@brightlayer-ui/react-native-vector-icons": "^3.0.0",
24
+ "@okta/okta-react-native": "^2.17.0",
25
+ "@react-native-async-storage/async-storage": "^2.2.0",
26
+ "@react-native-community/masked-view": "^0.1.11",
27
+ "@react-native-vector-icons/material-design-icons": "^12.2.0",
28
+ "@react-native-vector-icons/material-icons": "^12.2.0",
29
+ "@react-native/new-app-screen": "0.80.0",
23
30
  "@react-navigation/drawer": "^6.6.6",
24
31
  "@react-navigation/native": "^6.1.9",
25
32
  "@react-navigation/native-stack": "^6.9.26",
26
33
  "@react-navigation/stack": "^6.3.20",
27
- "i18next": "^23.7.16",
34
+ "date-fns": "^4.1.0",
35
+ "i18next": "^25.2.1",
28
36
  "intl-pluralrules": "^2.0.1",
29
- "react": "18.2.0",
30
- "react-i18next": "^14.0.0",
31
- "react-native": "0.73.2",
32
- "react-native-gesture-handler": "^2.14.1",
33
- "react-native-pager-view": "^6.2.3",
34
- "react-native-paper": "^5.12.1",
35
- "react-native-reanimated": "^3.6.1",
37
+ "react": "^19.1.0",
38
+ "react-i18next": "^15.5.3",
39
+ "react-native": "^0.80.0",
40
+ "react-native-dotenv": "^3.4.11",
41
+ "react-native-gesture-handler": "^2.26.0",
42
+ "react-native-keyboard-aware-scroll-view": "^0.9.5",
43
+ "react-native-modal": "^13.0.2",
44
+ "react-native-pager-view": "^6.8.1",
45
+ "react-native-paper": "^5.14.5",
46
+ "react-native-reanimated": "^3.18.0",
36
47
  "react-native-restart": "^0.0.27",
37
- "react-native-safe-area-context": "^4.8.2",
38
- "react-native-screens": "^3.29.0",
39
- "react-native-select-dropdown": "^3.4.0",
40
- "@brightlayer-ui/icons-svg": "^1.14.0",
41
- "@brightlayer-ui/react-native-auth-workflow": "^6.0.0",
42
- "@react-native-community/masked-view": "^0.1.10",
43
- "date-fns": "^2.19.0",
44
- "react-native-keyboard-aware-scroll-view": "^0.9.3",
45
- "react-native-modal": "^12.0.2",
46
- "react-native-svg": "^12.1.0",
47
- "react-native-svg-transformer": "^1.3.0",
48
- "react-native-vector-icons": "^9.2.0",
49
- "react-native-webview": "^13.8.1"
48
+ "react-native-safe-area-context": "^5.5.0",
49
+ "react-native-screens": "^4.11.1",
50
+ "react-native-select-dropdown": "^4.0.1",
51
+ "react-native-svg": "^15.12.0",
52
+ "react-native-svg-transformer": "^1.5.1",
53
+ "react-native-vector-icons": "^10.2.0",
54
+ "react-native-webview": "^13.15.0"
50
55
  },
51
56
  "devDependencies": {
52
- "@babel/core": "^7.20.0",
53
- "@babel/preset-env": "^7.20.0",
54
- "@babel/runtime": "^7.20.0",
55
- "@brightlayer-ui/eslint-config": "^3.0.1",
57
+ "@babel/core": "^7.27.7",
58
+ "@babel/preset-env": "^7.27.2",
59
+ "@babel/runtime": "^7.27.6",
60
+ "@brightlayer-ui/eslint-config": "^4.0.0",
56
61
  "@brightlayer-ui/prettier-config": "^1.0.3",
57
- "@react-native/babel-preset": "0.74.0",
58
- "@react-native/eslint-config": "0.74.0",
59
- "@react-native/metro-config": "0.74.0",
60
- "@react-native/typescript-config": "0.74.0",
61
- "@types/react": "^18.2.6",
62
+ "@react-native-community/cli": "19.0.0",
63
+ "@react-native-community/cli-platform-android": "19.0.0",
64
+ "@react-native-community/cli-platform-ios": "19.0.0",
65
+ "@react-native/babel-preset": "0.80.0",
66
+ "@react-native/eslint-config": "0.80.0",
67
+ "@react-native/metro-config": "0.80.0",
68
+ "@react-native/typescript-config": "0.80.0",
69
+ "@types/jest": "^30.0.0",
70
+ "@types/react": "^19.1.8",
62
71
  "@types/react-native-vector-icons": "^6.4.18",
63
- "@types/react-test-renderer": "^18.0.0",
64
- "@typescript-eslint/eslint-plugin": "^6.19.0",
65
- "@typescript-eslint/parser": "^6.19.0",
66
- "babel-jest": "^29.6.3",
67
- "eslint": "^8.56.0",
68
- "eslint-config-prettier": "^9.1.0",
69
- "eslint-plugin-react": "^7.33.2",
70
- "eslint-plugin-react-hooks": "^4.6.0",
71
- "jest": "^29.6.3",
72
+ "@types/react-test-renderer": "^19.1.0",
73
+ "@typescript-eslint/eslint-plugin": "^8.35.0",
74
+ "@typescript-eslint/parser": "^8.35.0",
75
+ "babel-jest": "^30.0.2",
76
+ "eslint": "^9.29.0",
77
+ "eslint-config-prettier": "^10.1.5",
78
+ "eslint-plugin-react": "^7.37.5",
79
+ "eslint-plugin-react-hooks": "^5.2.0",
80
+ "jest": "^30.0.3",
72
81
  "jest-transform-stub": "^2.0.0",
73
- "prettier": "2.8.8",
74
- "react-test-renderer": "18.2.0",
75
- "typescript": "5.0.4"
82
+ "prettier": "3.6.2",
83
+ "react-test-renderer": "19.1.0",
84
+ "typescript": "5.8.3"
76
85
  },
77
86
  "prettier": "@brightlayer-ui/prettier-config"
78
87
  }
@@ -2,7 +2,6 @@ import { InfoListItemProps, UserMenu } from '@brightlayer-ui/react-native-compon
2
2
  import React from 'react';
3
3
  import { Avatar } from 'react-native-paper';
4
4
  import * as BLUIColors from '@brightlayer-ui/colors';
5
- import { IconFamily } from '@brightlayer-ui/react-native-components/core/__types__';
6
5
  import SelectDropdown from 'react-native-select-dropdown';
7
6
  import { useTranslation } from 'react-i18next';
8
7
  import { useExtendedTheme } from '@brightlayer-ui/react-native-themes';
@@ -11,6 +10,8 @@ import AsyncStorage from '@react-native-async-storage/async-storage';
11
10
  import { LocalStorage } from '../store/local-storage';
12
11
  import { useNavigation } from '@react-navigation/native';
13
12
  import { NativeStackNavigationProp } from '@react-navigation/native-stack';
13
+ import { revokeAccessToken, clearTokens, signOut } from '@okta/okta-react-native';
14
+ import { IconFamily } from '@brightlayer-ui/react-native-components/core/__types__';
14
15
 
15
16
  const SwapIcon: IconFamily = {
16
17
  family: 'material',
@@ -53,10 +54,43 @@ export const UserMenuComponent: React.FC<UserMenuExampleProps> = (props) => {
53
54
  console.error('Error setting new language:', error);
54
55
  }
55
56
  };
56
- const logout = (): void => {
57
+ const logout = async (): Promise<void> => {
58
+ // Clear local credentials first
57
59
  LocalStorage.clearAuthCredentials();
60
+
61
+ // Try to sign out from Okta, but continue with local logout even if it fails
62
+ try {
63
+ await signOut();
64
+ } catch (signOutError) {
65
+ // eslint-disable-next-line no-console
66
+ console.error('Sign out from Okta failed:', signOutError);
67
+ }
68
+
69
+ try {
70
+ await revokeAccessToken();
71
+ } catch (revokeError) {
72
+ // eslint-disable-next-line no-console
73
+ console.error('Token revocation failed:', revokeError);
74
+ }
75
+
76
+ try {
77
+ await clearTokens();
78
+ } catch (clearError) {
79
+ // eslint-disable-next-line no-console
80
+ console.error('Clear tokens failed:', clearError);
81
+ }
82
+
83
+ // Always proceed with local logout regardless of Okta errors
58
84
  app.onUserNotAuthenticated();
59
85
  };
86
+ const handleLogout = (): void => {
87
+ logout().catch((error) => {
88
+ // Handle any errors here if needed
89
+ console.error('Logout process failed:', error);
90
+ // Even if logout fails, ensure user is logged out locally
91
+ app.onUserNotAuthenticated();
92
+ });
93
+ };
60
94
  const changePassword = (): void => {
61
95
  navigation.navigate('ChangePassword');
62
96
  };
@@ -81,8 +115,9 @@ export const UserMenuComponent: React.FC<UserMenuExampleProps> = (props) => {
81
115
  rightComponent: (
82
116
  <SelectDropdown
83
117
  defaultValue={languageOptions.find((option) => option.value === i18n.language)}
84
- // eslint-disable-next-line
85
- onSelect={(item) => handleLanguageChange(item.value)}
118
+ onSelect={(item) => {
119
+ void handleLanguageChange(item.value);
120
+ }}
86
121
  data={languageOptions}
87
122
  buttonStyle={{ backgroundColor: theme.colors.background }}
88
123
  buttonTextStyle={{ color: theme.colors.primary }}
@@ -95,7 +130,7 @@ export const UserMenuComponent: React.FC<UserMenuExampleProps> = (props) => {
95
130
  ),
96
131
  },
97
132
  { title: t('USER_MENU.CHANGE_PASSWORD'), icon: LockIcon, onPress: (): void => changePassword() },
98
- { title: t('USER_MENU.LOG_OUT'), icon: ExitToAppIcon, onPress: (): void => logout() },
133
+ { title: t('USER_MENU.LOG_OUT'), icon: ExitToAppIcon, onPress: handleLogout },
99
134
  ];
100
135
 
101
136
  return (
@@ -0,0 +1,26 @@
1
+ import React, { createContext, useState, useContext, ReactNode } from 'react';
2
+
3
+ type RegistrationContextType = {
4
+ isRequestingCode: number;
5
+ setIsRequestingCode: (value: number) => void;
6
+ };
7
+
8
+ const RegistrationContext = createContext<RegistrationContextType | undefined>(undefined);
9
+
10
+ export const RegistrationProvider: React.FC<{ children: ReactNode }> = ({ children }) => {
11
+ const [isRequestingCode, setIsRequestingCode] = useState(0);
12
+
13
+ return (
14
+ <RegistrationContext.Provider value={{ isRequestingCode, setIsRequestingCode }}>
15
+ {children}
16
+ </RegistrationContext.Provider>
17
+ );
18
+ };
19
+
20
+ export const useRegistrationContext = (): RegistrationContextType => {
21
+ const context = useContext(RegistrationContext);
22
+ if (!context) {
23
+ throw new Error('useRegistrationContext must be used within a RegistrationProvider');
24
+ }
25
+ return context;
26
+ };
@@ -1,4 +1,4 @@
1
- import React, { ReactNode } from 'react';
1
+ import React, { ReactNode, useCallback } from 'react';
2
2
  import { NavigationContainer, createNavigationContainerRef, useNavigation } from '@react-navigation/native';
3
3
  import { useApp } from '../contexts/AppContextProvider';
4
4
  import {
@@ -16,7 +16,6 @@ import { Dimensions, View } from 'react-native';
16
16
  import { ProjectAuthUIActions } from '../actions/AuthUIActions';
17
17
  import { ProjectRegistrationUIActions } from '../actions/RegistrationUIActions';
18
18
 
19
- import { Login } from '../screens/Login';
20
19
  import { ChangePassword } from '../screens/ChangePassword';
21
20
  import { Registration } from '../screens/Registration';
22
21
  import { RegistrationInvite } from '../screens/RegistrationInvite';
@@ -25,9 +24,11 @@ import { Homepage } from '../screens/Homepage';
25
24
  import Locations from '../screens/Locations';
26
25
  import Dashboard from '../screens/Dashboard';
27
26
  import { NativeStackNavigationProp, createNativeStackNavigator } from '@react-navigation/native-stack';
27
+ import { OktaLogin } from '../screens/OktaLogin';
28
28
 
29
29
  const Stack = createNativeStackNavigator();
30
30
  const Drawer = createDrawerNavigator();
31
+ const LoginStack = createNativeStackNavigator();
31
32
  const navigationRef = createNavigationContainerRef();
32
33
 
33
34
  export type RootStackParamList = {
@@ -48,6 +49,57 @@ const AuthRouter = (): any => {
48
49
  const { email, rememberMe } = app.loginData;
49
50
  const navigation = useNavigation<NativeStackNavigationProp<any>>();
50
51
 
52
+ const LoginNavigatorComponent = useCallback(
53
+ () => (
54
+ <LoginStack.Navigator screenOptions={{ headerShown: false }}>
55
+ <LoginStack.Screen name="Login" component={OktaLogin} />
56
+ <LoginStack.Screen name="ForgotPassword" component={ForgotPasswordScreen} />
57
+ <LoginStack.Screen name="ResetPassword" component={ResetPasswordScreen} />
58
+ <LoginStack.Screen name="ContactSupport" component={ContactSupportScreen} />
59
+ </LoginStack.Navigator>
60
+ ),
61
+ []
62
+ );
63
+
64
+ const DrawerNavigatorComponent = (): any => (
65
+ <Drawer.Navigator
66
+ screenOptions={{
67
+ headerShown: false,
68
+ drawerType: 'front',
69
+ drawerStyle: { backgroundColor: 'transparent' },
70
+ }}
71
+ drawerContent={(props: any): ReactNode => <CustomDrawerContent {...props} />}
72
+ backBehavior="history"
73
+ initialRouteName="LoginScreen"
74
+ >
75
+ {!app.isAuthenticated && <Drawer.Screen name="LoginScreen" component={LoginNavigatorComponent} />}
76
+
77
+ {app.isAuthenticated && (
78
+ <>
79
+ <Drawer.Screen name="Homepage" component={Homepage} />
80
+ <Drawer.Screen name="Dashboard" component={Dashboard} />
81
+ <Drawer.Screen name="Locations" component={Locations} />
82
+
83
+ <Drawer.Screen
84
+ name="ContactSupport"
85
+ options={{
86
+ swipeEnabled: false,
87
+ }}
88
+ component={ContactSupportScreen}
89
+ />
90
+
91
+ <Drawer.Screen
92
+ name="ChangePassword"
93
+ options={{
94
+ swipeEnabled: false,
95
+ }}
96
+ component={ChangePassword}
97
+ />
98
+ </>
99
+ )}
100
+ </Drawer.Navigator>
101
+ );
102
+
51
103
  return (
52
104
  <>
53
105
  <AuthContextProvider
@@ -79,65 +131,7 @@ const AuthRouter = (): any => {
79
131
  }}
80
132
  rememberMeDetails={{ email: rememberMe ? email : '', rememberMe: rememberMe }}
81
133
  >
82
- <Drawer.Navigator
83
- screenOptions={{
84
- headerShown: false,
85
- drawerType: 'front',
86
- drawerStyle: { backgroundColor: 'transparent' },
87
- }}
88
- drawerContent={(props: any): ReactNode => <CustomDrawerContent {...props} />}
89
- backBehavior="history"
90
- initialRouteName="Login"
91
- >
92
- {!app.isAuthenticated && (
93
- <Drawer.Screen
94
- options={{
95
- swipeEnabled: false,
96
- }}
97
- name="Login"
98
- component={Login}
99
- />
100
- )}
101
- {!app.isAuthenticated && (
102
- <Drawer.Screen
103
- options={{
104
- swipeEnabled: false,
105
- }}
106
- name="ForgotPassword"
107
- component={ForgotPasswordScreen}
108
- />
109
- )}
110
- {!app.isAuthenticated && (
111
- <Drawer.Screen
112
- options={{
113
- swipeEnabled: false,
114
- }}
115
- name="ResetPassword"
116
- component={ResetPasswordScreen}
117
- />
118
- )}
119
-
120
- {app.isAuthenticated && <Drawer.Screen name="Homepage" component={Homepage} />}
121
- {app.isAuthenticated && <Drawer.Screen name="Dashboard" component={Dashboard} />}
122
- {app.isAuthenticated && <Drawer.Screen name="Locations" component={Locations} />}
123
-
124
- <Drawer.Screen
125
- name="ContactSupport"
126
- options={{
127
- swipeEnabled: false,
128
- }}
129
- component={ContactSupportScreen}
130
- />
131
- {app.isAuthenticated && (
132
- <Drawer.Screen
133
- name="ChangePassword"
134
- options={{
135
- swipeEnabled: false,
136
- }}
137
- component={ChangePassword}
138
- />
139
- )}
140
- </Drawer.Navigator>
134
+ {DrawerNavigatorComponent()}
141
135
  </AuthContextProvider>
142
136
  </>
143
137
  );
@@ -201,6 +195,7 @@ const RegistrationRouter = (): any => {
201
195
  </>
202
196
  );
203
197
  };
198
+
204
199
  export const MainRouter = (): any => {
205
200
  const { height, width } = Dimensions.get('screen');
206
201
  return (
@@ -1,24 +1,22 @@
1
- import { Drawer, DrawerBody, DrawerHeader, DrawerNavGroup } from '@brightlayer-ui/react-native-components';
2
- import React, { useState, useCallback, useEffect } from 'react';
1
+ import { Drawer, DrawerBody, DrawerHeader, DrawerNavGroup, NavItem } from '@brightlayer-ui/react-native-components';
2
+ import React, { useState, useCallback, useEffect, useMemo } from 'react';
3
+ import { StackNavigationProp } from '@react-navigation/stack';
3
4
  import { RootStackParamList } from './index';
4
5
  import { DrawerActions } from '@react-navigation/native';
5
6
  import { useTranslation } from 'react-i18next';
6
7
  import { IconFamily } from '@brightlayer-ui/react-native-components/core/__types__';
7
- import { NativeStackNavigationProp } from '@react-navigation/native-stack';
8
8
 
9
9
  export type NavDrawerProps = {
10
- navigation: NativeStackNavigationProp<RootStackParamList, 'NavigationDrawer'>;
10
+ navigation: StackNavigationProp<RootStackParamList, 'NavigationDrawer'>;
11
11
  };
12
12
 
13
13
  export const NavigationDrawer: React.FC<NavDrawerProps> = ({ navigation }) => {
14
14
  const [selected, setSelected] = useState('Home');
15
15
  const { t } = useTranslation();
16
16
  const navigationState = navigation.getState();
17
-
18
17
  const Homepage: IconFamily = { family: 'material', name: 'home', direction: 'ltr' };
19
18
  const Dashboard: IconFamily = { family: 'material', name: 'dashboard', direction: 'ltr' };
20
19
  const Notifications: IconFamily = { family: 'material', name: 'notifications', direction: 'ltr' };
21
-
22
20
  const selectItem = useCallback(
23
21
  (id: any) => {
24
22
  navigation.navigate(id);
@@ -27,8 +25,8 @@ export const NavigationDrawer: React.FC<NavDrawerProps> = ({ navigation }) => {
27
25
  [navigation]
28
26
  );
29
27
 
30
- const navGroupItems = React.useMemo(
31
- () => [
28
+ const navGroupItems = useMemo(
29
+ (): NavItem[] => [
32
30
  {
33
31
  title: `${t('TOOLBAR_MENU.HOME_PAGE')}`,
34
32
  itemID: 'Homepage',
@@ -45,7 +43,8 @@ export const NavigationDrawer: React.FC<NavDrawerProps> = ({ navigation }) => {
45
43
  icon: Notifications,
46
44
  },
47
45
  ],
48
- [t]
46
+
47
+ []
49
48
  );
50
49
 
51
50
  useEffect(() => {
@@ -2,14 +2,30 @@ import React from 'react';
2
2
  import { ChangePasswordScreen } from '@brightlayer-ui/react-native-auth-workflow';
3
3
  import { useApp } from '../contexts/AppContextProvider';
4
4
  import { LocalStorage } from '../store/local-storage';
5
+ import { clearTokens, revokeAccessToken } from '@okta/okta-react-native';
5
6
 
6
- export const ChangePassword = (): JSX.Element => {
7
+ export const ChangePassword = (): React.JSX.Element => {
7
8
  const app = useApp();
8
- const logOut = (): void => {
9
+ const logOut = async (): Promise<void> => {
9
10
  LocalStorage.clearAuthCredentials();
11
+ try {
12
+ await revokeAccessToken();
13
+ await clearTokens();
14
+ } catch (_error) {
15
+ // eslint-disable-next-line no-console
16
+ console.log(_error as Error);
17
+ }
10
18
  app.onUserNotAuthenticated();
11
- app.setLoginData({ email: '', rememberMe: false });
19
+ // below line is not need for okta workflow
20
+ // app.setLoginData({ email: '', rememberMe: false });
12
21
  };
13
22
 
14
- return <ChangePasswordScreen onFinish={(): void => logOut()} showSuccessScreen />;
23
+ const handleLogout = (): void => {
24
+ logOut().catch((error) => {
25
+ // Handle any errors here if needed
26
+ console.error(error);
27
+ });
28
+ };
29
+
30
+ return <ChangePasswordScreen onFinish={handleLogout} showSuccessScreen />;
15
31
  };
@@ -0,0 +1,58 @@
1
+ import React from 'react';
2
+ import { Image } from 'react-native';
3
+ import {
4
+ OktaAuthContextProvider,
5
+ OktaLoginScreenProps,
6
+ OktaRedirectLoginScreen,
7
+ } from '@brightlayer-ui/react-native-auth-workflow';
8
+ import { useApp } from '../contexts/AppContextProvider';
9
+ import { useNavigation } from '@react-navigation/native';
10
+ import { NativeStackNavigationProp } from '@react-navigation/native-stack';
11
+ import i18nAppInstance from '../../translations/i18n';
12
+ import oktaConfig from '../../okta.config';
13
+
14
+ export const OktaLogin: React.FC<React.PropsWithChildren<OktaLoginScreenProps>> = () => {
15
+ const app = useApp();
16
+ const navigation = useNavigation<NativeStackNavigationProp<any>>();
17
+
18
+ return (
19
+ <OktaAuthContextProvider
20
+ language={app.language}
21
+ i18n={i18nAppInstance}
22
+ navigate={(destination: -1 | string) => {
23
+ if (typeof destination === 'string') {
24
+ switch (destination) {
25
+ case 'SelfRegister':
26
+ case 'RegisterInvite':
27
+ navigation.navigate('RegistrationProviderExample', { screen: destination });
28
+ break;
29
+ default:
30
+ navigation.navigate(destination);
31
+ break;
32
+ }
33
+ } else if (destination === -1) {
34
+ navigation.goBack();
35
+ }
36
+ }}
37
+ routeConfig={{
38
+ LOGIN: 'Login',
39
+ FORGOT_PASSWORD: 'ForgotPassword',
40
+ RESET_PASSWORD: 'ResetPassword',
41
+ REGISTER_INVITE: 'RegisterInvite',
42
+ REGISTER_SELF: 'SelfRegister',
43
+ SUPPORT: 'ContactSupport',
44
+ }}
45
+ >
46
+ <OktaRedirectLoginScreen
47
+ projectImage={
48
+ <Image
49
+ style={{ width: '100%' }}
50
+ resizeMode="contain"
51
+ source={require('../assets/images/eaton_stacked_logo.png')}
52
+ />
53
+ }
54
+ oktaConfigObject={oktaConfig.oidc}
55
+ />
56
+ </OktaAuthContextProvider>
57
+ );
58
+ };
@@ -1,12 +1,12 @@
1
1
  import i18next from 'i18next';
2
2
  import { AppDictionaries } from './dictionary';
3
3
  import { initReactI18next } from 'react-i18next';
4
- import { NativeModules, Platform } from 'react-native';
4
+ // import { NativeModules, Platform } from 'react-native';
5
5
 
6
- const locale =
7
- Platform.OS === 'ios'
8
- ? NativeModules.SettingsManager.settings.AppleLocale
9
- : NativeModules.I18nManager.localeIdentifier;
6
+ const locale = 'en';
7
+ // Platform.OS === 'ios'
8
+ // ? NativeModules.SettingsManager.settings.AppleLocale
9
+ // : NativeModules.I18nManager.localeIdentifier;
10
10
  void i18next
11
11
  .use(initReactI18next) // passes i18n down to react-i18next
12
12
  .init(