mirror of
https://github.com/urosran/cally.git
synced 2025-11-26 08:24:55 +00:00
Merge branch 'refs/heads/dev'
# Conflicts: # app.json # ios/cally/Info.plist
This commit is contained in:
@ -14,9 +14,14 @@
|
|||||||
</intent>
|
</intent>
|
||||||
</queries>
|
</queries>
|
||||||
<application android:name=".MainApplication" android:label="@string/app_name" android:icon="@mipmap/ic_launcher" android:roundIcon="@mipmap/ic_launcher_round" android:allowBackup="true" android:theme="@style/AppTheme">
|
<application android:name=".MainApplication" android:label="@string/app_name" android:icon="@mipmap/ic_launcher" android:roundIcon="@mipmap/ic_launcher_round" android:allowBackup="true" android:theme="@style/AppTheme">
|
||||||
<meta-data android:name="expo.modules.updates.ENABLED" android:value="false"/>
|
<meta-data android:name="com.google.firebase.messaging.default_notification_channel_id" android:value="default"/>
|
||||||
|
<meta-data android:name="com.google.firebase.messaging.default_notification_color" android:resource="@color/notification_icon_color"/>
|
||||||
|
<meta-data android:name="expo.modules.notifications.default_notification_color" android:resource="@color/notification_icon_color"/>
|
||||||
|
<meta-data android:name="expo.modules.updates.ENABLED" android:value="true"/>
|
||||||
<meta-data android:name="expo.modules.updates.EXPO_UPDATES_CHECK_ON_LAUNCH" android:value="ALWAYS"/>
|
<meta-data android:name="expo.modules.updates.EXPO_UPDATES_CHECK_ON_LAUNCH" android:value="ALWAYS"/>
|
||||||
<meta-data android:name="expo.modules.updates.EXPO_UPDATES_LAUNCH_WAIT_MS" android:value="0"/>
|
<meta-data android:name="expo.modules.updates.EXPO_UPDATES_LAUNCH_WAIT_MS" android:value="0"/>
|
||||||
|
<meta-data android:name="expo.modules.updates.EXPO_UPDATE_URL" android:value="https://u.expo.dev/bdb8c57b-25bb-4d36-b3b8-5b09c5092f52"/>
|
||||||
|
<meta-data android:name="expo.modules.updates.EXPO_RUNTIME_VERSION" android:value="@string/expo_runtime_version"/>
|
||||||
<activity android:name=".MainActivity" android:configChanges="keyboard|keyboardHidden|orientation|screenSize|screenLayout|uiMode" android:launchMode="singleTask" android:windowSoftInputMode="adjustResize" android:theme="@style/Theme.App.SplashScreen" android:exported="true" android:screenOrientation="portrait">
|
<activity android:name=".MainActivity" android:configChanges="keyboard|keyboardHidden|orientation|screenSize|screenLayout|uiMode" android:launchMode="singleTask" android:windowSoftInputMode="adjustResize" android:theme="@style/Theme.App.SplashScreen" android:exported="true" android:screenOrientation="portrait">
|
||||||
<intent-filter>
|
<intent-filter>
|
||||||
<action android:name="android.intent.action.MAIN"/>
|
<action android:name="android.intent.action.MAIN"/>
|
||||||
|
|||||||
@ -3,4 +3,5 @@
|
|||||||
<color name="iconBackground">#ffffff</color>
|
<color name="iconBackground">#ffffff</color>
|
||||||
<color name="colorPrimary">#023c69</color>
|
<color name="colorPrimary">#023c69</color>
|
||||||
<color name="colorPrimaryDark">#ffffff</color>
|
<color name="colorPrimaryDark">#ffffff</color>
|
||||||
|
<color name="notification_icon_color">#ffffff</color>
|
||||||
</resources>
|
</resources>
|
||||||
@ -3,4 +3,5 @@
|
|||||||
<string name="expo_splash_screen_resize_mode" translatable="false">contain</string>
|
<string name="expo_splash_screen_resize_mode" translatable="false">contain</string>
|
||||||
<string name="expo_splash_screen_status_bar_translucent" translatable="false">false</string>
|
<string name="expo_splash_screen_status_bar_translucent" translatable="false">false</string>
|
||||||
<string name="expo_system_ui_user_interface_style" translatable="false">light</string>
|
<string name="expo_system_ui_user_interface_style" translatable="false">light</string>
|
||||||
|
<string name="expo_runtime_version">1.0.0</string>
|
||||||
</resources>
|
</resources>
|
||||||
15
app.json
15
app.json
@ -25,6 +25,10 @@
|
|||||||
},
|
},
|
||||||
"package": "com.cally.app",
|
"package": "com.cally.app",
|
||||||
"googleServicesFile": "./android/app/google-services.json",
|
"googleServicesFile": "./android/app/google-services.json",
|
||||||
|
"permissions": [
|
||||||
|
"android.permission.CAMERA",
|
||||||
|
"android.permission.RECORD_AUDIO"
|
||||||
|
]
|
||||||
},
|
},
|
||||||
"web": {
|
"web": {
|
||||||
"bundler": "metro",
|
"bundler": "metro",
|
||||||
@ -51,6 +55,13 @@
|
|||||||
"microphonePermission": "Allow $(PRODUCT_NAME) to access your microphone",
|
"microphonePermission": "Allow $(PRODUCT_NAME) to access your microphone",
|
||||||
"recordAudioAndroid": true
|
"recordAudioAndroid": true
|
||||||
}
|
}
|
||||||
|
],
|
||||||
|
[
|
||||||
|
"expo-notifications",
|
||||||
|
{
|
||||||
|
"color": "#ffffff",
|
||||||
|
"defaultChannel": "default"
|
||||||
|
}
|
||||||
]
|
]
|
||||||
],
|
],
|
||||||
"experiments": {
|
"experiments": {
|
||||||
@ -63,6 +74,10 @@
|
|||||||
"eas": {
|
"eas": {
|
||||||
"projectId": "bdb8c57b-25bb-4d36-b3b8-5b09c5092f52"
|
"projectId": "bdb8c57b-25bb-4d36-b3b8-5b09c5092f52"
|
||||||
}
|
}
|
||||||
|
},
|
||||||
|
"runtimeVersion": "1.0.0",
|
||||||
|
"updates": {
|
||||||
|
"url": "https://u.expo.dev/bdb8c57b-25bb-4d36-b3b8-5b09c5092f52"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -18,6 +18,11 @@ import {
|
|||||||
} from "@expo/vector-icons";
|
} from "@expo/vector-icons";
|
||||||
import MenuIcon from "@/assets/svgs/MenuIcon";
|
import MenuIcon from "@/assets/svgs/MenuIcon";
|
||||||
import { router } from "expo-router";
|
import { router } from "expo-router";
|
||||||
|
import NavGroceryIcon from "@/assets/svgs/NavGroceryIcon";
|
||||||
|
import NavToDosIcon from "@/assets/svgs/NavToDosIcon";
|
||||||
|
import NavBrainDumpIcon from "@/assets/svgs/NavBrainDumpIcon";
|
||||||
|
import NavCalendarIcon from "@/assets/svgs/NavCalendarIcon";
|
||||||
|
import NavSettingsIcon from "@/assets/svgs/NavSettingsIcon";
|
||||||
|
|
||||||
export default function TabLayout() {
|
export default function TabLayout() {
|
||||||
const { mutateAsync: signOut } = useSignOut();
|
const { mutateAsync: signOut } = useSignOut();
|
||||||
@ -38,7 +43,7 @@ export default function TabLayout() {
|
|||||||
return (
|
return (
|
||||||
<DrawerContentScrollView {...props} style={{ height: "100%" }}>
|
<DrawerContentScrollView {...props} style={{ height: "100%" }}>
|
||||||
<View centerH centerV margin-30>
|
<View centerH centerV margin-30>
|
||||||
<Text text50>Welcome to Kali</Text>
|
<Text text50>Welcome to Cally</Text>
|
||||||
</View>
|
</View>
|
||||||
<View
|
<View
|
||||||
style={{
|
style={{
|
||||||
@ -52,26 +57,14 @@ export default function TabLayout() {
|
|||||||
color="rgb(7, 184, 199)"
|
color="rgb(7, 184, 199)"
|
||||||
bgColor={"rgb(231, 248, 250)"}
|
bgColor={"rgb(231, 248, 250)"}
|
||||||
pressFunc={() => props.navigation.navigate("calendar")}
|
pressFunc={() => props.navigation.navigate("calendar")}
|
||||||
icon={
|
icon={<NavCalendarIcon />}
|
||||||
<Feather
|
|
||||||
name="calendar"
|
|
||||||
size={30}
|
|
||||||
color="rgb(7, 184, 199)"
|
|
||||||
/>
|
|
||||||
}
|
|
||||||
/>
|
/>
|
||||||
<DrawerButton
|
<DrawerButton
|
||||||
color="#50be0c"
|
color="#50be0c"
|
||||||
title={"Groceries"}
|
title={"Groceries"}
|
||||||
bgColor={"#eef9e7"}
|
bgColor={"#eef9e7"}
|
||||||
pressFunc={() => props.navigation.navigate("grocery")}
|
pressFunc={() => props.navigation.navigate("grocery")}
|
||||||
icon={
|
icon={<NavGroceryIcon />}
|
||||||
<MaterialCommunityIcons
|
|
||||||
name="food-apple-outline"
|
|
||||||
size={30}
|
|
||||||
color="#50be0c"
|
|
||||||
/>
|
|
||||||
}
|
|
||||||
/>
|
/>
|
||||||
</View>
|
</View>
|
||||||
<View style={{ flex: 1 }}>
|
<View style={{ flex: 1 }}>
|
||||||
@ -90,19 +83,17 @@ export default function TabLayout() {
|
|||||||
/>*/}
|
/>*/}
|
||||||
<DrawerButton
|
<DrawerButton
|
||||||
color="#8005eb"
|
color="#8005eb"
|
||||||
title={"To Dos"}
|
title={"To Do's"}
|
||||||
bgColor={"#f3e6fd"}
|
bgColor={"#f3e6fd"}
|
||||||
pressFunc={() => props.navigation.navigate("todos")}
|
pressFunc={() => props.navigation.navigate("todos")}
|
||||||
icon={
|
icon={<NavToDosIcon />}
|
||||||
<AntDesign name="checkcircleo" size={30} color="#8005eb" />
|
|
||||||
}
|
|
||||||
/>
|
/>
|
||||||
<DrawerButton
|
<DrawerButton
|
||||||
color="#e0ca03"
|
color="#e0ca03"
|
||||||
title={"Brain Dump"}
|
title={"Brain Dump"}
|
||||||
bgColor={"#fffacb"}
|
bgColor={"#fffacb"}
|
||||||
pressFunc={() => props.navigation.navigate("brain_dump")}
|
pressFunc={() => props.navigation.navigate("brain_dump")}
|
||||||
icon={<AntDesign name="book" size={30} color="#e0ca03" />}
|
icon={<NavBrainDumpIcon />}
|
||||||
/>
|
/>
|
||||||
{/*<DrawerItem label="Logout" onPress={() => signOut()} />*/}
|
{/*<DrawerItem label="Logout" onPress={() => signOut()} />*/}
|
||||||
</View>
|
</View>
|
||||||
@ -120,7 +111,7 @@ export default function TabLayout() {
|
|||||||
centerV
|
centerV
|
||||||
centerH
|
centerH
|
||||||
>
|
>
|
||||||
<Octicons name="gear" size={30} color="#6c645b" />
|
<NavSettingsIcon />
|
||||||
</View>
|
</View>
|
||||||
)}
|
)}
|
||||||
backgroundColor="white"
|
backgroundColor="white"
|
||||||
@ -142,7 +133,7 @@ export default function TabLayout() {
|
|||||||
borderWidth: 2,
|
borderWidth: 2,
|
||||||
borderColor: "#fd1775",
|
borderColor: "#fd1775",
|
||||||
}}
|
}}
|
||||||
label="Sign out of Kali"
|
label="Sign out of Cally"
|
||||||
color="#fd1775"
|
color="#fd1775"
|
||||||
onPress={() => signOut()}
|
onPress={() => signOut()}
|
||||||
/>
|
/>
|
||||||
@ -197,7 +188,7 @@ export default function TabLayout() {
|
|||||||
name="todos"
|
name="todos"
|
||||||
options={{
|
options={{
|
||||||
drawerLabel: "To-Do",
|
drawerLabel: "To-Do",
|
||||||
title: "To-Do",
|
title: "To-Do's",
|
||||||
}}
|
}}
|
||||||
/>
|
/>
|
||||||
</Drawer>
|
</Drawer>
|
||||||
|
|||||||
@ -1,30 +1,16 @@
|
|||||||
import {DarkTheme, DefaultTheme, ThemeProvider} from '@react-navigation/native';
|
import {DefaultTheme, ThemeProvider} from '@react-navigation/native';
|
||||||
import {useFonts} from 'expo-font';
|
import {useFonts} from 'expo-font';
|
||||||
import {Stack} from 'expo-router';
|
import {Stack} from 'expo-router';
|
||||||
import * as SplashScreen from 'expo-splash-screen';
|
import * as SplashScreen from 'expo-splash-screen';
|
||||||
import {useEffect} from 'react';
|
import {useEffect} from 'react';
|
||||||
import 'react-native-reanimated';
|
import 'react-native-reanimated';
|
||||||
|
|
||||||
import {useColorScheme} from '@/hooks/useColorScheme';
|
|
||||||
import {AuthContextProvider} from "@/contexts/AuthContext";
|
import {AuthContextProvider} from "@/contexts/AuthContext";
|
||||||
|
|
||||||
import functions from "@react-native-firebase/functions";
|
|
||||||
import firestore from "@react-native-firebase/firestore";
|
|
||||||
import auth from "@react-native-firebase/auth";
|
|
||||||
import {QueryClient, QueryClientProvider} from "react-query";
|
import {QueryClient, QueryClientProvider} from "react-query";
|
||||||
import {Toast} from "react-native-ui-lib";
|
import {Toast} from "react-native-ui-lib";
|
||||||
|
|
||||||
// Prevent the splash screen from auto-hiding before asset loading is complete.
|
|
||||||
SplashScreen.preventAutoHideAsync();
|
SplashScreen.preventAutoHideAsync();
|
||||||
|
|
||||||
const queryClient = new QueryClient()
|
const queryClient = new QueryClient();
|
||||||
|
|
||||||
|
|
||||||
if (__DEV__) {
|
|
||||||
functions().useEmulator('localhost', 5001);
|
|
||||||
firestore().useEmulator("localhost", 5471);
|
|
||||||
auth().useEmulator("http://localhost:9099");
|
|
||||||
}
|
|
||||||
|
|
||||||
export default function RootLayout() {
|
export default function RootLayout() {
|
||||||
const [loaded] = useFonts({
|
const [loaded] = useFonts({
|
||||||
|
|||||||
19
assets/svgs/CalendarIcon.tsx
Normal file
19
assets/svgs/CalendarIcon.tsx
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
import * as React from "react"
|
||||||
|
import Svg, { Path, SvgProps } from "react-native-svg"
|
||||||
|
const CalendarIcon: React.FC<SvgProps> = (props) => (
|
||||||
|
<Svg
|
||||||
|
width={props.width || 21}
|
||||||
|
height={props.height || 21}
|
||||||
|
fill="none"
|
||||||
|
{...props}
|
||||||
|
>
|
||||||
|
<Path
|
||||||
|
stroke={props.color || "#FD1775"}
|
||||||
|
strokeLinecap="round"
|
||||||
|
strokeLinejoin="round"
|
||||||
|
strokeWidth={1.455}
|
||||||
|
d="M1.413 7.359h18.294m-4.065 4.067-10.164-.002m3.388 4.066H5.478m0-14.23v2.033m10.164-2.032v2.032M4.665 19.555h11.79c1.138 0 1.708 0 2.142-.222.383-.194.694-.505.889-.888.221-.435.221-1.004.221-2.142V6.546c0-1.139 0-1.708-.221-2.143a2.032 2.032 0 0 0-.889-.888c-.434-.222-1.004-.222-2.142-.222H4.665c-1.138 0-1.707 0-2.142.222a2.033 2.033 0 0 0-.888.888c-.222.435-.222 1.004-.222 2.143v9.757c0 1.138 0 1.707.222 2.142.195.383.505.694.888.888.435.222 1.004.222 2.142.222Z"
|
||||||
|
/>
|
||||||
|
</Svg>
|
||||||
|
)
|
||||||
|
export default CalendarIcon
|
||||||
36
assets/svgs/NavBrainDumpIcon.tsx
Normal file
36
assets/svgs/NavBrainDumpIcon.tsx
Normal file
@ -0,0 +1,36 @@
|
|||||||
|
import * as React from "react"
|
||||||
|
import Svg, { Path, SvgProps } from "react-native-svg"
|
||||||
|
const NavBrainDumpIcon: React.FC<SvgProps> = (props) => (
|
||||||
|
<Svg
|
||||||
|
width={22}
|
||||||
|
height={28}
|
||||||
|
fill="none"
|
||||||
|
{...props}
|
||||||
|
>
|
||||||
|
<Path
|
||||||
|
stroke="#F90"
|
||||||
|
strokeLinecap="round"
|
||||||
|
strokeLinejoin="round"
|
||||||
|
strokeMiterlimit={10}
|
||||||
|
strokeWidth={1.509}
|
||||||
|
d="M21.1.859H3.994C2.284.859.976 2.167.976 3.877c0 1.71 1.308 3.019 3.018 3.019H21.1V27.02"
|
||||||
|
/>
|
||||||
|
<Path
|
||||||
|
stroke="#F90"
|
||||||
|
strokeLinecap="round"
|
||||||
|
strokeLinejoin="round"
|
||||||
|
strokeMiterlimit={10}
|
||||||
|
strokeWidth={1.509}
|
||||||
|
d="M21.1 27.021H3.994c-1.71 0-3.018-1.308-3.018-3.018V3.878M21.097 3.878H3.991"
|
||||||
|
/>
|
||||||
|
<Path
|
||||||
|
stroke="#F90"
|
||||||
|
strokeLinecap="round"
|
||||||
|
strokeLinejoin="round"
|
||||||
|
strokeMiterlimit={10}
|
||||||
|
strokeWidth={1.509}
|
||||||
|
d="M6.007 6.897v12.075l3.019-1.006 3.018 1.006V6.897"
|
||||||
|
/>
|
||||||
|
</Svg>
|
||||||
|
)
|
||||||
|
export default NavBrainDumpIcon
|
||||||
19
assets/svgs/NavCalendarIcon.tsx
Normal file
19
assets/svgs/NavCalendarIcon.tsx
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
import * as React from "react"
|
||||||
|
import Svg, { Path, SvgProps } from "react-native-svg"
|
||||||
|
const NavCalendarIcon: React.FC<SvgProps> = (props) => (
|
||||||
|
<Svg
|
||||||
|
width={28}
|
||||||
|
height={28}
|
||||||
|
fill="none"
|
||||||
|
{...props}
|
||||||
|
>
|
||||||
|
<Path
|
||||||
|
stroke="#07B8C7"
|
||||||
|
strokeLinecap="round"
|
||||||
|
strokeLinejoin="round"
|
||||||
|
strokeWidth={2.124}
|
||||||
|
d="M1.825 10.075h25.043m-5.565 5.567L7.39 15.64m4.638 5.566H7.39m0-19.478V4.51m13.913-2.782V4.51M6.277 26.77h16.139c1.558 0 2.337 0 2.933-.303.523-.267.949-.692 1.216-1.216.303-.595.303-1.375.303-2.933V8.962c0-1.558 0-2.337-.303-2.933a2.782 2.782 0 0 0-1.216-1.216c-.596-.303-1.375-.303-2.933-.303H6.277c-1.558 0-2.337 0-2.933.303-.523.267-.949.693-1.216 1.216-.303.596-.303 1.375-.303 2.933v13.356c0 1.558 0 2.338.303 2.933.267.523.693.95 1.216 1.216.596.303 1.375.303 2.933.303Z"
|
||||||
|
/>
|
||||||
|
</Svg>
|
||||||
|
)
|
||||||
|
export default NavCalendarIcon
|
||||||
20
assets/svgs/NavGroceryIcon.tsx
Normal file
20
assets/svgs/NavGroceryIcon.tsx
Normal file
@ -0,0 +1,20 @@
|
|||||||
|
import * as React from "react";
|
||||||
|
import Svg, { Path, SvgProps } from "react-native-svg";
|
||||||
|
const NavGroceryIcon: React.FC<SvgProps> = (props) => (
|
||||||
|
<Svg
|
||||||
|
width={29}
|
||||||
|
height={32}
|
||||||
|
fill="none"
|
||||||
|
{...props}
|
||||||
|
>
|
||||||
|
<Path
|
||||||
|
fill="#50BE0C"
|
||||||
|
d="M27.8 12c-.888-2.27-2.662-4.14-4.983-4.956-2.518-.883-5.143-.382-7.636.307-.047-1.362.068-2.728.262-4.076.11-.761.634-2.335-.668-2.389-1.081-.045-1.084 1.402-1.19 2.14-.203 1.416-.323 2.85-.284 4.281-.599-.1-1.19-.322-1.787-.446a13.485 13.485 0 0 0-2.704-.3c-1.752 0-3.48.465-4.922 1.479C1.09 10.01 0 13.446.046 16.747c.052 3.575 1.263 6.99 3.3 9.905.899 1.288 1.932 2.522 3.21 3.451 1.241.903 2.628 1.325 4.133 1.54.64.093 1.29.096 1.927-.009.557-.09 1.078-.325 1.63-.419.417-.07 1.005.258 1.408.348a6.297 6.297 0 0 0 2.096.107c2.563-.292 4.594-1.449 6.28-3.387 3.71-4.264 5.921-10.791 3.77-16.284Zm-1.69 8.743c-.474 1.663-1.225 3.182-2.195 4.608-.86 1.263-1.855 2.514-3.131 3.377-1.172.79-2.76 1.223-4.173 1.093-.719-.065-1.373-.41-2.087-.478-.8-.076-1.538.352-2.318.459-3.064.416-5.485-1.665-7.146-3.972-2.04-2.831-3.249-6.214-3.134-9.732.106-3.223 1.643-6.55 4.998-7.432 1.678-.44 3.446-.188 5.099.238.715.183 1.454.48 2.196.52.572.066 1.2-.196 1.74-.344 3.233-.89 6.873-1.105 9.124 1.855 2.08 2.732 1.925 6.666 1.027 9.808Z"
|
||||||
|
/>
|
||||||
|
<Path
|
||||||
|
fill="#50BE0C"
|
||||||
|
d="M12 17.966c-.778.285-1.977.71-2.432 1.454.11-.183.221-.363-.002.002-.222.365-.113.186-.001.003-.668 1.099.272 2.53 1.547 2.347 1.258-.18 1.378-1.419 1.364-2.443a8.822 8.822 0 0 0-.095-1.282c-.043-.264-.157-.164-.382-.08ZM18.096 18.917c-.435-.304-.919-.542-1.405-.752-.118-.05-.698-.375-.832-.297.018-.01.036-.021 0 0-.036.023-.02.012-.001.001-.11.07-.096.609-.104.716a9.003 9.003 0 0 0-.01 1.534c.1 1.117 1.049 2.082 2.228 1.517 1.165-.558 1.095-2.04.124-2.719ZM12.223 3.815C12.343.28 8.347-.271 6.922.432c.371 4.075 3.48 4.164 5.301 3.383Z"
|
||||||
|
/>
|
||||||
|
</Svg>
|
||||||
|
);
|
||||||
|
export default NavGroceryIcon;
|
||||||
28
assets/svgs/NavSettingsIcon.tsx
Normal file
28
assets/svgs/NavSettingsIcon.tsx
Normal file
@ -0,0 +1,28 @@
|
|||||||
|
import * as React from "react";
|
||||||
|
import Svg, { Path, SvgProps } from "react-native-svg";
|
||||||
|
const NavSettingsIcon: React.FC<SvgProps> = (props) => (
|
||||||
|
<Svg
|
||||||
|
width={26}
|
||||||
|
height={28}
|
||||||
|
fill="none"
|
||||||
|
{...props}
|
||||||
|
>
|
||||||
|
<Path
|
||||||
|
stroke="#6C645B"
|
||||||
|
strokeLinecap="round"
|
||||||
|
strokeLinejoin="round"
|
||||||
|
strokeMiterlimit={10}
|
||||||
|
strokeWidth={1.69}
|
||||||
|
d="M12.972 17.893a3.887 3.887 0 1 0 0-7.774 3.887 3.887 0 0 0 0 7.774Z"
|
||||||
|
/>
|
||||||
|
<Path
|
||||||
|
stroke="#6C645B"
|
||||||
|
strokeLinecap="round"
|
||||||
|
strokeLinejoin="round"
|
||||||
|
strokeMiterlimit={10}
|
||||||
|
strokeWidth={1.69}
|
||||||
|
d="m24.398 8.531-.972-1.683a1.943 1.943 0 0 0-2.655-.711l-.511.295c-1.944 1.121-4.373-.28-4.373-2.525v-.59c0-1.074-.87-1.944-1.944-1.944H12c-1.073 0-1.943.87-1.943 1.943v.591c0 2.244-2.43 3.647-4.373 2.525l-.511-.295a1.943 1.943 0 0 0-2.655.711l-.972 1.683a1.943 1.943 0 0 0 .711 2.655l.511.296c1.944 1.122 1.944 3.927 0 5.049l-.51.295a1.943 1.943 0 0 0-.712 2.655l.972 1.684a1.943 1.943 0 0 0 2.655.71l.51-.294c1.944-1.123 4.374.28 4.374 2.524v.591c0 1.074.87 1.944 1.944 1.944h1.943c1.074 0 1.944-.87 1.944-1.944v-.59c0-2.245 2.43-3.648 4.373-2.526l.511.296c.93.536 2.119.219 2.655-.711l.972-1.684a1.943 1.943 0 0 0-.712-2.655l-.51-.295c-1.944-1.122-1.944-3.927 0-5.05l.51-.295a1.942 1.942 0 0 0 .712-2.655Z"
|
||||||
|
/>
|
||||||
|
</Svg>
|
||||||
|
);
|
||||||
|
export default NavSettingsIcon;
|
||||||
18
assets/svgs/NavToDosIcon.tsx
Normal file
18
assets/svgs/NavToDosIcon.tsx
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
import * as React from "react"
|
||||||
|
import Svg, { Path, SvgProps } from "react-native-svg"
|
||||||
|
const NavToDosIcon: React.FC<SvgProps> = (props) => (
|
||||||
|
<Svg
|
||||||
|
width={30}
|
||||||
|
height={30}
|
||||||
|
fill="none"
|
||||||
|
{...props}
|
||||||
|
>
|
||||||
|
<Path
|
||||||
|
fill="#8005EB"
|
||||||
|
stroke="#8005EB"
|
||||||
|
strokeWidth={0.5}
|
||||||
|
d="M15.038 29.649c-7.953 0-14.4-6.447-14.4-14.4s6.447-14.4 14.4-14.4 14.4 6.447 14.4 14.4-6.447 14.4-14.4 14.4Zm0-1.44c7.157 0 12.96-5.802 12.96-12.96 0-7.158-5.803-12.96-12.96-12.96-7.158 0-12.96 5.802-12.96 12.96 0 7.158 5.802 12.96 12.96 12.96Zm4.53-17.07a.72.72 0 1 1 1.019 1.019l-7.2 7.2a.72.72 0 0 1-1.018 0l-2.88-2.88a.72.72 0 1 1 1.018-1.018l2.37 2.37 6.692-6.69Z"
|
||||||
|
/>
|
||||||
|
</Svg>
|
||||||
|
)
|
||||||
|
export default NavToDosIcon
|
||||||
23
assets/svgs/PrivacyPolicyIcon.tsx
Normal file
23
assets/svgs/PrivacyPolicyIcon.tsx
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
import * as React from "react"
|
||||||
|
import Svg, { Path, SvgProps } from "react-native-svg"
|
||||||
|
const PrivacyPolicyIcon: React.FC<SvgProps> = (props) => (
|
||||||
|
<Svg
|
||||||
|
width={props.width ||20}
|
||||||
|
height={props.height ||22}
|
||||||
|
fill="none"
|
||||||
|
{...props}
|
||||||
|
>
|
||||||
|
<Path
|
||||||
|
stroke={props.color || "#6C645B"}
|
||||||
|
strokeWidth={1.2}
|
||||||
|
d="M1.413 8.656c0-3.7 0-5.55 1.15-6.7 1.15-1.15 3-1.15 6.7-1.15h1.962c3.7 0 5.55 0 6.7 1.15 1.149 1.15 1.149 3 1.149 6.7v3.925c0 3.7 0 5.55-1.15 6.7-1.15 1.149-3 1.149-6.7 1.149H9.263c-3.7 0-5.55 0-6.7-1.15-1.149-1.15-1.149-3-1.149-6.7V8.657Z"
|
||||||
|
/>
|
||||||
|
<Path
|
||||||
|
stroke={props.color || "#6C645B"}
|
||||||
|
strokeLinecap="round"
|
||||||
|
strokeWidth={1.2}
|
||||||
|
d="M6.324 10.617h7.85M6.324 6.694h7.85M6.324 14.541h4.906"
|
||||||
|
/>
|
||||||
|
</Svg>
|
||||||
|
)
|
||||||
|
export default PrivacyPolicyIcon
|
||||||
26
assets/svgs/ProfileIcon.tsx
Normal file
26
assets/svgs/ProfileIcon.tsx
Normal file
@ -0,0 +1,26 @@
|
|||||||
|
import * as React from "react"
|
||||||
|
import Svg, { Path, SvgProps } from "react-native-svg"
|
||||||
|
const ProfileIcon: React.FC<SvgProps> = (props) => (
|
||||||
|
<Svg
|
||||||
|
width={21}
|
||||||
|
height={21}
|
||||||
|
fill="none"
|
||||||
|
{...props}
|
||||||
|
>
|
||||||
|
<Path
|
||||||
|
stroke={props.color || "red"}
|
||||||
|
strokeLinecap="round"
|
||||||
|
strokeLinejoin="round"
|
||||||
|
strokeWidth={1.414}
|
||||||
|
d="M10.956 11.538a.91.91 0 0 0-.226 0 3.083 3.083 0 0 1-2.98-3.084 3.089 3.089 0 0 1 3.093-3.093 3.09 3.09 0 0 1 .113 6.176ZM17.199 17.762a9.368 9.368 0 0 1-6.356 2.47 9.368 9.368 0 0 1-6.356-2.47c.095-.886.66-1.754 1.67-2.433 2.583-1.716 6.808-1.716 9.373 0 1.009.68 1.575 1.547 1.669 2.433Z"
|
||||||
|
/>
|
||||||
|
<Path
|
||||||
|
stroke={props.color || "red"}
|
||||||
|
strokeLinecap="round"
|
||||||
|
strokeLinejoin="round"
|
||||||
|
strokeWidth={1.414}
|
||||||
|
d="M10.843 20.233a9.43 9.43 0 1 0 0-18.86 9.43 9.43 0 0 0 0 18.86Z"
|
||||||
|
/>
|
||||||
|
</Svg>
|
||||||
|
)
|
||||||
|
export default ProfileIcon
|
||||||
@ -1,4 +1,5 @@
|
|||||||
export async function fetchGoogleCalendarEvents(token, startDate, endDate) {
|
export async function fetchGoogleCalendarEvents(token, startDate, endDate) {
|
||||||
|
console.log(token);
|
||||||
const response = await fetch(
|
const response = await fetch(
|
||||||
`https://www.googleapis.com/calendar/v3/calendars/primary/events?single_events=true&time_min=${startDate}&time_max=${endDate}`,
|
`https://www.googleapis.com/calendar/v3/calendars/primary/events?single_events=true&time_min=${startDate}&time_max=${endDate}`,
|
||||||
{
|
{
|
||||||
@ -9,6 +10,7 @@ export async function fetchGoogleCalendarEvents(token, startDate, endDate) {
|
|||||||
);
|
);
|
||||||
|
|
||||||
const data = await response.json();
|
const data = await response.json();
|
||||||
|
console.log(data);
|
||||||
const googleEvents = [];
|
const googleEvents = [];
|
||||||
data.items?.forEach((item) => {
|
data.items?.forEach((item) => {
|
||||||
let isAllDay = false;
|
let isAllDay = false;
|
||||||
|
|||||||
@ -47,7 +47,7 @@ export default function CalendarPage() {
|
|||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
const [isFamilyView, setIsFamilyView] = useState<boolean>(true);
|
const [isFamilyView, setIsFamilyView] = useState<boolean>(false);
|
||||||
const [calendarHeight, setCalendarHeight] = useState(0);
|
const [calendarHeight, setCalendarHeight] = useState(0);
|
||||||
const [mode, setMode] = useState<"week" | "month" | "day">("week");
|
const [mode, setMode] = useState<"week" | "month" | "day">("week");
|
||||||
const [selectedDate, setSelectedDate] = useState<Date>(new Date());
|
const [selectedDate, setSelectedDate] = useState<Date>(new Date());
|
||||||
|
|||||||
@ -1,7 +1,5 @@
|
|||||||
import { View, Text, Button, Switch } from "react-native-ui-lib";
|
import { View, Text, Button, Switch } from "react-native-ui-lib";
|
||||||
import React, { useEffect, useState } from "react";
|
import React, { useEffect, useState } from "react";
|
||||||
import PointsSlider from "@/components/shared/PointsSlider";
|
|
||||||
import { repeatOptions, useToDosContext } from "@/contexts/ToDosContext";
|
|
||||||
import { Feather, AntDesign, Ionicons } from "@expo/vector-icons";
|
import { Feather, AntDesign, Ionicons } from "@expo/vector-icons";
|
||||||
import {
|
import {
|
||||||
Dialog,
|
Dialog,
|
||||||
@ -13,11 +11,11 @@ import {
|
|||||||
import { PanningDirectionsEnum } from "react-native-ui-lib/src/incubator/panView";
|
import { PanningDirectionsEnum } from "react-native-ui-lib/src/incubator/panView";
|
||||||
import { StyleSheet } from "react-native";
|
import { StyleSheet } from "react-native";
|
||||||
import DropModalIcon from "@/assets/svgs/DropModalIcon";
|
import DropModalIcon from "@/assets/svgs/DropModalIcon";
|
||||||
import { CalendarEvent, useCalendarContext } from "@/contexts/CalendarContext";
|
import { CalendarEvent } from "@/contexts/CalendarContext";
|
||||||
import ClockIcon from "@/assets/svgs/ClockIcon";
|
import ClockIcon from "@/assets/svgs/ClockIcon";
|
||||||
import LockIcon from "@/assets/svgs/LockIcon";
|
import LockIcon from "@/assets/svgs/LockIcon";
|
||||||
import MenuIcon from "@/assets/svgs/MenuIcon";
|
import MenuIcon from "@/assets/svgs/MenuIcon";
|
||||||
import { eventCellCss } from "react-native-big-calendar";
|
import { useUpdateEvent } from "@/hooks/firebase/useUpdateEvent";
|
||||||
|
|
||||||
interface IEditEventDialog {
|
interface IEditEventDialog {
|
||||||
event: CalendarEvent;
|
event: CalendarEvent;
|
||||||
@ -25,9 +23,10 @@ interface IEditEventDialog {
|
|||||||
setIsVisible: (value: boolean) => void;
|
setIsVisible: (value: boolean) => void;
|
||||||
}
|
}
|
||||||
const EditEventDialog = (editEventProps: IEditEventDialog) => {
|
const EditEventDialog = (editEventProps: IEditEventDialog) => {
|
||||||
const { updateEvent } = useCalendarContext();
|
|
||||||
const [event, setEvent] = useState<CalendarEvent>(editEventProps.event);
|
const [event, setEvent] = useState<CalendarEvent>(editEventProps.event);
|
||||||
|
|
||||||
|
const { mutateAsync: updateEvent } = useUpdateEvent();
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
setEvent(editEventProps.event);
|
setEvent(editEventProps.event);
|
||||||
}, [editEventProps.isVisible]);
|
}, [editEventProps.isVisible]);
|
||||||
@ -72,8 +71,7 @@ const EditEventDialog = (editEventProps: IEditEventDialog) => {
|
|||||||
onPress={() => {
|
onPress={() => {
|
||||||
try {
|
try {
|
||||||
if (event.id) {
|
if (event.id) {
|
||||||
updateEvent(event, event.id);
|
updateEvent(event).then(() => editEventProps.setIsVisible(false));
|
||||||
editEventProps.setIsVisible(false);
|
|
||||||
}
|
}
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.error(error);
|
console.error(error);
|
||||||
|
|||||||
@ -81,8 +81,9 @@ export const ManuallyAddEventModal = ({
|
|||||||
|
|
||||||
const { mutateAsync: createEvent, isLoading, isError } = useCreateEvent();
|
const { mutateAsync: createEvent, isLoading, isError } = useCreateEvent();
|
||||||
|
|
||||||
const formatDateTime = (date: Date) => {
|
const formatDateTime = (date?: Date | string) => {
|
||||||
return date.toLocaleDateString("en-US", {
|
if(!date) return undefined
|
||||||
|
return new Date(date).toLocaleDateString("en-US", {
|
||||||
weekday: "long",
|
weekday: "long",
|
||||||
month: "short",
|
month: "short",
|
||||||
day: "numeric",
|
day: "numeric",
|
||||||
@ -98,7 +99,7 @@ export const ManuallyAddEventModal = ({
|
|||||||
return combined;
|
return combined;
|
||||||
};
|
};
|
||||||
|
|
||||||
const handleSave = () => {
|
const handleSave = async () => {
|
||||||
let finalStartDate: Date;
|
let finalStartDate: Date;
|
||||||
let finalEndDate: Date;
|
let finalEndDate: Date;
|
||||||
|
|
||||||
@ -113,15 +114,14 @@ export const ManuallyAddEventModal = ({
|
|||||||
finalEndDate = combineDateAndTime(endDate, endTime);
|
finalEndDate = combineDateAndTime(endDate, endTime);
|
||||||
}
|
}
|
||||||
|
|
||||||
const eventData: CalendarEvent = {
|
const eventData: Partial<EventData> = {
|
||||||
title: title,
|
title: title,
|
||||||
start: finalStartDate,
|
startDate: finalStartDate,
|
||||||
end: finalEndDate,
|
endDate: finalEndDate,
|
||||||
allDay: isAllDay,
|
allDay: isAllDay,
|
||||||
private: isPrivate,
|
|
||||||
};
|
};
|
||||||
|
|
||||||
addEvent(eventData);
|
await createEvent(eventData);
|
||||||
|
|
||||||
close();
|
close();
|
||||||
};
|
};
|
||||||
|
|||||||
@ -1,5 +1,5 @@
|
|||||||
import { StyleSheet } from "react-native";
|
import { StyleSheet } from "react-native";
|
||||||
import React, { useState } from "react";
|
import React from "react";
|
||||||
import {
|
import {
|
||||||
Dialog,
|
Dialog,
|
||||||
Text,
|
Text,
|
||||||
@ -11,9 +11,9 @@ import {
|
|||||||
} from "react-native-ui-lib";
|
} from "react-native-ui-lib";
|
||||||
import {
|
import {
|
||||||
GroceryFrequency,
|
GroceryFrequency,
|
||||||
IGrocery,
|
|
||||||
useGroceryContext,
|
useGroceryContext,
|
||||||
} from "@/contexts/GroceryContext";
|
} from "@/contexts/GroceryContext";
|
||||||
|
import { IGrocery } from "@/hooks/firebase/types/groceryData";
|
||||||
interface EditGroceryFrequencyProps {
|
interface EditGroceryFrequencyProps {
|
||||||
visible: boolean;
|
visible: boolean;
|
||||||
onClose: () => void;
|
onClose: () => void;
|
||||||
@ -42,7 +42,7 @@ const EditGroceryFrequency = (props: EditGroceryFrequencyProps) => {
|
|||||||
<Switch
|
<Switch
|
||||||
value={props.item.recurring}
|
value={props.item.recurring}
|
||||||
onValueChange={(value) =>
|
onValueChange={(value) =>
|
||||||
updateGroceryItem(props.item.id, { recurring: value })
|
updateGroceryItem({id: props.item.id, recurring: value})
|
||||||
}
|
}
|
||||||
onColor={"lime"}
|
onColor={"lime"}
|
||||||
/>
|
/>
|
||||||
@ -56,7 +56,8 @@ const EditGroceryFrequency = (props: EditGroceryFrequencyProps) => {
|
|||||||
const selectedFrequency =
|
const selectedFrequency =
|
||||||
GroceryFrequency[item as keyof typeof GroceryFrequency];
|
GroceryFrequency[item as keyof typeof GroceryFrequency];
|
||||||
if (selectedFrequency) {
|
if (selectedFrequency) {
|
||||||
updateGroceryItem(props.item.id, {
|
updateGroceryItem({
|
||||||
|
id: props.item.id,
|
||||||
frequency: selectedFrequency,
|
frequency: selectedFrequency,
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
|
|||||||
@ -1,53 +1,58 @@
|
|||||||
import {
|
import {Checkbox, Text, TouchableOpacity, View,} from "react-native-ui-lib";
|
||||||
View,
|
|
||||||
Text,
|
|
||||||
Button,
|
|
||||||
TouchableOpacity,
|
|
||||||
Checkbox,
|
|
||||||
ButtonSize,
|
|
||||||
} from "react-native-ui-lib";
|
|
||||||
import React, {useEffect, useState} from "react";
|
import React, {useEffect, useState} from "react";
|
||||||
import { ProfileType, useAuthContext } from "@/contexts/AuthContext";
|
import {AntDesign} from "@expo/vector-icons";
|
||||||
import { MaterialCommunityIcons, AntDesign } from "@expo/vector-icons";
|
import {GroceryCategory, useGroceryContext,} from "@/contexts/GroceryContext";
|
||||||
import { ListItem } from "react-native-ui-lib";
|
|
||||||
import {
|
|
||||||
GroceryCategory,
|
|
||||||
IGrocery,
|
|
||||||
useGroceryContext,
|
|
||||||
} from "@/contexts/GroceryContext";
|
|
||||||
import EditGroceryFrequency from "./EditGroceryFrequency";
|
import EditGroceryFrequency from "./EditGroceryFrequency";
|
||||||
import EditGroceryItem from "./EditGroceryItem";
|
import EditGroceryItem from "./EditGroceryItem";
|
||||||
import {StyleSheet} from "react-native";
|
import {StyleSheet} from "react-native";
|
||||||
|
import {IGrocery} from "@/hooks/firebase/types/groceryData";
|
||||||
|
import firestore from "@react-native-firebase/firestore";
|
||||||
|
import {UserProfile} from "@/hooks/firebase/types/profileTypes";
|
||||||
|
|
||||||
const GroceryItem = ({
|
const GroceryItem = ({
|
||||||
item,
|
item,
|
||||||
handleItemApproved,
|
handleItemApproved,
|
||||||
}: {
|
}: {
|
||||||
item: IGrocery;
|
item: IGrocery;
|
||||||
handleItemApproved: (id: number, changes: Partial<IGrocery>) => void;
|
handleItemApproved: (id: string, changes: Partial<IGrocery>) => void;
|
||||||
}) => {
|
}) => {
|
||||||
const { updateGroceryItem, groceries } = useGroceryContext();
|
const { updateGroceryItem } = useGroceryContext();
|
||||||
|
|
||||||
const { profileType } = useAuthContext();
|
|
||||||
const [openFreqEdit, setOpenFreqEdit] = useState<boolean>(false);
|
const [openFreqEdit, setOpenFreqEdit] = useState<boolean>(false);
|
||||||
const [isEditingTitle, setIsEditingTitle] = useState<boolean>(false);
|
const [isEditingTitle, setIsEditingTitle] = useState<boolean>(false);
|
||||||
const [newTitle, setNewTitle] = useState<string>("");
|
const [newTitle, setNewTitle] = useState<string>("");
|
||||||
const [category, setCategory] = useState<GroceryCategory>(
|
const [category, setCategory] = useState<GroceryCategory>(
|
||||||
GroceryCategory.None
|
GroceryCategory.None
|
||||||
);
|
);
|
||||||
|
const [itemCreator, setItemCreator] = useState<UserProfile>(null);
|
||||||
|
|
||||||
const handleTitleChange = (newTitle: string) => {
|
const handleTitleChange = (newTitle: string) => {
|
||||||
updateGroceryItem(item.id, { title: newTitle });
|
updateGroceryItem({id: item?.id, title: newTitle});
|
||||||
};
|
};
|
||||||
|
|
||||||
const handleCategoryChange = (newCategory: GroceryCategory) => {
|
const handleCategoryChange = (newCategory: GroceryCategory) => {
|
||||||
updateGroceryItem(item.id, { category: newCategory });
|
updateGroceryItem({id: item?.id, category: newCategory});
|
||||||
};
|
};
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
setNewTitle(item.title);
|
setNewTitle(item.title);
|
||||||
|
|
||||||
|
getItemCreator(item?.creatorId);
|
||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
|
const getItemCreator = async (uid: string | undefined) => {
|
||||||
|
if (uid) {
|
||||||
|
const documentSnapshot = await firestore()
|
||||||
|
.collection("Profiles")
|
||||||
|
.doc(uid)
|
||||||
|
.get();
|
||||||
|
|
||||||
|
if (documentSnapshot.exists) {
|
||||||
|
setItemCreator(documentSnapshot.data() as UserProfile)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<View
|
<View
|
||||||
key={item.id}
|
key={item.id}
|
||||||
@ -114,7 +119,7 @@ const GroceryItem = ({
|
|||||||
containerStyle={styles.checkbox}
|
containerStyle={styles.checkbox}
|
||||||
hitSlop={20}
|
hitSlop={20}
|
||||||
onValueChange={() =>
|
onValueChange={() =>
|
||||||
updateGroceryItem(item.id, { bought: !item.bought })
|
updateGroceryItem({ id: item.id, bought: !item.bought })
|
||||||
}
|
}
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
@ -135,7 +140,7 @@ const GroceryItem = ({
|
|||||||
}}
|
}}
|
||||||
></View>
|
></View>
|
||||||
<Text color="#858585" text70>
|
<Text color="#858585" text70>
|
||||||
Requested by Austin
|
Requested by {itemCreator?.firstName}
|
||||||
</Text>
|
</Text>
|
||||||
</View>
|
</View>
|
||||||
</View>
|
</View>
|
||||||
|
|||||||
@ -1,18 +1,13 @@
|
|||||||
import {FlatList, StyleSheet} from "react-native";
|
import {FlatList, StyleSheet} from "react-native";
|
||||||
import React, { RefObject, useEffect, useState } from "react";
|
import React, {useEffect, useState} from "react";
|
||||||
import { View, Text, ListItem, Button, TextField, TextFieldRef } from "react-native-ui-lib";
|
import {Button, Text, View} from "react-native-ui-lib";
|
||||||
import GroceryItem from "./GroceryItem";
|
import GroceryItem from "./GroceryItem";
|
||||||
import {
|
import {GroceryCategory, GroceryFrequency, useGroceryContext,} from "@/contexts/GroceryContext";
|
||||||
IGrocery,
|
|
||||||
GroceryCategory,
|
|
||||||
GroceryFrequency,
|
|
||||||
useGroceryContext,
|
|
||||||
} from "@/contexts/GroceryContext";
|
|
||||||
import HeaderTemplate from "@/components/shared/HeaderTemplate";
|
import HeaderTemplate from "@/components/shared/HeaderTemplate";
|
||||||
import CategoryDropdown from "./CategoryDropdown";
|
|
||||||
import {AntDesign, MaterialIcons} from "@expo/vector-icons";
|
import {AntDesign, MaterialIcons} from "@expo/vector-icons";
|
||||||
import EditGroceryItem from "./EditGroceryItem";
|
import EditGroceryItem from "./EditGroceryItem";
|
||||||
import {ProfileType, useAuthContext} from "@/contexts/AuthContext";
|
import {ProfileType, useAuthContext} from "@/contexts/AuthContext";
|
||||||
|
import {IGrocery} from "@/hooks/firebase/types/groceryData";
|
||||||
|
|
||||||
const GroceryList = () => {
|
const GroceryList = () => {
|
||||||
const {
|
const {
|
||||||
@ -24,10 +19,10 @@ const GroceryList = () => {
|
|||||||
} = useGroceryContext();
|
} = useGroceryContext();
|
||||||
const { profileData } = useAuthContext();
|
const { profileData } = useAuthContext();
|
||||||
const [approvedGroceries, setapprovedGroceries] = useState<IGrocery[]>(
|
const [approvedGroceries, setapprovedGroceries] = useState<IGrocery[]>(
|
||||||
groceries.filter((item) => item.approved === true)
|
groceries?.filter((item) => item.approved === true)
|
||||||
);
|
);
|
||||||
const [pendingGroceries, setPendingGroceries] = useState<IGrocery[]>(
|
const [pendingGroceries, setPendingGroceries] = useState<IGrocery[]>(
|
||||||
groceries.filter((item) => item.approved !== true)
|
groceries?.filter((item) => item.approved !== true)
|
||||||
);
|
);
|
||||||
const [category, setCategory] = useState<GroceryCategory>(
|
const [category, setCategory] = useState<GroceryCategory>(
|
||||||
GroceryCategory.Bakery
|
GroceryCategory.Bakery
|
||||||
@ -39,7 +34,7 @@ const GroceryList = () => {
|
|||||||
const [approvedVisible, setApprovedVisible] = useState<boolean>(true);
|
const [approvedVisible, setApprovedVisible] = useState<boolean>(true);
|
||||||
|
|
||||||
// Group approved groceries by category
|
// Group approved groceries by category
|
||||||
const approvedGroceriesByCategory = approvedGroceries.reduce(
|
const approvedGroceriesByCategory = approvedGroceries?.reduce(
|
||||||
(groups: any, item: IGrocery) => {
|
(groups: any, item: IGrocery) => {
|
||||||
const category = item.category || "Uncategorized";
|
const category = item.category || "Uncategorized";
|
||||||
if (!groups[category]) {
|
if (!groups[category]) {
|
||||||
@ -55,10 +50,10 @@ const GroceryList = () => {
|
|||||||
if (submit) {
|
if (submit) {
|
||||||
if (title?.length > 2 && title?.length <= 25) {
|
if (title?.length > 2 && title?.length <= 25) {
|
||||||
addGrocery({
|
addGrocery({
|
||||||
id: 0,
|
id: "",
|
||||||
title: title,
|
title: title,
|
||||||
category: category,
|
category: category,
|
||||||
approved: profileData?.userType === ProfileType.PARENT ? true : false,
|
approved: profileData?.userType === ProfileType.PARENT,
|
||||||
recurring: false,
|
recurring: false,
|
||||||
frequency: GroceryFrequency.Never,
|
frequency: GroceryFrequency.Never,
|
||||||
bought: false,
|
bought: false,
|
||||||
@ -76,8 +71,8 @@ const GroceryList = () => {
|
|||||||
}, [category]);
|
}, [category]);
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
setapprovedGroceries(groceries.filter((item) => item.approved === true));
|
setapprovedGroceries(groceries?.filter((item) => item.approved === true));
|
||||||
setPendingGroceries(groceries.filter((item) => item.approved !== true));
|
setPendingGroceries(groceries?.filter((item) => item.approved !== true));
|
||||||
}, [groceries]);
|
}, [groceries]);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
@ -93,8 +88,8 @@ const GroceryList = () => {
|
|||||||
style={{ borderRadius: 50 }}
|
style={{ borderRadius: 50 }}
|
||||||
>
|
>
|
||||||
<Text text70BL color="#46a80a">
|
<Text text70BL color="#46a80a">
|
||||||
{approvedGroceries.length} list{" "}
|
{approvedGroceries?.length} list{" "}
|
||||||
{approvedGroceries.length === 1 ? (
|
{approvedGroceries?.length === 1 ? (
|
||||||
<Text text70BL color="#46a80a">
|
<Text text70BL color="#46a80a">
|
||||||
item
|
item
|
||||||
</Text>
|
</Text>
|
||||||
@ -111,7 +106,7 @@ const GroceryList = () => {
|
|||||||
style={{ borderRadius: 50 }}
|
style={{ borderRadius: 50 }}
|
||||||
>
|
>
|
||||||
<Text text70BL color="#e28800">
|
<Text text70BL color="#e28800">
|
||||||
{pendingGroceries.length} pending
|
{pendingGroceries?.length} pending
|
||||||
</Text>
|
</Text>
|
||||||
</View>
|
</View>
|
||||||
<Button
|
<Button
|
||||||
@ -161,18 +156,18 @@ const GroceryList = () => {
|
|||||||
}}
|
}}
|
||||||
>
|
>
|
||||||
<Text text70 center color="#e28800">
|
<Text text70 center color="#e28800">
|
||||||
{pendingGroceries.length.toString()}
|
{pendingGroceries?.length.toString()}
|
||||||
</Text>
|
</Text>
|
||||||
</View>
|
</View>
|
||||||
</View>
|
</View>
|
||||||
{pendingGroceries.length > 0
|
{pendingGroceries?.length > 0
|
||||||
? pendingVisible && (
|
? pendingVisible && (
|
||||||
<FlatList
|
<FlatList
|
||||||
data={pendingGroceries}
|
data={pendingGroceries}
|
||||||
renderItem={({ item }) => (
|
renderItem={({ item }) => (
|
||||||
<GroceryItem
|
<GroceryItem
|
||||||
item={item}
|
item={item}
|
||||||
handleItemApproved={updateGroceryItem}
|
handleItemApproved={(id, changes) => updateGroceryItem({...changes, id: id})}
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
keyExtractor={(item) => item.id.toString()}
|
keyExtractor={(item) => item.id.toString()}
|
||||||
@ -217,7 +212,7 @@ const GroceryList = () => {
|
|||||||
}}
|
}}
|
||||||
>
|
>
|
||||||
<Text text70 center color="#46a80a">
|
<Text text70 center color="#46a80a">
|
||||||
{approvedGroceries.length.toString()}
|
{approvedGroceries?.length.toString()}
|
||||||
</Text>
|
</Text>
|
||||||
</View>
|
</View>
|
||||||
</View>
|
</View>
|
||||||
@ -234,7 +229,7 @@ const GroceryList = () => {
|
|||||||
)}
|
)}
|
||||||
|
|
||||||
{/* Render Approved Groceries Grouped by Category */}
|
{/* Render Approved Groceries Grouped by Category */}
|
||||||
{approvedGroceries.length > 0
|
{approvedGroceries?.length > 0
|
||||||
? approvedVisible && (
|
? approvedVisible && (
|
||||||
<FlatList
|
<FlatList
|
||||||
data={Object.keys(approvedGroceriesByCategory)}
|
data={Object.keys(approvedGroceriesByCategory)}
|
||||||
@ -250,7 +245,7 @@ const GroceryList = () => {
|
|||||||
<GroceryItem
|
<GroceryItem
|
||||||
key={grocery.id}
|
key={grocery.id}
|
||||||
item={grocery}
|
item={grocery}
|
||||||
handleItemApproved={updateGroceryItem}
|
handleItemApproved={(id, changes) => updateGroceryItem({...changes, id: id})}
|
||||||
/>
|
/>
|
||||||
)
|
)
|
||||||
)}
|
)}
|
||||||
|
|||||||
@ -31,7 +31,7 @@ const SignUpPage = ({setTab}: { setTab: React.Dispatch<React.SetStateAction<"re
|
|||||||
return (
|
return (
|
||||||
<View padding-10 height={"100%"} flexG>
|
<View padding-10 height={"100%"} flexG>
|
||||||
<Text text30 center>
|
<Text text30 center>
|
||||||
Get started with Kali
|
Get started with Cally
|
||||||
</Text>
|
</Text>
|
||||||
<Text center>Please enter your details.</Text>
|
<Text center>Please enter your details.</Text>
|
||||||
<TextField
|
<TextField
|
||||||
|
|||||||
@ -28,21 +28,28 @@ const OnboardingFlow = () => {
|
|||||||
width={10}
|
width={10}
|
||||||
/>
|
/>
|
||||||
),
|
),
|
||||||
title: <Text text30>Welcome to Kali</Text>,
|
title: <Text text30>Welcome to Cally</Text>,
|
||||||
subtitle: (
|
subtitle: (
|
||||||
<View paddingB-250 marginH-20 spread>
|
<View paddingB-250 marginH-20 spread>
|
||||||
<Text text50R>Lightening Mental Loads, One Family at a Time</Text>
|
<Text text50R>Lightening Mental Loads, One Family at a Time</Text>
|
||||||
<Button
|
<Button
|
||||||
label="Continue"
|
label="Continue"
|
||||||
style={{ backgroundColor: "#fd1775" }}
|
style={{ backgroundColor: "#fd1775" }}
|
||||||
onPress={() => onboardingRef.current.goToPage(1, true)}
|
onPress={() => onboardingRef?.current?.goToPage(1, true)}
|
||||||
/>
|
/>
|
||||||
</View>
|
</View>
|
||||||
),
|
),
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
backgroundColor: "#f9f8f7",
|
backgroundColor: "#f9f8f7",
|
||||||
title: <Text>Get started with Kali</Text>,
|
title: <Text>Get started with Cally</Text>,
|
||||||
|
image: (
|
||||||
|
<Image
|
||||||
|
source={require("../../../assets/images/splash-clock.png")}
|
||||||
|
height={10}
|
||||||
|
width={10}
|
||||||
|
/>
|
||||||
|
),
|
||||||
subtitle: (
|
subtitle: (
|
||||||
<View
|
<View
|
||||||
style={{
|
style={{
|
||||||
|
|||||||
@ -1,5 +1,5 @@
|
|||||||
import { AntDesign, Ionicons } from "@expo/vector-icons";
|
import { AntDesign, Ionicons } from "@expo/vector-icons";
|
||||||
import React, { useCallback, useState } from "react";
|
import React, {useCallback, useEffect, useState} from "react";
|
||||||
import { Button, Checkbox, Text, View } from "react-native-ui-lib";
|
import { Button, Checkbox, Text, View } from "react-native-ui-lib";
|
||||||
import { ScrollView, StyleSheet } from "react-native";
|
import { ScrollView, StyleSheet } from "react-native";
|
||||||
import { colorMap } from "@/contexts/SettingsContext";
|
import { colorMap } from "@/contexts/SettingsContext";
|
||||||
@ -9,21 +9,19 @@ import { fetchMicrosoftCalendarEvents } from "@/calendar-integration/microsoft-c
|
|||||||
import { useCreateEventFromProvider } from "@/hooks/firebase/useCreateEvent";
|
import { useCreateEventFromProvider } from "@/hooks/firebase/useCreateEvent";
|
||||||
import { useAuthContext } from "@/contexts/AuthContext";
|
import { useAuthContext } from "@/contexts/AuthContext";
|
||||||
import { useUpdateUserData } from "@/hooks/firebase/useUpdateUserData";
|
import { useUpdateUserData } from "@/hooks/firebase/useUpdateUserData";
|
||||||
import { GoogleSignin } from "@react-native-google-signin/google-signin";
|
|
||||||
import * as AuthSession from "expo-auth-session";
|
|
||||||
import debounce from "debounce";
|
import debounce from "debounce";
|
||||||
import AppleIcon from "@/assets/svgs/AppleIcon";
|
import AppleIcon from "@/assets/svgs/AppleIcon";
|
||||||
import GoogleIcon from "@/assets/svgs/GoogleIcon";
|
import GoogleIcon from "@/assets/svgs/GoogleIcon";
|
||||||
import OutlookIcon from "@/assets/svgs/OutlookIcon";
|
import OutlookIcon from "@/assets/svgs/OutlookIcon";
|
||||||
|
import * as AuthSession from "expo-auth-session";
|
||||||
|
import * as Google from "expo-auth-session/providers/google";
|
||||||
|
import * as WebBrowser from "expo-web-browser";
|
||||||
|
|
||||||
GoogleSignin.configure({
|
const googleConfig = {
|
||||||
webClientId:
|
androidClientId: "406146460310-2u67ab2nbhu23trp8auho1fq4om29fc0.apps.googleusercontent.com",
|
||||||
"406146460310-hjadmfa1gg4ptaouira5rkhu0djlo5ut.apps.googleusercontent.com",
|
iosClientId: "406146460310-2u67ab2nbhu23trp8auho1fq4om29fc0.apps.googleusercontent.com",
|
||||||
scopes: ["profile", "email"], // Note: add calendar scope
|
webClientId: "406146460310-2u67ab2nbhu23trp8auho1fq4om29fc0.apps.googleusercontent.com",
|
||||||
});
|
scopes: ["email", "profile", "https://www.googleapis.com/auth/calendar.events.owned"]
|
||||||
|
|
||||||
const GoogleLogin = async () => {
|
|
||||||
return await GoogleSignin.signIn();
|
|
||||||
};
|
};
|
||||||
|
|
||||||
const microsoftConfig = {
|
const microsoftConfig = {
|
||||||
@ -57,7 +55,15 @@ const CalendarSettingsPage = (props: {
|
|||||||
const { mutateAsync: createEventFromProvider } = useCreateEventFromProvider();
|
const { mutateAsync: createEventFromProvider } = useCreateEventFromProvider();
|
||||||
const { mutateAsync: updateUserData } = useUpdateUserData();
|
const { mutateAsync: updateUserData } = useUpdateUserData();
|
||||||
|
|
||||||
|
WebBrowser.maybeCompleteAuthSession()
|
||||||
|
const [request, response, promptAsync] = Google.useAuthRequest(googleConfig);
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
signInWithGoogle();
|
||||||
|
}, [response]);
|
||||||
|
|
||||||
const fetchAndSaveGoogleEvents = () => {
|
const fetchAndSaveGoogleEvents = () => {
|
||||||
|
console.log("fetch");
|
||||||
const timeMin = new Date(new Date().setHours(0, 0, 0, 0));
|
const timeMin = new Date(new Date().setHours(0, 0, 0, 0));
|
||||||
const timeMax = new Date(
|
const timeMax = new Date(
|
||||||
new Date(new Date().setHours(0, 0, 0, 0)).setDate(timeMin.getDate() + 30)
|
new Date(new Date().setHours(0, 0, 0, 0)).setDate(timeMin.getDate() + 30)
|
||||||
@ -94,19 +100,16 @@ const CalendarSettingsPage = (props: {
|
|||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
const handleGoogleLogin = async () => {
|
const signInWithGoogle = async () => {
|
||||||
try {
|
try {
|
||||||
const response = await GoogleLogin();
|
// Attempt to retrieve user information from AsyncStorage
|
||||||
if (response) {
|
if (response?.type === 'success') {
|
||||||
const googleUserData = response.data;
|
console.log(response.authentication)
|
||||||
let idToken = googleUserData?.idToken;
|
await updateUserData({newUserData: {googleToken: response.authentication?.accessToken}})
|
||||||
|
|
||||||
if (idToken) {
|
|
||||||
await updateUserData({ newUserData: { googleToken: idToken } });
|
|
||||||
}
|
}
|
||||||
}
|
} catch (error) {
|
||||||
} catch (apiError) {
|
// Handle any errors that occur during AsyncStorage retrieval or other operations
|
||||||
console.log(apiError || "Something went wrong");
|
console.error("Error retrieving user data from AsyncStorage:", error);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -290,7 +293,7 @@ const CalendarSettingsPage = (props: {
|
|||||||
</Text>
|
</Text>
|
||||||
|
|
||||||
<Button
|
<Button
|
||||||
onPress={handleGoogleLogin}
|
onPress={() => promptAsync()}
|
||||||
label="Connect Google"
|
label="Connect Google"
|
||||||
iconSource={() => (
|
iconSource={() => (
|
||||||
<View marginR-15>
|
<View marginR-15>
|
||||||
@ -329,50 +332,31 @@ const CalendarSettingsPage = (props: {
|
|||||||
Connected Calendars
|
Connected Calendars
|
||||||
</Text>
|
</Text>
|
||||||
<View style={styles.card}>
|
<View style={styles.card}>
|
||||||
<Text text70>Calendars</Text>
|
|
||||||
<View style={{ marginTop: 20 }}>
|
<View style={{ marginTop: 20 }}>
|
||||||
<Button
|
<Button
|
||||||
label={"Sync Outlook"}
|
|
||||||
iconSource={() => (
|
|
||||||
<View
|
|
||||||
backgroundColor="#ededed"
|
|
||||||
width={40}
|
|
||||||
height={40}
|
|
||||||
style={{ borderRadius: 50 }}
|
|
||||||
marginR-10
|
|
||||||
centerV
|
|
||||||
centerH
|
|
||||||
>
|
|
||||||
<Ionicons name="logo-microsoft" size={22} color="#979797" />
|
|
||||||
</View>
|
|
||||||
)}
|
|
||||||
backgroundColor="white"
|
|
||||||
color="#464039"
|
|
||||||
borderRadius={15}
|
|
||||||
onPress={fetchAndSaveMicrosoftEvents}
|
|
||||||
/>
|
|
||||||
{profileData?.googleToken !== undefined && (
|
|
||||||
<Button
|
|
||||||
label={"Sync Google"}
|
|
||||||
iconSource={() => (
|
|
||||||
<View
|
|
||||||
backgroundColor="#ededed"
|
|
||||||
width={40}
|
|
||||||
height={40}
|
|
||||||
style={{ borderRadius: 50 }}
|
|
||||||
marginR-10
|
|
||||||
centerV
|
|
||||||
centerH
|
|
||||||
>
|
|
||||||
<Ionicons name="logo-google" size={22} color="#979797" />
|
|
||||||
</View>
|
|
||||||
)}
|
|
||||||
backgroundColor="white"
|
|
||||||
color="#464039"
|
|
||||||
borderRadius={15}
|
|
||||||
onPress={fetchAndSaveGoogleEvents}
|
onPress={fetchAndSaveGoogleEvents}
|
||||||
/>
|
label="Sync Google"
|
||||||
|
iconSource={() => (
|
||||||
|
<View marginR-15>
|
||||||
|
<GoogleIcon />
|
||||||
|
</View>
|
||||||
)}
|
)}
|
||||||
|
style={styles.addCalBtn}
|
||||||
|
color="black"
|
||||||
|
text70BL
|
||||||
|
/>
|
||||||
|
<Button
|
||||||
|
onPress={fetchAndSaveMicrosoftEvents}
|
||||||
|
label="Sync Outlook"
|
||||||
|
iconSource={() => (
|
||||||
|
<View marginR-15>
|
||||||
|
<OutlookIcon />
|
||||||
|
</View>
|
||||||
|
)}
|
||||||
|
style={styles.addCalBtn}
|
||||||
|
color="black"
|
||||||
|
text70BL
|
||||||
|
/>
|
||||||
</View>
|
</View>
|
||||||
</View>
|
</View>
|
||||||
</View>
|
</View>
|
||||||
|
|||||||
@ -6,6 +6,9 @@ import CalendarSettingsPage from "./CalendarSettingsPage";
|
|||||||
import ChoreRewardSettings from "./ChoreRewardSettings";
|
import ChoreRewardSettings from "./ChoreRewardSettings";
|
||||||
import UserSettings from "./UserSettings";
|
import UserSettings from "./UserSettings";
|
||||||
import { AuthContextProvider } from "@/contexts/AuthContext";
|
import { AuthContextProvider } from "@/contexts/AuthContext";
|
||||||
|
import ProfileIcon from "@/assets/svgs/ProfileIcon";
|
||||||
|
import CalendarIcon from "@/assets/svgs/CalendarIcon";
|
||||||
|
import PrivacyPolicyIcon from "@/assets/svgs/PrivacyPolicyIcon";
|
||||||
|
|
||||||
const styles = StyleSheet.create({
|
const styles = StyleSheet.create({
|
||||||
mainBtn: {
|
mainBtn: {
|
||||||
@ -34,12 +37,7 @@ const SettingsPage = () => {
|
|||||||
label="Manage my profile"
|
label="Manage my profile"
|
||||||
color="#07b8c7"
|
color="#07b8c7"
|
||||||
iconSource={() => (
|
iconSource={() => (
|
||||||
<Ionicons
|
<ProfileIcon style={{marginRight: 10}} color="#07b9c8" />
|
||||||
name="person-circle-sharp"
|
|
||||||
size={24}
|
|
||||||
color="#07b8c7"
|
|
||||||
style={{ marginRight: 10 }}
|
|
||||||
/>
|
|
||||||
)}
|
)}
|
||||||
onPress={() => setSelectedPage(pageIndex.user)}
|
onPress={() => setSelectedPage(pageIndex.user)}
|
||||||
/>
|
/>
|
||||||
@ -49,12 +47,7 @@ const SettingsPage = () => {
|
|||||||
label="Calendar settings"
|
label="Calendar settings"
|
||||||
color="#fd1775"
|
color="#fd1775"
|
||||||
iconSource={() => (
|
iconSource={() => (
|
||||||
<Ionicons
|
<CalendarIcon style={{marginRight: 10}}/>
|
||||||
name="home-outline"
|
|
||||||
size={24}
|
|
||||||
color="#fd1775"
|
|
||||||
style={{ marginRight: 10 }}
|
|
||||||
/>
|
|
||||||
)}
|
)}
|
||||||
onPress={() => {
|
onPress={() => {
|
||||||
setSelectedPage(pageIndex.calendar);
|
setSelectedPage(pageIndex.calendar);
|
||||||
@ -80,12 +73,7 @@ const SettingsPage = () => {
|
|||||||
style={styles.mainBtn}
|
style={styles.mainBtn}
|
||||||
label="Kaly privacy policy"
|
label="Kaly privacy policy"
|
||||||
iconSource={() => (
|
iconSource={() => (
|
||||||
<Entypo
|
<PrivacyPolicyIcon style={{marginRight: 10}}/>
|
||||||
name="text-document"
|
|
||||||
size={24}
|
|
||||||
color="#6c645b"
|
|
||||||
style={{ marginRight: 10 }}
|
|
||||||
/>
|
|
||||||
)}
|
)}
|
||||||
color="#6c645b"
|
color="#6c645b"
|
||||||
/>
|
/>
|
||||||
|
|||||||
@ -44,7 +44,7 @@ const AddChore = () => {
|
|||||||
>
|
>
|
||||||
<AntDesign name="plus" size={24} color="white" />
|
<AntDesign name="plus" size={24} color="white" />
|
||||||
<Text white text60R marginL-10>
|
<Text white text60R marginL-10>
|
||||||
Add to do
|
Add To Do
|
||||||
</Text>
|
</Text>
|
||||||
</Button>
|
</Button>
|
||||||
</View>
|
</View>
|
||||||
|
|||||||
@ -1,5 +1,5 @@
|
|||||||
import { View, Text, Button, Switch } from "react-native-ui-lib";
|
import { View, Text, Button, Switch } from "react-native-ui-lib";
|
||||||
import React, { useState } from "react";
|
import React, { useEffect, useState } from "react";
|
||||||
import PointsSlider from "@/components/shared/PointsSlider";
|
import PointsSlider from "@/components/shared/PointsSlider";
|
||||||
import { repeatOptions, useToDosContext } from "@/contexts/ToDosContext";
|
import { repeatOptions, useToDosContext } from "@/contexts/ToDosContext";
|
||||||
import { Feather, AntDesign, Ionicons } from "@expo/vector-icons";
|
import { Feather, AntDesign, Ionicons } from "@expo/vector-icons";
|
||||||
@ -27,6 +27,15 @@ const AddChoreDialog = (addChoreDialogProps: IAddChoreDialog) => {
|
|||||||
const [rotate, setRotate] = useState<boolean>(false);
|
const [rotate, setRotate] = useState<boolean>(false);
|
||||||
const [repeatType, setRepeatType] = useState<string>("Every week");
|
const [repeatType, setRepeatType] = useState<string>("Every week");
|
||||||
|
|
||||||
|
const handleCLose = () => {
|
||||||
|
setNewTitle("");
|
||||||
|
setPoints(10);
|
||||||
|
setChoreDate(new Date());
|
||||||
|
setRotate(false);
|
||||||
|
setRepeatType("every week");
|
||||||
|
addChoreDialogProps.setIsVisible(false);
|
||||||
|
};
|
||||||
|
|
||||||
const handleChange = (text: string) => {
|
const handleChange = (text: string) => {
|
||||||
const numericValue = parseInt(text, 10);
|
const numericValue = parseInt(text, 10);
|
||||||
|
|
||||||
@ -41,7 +50,7 @@ const AddChoreDialog = (addChoreDialogProps: IAddChoreDialog) => {
|
|||||||
bottom={true}
|
bottom={true}
|
||||||
height={"90%"}
|
height={"90%"}
|
||||||
panDirection={PanningDirectionsEnum.DOWN}
|
panDirection={PanningDirectionsEnum.DOWN}
|
||||||
onDismiss={() => addChoreDialogProps.setIsVisible(false)}
|
onDismiss={() => handleCLose}
|
||||||
containerStyle={{
|
containerStyle={{
|
||||||
borderRadius: 10,
|
borderRadius: 10,
|
||||||
backgroundColor: "white",
|
backgroundColor: "white",
|
||||||
@ -59,13 +68,13 @@ const AddChoreDialog = (addChoreDialogProps: IAddChoreDialog) => {
|
|||||||
style={styles.topBtn}
|
style={styles.topBtn}
|
||||||
label="Cancel"
|
label="Cancel"
|
||||||
onPress={() => {
|
onPress={() => {
|
||||||
addChoreDialogProps.setIsVisible(false);
|
handleCLose();
|
||||||
}}
|
}}
|
||||||
/>
|
/>
|
||||||
<View marginT-12>
|
<View marginT-12>
|
||||||
<DropModalIcon
|
<DropModalIcon
|
||||||
onPress={() => {
|
onPress={() => {
|
||||||
addChoreDialogProps.setIsVisible(false);
|
handleCLose()
|
||||||
}}
|
}}
|
||||||
/>
|
/>
|
||||||
</View>
|
</View>
|
||||||
@ -84,7 +93,7 @@ const AddChoreDialog = (addChoreDialogProps: IAddChoreDialog) => {
|
|||||||
rotate: rotate,
|
rotate: rotate,
|
||||||
repeatType: repeatType,
|
repeatType: repeatType,
|
||||||
});
|
});
|
||||||
addChoreDialogProps.setIsVisible(false);
|
handleCLose();
|
||||||
console.log(toDos);
|
console.log(toDos);
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.error(error);
|
console.error(error);
|
||||||
|
|||||||
@ -1,8 +1,10 @@
|
|||||||
import { View, Text } from "react-native-ui-lib";
|
import { View, Text, TouchableOpacity, Icon } from "react-native-ui-lib";
|
||||||
import React from "react";
|
import React, { useState } from "react";
|
||||||
import { IToDo, useToDosContext } from "@/contexts/ToDosContext";
|
import { IToDo, useToDosContext } from "@/contexts/ToDosContext";
|
||||||
import ToDoItem from "./ToDoItem";
|
import ToDoItem from "./ToDoItem";
|
||||||
import { format, isToday, isTomorrow } from "date-fns";
|
import { format, isToday, isTomorrow } from "date-fns";
|
||||||
|
import DropModalIcon from "@/assets/svgs/DropModalIcon";
|
||||||
|
import { AntDesign } from "@expo/vector-icons";
|
||||||
|
|
||||||
const groupToDosByDate = (toDos: IToDo[]) => {
|
const groupToDosByDate = (toDos: IToDo[]) => {
|
||||||
return toDos.reduce((groups, toDo) => {
|
return toDos.reduce((groups, toDo) => {
|
||||||
@ -31,23 +33,53 @@ const ToDosList = () => {
|
|||||||
const { toDos } = useToDosContext();
|
const { toDos } = useToDosContext();
|
||||||
const groupedToDos = groupToDosByDate(toDos);
|
const groupedToDos = groupToDosByDate(toDos);
|
||||||
|
|
||||||
|
const [expandedGroups, setExpandedGroups] = useState<{
|
||||||
|
[key: string]: boolean;
|
||||||
|
}>({});
|
||||||
|
|
||||||
|
const [expandNoDate, setExpandNoDate] = useState<boolean>(true);
|
||||||
|
|
||||||
|
const toggleExpand = (dateKey: string) => {
|
||||||
|
setExpandedGroups((prev) => ({
|
||||||
|
...prev,
|
||||||
|
[dateKey]: !prev[dateKey],
|
||||||
|
}));
|
||||||
|
};
|
||||||
|
|
||||||
const noDateToDos = groupedToDos["No Date"] || [];
|
const noDateToDos = groupedToDos["No Date"] || [];
|
||||||
const datedToDos = Object.keys(groupedToDos).filter((key) => key !== "No Date");
|
const datedToDos = Object.keys(groupedToDos).filter(
|
||||||
|
(key) => key !== "No Date"
|
||||||
|
);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<View marginB-140>
|
<View marginB-402>
|
||||||
|
|
||||||
{noDateToDos.length > 0 && (
|
{noDateToDos.length > 0 && (
|
||||||
<View key="No Date">
|
<View key="No Date">
|
||||||
{noDateToDos
|
<View row spread paddingH-19 marginB-12>
|
||||||
|
<Text
|
||||||
|
text70
|
||||||
|
style={{
|
||||||
|
fontWeight: "bold",
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
Unscheduled
|
||||||
|
</Text>
|
||||||
|
{!expandNoDate && (
|
||||||
|
<AntDesign name="caretright" size={24} color="#fd1575" onPress={() => {setExpandNoDate(!expandNoDate)}}/>
|
||||||
|
)}
|
||||||
|
{expandNoDate && (
|
||||||
|
<AntDesign name="caretdown" size={24} color="#fd1575" onPress={() => {setExpandNoDate(!expandNoDate)}}/>
|
||||||
|
)}
|
||||||
|
</View>
|
||||||
|
{expandNoDate &&
|
||||||
|
noDateToDos
|
||||||
.sort((a, b) => Number(a.done) - Number(b.done))
|
.sort((a, b) => Number(a.done) - Number(b.done))
|
||||||
.map((item) => (
|
.map((item) => <ToDoItem key={item.id} item={item} />)}
|
||||||
<ToDoItem key={item.id} item={item} />
|
|
||||||
))}
|
|
||||||
</View>
|
</View>
|
||||||
)}
|
)}
|
||||||
|
|
||||||
{datedToDos.map((dateKey) => {
|
{datedToDos.map((dateKey) => {
|
||||||
|
const isExpanded = expandedGroups[dateKey] || false;
|
||||||
const sortedToDos = [
|
const sortedToDos = [
|
||||||
...groupedToDos[dateKey].filter((toDo) => !toDo.done),
|
...groupedToDos[dateKey].filter((toDo) => !toDo.done),
|
||||||
...groupedToDos[dateKey].filter((toDo) => toDo.done),
|
...groupedToDos[dateKey].filter((toDo) => toDo.done),
|
||||||
@ -55,19 +87,34 @@ const ToDosList = () => {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<View key={dateKey}>
|
<View key={dateKey}>
|
||||||
|
<TouchableOpacity
|
||||||
|
onPress={() => toggleExpand(dateKey)}
|
||||||
|
style={{
|
||||||
|
flexDirection: "row",
|
||||||
|
justifyContent: "space-between",
|
||||||
|
alignItems: "center",
|
||||||
|
paddingHorizontal: 20,
|
||||||
|
marginVertical: 8,
|
||||||
|
}}
|
||||||
|
>
|
||||||
<Text
|
<Text
|
||||||
text70
|
text70
|
||||||
style={{
|
style={{
|
||||||
fontWeight: "bold",
|
fontWeight: "bold",
|
||||||
marginVertical: 8,
|
|
||||||
paddingHorizontal: 20,
|
|
||||||
}}
|
}}
|
||||||
>
|
>
|
||||||
{dateKey}
|
{dateKey}
|
||||||
</Text>
|
</Text>
|
||||||
{sortedToDos.map((item) => (
|
{!isExpanded && (
|
||||||
<ToDoItem key={item.id} item={item} />
|
<AntDesign name="caretright" size={24} color="#fd1575" />
|
||||||
))}
|
)}
|
||||||
|
{isExpanded && (
|
||||||
|
<AntDesign name="caretdown" size={24} color="#fd1575" />
|
||||||
|
)}
|
||||||
|
</TouchableOpacity>
|
||||||
|
|
||||||
|
{isExpanded &&
|
||||||
|
sortedToDos.map((item) => <ToDoItem key={item.id} item={item} />)}
|
||||||
</View>
|
</View>
|
||||||
);
|
);
|
||||||
})}
|
})}
|
||||||
|
|||||||
@ -5,6 +5,11 @@ import {useRouter} from "expo-router";
|
|||||||
import firestore from "@react-native-firebase/firestore";
|
import firestore from "@react-native-firebase/firestore";
|
||||||
import {UserProfile} from "@/hooks/firebase/types/profileTypes";
|
import {UserProfile} from "@/hooks/firebase/types/profileTypes";
|
||||||
|
|
||||||
|
import * as Notifications from 'expo-notifications';
|
||||||
|
import * as Device from 'expo-device';
|
||||||
|
import Constants from 'expo-constants';
|
||||||
|
import { Platform } from 'react-native';
|
||||||
|
|
||||||
export enum ProfileType {
|
export enum ProfileType {
|
||||||
"PARENT" = "parent",
|
"PARENT" = "parent",
|
||||||
"CHILD" = "child",
|
"CHILD" = "child",
|
||||||
@ -19,48 +24,118 @@ interface IAuthContext {
|
|||||||
refreshProfileData: () => Promise<void>
|
refreshProfileData: () => Promise<void>
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Notifications.setNotificationHandler({
|
||||||
|
handleNotification: async () => ({
|
||||||
|
shouldShowAlert: true,
|
||||||
|
shouldPlaySound: true,
|
||||||
|
shouldSetBadge: true,
|
||||||
|
}),
|
||||||
|
});
|
||||||
|
|
||||||
|
Notifications.addNotificationReceivedListener(notification => {
|
||||||
|
console.log('Notification received:', notification);
|
||||||
|
});
|
||||||
|
|
||||||
|
async function registerForPushNotificationsAsync() {
|
||||||
|
if (Platform.OS === 'android') {
|
||||||
|
await Notifications.setNotificationChannelAsync('default', {
|
||||||
|
name: 'default',
|
||||||
|
importance: Notifications.AndroidImportance.MAX,
|
||||||
|
vibrationPattern: [0, 250, 250, 250],
|
||||||
|
lightColor: '#FF231F7C',
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
if (Device.isDevice) {
|
||||||
|
const { status: existingStatus } = await Notifications.getPermissionsAsync();
|
||||||
|
let finalStatus = existingStatus;
|
||||||
|
|
||||||
|
if (existingStatus !== 'granted') {
|
||||||
|
const { status } = await Notifications.requestPermissionsAsync();
|
||||||
|
finalStatus = status;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (finalStatus !== 'granted') {
|
||||||
|
alert('Failed to get push token for push notification!');
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const projectId =
|
||||||
|
Constants?.expoConfig?.extra?.eas?.projectId ?? Constants?.easConfig?.projectId;
|
||||||
|
|
||||||
|
if (!projectId) {
|
||||||
|
alert('Project ID not found');
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
const token = (await Notifications.getExpoPushTokenAsync({ projectId })).data;
|
||||||
|
console.log('Push Token:', token);
|
||||||
|
return token;
|
||||||
|
} catch (error) {
|
||||||
|
alert(`Error getting push token: ${error}`);
|
||||||
|
throw error;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
alert('Must use a physical device for push notifications');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
const AuthContext = createContext<IAuthContext>(undefined!)
|
const AuthContext = createContext<IAuthContext>(undefined!)
|
||||||
|
|
||||||
export const AuthContextProvider: FC<{ children: ReactNode }> = ({children}) => {
|
export const AuthContextProvider: FC<{ children: ReactNode }> = ({children}) => {
|
||||||
const [user, setUser] = useState<FirebaseAuthTypes.User | null>(null)
|
const [user, setUser] = useState<FirebaseAuthTypes.User | null>(null);
|
||||||
const [initializing, setInitializing] = useState(true);
|
const [initializing, setInitializing] = useState(true);
|
||||||
const [profileType, setProfileType] = useState<ProfileType | undefined>(undefined);
|
const [profileType, setProfileType] = useState<ProfileType | undefined>(undefined);
|
||||||
const [profileData, setProfileData] = useState<UserProfile | undefined>(undefined);
|
const [profileData, setProfileData] = useState<UserProfile | undefined>(undefined);
|
||||||
|
const {replace} = useRouter();
|
||||||
|
const ready = !initializing;
|
||||||
|
|
||||||
const {replace} = useRouter()
|
const onAuthStateChangedHandler = async (authUser: FirebaseAuthTypes.User | null) => {
|
||||||
const ready = !initializing
|
setUser(authUser);
|
||||||
|
|
||||||
const onAuthStateChanged = async (user: FirebaseAuthTypes.User | null) => {
|
if (authUser) {
|
||||||
setUser(user);
|
await refreshProfileData(authUser);
|
||||||
|
const pushToken = await registerForPushNotificationsAsync();
|
||||||
if (user) {
|
if (pushToken) {
|
||||||
await refreshProfileData();
|
await savePushTokenToFirestore(authUser.uid, pushToken);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (initializing) setInitializing(false);
|
if (initializing) setInitializing(false);
|
||||||
}
|
};
|
||||||
|
|
||||||
const refreshProfileData = async () => {
|
const refreshProfileData = async (user?: FirebaseAuthTypes.User) => {
|
||||||
if (user) {
|
const authUser = user ?? auth().currentUser
|
||||||
|
if (authUser) {
|
||||||
try {
|
try {
|
||||||
const documentSnapshot = await firestore()
|
const documentSnapshot = await firestore()
|
||||||
.collection("Profiles")
|
.collection("Profiles")
|
||||||
.doc(user.uid)
|
.doc(authUser.uid)
|
||||||
.get();
|
.get();
|
||||||
if (documentSnapshot.exists) {
|
if (documentSnapshot.exists) {
|
||||||
setProfileType(documentSnapshot.data()?.userType);
|
setProfileType(documentSnapshot.data()?.userType);
|
||||||
setProfileData(documentSnapshot.data() as UserProfile);
|
setProfileData(documentSnapshot.data() as UserProfile);
|
||||||
}
|
}
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.error("Error fetching user profile data:", error);
|
|
||||||
setProfileType(undefined);
|
setProfileType(undefined);
|
||||||
setProfileData(undefined);
|
setProfileData(undefined);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const savePushTokenToFirestore = async (uid: string, token: string) => {
|
||||||
|
try {
|
||||||
|
await firestore().collection("Profiles").doc(uid).update({
|
||||||
|
pushToken: token,
|
||||||
|
});
|
||||||
|
} catch (error) {
|
||||||
|
console.error('Error saving push token to Firestore:', error);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
const subscriber = auth().onAuthStateChanged(onAuthStateChanged);
|
const subscriber = auth().onAuthStateChanged(onAuthStateChangedHandler);
|
||||||
return subscriber;
|
return subscriber;
|
||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
@ -72,9 +147,9 @@ export const AuthContextProvider: FC<{ children: ReactNode }> = ({children}) =>
|
|||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (ready && user) {
|
if (ready && user) {
|
||||||
replace({pathname: "/(auth)/calendar"})
|
replace({pathname: "/(auth)/calendar"});
|
||||||
} else if (ready && !user) {
|
} else if (ready && !user) {
|
||||||
replace({pathname: "/(unauth)"})
|
replace({pathname: "/(unauth)"});
|
||||||
}
|
}
|
||||||
}, [user, ready]);
|
}, [user, ready]);
|
||||||
|
|
||||||
@ -86,7 +161,8 @@ export const AuthContextProvider: FC<{ children: ReactNode }> = ({children}) =>
|
|||||||
<AuthContext.Provider value={{user, profileType, profileData, setProfileData, refreshProfileData}}>
|
<AuthContext.Provider value={{user, profileType, profileData, setProfileData, refreshProfileData}}>
|
||||||
{children}
|
{children}
|
||||||
</AuthContext.Provider>
|
</AuthContext.Provider>
|
||||||
)
|
);
|
||||||
}
|
};
|
||||||
|
|
||||||
|
|
||||||
export const useAuthContext = () => useContext(AuthContext)!;
|
export const useAuthContext = () => useContext(AuthContext)!;
|
||||||
|
|||||||
@ -3,7 +3,7 @@ import React, { createContext, useContext, useState, ReactNode } from "react";
|
|||||||
|
|
||||||
// Define the CalendarEvent interface
|
// Define the CalendarEvent interface
|
||||||
export interface CalendarEvent {
|
export interface CalendarEvent {
|
||||||
id?: number; // Unique identifier for the event
|
id?: number | string; // Unique identifier for the event
|
||||||
user?: string;
|
user?: string;
|
||||||
title: string; // Event title or name
|
title: string; // Event title or name
|
||||||
description?: string; // Optional description for the event
|
description?: string; // Optional description for the event
|
||||||
|
|||||||
@ -1,6 +1,9 @@
|
|||||||
import { MaterialCommunityIcons } from "@expo/vector-icons";
|
|
||||||
import {createContext, useContext, useState} from "react";
|
import {createContext, useContext, useState} from "react";
|
||||||
import fuzzysort from "fuzzysort";
|
import fuzzysort from "fuzzysort";
|
||||||
|
import {useCreateGrocery} from "@/hooks/firebase/useCreateGrocery";
|
||||||
|
import {IGrocery} from "@/hooks/firebase/types/groceryData";
|
||||||
|
import {useUpdateGrocery} from "@/hooks/firebase/useUpdateGrocery";
|
||||||
|
import {useGetGroceries} from "@/hooks/firebase/useGetGroceries";
|
||||||
|
|
||||||
export enum GroceryFrequency {
|
export enum GroceryFrequency {
|
||||||
Never = "Never",
|
Never = "Never",
|
||||||
@ -11,16 +14,6 @@ export enum GroceryFrequency {
|
|||||||
Quarterly = "Quarterly",
|
Quarterly = "Quarterly",
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface IGrocery {
|
|
||||||
id: number;
|
|
||||||
title: string;
|
|
||||||
category: GroceryCategory;
|
|
||||||
approved: boolean;
|
|
||||||
recurring: boolean;
|
|
||||||
frequency: GroceryFrequency;
|
|
||||||
bought: boolean;
|
|
||||||
}
|
|
||||||
|
|
||||||
export enum GroceryCategory {
|
export enum GroceryCategory {
|
||||||
Fruit = "Fruit",
|
Fruit = "Fruit",
|
||||||
Dairy = "Dairy",
|
Dairy = "Dairy",
|
||||||
@ -52,23 +45,7 @@ const iconMapping: { [key in GroceryCategory]: MaterialIconNames } = {
|
|||||||
[GroceryCategory.Frozen]: "snowflake",
|
[GroceryCategory.Frozen]: "snowflake",
|
||||||
};*/
|
};*/
|
||||||
|
|
||||||
interface IGroceryContext {
|
const initialGroceryList = [
|
||||||
groceries: IGrocery[];
|
|
||||||
//iconMapping: { [key in GroceryCategory]: MaterialIconNames };
|
|
||||||
updateGroceryItem: (id: number, changes: Partial<IGrocery>) => void;
|
|
||||||
isAddingGrocery: boolean;
|
|
||||||
setIsAddingGrocery: (value: boolean) => void;
|
|
||||||
addGrocery: (grocery: IGrocery) => void;
|
|
||||||
fuzzyMatchGroceryCategory: (groceryTitle: string) => GroceryCategory;
|
|
||||||
}
|
|
||||||
|
|
||||||
const GroceryContext = createContext<IGroceryContext | undefined>(undefined);
|
|
||||||
|
|
||||||
export const GroceryProvider: React.FC<{ children: React.ReactNode }> = ({
|
|
||||||
children,
|
|
||||||
}) => {
|
|
||||||
const [isAddingGrocery, setIsAddingGrocery] = useState<boolean>(false);
|
|
||||||
const [groceries, setGroceries] = useState<IGrocery[]>([
|
|
||||||
{
|
{
|
||||||
id: 0,
|
id: 0,
|
||||||
title: "Carrots",
|
title: "Carrots",
|
||||||
@ -105,19 +82,7 @@ export const GroceryProvider: React.FC<{ children: React.ReactNode }> = ({
|
|||||||
recurring: false,
|
recurring: false,
|
||||||
frequency: GroceryFrequency.Never,
|
frequency: GroceryFrequency.Never,
|
||||||
},
|
},
|
||||||
]);
|
];
|
||||||
|
|
||||||
const addGrocery = (grocery: IGrocery) => {
|
|
||||||
setGroceries((prevGroceries) => [
|
|
||||||
...prevGroceries,
|
|
||||||
{
|
|
||||||
...grocery,
|
|
||||||
id: prevGroceries.length
|
|
||||||
? prevGroceries[prevGroceries.length - 1].id + 1
|
|
||||||
: 0,
|
|
||||||
},
|
|
||||||
]);
|
|
||||||
};
|
|
||||||
|
|
||||||
const groceryExamples = {
|
const groceryExamples = {
|
||||||
[GroceryCategory.Fruit]: [
|
[GroceryCategory.Fruit]: [
|
||||||
@ -206,6 +171,32 @@ export const GroceryProvider: React.FC<{ children: React.ReactNode }> = ({
|
|||||||
],
|
],
|
||||||
};
|
};
|
||||||
|
|
||||||
|
interface IGroceryContext {
|
||||||
|
groceries: IGrocery[];
|
||||||
|
//iconMapping: { [key in GroceryCategory]: MaterialIconNames };
|
||||||
|
updateGroceryItem: (changes: Partial<IGrocery>) => void;
|
||||||
|
isAddingGrocery: boolean;
|
||||||
|
setIsAddingGrocery: (value: boolean) => void;
|
||||||
|
addGrocery: (grocery: IGrocery) => void;
|
||||||
|
fuzzyMatchGroceryCategory: (groceryTitle: string) => GroceryCategory;
|
||||||
|
}
|
||||||
|
|
||||||
|
const GroceryContext = createContext<IGroceryContext | undefined>(undefined);
|
||||||
|
|
||||||
|
export const GroceryProvider: React.FC<{ children: React.ReactNode }> = ({
|
||||||
|
children,
|
||||||
|
}) => {
|
||||||
|
const [isAddingGrocery, setIsAddingGrocery] = useState<boolean>(false);
|
||||||
|
|
||||||
|
const { mutateAsync: createGrocery } = useCreateGrocery();
|
||||||
|
const { mutateAsync: updateGrocery } = useUpdateGrocery();
|
||||||
|
const { data: groceries } = useGetGroceries();
|
||||||
|
|
||||||
|
|
||||||
|
const addGrocery = (grocery: IGrocery) => {
|
||||||
|
createGrocery(grocery);
|
||||||
|
};
|
||||||
|
|
||||||
const fuzzyMatchGroceryCategory = (groceryTitle: string): GroceryCategory => {
|
const fuzzyMatchGroceryCategory = (groceryTitle: string): GroceryCategory => {
|
||||||
let bestMatchCategory = GroceryCategory.None;
|
let bestMatchCategory = GroceryCategory.None;
|
||||||
let bestMatchScore = -1000;
|
let bestMatchScore = -1000;
|
||||||
@ -221,12 +212,8 @@ export const GroceryProvider: React.FC<{ children: React.ReactNode }> = ({
|
|||||||
return bestMatchCategory;
|
return bestMatchCategory;
|
||||||
};
|
};
|
||||||
|
|
||||||
const updateGroceryItem = (id: number, changes: Partial<IGrocery>) => {
|
const updateGroceryItem = (changes: Partial<IGrocery>) => {
|
||||||
setGroceries((prevGroceries) =>
|
updateGrocery(changes);
|
||||||
prevGroceries.map((grocery) =>
|
|
||||||
grocery.id === id ? { ...grocery, ...changes } : grocery
|
|
||||||
)
|
|
||||||
);
|
|
||||||
};
|
};
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
|||||||
10
eas.json
10
eas.json
@ -5,12 +5,16 @@
|
|||||||
"build": {
|
"build": {
|
||||||
"development": {
|
"development": {
|
||||||
"developmentClient": true,
|
"developmentClient": true,
|
||||||
"distribution": "internal"
|
"distribution": "internal",
|
||||||
|
"channel": "development"
|
||||||
},
|
},
|
||||||
"preview": {
|
"preview": {
|
||||||
"distribution": "internal"
|
"distribution": "internal",
|
||||||
|
"channel": "preview"
|
||||||
},
|
},
|
||||||
"production": {}
|
"production": {
|
||||||
|
"channel": "production"
|
||||||
|
}
|
||||||
},
|
},
|
||||||
"submit": {
|
"submit": {
|
||||||
"production": {
|
"production": {
|
||||||
|
|||||||
@ -1,15 +1,110 @@
|
|||||||
const {onRequest} = require("firebase-functions/v2/https");
|
const {onRequest} = require("firebase-functions/v2/https");
|
||||||
const {getAuth} = require("firebase-admin/auth");
|
const {getAuth} = require("firebase-admin/auth");
|
||||||
const {getFirestore} = require("firebase-admin/firestore");
|
const {getFirestore} = require("firebase-admin/firestore");
|
||||||
const admin = require("firebase-admin");
|
|
||||||
const logger = require("firebase-functions/logger");
|
const logger = require("firebase-functions/logger");
|
||||||
|
const functions = require('firebase-functions');
|
||||||
|
const admin = require('firebase-admin');
|
||||||
|
const {Expo} = require('expo-server-sdk');
|
||||||
|
|
||||||
try {
|
|
||||||
admin.initializeApp();
|
admin.initializeApp();
|
||||||
} catch (error) {
|
const db = admin.firestore();
|
||||||
console.error(error)
|
|
||||||
|
let expo = new Expo({accessToken: process.env.EXPO_ACCESS_TOKEN});
|
||||||
|
|
||||||
|
// Firestore trigger that listens for new events in the 'Events' collection
|
||||||
|
exports.sendNotificationOnEventCreation = functions.firestore
|
||||||
|
.document('Events/{eventId}')
|
||||||
|
.onCreate(async (snapshot, context) => {
|
||||||
|
const eventData = snapshot.data();
|
||||||
|
const { familyId, creatorId } = eventData;
|
||||||
|
|
||||||
|
if (!familyId || !creatorId) {
|
||||||
|
console.error('Missing familyId or creatorId in event data');
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const pushTokens = await getPushTokensForFamilyExcludingCreator(familyId, creatorId);
|
||||||
|
|
||||||
|
if (!pushTokens.length) {
|
||||||
|
console.log('No push tokens available for the event.');
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
let messages = [];
|
||||||
|
for (let pushToken of pushTokens) {
|
||||||
|
if (!Expo.isExpoPushToken(pushToken)) {
|
||||||
|
console.error(`Push token ${pushToken} is not a valid Expo push token`);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
messages.push({
|
||||||
|
to: pushToken,
|
||||||
|
sound: 'default',
|
||||||
|
title: 'New Event Added!',
|
||||||
|
body: `An event "${eventData.title}" has been added. Check it out!`,
|
||||||
|
data: { eventId: context.params.eventId },
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
let chunks = expo.chunkPushNotifications(messages);
|
||||||
|
let tickets = [];
|
||||||
|
for (let chunk of chunks) {
|
||||||
|
try {
|
||||||
|
let ticketChunk = await expo.sendPushNotificationsAsync(chunk);
|
||||||
|
tickets.push(...ticketChunk);
|
||||||
|
|
||||||
|
for (let ticket of ticketChunk) {
|
||||||
|
if (ticket.status === 'ok') {
|
||||||
|
console.log('Notification successfully sent:', ticket.id);
|
||||||
|
} else if (ticket.status === 'error') {
|
||||||
|
console.error(`Notification error: ${ticket.message}`);
|
||||||
|
if (ticket.details && ticket.details.error) {
|
||||||
|
console.error('Error details:', ticket.details.error);
|
||||||
|
if (ticket.details.error === 'DeviceNotRegistered') {
|
||||||
|
console.log(`Removing invalid push token: ${ticket.to}`);
|
||||||
|
await removeInvalidPushToken(ticket.to);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} catch (error) {
|
||||||
|
console.error('Error sending notification:', error);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Retrieve and handle notification receipts
|
||||||
|
let receiptIds = [];
|
||||||
|
for (let ticket of tickets) {
|
||||||
|
if (ticket.id) {
|
||||||
|
receiptIds.push(ticket.id);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
let receiptIdChunks = expo.chunkPushNotificationReceiptIds(receiptIds);
|
||||||
|
for (let chunk of receiptIdChunks) {
|
||||||
|
try {
|
||||||
|
let receipts = await expo.getPushNotificationReceiptsAsync(chunk);
|
||||||
|
console.log('Receipts:', receipts);
|
||||||
|
|
||||||
|
for (let receiptId in receipts) {
|
||||||
|
let { status, message, details } = receipts[receiptId];
|
||||||
|
if (status === 'ok') {
|
||||||
|
console.log(`Notification with receipt ID ${receiptId} was delivered successfully`);
|
||||||
|
} else if (status === 'error') {
|
||||||
|
console.error(`Notification error: ${message}`);
|
||||||
|
if (details && details.error) {
|
||||||
|
console.error(`Error details: ${details.error}`);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} catch (error) {
|
||||||
|
console.error('Error retrieving receipts:', error);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return null;
|
||||||
|
});
|
||||||
|
|
||||||
exports.createSubUser = onRequest(async (request, response) => {
|
exports.createSubUser = onRequest(async (request, response) => {
|
||||||
const authHeader = request.get('Authorization');
|
const authHeader = request.get('Authorization');
|
||||||
|
|
||||||
@ -97,3 +192,35 @@ exports.generateCustomToken = onRequest(async (request, response) => {
|
|||||||
response.status(500).json({error: "Failed to generate custom token"});
|
response.status(500).json({error: "Failed to generate custom token"});
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
async function getPushTokensForEvent() {
|
||||||
|
const usersRef = db.collection('Profiles');
|
||||||
|
const snapshot = await usersRef.get();
|
||||||
|
let pushTokens = [];
|
||||||
|
|
||||||
|
snapshot.forEach(doc => {
|
||||||
|
const data = doc.data();
|
||||||
|
if (data.pushToken) {
|
||||||
|
pushTokens.push(data.pushToken);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
console.log('Push Tokens:', pushTokens);
|
||||||
|
return pushTokens;
|
||||||
|
}
|
||||||
|
|
||||||
|
async function getPushTokensForFamilyExcludingCreator(familyId, creatorId) {
|
||||||
|
const usersRef = db.collection('Profiles');
|
||||||
|
const snapshot = await usersRef.where('familyId', '==', familyId).get();
|
||||||
|
let pushTokens = [];
|
||||||
|
|
||||||
|
snapshot.forEach(doc => {
|
||||||
|
const data = doc.data();
|
||||||
|
// Exclude the creator
|
||||||
|
if (data.uid !== creatorId && data.pushToken) {
|
||||||
|
pushTokens.push(data.pushToken);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
return pushTokens;
|
||||||
|
}
|
||||||
|
|||||||
53
firebase/functions/package-lock.json
generated
53
firebase/functions/package-lock.json
generated
@ -6,6 +6,7 @@
|
|||||||
"": {
|
"": {
|
||||||
"name": "functions",
|
"name": "functions",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
|
"expo-server-sdk": "^3.11.0",
|
||||||
"firebase-admin": "^12.1.0",
|
"firebase-admin": "^12.1.0",
|
||||||
"firebase-functions": "^5.0.0"
|
"firebase-functions": "^5.0.0"
|
||||||
},
|
},
|
||||||
@ -3115,6 +3116,12 @@
|
|||||||
"once": "^1.4.0"
|
"once": "^1.4.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/err-code": {
|
||||||
|
"version": "2.0.3",
|
||||||
|
"resolved": "https://registry.npmjs.org/err-code/-/err-code-2.0.3.tgz",
|
||||||
|
"integrity": "sha512-2bmlRpNKBxT/CRmPOlyISQpNj+qSeYvcym/uT0Jx2bMOlKLtSy1ZmLuVxSEKKyor/N5yhvp/ZiG1oE3DEYMSFA==",
|
||||||
|
"license": "MIT"
|
||||||
|
},
|
||||||
"node_modules/error-ex": {
|
"node_modules/error-ex": {
|
||||||
"version": "1.3.2",
|
"version": "1.3.2",
|
||||||
"resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz",
|
"resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz",
|
||||||
@ -3425,6 +3432,16 @@
|
|||||||
"node": "^14.15.0 || ^16.10.0 || >=18.0.0"
|
"node": "^14.15.0 || ^16.10.0 || >=18.0.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/expo-server-sdk": {
|
||||||
|
"version": "3.11.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/expo-server-sdk/-/expo-server-sdk-3.11.0.tgz",
|
||||||
|
"integrity": "sha512-EGH82ZcdAFjKq+6daDE8Xj7BjaSeP1VDvZ3Hmtn/KzEQ3ffqHkauMsgXL2wLEPlvatLq3EsYNcejXRBV54WnFQ==",
|
||||||
|
"dependencies": {
|
||||||
|
"node-fetch": "^2.6.0",
|
||||||
|
"promise-limit": "^2.7.0",
|
||||||
|
"promise-retry": "^2.0.1"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/express": {
|
"node_modules/express": {
|
||||||
"version": "4.19.2",
|
"version": "4.19.2",
|
||||||
"resolved": "https://registry.npmjs.org/express/-/express-4.19.2.tgz",
|
"resolved": "https://registry.npmjs.org/express/-/express-4.19.2.tgz",
|
||||||
@ -5754,7 +5771,6 @@
|
|||||||
"resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.7.0.tgz",
|
"resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.7.0.tgz",
|
||||||
"integrity": "sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A==",
|
"integrity": "sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A==",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"optional": true,
|
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"whatwg-url": "^5.0.0"
|
"whatwg-url": "^5.0.0"
|
||||||
},
|
},
|
||||||
@ -6183,6 +6199,34 @@
|
|||||||
"url": "https://github.com/chalk/ansi-styles?sponsor=1"
|
"url": "https://github.com/chalk/ansi-styles?sponsor=1"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/promise-limit": {
|
||||||
|
"version": "2.7.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/promise-limit/-/promise-limit-2.7.0.tgz",
|
||||||
|
"integrity": "sha512-7nJ6v5lnJsXwGprnGXga4wx6d1POjvi5Qmf1ivTRxTjH4Z/9Czja/UCMLVmB9N93GeWOU93XaFaEt6jbuoagNw==",
|
||||||
|
"license": "ISC"
|
||||||
|
},
|
||||||
|
"node_modules/promise-retry": {
|
||||||
|
"version": "2.0.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/promise-retry/-/promise-retry-2.0.1.tgz",
|
||||||
|
"integrity": "sha512-y+WKFlBR8BGXnsNlIHFGPZmyDf3DFMoLhaflAnyZgV6rG6xu+JwesTo2Q9R6XwYmtmwAFCkAk3e35jEdoeh/3g==",
|
||||||
|
"license": "MIT",
|
||||||
|
"dependencies": {
|
||||||
|
"err-code": "^2.0.2",
|
||||||
|
"retry": "^0.12.0"
|
||||||
|
},
|
||||||
|
"engines": {
|
||||||
|
"node": ">=10"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"node_modules/promise-retry/node_modules/retry": {
|
||||||
|
"version": "0.12.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/retry/-/retry-0.12.0.tgz",
|
||||||
|
"integrity": "sha512-9LkiTwjUh6rT555DtE9rTX+BKByPfrMzEAtnlEtdEwr3Nkffwiihqe2bWADg+OQRjt9gl6ICdmB/ZFDCGAtSow==",
|
||||||
|
"license": "MIT",
|
||||||
|
"engines": {
|
||||||
|
"node": ">= 4"
|
||||||
|
}
|
||||||
|
},
|
||||||
"node_modules/prompts": {
|
"node_modules/prompts": {
|
||||||
"version": "2.4.2",
|
"version": "2.4.2",
|
||||||
"resolved": "https://registry.npmjs.org/prompts/-/prompts-2.4.2.tgz",
|
"resolved": "https://registry.npmjs.org/prompts/-/prompts-2.4.2.tgz",
|
||||||
@ -7048,8 +7092,7 @@
|
|||||||
"version": "0.0.3",
|
"version": "0.0.3",
|
||||||
"resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz",
|
"resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz",
|
||||||
"integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==",
|
"integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==",
|
||||||
"license": "MIT",
|
"license": "MIT"
|
||||||
"optional": true
|
|
||||||
},
|
},
|
||||||
"node_modules/ts-api-utils": {
|
"node_modules/ts-api-utils": {
|
||||||
"version": "1.3.0",
|
"version": "1.3.0",
|
||||||
@ -7268,8 +7311,7 @@
|
|||||||
"version": "3.0.1",
|
"version": "3.0.1",
|
||||||
"resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz",
|
"resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz",
|
||||||
"integrity": "sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==",
|
"integrity": "sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==",
|
||||||
"license": "BSD-2-Clause",
|
"license": "BSD-2-Clause"
|
||||||
"optional": true
|
|
||||||
},
|
},
|
||||||
"node_modules/websocket-driver": {
|
"node_modules/websocket-driver": {
|
||||||
"version": "0.7.4",
|
"version": "0.7.4",
|
||||||
@ -7299,7 +7341,6 @@
|
|||||||
"resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz",
|
"resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz",
|
||||||
"integrity": "sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==",
|
"integrity": "sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"optional": true,
|
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"tr46": "~0.0.3",
|
"tr46": "~0.0.3",
|
||||||
"webidl-conversions": "^3.0.0"
|
"webidl-conversions": "^3.0.0"
|
||||||
|
|||||||
@ -14,6 +14,7 @@
|
|||||||
},
|
},
|
||||||
"main": "index.js",
|
"main": "index.js",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
|
"expo-server-sdk": "^3.11.0",
|
||||||
"firebase-admin": "^12.1.0",
|
"firebase-admin": "^12.1.0",
|
||||||
"firebase-functions": "^5.0.0"
|
"firebase-functions": "^5.0.0"
|
||||||
},
|
},
|
||||||
|
|||||||
13
hooks/firebase/types/groceryData.ts
Normal file
13
hooks/firebase/types/groceryData.ts
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
import {GroceryCategory, GroceryFrequency} from "@/contexts/GroceryContext";
|
||||||
|
|
||||||
|
export interface IGrocery {
|
||||||
|
id: string;
|
||||||
|
title: string;
|
||||||
|
category: GroceryCategory;
|
||||||
|
approved: boolean;
|
||||||
|
recurring: boolean;
|
||||||
|
frequency: GroceryFrequency;
|
||||||
|
bought: boolean;
|
||||||
|
familyId?: string,
|
||||||
|
creatorId?: string
|
||||||
|
}
|
||||||
@ -4,16 +4,17 @@ import firestore from "@react-native-firebase/firestore";
|
|||||||
import { EventData } from "@/hooks/firebase/types/eventData";
|
import { EventData } from "@/hooks/firebase/types/eventData";
|
||||||
|
|
||||||
export const useCreateEvent = () => {
|
export const useCreateEvent = () => {
|
||||||
const {user: currentUser} = useAuthContext()
|
const {user: currentUser, profileData} = useAuthContext()
|
||||||
const queryClients = useQueryClient()
|
const queryClients = useQueryClient()
|
||||||
|
|
||||||
return useMutation({
|
return useMutation({
|
||||||
mutationKey: ["createEvent"],
|
mutationKey: ["createEvent"],
|
||||||
mutationFn: async (eventData: Partial<EventData>) => {
|
mutationFn: async (eventData: Partial<EventData>) => {
|
||||||
try {
|
try {
|
||||||
|
console.log("CALLLLL")
|
||||||
await firestore()
|
await firestore()
|
||||||
.collection("Events")
|
.collection("Events")
|
||||||
.add({...eventData, creatorId: currentUser?.uid})
|
.add({...eventData, creatorId: currentUser?.uid, familyId: profileData?.familyId})
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
console.error(e)
|
console.error(e)
|
||||||
}
|
}
|
||||||
|
|||||||
26
hooks/firebase/useCreateGrocery.ts
Normal file
26
hooks/firebase/useCreateGrocery.ts
Normal file
@ -0,0 +1,26 @@
|
|||||||
|
import { useMutation, useQueryClient } from "react-query";
|
||||||
|
import firestore from "@react-native-firebase/firestore";
|
||||||
|
import { useAuthContext } from "@/contexts/AuthContext";
|
||||||
|
import {IGrocery} from "@/hooks/firebase/types/groceryData";
|
||||||
|
|
||||||
|
export const useCreateGrocery = () => {
|
||||||
|
const { user: currentUser, profileData } = useAuthContext();
|
||||||
|
const queryClients = useQueryClient();
|
||||||
|
|
||||||
|
return useMutation({
|
||||||
|
mutationKey: ["createGrocery"],
|
||||||
|
mutationFn: async (groceryData: Partial<IGrocery>) => {
|
||||||
|
try {
|
||||||
|
const newDoc = firestore().collection('Groceries').doc();
|
||||||
|
await firestore()
|
||||||
|
.collection("Groceries")
|
||||||
|
.add({...groceryData, id: newDoc.id, familyId: profileData?.familyId, creatorId: currentUser?.uid})
|
||||||
|
} catch (e) {
|
||||||
|
console.error(e)
|
||||||
|
}
|
||||||
|
},
|
||||||
|
onSuccess: () => {
|
||||||
|
queryClients.invalidateQueries("groceries")
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
@ -31,6 +31,7 @@ export const useGetEvents = (isFamilyView: boolean) => {
|
|||||||
const eventColor: string = profileData?.eventColor || colorMap.pink // Default color if not found
|
const eventColor: string = profileData?.eventColor || colorMap.pink // Default color if not found
|
||||||
|
|
||||||
return {
|
return {
|
||||||
|
id: doc.id,
|
||||||
title: data.title,
|
title: data.title,
|
||||||
start: new Date(data.startDate.seconds * 1000),
|
start: new Date(data.startDate.seconds * 1000),
|
||||||
end: new Date(data.endDate.seconds * 1000),
|
end: new Date(data.endDate.seconds * 1000),
|
||||||
|
|||||||
32
hooks/firebase/useGetGroceries.ts
Normal file
32
hooks/firebase/useGetGroceries.ts
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
import {useQuery} from "react-query";
|
||||||
|
import firestore from "@react-native-firebase/firestore";
|
||||||
|
import {useAuthContext} from "@/contexts/AuthContext";
|
||||||
|
|
||||||
|
export const useGetGroceries = () => {
|
||||||
|
const { user, profileData } = useAuthContext();
|
||||||
|
|
||||||
|
return useQuery({
|
||||||
|
queryKey: ["groceries", user?.uid],
|
||||||
|
queryFn: async () => {
|
||||||
|
const snapshot = await firestore()
|
||||||
|
.collection("Groceries")
|
||||||
|
.where("familyId", "==", profileData?.familyId)
|
||||||
|
.get();
|
||||||
|
|
||||||
|
return snapshot.docs.map((doc) => {
|
||||||
|
const data = doc.data();
|
||||||
|
|
||||||
|
return {
|
||||||
|
id: doc.id,
|
||||||
|
title: data.title,
|
||||||
|
category: data.category,
|
||||||
|
approved: data.approved,
|
||||||
|
bought: data.bought,
|
||||||
|
recurring: data.recurring,
|
||||||
|
frequency: data.frequency,
|
||||||
|
creatorId: data.creatorId
|
||||||
|
};
|
||||||
|
});
|
||||||
|
}
|
||||||
|
})
|
||||||
|
};
|
||||||
26
hooks/firebase/useUpdateEvent.ts
Normal file
26
hooks/firebase/useUpdateEvent.ts
Normal file
@ -0,0 +1,26 @@
|
|||||||
|
import {useAuthContext} from "@/contexts/AuthContext";
|
||||||
|
import {useMutation, useQueryClient} from "react-query";
|
||||||
|
import firestore from "@react-native-firebase/firestore";
|
||||||
|
import {EventData} from "@/hooks/firebase/types/eventData";
|
||||||
|
|
||||||
|
export const useUpdateEvent = () => {
|
||||||
|
const {user: currentUser} = useAuthContext()
|
||||||
|
const queryClients = useQueryClient()
|
||||||
|
|
||||||
|
return useMutation({
|
||||||
|
mutationKey: ["updateEvent"],
|
||||||
|
mutationFn: async (eventData: Partial<EventData>) => {
|
||||||
|
try {
|
||||||
|
await firestore()
|
||||||
|
.collection("Events")
|
||||||
|
.doc(eventData.id)
|
||||||
|
.update(eventData);
|
||||||
|
} catch (e) {
|
||||||
|
console.error(e)
|
||||||
|
}
|
||||||
|
},
|
||||||
|
onSuccess: () => {
|
||||||
|
queryClients.invalidateQueries("events")
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
24
hooks/firebase/useUpdateGrocery.ts
Normal file
24
hooks/firebase/useUpdateGrocery.ts
Normal file
@ -0,0 +1,24 @@
|
|||||||
|
import {useMutation, useQueryClient} from "react-query";
|
||||||
|
import firestore from "@react-native-firebase/firestore";
|
||||||
|
import {IGrocery} from "@/hooks/firebase/types/groceryData";
|
||||||
|
|
||||||
|
export const useUpdateGrocery = () => {
|
||||||
|
const queryClients = useQueryClient()
|
||||||
|
|
||||||
|
return useMutation({
|
||||||
|
mutationKey: ["updateGrocery"],
|
||||||
|
mutationFn: async (groceryData: Partial<IGrocery>) => {
|
||||||
|
try {
|
||||||
|
await firestore()
|
||||||
|
.collection("Groceries")
|
||||||
|
.doc(groceryData.id)
|
||||||
|
.update(groceryData);
|
||||||
|
} catch (e) {
|
||||||
|
console.error(e)
|
||||||
|
}
|
||||||
|
},
|
||||||
|
onSuccess: () => {
|
||||||
|
queryClients.invalidateQueries("groceries")
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
@ -962,6 +962,8 @@ PODS:
|
|||||||
- BVLinearGradient (2.8.3):
|
- BVLinearGradient (2.8.3):
|
||||||
- React-Core
|
- React-Core
|
||||||
- DoubleConversion (1.1.6)
|
- DoubleConversion (1.1.6)
|
||||||
|
- EASClient (0.12.0):
|
||||||
|
- ExpoModulesCore
|
||||||
- EXApplication (5.9.1):
|
- EXApplication (5.9.1):
|
||||||
- ExpoModulesCore
|
- ExpoModulesCore
|
||||||
- EXBarCodeScanner (13.0.1):
|
- EXBarCodeScanner (13.0.1):
|
||||||
@ -977,6 +979,8 @@ PODS:
|
|||||||
- EXJSONUtils (0.13.1)
|
- EXJSONUtils (0.13.1)
|
||||||
- EXManifests (0.14.3):
|
- EXManifests (0.14.3):
|
||||||
- ExpoModulesCore
|
- ExpoModulesCore
|
||||||
|
- EXNotifications (0.28.18):
|
||||||
|
- ExpoModulesCore
|
||||||
- Expo (51.0.34):
|
- Expo (51.0.34):
|
||||||
- ExpoModulesCore
|
- ExpoModulesCore
|
||||||
- expo-dev-client (4.0.27):
|
- expo-dev-client (4.0.27):
|
||||||
@ -1186,10 +1190,6 @@ PODS:
|
|||||||
- ReactCommon/turbomodule/bridging
|
- ReactCommon/turbomodule/bridging
|
||||||
- ReactCommon/turbomodule/core
|
- ReactCommon/turbomodule/core
|
||||||
- Yoga
|
- Yoga
|
||||||
- ExpoAdapterGoogleSignIn (13.1.0):
|
|
||||||
- ExpoModulesCore
|
|
||||||
- GoogleSignIn (~> 7.1)
|
|
||||||
- React-Core
|
|
||||||
- ExpoAsset (10.0.10):
|
- ExpoAsset (10.0.10):
|
||||||
- ExpoModulesCore
|
- ExpoModulesCore
|
||||||
- ExpoCamera (15.0.16):
|
- ExpoCamera (15.0.16):
|
||||||
@ -1198,6 +1198,8 @@ PODS:
|
|||||||
- ZXingObjC/PDF417
|
- ZXingObjC/PDF417
|
||||||
- ExpoCrypto (13.0.2):
|
- ExpoCrypto (13.0.2):
|
||||||
- ExpoModulesCore
|
- ExpoModulesCore
|
||||||
|
- ExpoDevice (6.0.2):
|
||||||
|
- ExpoModulesCore
|
||||||
- ExpoFileSystem (17.0.1):
|
- ExpoFileSystem (17.0.1):
|
||||||
- ExpoModulesCore
|
- ExpoModulesCore
|
||||||
- ExpoFont (12.0.10):
|
- ExpoFont (12.0.10):
|
||||||
@ -1257,6 +1259,35 @@ PODS:
|
|||||||
- ReactCommon/turbomodule/bridging
|
- ReactCommon/turbomodule/bridging
|
||||||
- ReactCommon/turbomodule/core
|
- ReactCommon/turbomodule/core
|
||||||
- Yoga
|
- Yoga
|
||||||
|
- EXStructuredHeaders (3.8.0)
|
||||||
|
- EXUpdates (0.25.27):
|
||||||
|
- DoubleConversion
|
||||||
|
- EASClient
|
||||||
|
- EXManifests
|
||||||
|
- ExpoModulesCore
|
||||||
|
- EXStructuredHeaders
|
||||||
|
- EXUpdatesInterface
|
||||||
|
- glog
|
||||||
|
- hermes-engine
|
||||||
|
- RCT-Folly (= 2024.01.01.00)
|
||||||
|
- RCTRequired
|
||||||
|
- RCTTypeSafety
|
||||||
|
- ReachabilitySwift
|
||||||
|
- React-Codegen
|
||||||
|
- React-Core
|
||||||
|
- React-debug
|
||||||
|
- React-Fabric
|
||||||
|
- React-featureflags
|
||||||
|
- React-graphics
|
||||||
|
- React-ImageManager
|
||||||
|
- React-NativeModulesApple
|
||||||
|
- React-RCTFabric
|
||||||
|
- React-rendererdebug
|
||||||
|
- React-utils
|
||||||
|
- ReactCommon/turbomodule/bridging
|
||||||
|
- ReactCommon/turbomodule/core
|
||||||
|
- "sqlite3 (~> 3.45.3+1)"
|
||||||
|
- Yoga
|
||||||
- EXUpdatesInterface (0.16.2):
|
- EXUpdatesInterface (0.16.2):
|
||||||
- ExpoModulesCore
|
- ExpoModulesCore
|
||||||
- FBLazyVector (0.74.3)
|
- FBLazyVector (0.74.3)
|
||||||
@ -1351,10 +1382,6 @@ PODS:
|
|||||||
- GoogleUtilities/Environment (~> 7.7)
|
- GoogleUtilities/Environment (~> 7.7)
|
||||||
- nanopb (< 2.30911.0, >= 2.30908.0)
|
- nanopb (< 2.30911.0, >= 2.30908.0)
|
||||||
- PromisesObjC (< 3.0, >= 1.2)
|
- PromisesObjC (< 3.0, >= 1.2)
|
||||||
- GoogleSignIn (7.1.0):
|
|
||||||
- AppAuth (< 2.0, >= 1.7.3)
|
|
||||||
- GTMAppAuth (< 5.0, >= 4.1.1)
|
|
||||||
- GTMSessionFetcher/Core (~> 3.3)
|
|
||||||
- GoogleUtilities/AppDelegateSwizzler (7.13.3):
|
- GoogleUtilities/AppDelegateSwizzler (7.13.3):
|
||||||
- GoogleUtilities/Environment
|
- GoogleUtilities/Environment
|
||||||
- GoogleUtilities/Logger
|
- GoogleUtilities/Logger
|
||||||
@ -1458,9 +1485,6 @@ PODS:
|
|||||||
- gRPC-Core/Privacy (= 1.62.5)
|
- gRPC-Core/Privacy (= 1.62.5)
|
||||||
- gRPC-Core/Interface (1.62.5)
|
- gRPC-Core/Interface (1.62.5)
|
||||||
- gRPC-Core/Privacy (1.62.5)
|
- gRPC-Core/Privacy (1.62.5)
|
||||||
- GTMAppAuth (4.1.1):
|
|
||||||
- AppAuth/Core (~> 1.7)
|
|
||||||
- GTMSessionFetcher/Core (< 4.0, >= 3.3)
|
|
||||||
- GTMSessionFetcher/Core (3.5.0)
|
- GTMSessionFetcher/Core (3.5.0)
|
||||||
- hermes-engine (0.74.3):
|
- hermes-engine (0.74.3):
|
||||||
- hermes-engine/Pre-built (= 0.74.3)
|
- hermes-engine/Pre-built (= 0.74.3)
|
||||||
@ -1496,6 +1520,7 @@ PODS:
|
|||||||
- FBLazyVector (= 0.74.3)
|
- FBLazyVector (= 0.74.3)
|
||||||
- RCTRequired (= 0.74.3)
|
- RCTRequired (= 0.74.3)
|
||||||
- React-Core (= 0.74.3)
|
- React-Core (= 0.74.3)
|
||||||
|
- ReachabilitySwift (5.2.3)
|
||||||
- React (0.74.3):
|
- React (0.74.3):
|
||||||
- React-Core (= 0.74.3)
|
- React-Core (= 0.74.3)
|
||||||
- React-Core/DevSupport (= 0.74.3)
|
- React-Core/DevSupport (= 0.74.3)
|
||||||
@ -2704,9 +2729,6 @@ PODS:
|
|||||||
- ReactCommon/turbomodule/bridging
|
- ReactCommon/turbomodule/bridging
|
||||||
- ReactCommon/turbomodule/core
|
- ReactCommon/turbomodule/core
|
||||||
- Yoga
|
- Yoga
|
||||||
- RNGoogleSignin (13.1.0):
|
|
||||||
- GoogleSignIn (~> 7.1)
|
|
||||||
- React-Core
|
|
||||||
- RNReanimated (3.10.1):
|
- RNReanimated (3.10.1):
|
||||||
- DoubleConversion
|
- DoubleConversion
|
||||||
- glog
|
- glog
|
||||||
@ -2753,6 +2775,9 @@ PODS:
|
|||||||
- RNSVG (15.7.1):
|
- RNSVG (15.7.1):
|
||||||
- React-Core
|
- React-Core
|
||||||
- SocketRocket (0.7.0)
|
- SocketRocket (0.7.0)
|
||||||
|
- "sqlite3 (3.45.3+1)":
|
||||||
|
- "sqlite3/common (= 3.45.3+1)"
|
||||||
|
- "sqlite3/common (3.45.3+1)"
|
||||||
- Yoga (0.0.0)
|
- Yoga (0.0.0)
|
||||||
- ZXingObjC/Core (3.6.9)
|
- ZXingObjC/Core (3.6.9)
|
||||||
- ZXingObjC/OneD (3.6.9):
|
- ZXingObjC/OneD (3.6.9):
|
||||||
@ -2764,21 +2789,23 @@ DEPENDENCIES:
|
|||||||
- boost (from `../node_modules/react-native/third-party-podspecs/boost.podspec`)
|
- boost (from `../node_modules/react-native/third-party-podspecs/boost.podspec`)
|
||||||
- BVLinearGradient (from `../node_modules/react-native-linear-gradient`)
|
- BVLinearGradient (from `../node_modules/react-native-linear-gradient`)
|
||||||
- DoubleConversion (from `../node_modules/react-native/third-party-podspecs/DoubleConversion.podspec`)
|
- DoubleConversion (from `../node_modules/react-native/third-party-podspecs/DoubleConversion.podspec`)
|
||||||
|
- EASClient (from `../node_modules/expo-eas-client/ios`)
|
||||||
- EXApplication (from `../node_modules/expo-application/ios`)
|
- EXApplication (from `../node_modules/expo-application/ios`)
|
||||||
- EXBarCodeScanner (from `../node_modules/expo-barcode-scanner/ios`)
|
- EXBarCodeScanner (from `../node_modules/expo-barcode-scanner/ios`)
|
||||||
- EXConstants (from `../node_modules/expo-constants/ios`)
|
- EXConstants (from `../node_modules/expo-constants/ios`)
|
||||||
- EXImageLoader (from `../node_modules/expo-image-loader/ios`)
|
- EXImageLoader (from `../node_modules/expo-image-loader/ios`)
|
||||||
- EXJSONUtils (from `../node_modules/expo-json-utils/ios`)
|
- EXJSONUtils (from `../node_modules/expo-json-utils/ios`)
|
||||||
- EXManifests (from `../node_modules/expo-manifests/ios`)
|
- EXManifests (from `../node_modules/expo-manifests/ios`)
|
||||||
|
- EXNotifications (from `../node_modules/expo-notifications/ios`)
|
||||||
- Expo (from `../node_modules/expo`)
|
- Expo (from `../node_modules/expo`)
|
||||||
- expo-dev-client (from `../node_modules/expo-dev-client/ios`)
|
- expo-dev-client (from `../node_modules/expo-dev-client/ios`)
|
||||||
- expo-dev-launcher (from `../node_modules/expo-dev-launcher`)
|
- expo-dev-launcher (from `../node_modules/expo-dev-launcher`)
|
||||||
- expo-dev-menu (from `../node_modules/expo-dev-menu`)
|
- expo-dev-menu (from `../node_modules/expo-dev-menu`)
|
||||||
- expo-dev-menu-interface (from `../node_modules/expo-dev-menu-interface/ios`)
|
- expo-dev-menu-interface (from `../node_modules/expo-dev-menu-interface/ios`)
|
||||||
- "ExpoAdapterGoogleSignIn (from `../node_modules/@react-native-google-signin/google-signin/expo/ios`)"
|
|
||||||
- ExpoAsset (from `../node_modules/expo-asset/ios`)
|
- ExpoAsset (from `../node_modules/expo-asset/ios`)
|
||||||
- ExpoCamera (from `../node_modules/expo-camera/ios`)
|
- ExpoCamera (from `../node_modules/expo-camera/ios`)
|
||||||
- ExpoCrypto (from `../node_modules/expo-crypto/ios`)
|
- ExpoCrypto (from `../node_modules/expo-crypto/ios`)
|
||||||
|
- ExpoDevice (from `../node_modules/expo-device/ios`)
|
||||||
- ExpoFileSystem (from `../node_modules/expo-file-system/ios`)
|
- ExpoFileSystem (from `../node_modules/expo-file-system/ios`)
|
||||||
- ExpoFont (from `../node_modules/expo-font/ios`)
|
- ExpoFont (from `../node_modules/expo-font/ios`)
|
||||||
- ExpoHead (from `../node_modules/expo-router/ios`)
|
- ExpoHead (from `../node_modules/expo-router/ios`)
|
||||||
@ -2788,6 +2815,8 @@ DEPENDENCIES:
|
|||||||
- ExpoSystemUI (from `../node_modules/expo-system-ui/ios`)
|
- ExpoSystemUI (from `../node_modules/expo-system-ui/ios`)
|
||||||
- ExpoWebBrowser (from `../node_modules/expo-web-browser/ios`)
|
- ExpoWebBrowser (from `../node_modules/expo-web-browser/ios`)
|
||||||
- EXSplashScreen (from `../node_modules/expo-splash-screen/ios`)
|
- EXSplashScreen (from `../node_modules/expo-splash-screen/ios`)
|
||||||
|
- EXStructuredHeaders (from `../node_modules/expo-structured-headers/ios`)
|
||||||
|
- EXUpdates (from `../node_modules/expo-updates/ios`)
|
||||||
- EXUpdatesInterface (from `../node_modules/expo-updates-interface/ios`)
|
- EXUpdatesInterface (from `../node_modules/expo-updates-interface/ios`)
|
||||||
- FBLazyVector (from `../node_modules/react-native/Libraries/FBLazyVector`)
|
- FBLazyVector (from `../node_modules/react-native/Libraries/FBLazyVector`)
|
||||||
- fmt (from `../node_modules/react-native/third-party-podspecs/fmt.podspec`)
|
- fmt (from `../node_modules/react-native/third-party-podspecs/fmt.podspec`)
|
||||||
@ -2853,7 +2882,6 @@ DEPENDENCIES:
|
|||||||
- "RNFBFirestore (from `../node_modules/@react-native-firebase/firestore`)"
|
- "RNFBFirestore (from `../node_modules/@react-native-firebase/firestore`)"
|
||||||
- "RNFBFunctions (from `../node_modules/@react-native-firebase/functions`)"
|
- "RNFBFunctions (from `../node_modules/@react-native-firebase/functions`)"
|
||||||
- RNGestureHandler (from `../node_modules/react-native-gesture-handler`)
|
- RNGestureHandler (from `../node_modules/react-native-gesture-handler`)
|
||||||
- "RNGoogleSignin (from `../node_modules/@react-native-google-signin/google-signin`)"
|
|
||||||
- RNReanimated (from `../node_modules/react-native-reanimated`)
|
- RNReanimated (from `../node_modules/react-native-reanimated`)
|
||||||
- RNScreens (from `../node_modules/react-native-screens`)
|
- RNScreens (from `../node_modules/react-native-screens`)
|
||||||
- RNSVG (from `../node_modules/react-native-svg`)
|
- RNSVG (from `../node_modules/react-native-svg`)
|
||||||
@ -2881,18 +2909,18 @@ SPEC REPOS:
|
|||||||
- FirebaseSessions
|
- FirebaseSessions
|
||||||
- FirebaseSharedSwift
|
- FirebaseSharedSwift
|
||||||
- GoogleDataTransport
|
- GoogleDataTransport
|
||||||
- GoogleSignIn
|
|
||||||
- GoogleUtilities
|
- GoogleUtilities
|
||||||
- "gRPC-C++"
|
- "gRPC-C++"
|
||||||
- gRPC-Core
|
- gRPC-Core
|
||||||
- GTMAppAuth
|
|
||||||
- GTMSessionFetcher
|
- GTMSessionFetcher
|
||||||
- leveldb-library
|
- leveldb-library
|
||||||
- nanopb
|
- nanopb
|
||||||
- PromisesObjC
|
- PromisesObjC
|
||||||
- PromisesSwift
|
- PromisesSwift
|
||||||
|
- ReachabilitySwift
|
||||||
- RecaptchaInterop
|
- RecaptchaInterop
|
||||||
- SocketRocket
|
- SocketRocket
|
||||||
|
- sqlite3
|
||||||
- ZXingObjC
|
- ZXingObjC
|
||||||
|
|
||||||
EXTERNAL SOURCES:
|
EXTERNAL SOURCES:
|
||||||
@ -2902,6 +2930,8 @@ EXTERNAL SOURCES:
|
|||||||
:path: "../node_modules/react-native-linear-gradient"
|
:path: "../node_modules/react-native-linear-gradient"
|
||||||
DoubleConversion:
|
DoubleConversion:
|
||||||
:podspec: "../node_modules/react-native/third-party-podspecs/DoubleConversion.podspec"
|
:podspec: "../node_modules/react-native/third-party-podspecs/DoubleConversion.podspec"
|
||||||
|
EASClient:
|
||||||
|
:path: "../node_modules/expo-eas-client/ios"
|
||||||
EXApplication:
|
EXApplication:
|
||||||
:path: "../node_modules/expo-application/ios"
|
:path: "../node_modules/expo-application/ios"
|
||||||
EXBarCodeScanner:
|
EXBarCodeScanner:
|
||||||
@ -2914,6 +2944,8 @@ EXTERNAL SOURCES:
|
|||||||
:path: "../node_modules/expo-json-utils/ios"
|
:path: "../node_modules/expo-json-utils/ios"
|
||||||
EXManifests:
|
EXManifests:
|
||||||
:path: "../node_modules/expo-manifests/ios"
|
:path: "../node_modules/expo-manifests/ios"
|
||||||
|
EXNotifications:
|
||||||
|
:path: "../node_modules/expo-notifications/ios"
|
||||||
Expo:
|
Expo:
|
||||||
:path: "../node_modules/expo"
|
:path: "../node_modules/expo"
|
||||||
expo-dev-client:
|
expo-dev-client:
|
||||||
@ -2924,14 +2956,14 @@ EXTERNAL SOURCES:
|
|||||||
:path: "../node_modules/expo-dev-menu"
|
:path: "../node_modules/expo-dev-menu"
|
||||||
expo-dev-menu-interface:
|
expo-dev-menu-interface:
|
||||||
:path: "../node_modules/expo-dev-menu-interface/ios"
|
:path: "../node_modules/expo-dev-menu-interface/ios"
|
||||||
ExpoAdapterGoogleSignIn:
|
|
||||||
:path: "../node_modules/@react-native-google-signin/google-signin/expo/ios"
|
|
||||||
ExpoAsset:
|
ExpoAsset:
|
||||||
:path: "../node_modules/expo-asset/ios"
|
:path: "../node_modules/expo-asset/ios"
|
||||||
ExpoCamera:
|
ExpoCamera:
|
||||||
:path: "../node_modules/expo-camera/ios"
|
:path: "../node_modules/expo-camera/ios"
|
||||||
ExpoCrypto:
|
ExpoCrypto:
|
||||||
:path: "../node_modules/expo-crypto/ios"
|
:path: "../node_modules/expo-crypto/ios"
|
||||||
|
ExpoDevice:
|
||||||
|
:path: "../node_modules/expo-device/ios"
|
||||||
ExpoFileSystem:
|
ExpoFileSystem:
|
||||||
:path: "../node_modules/expo-file-system/ios"
|
:path: "../node_modules/expo-file-system/ios"
|
||||||
ExpoFont:
|
ExpoFont:
|
||||||
@ -2950,6 +2982,10 @@ EXTERNAL SOURCES:
|
|||||||
:path: "../node_modules/expo-web-browser/ios"
|
:path: "../node_modules/expo-web-browser/ios"
|
||||||
EXSplashScreen:
|
EXSplashScreen:
|
||||||
:path: "../node_modules/expo-splash-screen/ios"
|
:path: "../node_modules/expo-splash-screen/ios"
|
||||||
|
EXStructuredHeaders:
|
||||||
|
:path: "../node_modules/expo-structured-headers/ios"
|
||||||
|
EXUpdates:
|
||||||
|
:path: "../node_modules/expo-updates/ios"
|
||||||
EXUpdatesInterface:
|
EXUpdatesInterface:
|
||||||
:path: "../node_modules/expo-updates-interface/ios"
|
:path: "../node_modules/expo-updates-interface/ios"
|
||||||
FBLazyVector:
|
FBLazyVector:
|
||||||
@ -3077,8 +3113,6 @@ EXTERNAL SOURCES:
|
|||||||
:path: "../node_modules/@react-native-firebase/functions"
|
:path: "../node_modules/@react-native-firebase/functions"
|
||||||
RNGestureHandler:
|
RNGestureHandler:
|
||||||
:path: "../node_modules/react-native-gesture-handler"
|
:path: "../node_modules/react-native-gesture-handler"
|
||||||
RNGoogleSignin:
|
|
||||||
:path: "../node_modules/@react-native-google-signin/google-signin"
|
|
||||||
RNReanimated:
|
RNReanimated:
|
||||||
:path: "../node_modules/react-native-reanimated"
|
:path: "../node_modules/react-native-reanimated"
|
||||||
RNScreens:
|
RNScreens:
|
||||||
@ -3095,21 +3129,23 @@ SPEC CHECKSUMS:
|
|||||||
BoringSSL-GRPC: 1e2348957acdbcad360b80a264a90799984b2ba6
|
BoringSSL-GRPC: 1e2348957acdbcad360b80a264a90799984b2ba6
|
||||||
BVLinearGradient: 880f91a7854faff2df62518f0281afb1c60d49a3
|
BVLinearGradient: 880f91a7854faff2df62518f0281afb1c60d49a3
|
||||||
DoubleConversion: 76ab83afb40bddeeee456813d9c04f67f78771b5
|
DoubleConversion: 76ab83afb40bddeeee456813d9c04f67f78771b5
|
||||||
|
EASClient: 1509a9a6b48b932ec61667644634daf2562983b8
|
||||||
EXApplication: c08200c34daca7af7fd76ac4b9d606077410e8ad
|
EXApplication: c08200c34daca7af7fd76ac4b9d606077410e8ad
|
||||||
EXBarCodeScanner: e2dd9b42c1b522a2adc9202b1dfbc64cb34456d1
|
EXBarCodeScanner: e2dd9b42c1b522a2adc9202b1dfbc64cb34456d1
|
||||||
EXConstants: 409690fbfd5afea964e5e9d6c4eb2c2b59222c59
|
EXConstants: 409690fbfd5afea964e5e9d6c4eb2c2b59222c59
|
||||||
EXImageLoader: ab589d67d6c5f2c33572afea9917304418566334
|
EXImageLoader: ab589d67d6c5f2c33572afea9917304418566334
|
||||||
EXJSONUtils: 30c17fd9cc364d722c0946a550dfbf1be92ef6a4
|
EXJSONUtils: 30c17fd9cc364d722c0946a550dfbf1be92ef6a4
|
||||||
EXManifests: c1fab4c3237675e7b0299ea8df0bcb14baca4f42
|
EXManifests: c1fab4c3237675e7b0299ea8df0bcb14baca4f42
|
||||||
|
EXNotifications: dd289340c26bc5388e440fc90d0b2c661cbd0285
|
||||||
Expo: 963ef4ae102e4f4ac114a8510d70127c44adffbf
|
Expo: 963ef4ae102e4f4ac114a8510d70127c44adffbf
|
||||||
expo-dev-client: 85deba11af998ea86e62093b17fce56aa2c6f26b
|
expo-dev-client: 85deba11af998ea86e62093b17fce56aa2c6f26b
|
||||||
expo-dev-launcher: fe4f2c0a0aa627449eeaec5f9f11e04090f97c40
|
expo-dev-launcher: fe4f2c0a0aa627449eeaec5f9f11e04090f97c40
|
||||||
expo-dev-menu: 5b14897ecce3a8cf9e9cf9109344c2c192a3766a
|
expo-dev-menu: 5b14897ecce3a8cf9e9cf9109344c2c192a3766a
|
||||||
expo-dev-menu-interface: be32c09f1e03833050f0ee290dcc86b3ad0e73e4
|
expo-dev-menu-interface: be32c09f1e03833050f0ee290dcc86b3ad0e73e4
|
||||||
ExpoAdapterGoogleSignIn: da10ae7e7c1d73a10c2facebcdfe5ebea8e073ce
|
|
||||||
ExpoAsset: 323700f291684f110fb55f0d4022a3362ea9f875
|
ExpoAsset: 323700f291684f110fb55f0d4022a3362ea9f875
|
||||||
ExpoCamera: 929be541d1c1319fcf32f9f5d9df8b97804346b5
|
ExpoCamera: 929be541d1c1319fcf32f9f5d9df8b97804346b5
|
||||||
ExpoCrypto: 156078f266bf28f80ecf5e2a9c3a0d6ffce07a1c
|
ExpoCrypto: 156078f266bf28f80ecf5e2a9c3a0d6ffce07a1c
|
||||||
|
ExpoDevice: fc94f0e42ecdfd897e7590f2874fc64dfa7e9b1c
|
||||||
ExpoFileSystem: 80bfe850b1f9922c16905822ecbf97acd711dc51
|
ExpoFileSystem: 80bfe850b1f9922c16905822ecbf97acd711dc51
|
||||||
ExpoFont: 00756e6c796d8f7ee8d211e29c8b619e75cbf238
|
ExpoFont: 00756e6c796d8f7ee8d211e29c8b619e75cbf238
|
||||||
ExpoHead: fcb28a68ed4ba28f177394d2dfb8a0a8824cd103
|
ExpoHead: fcb28a68ed4ba28f177394d2dfb8a0a8824cd103
|
||||||
@ -3119,6 +3155,8 @@ SPEC CHECKSUMS:
|
|||||||
ExpoSystemUI: d4f065a016cae6721b324eb659cdee4d4cf0cb26
|
ExpoSystemUI: d4f065a016cae6721b324eb659cdee4d4cf0cb26
|
||||||
ExpoWebBrowser: 7595ccac6938eb65b076385fd23d035db9ecdc8e
|
ExpoWebBrowser: 7595ccac6938eb65b076385fd23d035db9ecdc8e
|
||||||
EXSplashScreen: d8b3c547b9b18a41d80c6f6b274c4c26664febd4
|
EXSplashScreen: d8b3c547b9b18a41d80c6f6b274c4c26664febd4
|
||||||
|
EXStructuredHeaders: cb8d1f698e144f4c5547b4c4963e1552f5d2b457
|
||||||
|
EXUpdates: fe42e1cdace89a8db450351fbc38577b237af76b
|
||||||
EXUpdatesInterface: 996527fd7d1a5d271eb523258d603f8f92038f24
|
EXUpdatesInterface: 996527fd7d1a5d271eb523258d603f8f92038f24
|
||||||
FBLazyVector: 7e977dd099937dc5458851233141583abba49ff2
|
FBLazyVector: 7e977dd099937dc5458851233141583abba49ff2
|
||||||
Firebase: cec914dab6fd7b1bd8ab56ea07ce4e03dd251c2d
|
Firebase: cec914dab6fd7b1bd8ab56ea07ce4e03dd251c2d
|
||||||
@ -3140,11 +3178,9 @@ SPEC CHECKSUMS:
|
|||||||
fmt: 4c2741a687cc09f0634a2e2c72a838b99f1ff120
|
fmt: 4c2741a687cc09f0634a2e2c72a838b99f1ff120
|
||||||
glog: fdfdfe5479092de0c4bdbebedd9056951f092c4f
|
glog: fdfdfe5479092de0c4bdbebedd9056951f092c4f
|
||||||
GoogleDataTransport: 6c09b596d841063d76d4288cc2d2f42cc36e1e2a
|
GoogleDataTransport: 6c09b596d841063d76d4288cc2d2f42cc36e1e2a
|
||||||
GoogleSignIn: d4281ab6cf21542b1cfaff85c191f230b399d2db
|
|
||||||
GoogleUtilities: ea963c370a38a8069cc5f7ba4ca849a60b6d7d15
|
GoogleUtilities: ea963c370a38a8069cc5f7ba4ca849a60b6d7d15
|
||||||
"gRPC-C++": e725ef63c4475d7cdb7e2cf16eb0fde84bd9ee51
|
"gRPC-C++": e725ef63c4475d7cdb7e2cf16eb0fde84bd9ee51
|
||||||
gRPC-Core: eee4be35df218649fe66d721a05a7f27a28f069b
|
gRPC-Core: eee4be35df218649fe66d721a05a7f27a28f069b
|
||||||
GTMAppAuth: f69bd07d68cd3b766125f7e072c45d7340dea0de
|
|
||||||
GTMSessionFetcher: 5aea5ba6bd522a239e236100971f10cb71b96ab6
|
GTMSessionFetcher: 5aea5ba6bd522a239e236100971f10cb71b96ab6
|
||||||
hermes-engine: 1f547997900dd0752dc0cc0ae6dd16173c49e09b
|
hermes-engine: 1f547997900dd0752dc0cc0ae6dd16173c49e09b
|
||||||
leveldb-library: e8eadf9008a61f9e1dde3978c086d2b6d9b9dc28
|
leveldb-library: e8eadf9008a61f9e1dde3978c086d2b6d9b9dc28
|
||||||
@ -3155,6 +3191,7 @@ SPEC CHECKSUMS:
|
|||||||
RCTDeprecation: 4c7eeb42be0b2e95195563c49be08d0b839d22b4
|
RCTDeprecation: 4c7eeb42be0b2e95195563c49be08d0b839d22b4
|
||||||
RCTRequired: d530a0f489699c8500e944fde963102c42dcd0c2
|
RCTRequired: d530a0f489699c8500e944fde963102c42dcd0c2
|
||||||
RCTTypeSafety: b20878506b094fa3d9007d7b9e4be0faa3562499
|
RCTTypeSafety: b20878506b094fa3d9007d7b9e4be0faa3562499
|
||||||
|
ReachabilitySwift: 7f151ff156cea1481a8411701195ac6a984f4979
|
||||||
React: 2f9da0177233f60fa3462d83fcccde245759f81a
|
React: 2f9da0177233f60fa3462d83fcccde245759f81a
|
||||||
React-callinvoker: d0205f0dcebf72ec27263ab41e3a5ad827ed503f
|
React-callinvoker: d0205f0dcebf72ec27263ab41e3a5ad827ed503f
|
||||||
React-Codegen: 27212e14727ad7d6d9fd1b1967fbf21929e4ce29
|
React-Codegen: 27212e14727ad7d6d9fd1b1967fbf21929e4ce29
|
||||||
@ -3210,11 +3247,11 @@ SPEC CHECKSUMS:
|
|||||||
RNFBFirestore: e47cdde04ea3d9e73e58e037e1aa1d0b1141c316
|
RNFBFirestore: e47cdde04ea3d9e73e58e037e1aa1d0b1141c316
|
||||||
RNFBFunctions: 738cc9e2177d060d29b5d143ef2f9ed0eda4bb1f
|
RNFBFunctions: 738cc9e2177d060d29b5d143ef2f9ed0eda4bb1f
|
||||||
RNGestureHandler: 20a4307fd21cbff339abfcfa68192f3f0a6a518b
|
RNGestureHandler: 20a4307fd21cbff339abfcfa68192f3f0a6a518b
|
||||||
RNGoogleSignin: 9e68b9bcc3888219357924e32ee563624745647d
|
|
||||||
RNReanimated: d51431fd3597a8f8320319dce8e42cee82a5445f
|
RNReanimated: d51431fd3597a8f8320319dce8e42cee82a5445f
|
||||||
RNScreens: 30249f9331c3b00ae7cb7922e11f58b3ed369c07
|
RNScreens: 30249f9331c3b00ae7cb7922e11f58b3ed369c07
|
||||||
RNSVG: 4590aa95758149fa27c5c83e54a6a466349a1688
|
RNSVG: 4590aa95758149fa27c5c83e54a6a466349a1688
|
||||||
SocketRocket: abac6f5de4d4d62d24e11868d7a2f427e0ef940d
|
SocketRocket: abac6f5de4d4d62d24e11868d7a2f427e0ef940d
|
||||||
|
sqlite3: 02d1f07eaaa01f80a1c16b4b31dfcbb3345ee01a
|
||||||
Yoga: bd92064a0d558be92786820514d74fc4dddd1233
|
Yoga: bd92064a0d558be92786820514d74fc4dddd1233
|
||||||
ZXingObjC: 8898711ab495761b2dbbdec76d90164a6d7e14c5
|
ZXingObjC: 8898711ab495761b2dbbdec76d90164a6d7e14c5
|
||||||
|
|
||||||
|
|||||||
@ -298,6 +298,9 @@
|
|||||||
"${PODS_CONFIGURATION_BUILD_DIR}/EXApplication/ExpoApplication_privacy.bundle",
|
"${PODS_CONFIGURATION_BUILD_DIR}/EXApplication/ExpoApplication_privacy.bundle",
|
||||||
"${PODS_CONFIGURATION_BUILD_DIR}/EXConstants/EXConstants.bundle",
|
"${PODS_CONFIGURATION_BUILD_DIR}/EXConstants/EXConstants.bundle",
|
||||||
"${PODS_CONFIGURATION_BUILD_DIR}/EXConstants/ExpoConstants_privacy.bundle",
|
"${PODS_CONFIGURATION_BUILD_DIR}/EXConstants/ExpoConstants_privacy.bundle",
|
||||||
|
"${PODS_CONFIGURATION_BUILD_DIR}/EXNotifications/ExpoNotifications_privacy.bundle",
|
||||||
|
"${PODS_CONFIGURATION_BUILD_DIR}/EXUpdates/EXUpdates.bundle",
|
||||||
|
"${PODS_CONFIGURATION_BUILD_DIR}/ExpoDevice/ExpoDevice_privacy.bundle",
|
||||||
"${PODS_CONFIGURATION_BUILD_DIR}/ExpoFileSystem/ExpoFileSystem_privacy.bundle",
|
"${PODS_CONFIGURATION_BUILD_DIR}/ExpoFileSystem/ExpoFileSystem_privacy.bundle",
|
||||||
"${PODS_CONFIGURATION_BUILD_DIR}/ExpoSystemUI/ExpoSystemUI_privacy.bundle",
|
"${PODS_CONFIGURATION_BUILD_DIR}/ExpoSystemUI/ExpoSystemUI_privacy.bundle",
|
||||||
"${PODS_CONFIGURATION_BUILD_DIR}/FirebaseAuth/FirebaseAuth_Privacy.bundle",
|
"${PODS_CONFIGURATION_BUILD_DIR}/FirebaseAuth/FirebaseAuth_Privacy.bundle",
|
||||||
@ -308,13 +311,12 @@
|
|||||||
"${PODS_CONFIGURATION_BUILD_DIR}/FirebaseFirestore/FirebaseFirestore_Privacy.bundle",
|
"${PODS_CONFIGURATION_BUILD_DIR}/FirebaseFirestore/FirebaseFirestore_Privacy.bundle",
|
||||||
"${PODS_CONFIGURATION_BUILD_DIR}/FirebaseFirestoreInternal/FirebaseFirestoreInternal_Privacy.bundle",
|
"${PODS_CONFIGURATION_BUILD_DIR}/FirebaseFirestoreInternal/FirebaseFirestoreInternal_Privacy.bundle",
|
||||||
"${PODS_CONFIGURATION_BUILD_DIR}/FirebaseInstallations/FirebaseInstallations_Privacy.bundle",
|
"${PODS_CONFIGURATION_BUILD_DIR}/FirebaseInstallations/FirebaseInstallations_Privacy.bundle",
|
||||||
"${PODS_CONFIGURATION_BUILD_DIR}/GTMAppAuth/GTMAppAuth_Privacy.bundle",
|
|
||||||
"${PODS_CONFIGURATION_BUILD_DIR}/GTMSessionFetcher/GTMSessionFetcher_Core_Privacy.bundle",
|
"${PODS_CONFIGURATION_BUILD_DIR}/GTMSessionFetcher/GTMSessionFetcher_Core_Privacy.bundle",
|
||||||
"${PODS_CONFIGURATION_BUILD_DIR}/GoogleDataTransport/GoogleDataTransport_Privacy.bundle",
|
"${PODS_CONFIGURATION_BUILD_DIR}/GoogleDataTransport/GoogleDataTransport_Privacy.bundle",
|
||||||
"${PODS_CONFIGURATION_BUILD_DIR}/GoogleSignIn/GoogleSignIn.bundle",
|
|
||||||
"${PODS_CONFIGURATION_BUILD_DIR}/GoogleUtilities/GoogleUtilities_Privacy.bundle",
|
"${PODS_CONFIGURATION_BUILD_DIR}/GoogleUtilities/GoogleUtilities_Privacy.bundle",
|
||||||
"${PODS_CONFIGURATION_BUILD_DIR}/PromisesObjC/FBLPromises_Privacy.bundle",
|
"${PODS_CONFIGURATION_BUILD_DIR}/PromisesObjC/FBLPromises_Privacy.bundle",
|
||||||
"${PODS_CONFIGURATION_BUILD_DIR}/PromisesSwift/Promises_Privacy.bundle",
|
"${PODS_CONFIGURATION_BUILD_DIR}/PromisesSwift/Promises_Privacy.bundle",
|
||||||
|
"${PODS_CONFIGURATION_BUILD_DIR}/ReachabilitySwift/ReachabilitySwift.bundle",
|
||||||
"${PODS_CONFIGURATION_BUILD_DIR}/React-Core/RCTI18nStrings.bundle",
|
"${PODS_CONFIGURATION_BUILD_DIR}/React-Core/RCTI18nStrings.bundle",
|
||||||
"${PODS_CONFIGURATION_BUILD_DIR}/abseil/xcprivacy.bundle",
|
"${PODS_CONFIGURATION_BUILD_DIR}/abseil/xcprivacy.bundle",
|
||||||
"${PODS_CONFIGURATION_BUILD_DIR}/expo-dev-launcher/EXDevLauncher.bundle",
|
"${PODS_CONFIGURATION_BUILD_DIR}/expo-dev-launcher/EXDevLauncher.bundle",
|
||||||
@ -331,6 +333,9 @@
|
|||||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/ExpoApplication_privacy.bundle",
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/ExpoApplication_privacy.bundle",
|
||||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/EXConstants.bundle",
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/EXConstants.bundle",
|
||||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/ExpoConstants_privacy.bundle",
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/ExpoConstants_privacy.bundle",
|
||||||
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/ExpoNotifications_privacy.bundle",
|
||||||
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/EXUpdates.bundle",
|
||||||
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/ExpoDevice_privacy.bundle",
|
||||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/ExpoFileSystem_privacy.bundle",
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/ExpoFileSystem_privacy.bundle",
|
||||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/ExpoSystemUI_privacy.bundle",
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/ExpoSystemUI_privacy.bundle",
|
||||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/FirebaseAuth_Privacy.bundle",
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/FirebaseAuth_Privacy.bundle",
|
||||||
@ -341,13 +346,12 @@
|
|||||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/FirebaseFirestore_Privacy.bundle",
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/FirebaseFirestore_Privacy.bundle",
|
||||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/FirebaseFirestoreInternal_Privacy.bundle",
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/FirebaseFirestoreInternal_Privacy.bundle",
|
||||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/FirebaseInstallations_Privacy.bundle",
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/FirebaseInstallations_Privacy.bundle",
|
||||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/GTMAppAuth_Privacy.bundle",
|
|
||||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/GTMSessionFetcher_Core_Privacy.bundle",
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/GTMSessionFetcher_Core_Privacy.bundle",
|
||||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/GoogleDataTransport_Privacy.bundle",
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/GoogleDataTransport_Privacy.bundle",
|
||||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/GoogleSignIn.bundle",
|
|
||||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/GoogleUtilities_Privacy.bundle",
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/GoogleUtilities_Privacy.bundle",
|
||||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/FBLPromises_Privacy.bundle",
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/FBLPromises_Privacy.bundle",
|
||||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/Promises_Privacy.bundle",
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/Promises_Privacy.bundle",
|
||||||
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/ReachabilitySwift.bundle",
|
||||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/RCTI18nStrings.bundle",
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/RCTI18nStrings.bundle",
|
||||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/xcprivacy.bundle",
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/xcprivacy.bundle",
|
||||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/EXDevLauncher.bundle",
|
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/EXDevLauncher.bundle",
|
||||||
@ -437,7 +441,7 @@
|
|||||||
);
|
);
|
||||||
OTHER_SWIFT_FLAGS = "$(inherited) -D EXPO_CONFIGURATION_DEBUG";
|
OTHER_SWIFT_FLAGS = "$(inherited) -D EXPO_CONFIGURATION_DEBUG";
|
||||||
PRODUCT_BUNDLE_IDENTIFIER = com.cally.app;
|
PRODUCT_BUNDLE_IDENTIFIER = com.cally.app;
|
||||||
PRODUCT_NAME = "CallyFamilyPlanner";
|
PRODUCT_NAME = CallyFamilyPlanner;
|
||||||
SWIFT_OBJC_BRIDGING_HEADER = "cally/cally-Bridging-Header.h";
|
SWIFT_OBJC_BRIDGING_HEADER = "cally/cally-Bridging-Header.h";
|
||||||
SWIFT_OPTIMIZATION_LEVEL = "-Onone";
|
SWIFT_OPTIMIZATION_LEVEL = "-Onone";
|
||||||
SWIFT_VERSION = 5.0;
|
SWIFT_VERSION = 5.0;
|
||||||
@ -468,7 +472,7 @@
|
|||||||
);
|
);
|
||||||
OTHER_SWIFT_FLAGS = "$(inherited) -D EXPO_CONFIGURATION_RELEASE";
|
OTHER_SWIFT_FLAGS = "$(inherited) -D EXPO_CONFIGURATION_RELEASE";
|
||||||
PRODUCT_BUNDLE_IDENTIFIER = com.cally.app;
|
PRODUCT_BUNDLE_IDENTIFIER = com.cally.app;
|
||||||
PRODUCT_NAME = "CallyFamilyPlanner";
|
PRODUCT_NAME = CallyFamilyPlanner;
|
||||||
SWIFT_OBJC_BRIDGING_HEADER = "cally/cally-Bridging-Header.h";
|
SWIFT_OBJC_BRIDGING_HEADER = "cally/cally-Bridging-Header.h";
|
||||||
SWIFT_VERSION = 5.0;
|
SWIFT_VERSION = 5.0;
|
||||||
TARGETED_DEVICE_FAMILY = "1,2";
|
TARGETED_DEVICE_FAMILY = "1,2";
|
||||||
|
|||||||
@ -84,6 +84,11 @@
|
|||||||
<string>$(PRODUCT_BUNDLE_IDENTIFIER).expo.index_route</string>
|
<string>$(PRODUCT_BUNDLE_IDENTIFIER).expo.index_route</string>
|
||||||
<string>$(PRODUCT_BUNDLE_IDENTIFIER).expo.index_route</string>
|
<string>$(PRODUCT_BUNDLE_IDENTIFIER).expo.index_route</string>
|
||||||
<string>$(PRODUCT_BUNDLE_IDENTIFIER).expo.index_route</string>
|
<string>$(PRODUCT_BUNDLE_IDENTIFIER).expo.index_route</string>
|
||||||
|
<string>$(PRODUCT_BUNDLE_IDENTIFIER).expo.index_route</string>
|
||||||
|
<string>$(PRODUCT_BUNDLE_IDENTIFIER).expo.index_route</string>
|
||||||
|
<string>$(PRODUCT_BUNDLE_IDENTIFIER).expo.index_route</string>
|
||||||
|
<string>$(PRODUCT_BUNDLE_IDENTIFIER).expo.index_route</string>
|
||||||
|
<string>$(PRODUCT_BUNDLE_IDENTIFIER).expo.index_route</string>
|
||||||
</array>
|
</array>
|
||||||
<key>UILaunchStoryboardName</key>
|
<key>UILaunchStoryboardName</key>
|
||||||
<string>SplashScreen</string>
|
<string>SplashScreen</string>
|
||||||
|
|||||||
@ -5,8 +5,12 @@
|
|||||||
<key>EXUpdatesCheckOnLaunch</key>
|
<key>EXUpdatesCheckOnLaunch</key>
|
||||||
<string>ALWAYS</string>
|
<string>ALWAYS</string>
|
||||||
<key>EXUpdatesEnabled</key>
|
<key>EXUpdatesEnabled</key>
|
||||||
<false/>
|
<true/>
|
||||||
<key>EXUpdatesLaunchWaitMs</key>
|
<key>EXUpdatesLaunchWaitMs</key>
|
||||||
<integer>0</integer>
|
<integer>0</integer>
|
||||||
|
<key>EXUpdatesRuntimeVersion</key>
|
||||||
|
<string>1.0.0</string>
|
||||||
|
<key>EXUpdatesURL</key>
|
||||||
|
<string>https://u.expo.dev/bdb8c57b-25bb-4d36-b3b8-5b09c5092f52</string>
|
||||||
</dict>
|
</dict>
|
||||||
</plist>
|
</plist>
|
||||||
@ -1,5 +1,8 @@
|
|||||||
<?xml version="1.0" encoding="UTF-8"?>
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||||
<plist version="1.0">
|
<plist version="1.0">
|
||||||
<dict/>
|
<dict>
|
||||||
|
<key>aps-environment</key>
|
||||||
|
<string>development</string>
|
||||||
|
</dict>
|
||||||
</plist>
|
</plist>
|
||||||
@ -19,7 +19,7 @@
|
|||||||
"lint": "expo lint",
|
"lint": "expo lint",
|
||||||
"submit": "npx eas-cli submit -p ios",
|
"submit": "npx eas-cli submit -p ios",
|
||||||
"prebuild": "npx expo prebuild -p ios",
|
"prebuild": "npx expo prebuild -p ios",
|
||||||
"prebuild-build-submit-ios": "npm run prebuild && npm run build-ios && npm run submit",
|
"prebuild-build-submit-ios": "yarn run prebuild && yarn run build-ios && yarn run submit",
|
||||||
"prebuild-build-submit-ios-cicd": "yarn build-ios-cicd",
|
"prebuild-build-submit-ios-cicd": "yarn build-ios-cicd",
|
||||||
"prebuild-build-submit-cicd": "yarn build-cicd"
|
"prebuild-build-submit-cicd": "yarn build-cicd"
|
||||||
},
|
},
|
||||||
@ -35,7 +35,6 @@
|
|||||||
"@react-native-firebase/crashlytics": "^20.3.0",
|
"@react-native-firebase/crashlytics": "^20.3.0",
|
||||||
"@react-native-firebase/firestore": "^20.4.0",
|
"@react-native-firebase/firestore": "^20.4.0",
|
||||||
"@react-native-firebase/functions": "^20.4.0",
|
"@react-native-firebase/functions": "^20.4.0",
|
||||||
"@react-native-google-signin/google-signin": "^13.1.0",
|
|
||||||
"@react-navigation/drawer": "^6.7.2",
|
"@react-navigation/drawer": "^6.7.2",
|
||||||
"@react-navigation/native": "^6.0.2",
|
"@react-navigation/native": "^6.0.2",
|
||||||
"date-fns": "^3.6.0",
|
"date-fns": "^3.6.0",
|
||||||
@ -47,13 +46,16 @@
|
|||||||
"expo-camera": "~15.0.16",
|
"expo-camera": "~15.0.16",
|
||||||
"expo-constants": "~16.0.2",
|
"expo-constants": "~16.0.2",
|
||||||
"expo-dev-client": "~4.0.27",
|
"expo-dev-client": "~4.0.27",
|
||||||
|
"expo-device": "~6.0.2",
|
||||||
"expo-font": "~12.0.9",
|
"expo-font": "~12.0.9",
|
||||||
"expo-image-picker": "~15.0.7",
|
"expo-image-picker": "~15.0.7",
|
||||||
"expo-linking": "~6.3.1",
|
"expo-linking": "~6.3.1",
|
||||||
|
"expo-notifications": "~0.28.18",
|
||||||
"expo-router": "~3.5.20",
|
"expo-router": "~3.5.20",
|
||||||
"expo-splash-screen": "~0.27.5",
|
"expo-splash-screen": "~0.27.5",
|
||||||
"expo-status-bar": "~1.12.1",
|
"expo-status-bar": "~1.12.1",
|
||||||
"expo-system-ui": "~3.0.7",
|
"expo-system-ui": "~3.0.7",
|
||||||
|
"expo-updates": "~0.25.27",
|
||||||
"expo-web-browser": "~13.0.3",
|
"expo-web-browser": "~13.0.3",
|
||||||
"firebase-admin": "^12.3.1",
|
"firebase-admin": "^12.3.1",
|
||||||
"firebase-functions": "^5.1.0",
|
"firebase-functions": "^5.1.0",
|
||||||
|
|||||||
128
yarn.lock
128
yarn.lock
@ -1025,6 +1025,20 @@
|
|||||||
dotenv-expand "~11.0.6"
|
dotenv-expand "~11.0.6"
|
||||||
getenv "^1.0.0"
|
getenv "^1.0.0"
|
||||||
|
|
||||||
|
"@expo/fingerprint@^0.10.2":
|
||||||
|
version "0.10.3"
|
||||||
|
resolved "https://registry.yarnpkg.com/@expo/fingerprint/-/fingerprint-0.10.3.tgz#87c2811fe7773ec7d00cae86ab041d578f9041b5"
|
||||||
|
integrity sha512-h/BnnyloJyMSrzeXonKLE6HfiMpRg3e9m8CAv+eUaAozG9heKMG9ftHW4cfm2StDYj/rWjFc5YK6MSIX6qd+xg==
|
||||||
|
dependencies:
|
||||||
|
"@expo/spawn-async" "^1.7.2"
|
||||||
|
chalk "^4.1.2"
|
||||||
|
debug "^4.3.4"
|
||||||
|
find-up "^5.0.0"
|
||||||
|
minimatch "^3.0.4"
|
||||||
|
p-limit "^3.1.0"
|
||||||
|
resolve-from "^5.0.0"
|
||||||
|
semver "^7.6.0"
|
||||||
|
|
||||||
"@expo/image-utils@^0.5.0":
|
"@expo/image-utils@^0.5.0":
|
||||||
version "0.5.1"
|
version "0.5.1"
|
||||||
resolved "https://registry.npmjs.org/@expo/image-utils/-/image-utils-0.5.1.tgz"
|
resolved "https://registry.npmjs.org/@expo/image-utils/-/image-utils-0.5.1.tgz"
|
||||||
@ -1686,6 +1700,11 @@
|
|||||||
dependencies:
|
dependencies:
|
||||||
"@hapi/hoek" "^9.0.0"
|
"@hapi/hoek" "^9.0.0"
|
||||||
|
|
||||||
|
"@ide/backoff@^1.0.0":
|
||||||
|
version "1.0.0"
|
||||||
|
resolved "https://registry.yarnpkg.com/@ide/backoff/-/backoff-1.0.0.tgz#466842c25bd4a4833e0642fab41ccff064010176"
|
||||||
|
integrity sha512-F0YfUDjvT+Mtt/R4xdl2X0EYCHMMiJqNLdxHD++jDT5ydEFIyqbCHh51Qx2E211dgZprPKhV7sHmnXKpLuvc5g==
|
||||||
|
|
||||||
"@isaacs/cliui@^8.0.2":
|
"@isaacs/cliui@^8.0.2":
|
||||||
version "8.0.2"
|
version "8.0.2"
|
||||||
resolved "https://registry.npmjs.org/@isaacs/cliui/-/cliui-8.0.2.tgz"
|
resolved "https://registry.npmjs.org/@isaacs/cliui/-/cliui-8.0.2.tgz"
|
||||||
@ -2283,11 +2302,6 @@
|
|||||||
resolved "https://registry.npmjs.org/@react-native-firebase/functions/-/functions-20.4.0.tgz"
|
resolved "https://registry.npmjs.org/@react-native-firebase/functions/-/functions-20.4.0.tgz"
|
||||||
integrity sha512-g4kAWZboTE9cTdT7KT6k1haHDmEBA36bPCvrh2MJ2RACo2JxotB2MIOEPZ5U/cT94eIAlgI5YtxQQGQfC+VcBQ==
|
integrity sha512-g4kAWZboTE9cTdT7KT6k1haHDmEBA36bPCvrh2MJ2RACo2JxotB2MIOEPZ5U/cT94eIAlgI5YtxQQGQfC+VcBQ==
|
||||||
|
|
||||||
"@react-native-google-signin/google-signin@^13.1.0":
|
|
||||||
version "13.1.0"
|
|
||||||
resolved "https://registry.npmjs.org/@react-native-google-signin/google-signin/-/google-signin-13.1.0.tgz"
|
|
||||||
integrity sha512-C2/sqb0/s0c+Dwc/mykASZsRuHxGqn7SFrCxCY9D8p8IOQO05haInhCc7lzraJshRixGva5c/4usQZ71HMYSEQ==
|
|
||||||
|
|
||||||
"@react-native/assets-registry@0.74.85":
|
"@react-native/assets-registry@0.74.85":
|
||||||
version "0.74.85"
|
version "0.74.85"
|
||||||
resolved "https://registry.npmjs.org/@react-native/assets-registry/-/assets-registry-0.74.85.tgz"
|
resolved "https://registry.npmjs.org/@react-native/assets-registry/-/assets-registry-0.74.85.tgz"
|
||||||
@ -3247,6 +3261,11 @@ application-config-path@^0.1.0:
|
|||||||
resolved "https://registry.npmjs.org/application-config-path/-/application-config-path-0.1.1.tgz"
|
resolved "https://registry.npmjs.org/application-config-path/-/application-config-path-0.1.1.tgz"
|
||||||
integrity sha512-zy9cHePtMP0YhwG+CfHm0bgwdnga2X3gZexpdCwEj//dpb+TKajtiC8REEUJUSq6Ab4f9cgNy2l8ObXzCXFkEw==
|
integrity sha512-zy9cHePtMP0YhwG+CfHm0bgwdnga2X3gZexpdCwEj//dpb+TKajtiC8REEUJUSq6Ab4f9cgNy2l8ObXzCXFkEw==
|
||||||
|
|
||||||
|
arg@4.1.0:
|
||||||
|
version "4.1.0"
|
||||||
|
resolved "https://registry.yarnpkg.com/arg/-/arg-4.1.0.tgz#583c518199419e0037abb74062c37f8519e575f0"
|
||||||
|
integrity sha512-ZWc51jO3qegGkVh8Hwpv636EkbesNV5ZNQPCtRa+0qytRYPEs9IYT9qITY9buezqUH5uqyzlWLcufrzU2rffdg==
|
||||||
|
|
||||||
arg@5.0.2:
|
arg@5.0.2:
|
||||||
version "5.0.2"
|
version "5.0.2"
|
||||||
resolved "https://registry.npmjs.org/arg/-/arg-5.0.2.tgz"
|
resolved "https://registry.npmjs.org/arg/-/arg-5.0.2.tgz"
|
||||||
@ -3313,6 +3332,17 @@ asap@~2.0.3, asap@~2.0.6:
|
|||||||
resolved "https://registry.npmjs.org/asap/-/asap-2.0.6.tgz"
|
resolved "https://registry.npmjs.org/asap/-/asap-2.0.6.tgz"
|
||||||
integrity sha512-BSHWgDSAiKs50o2Re8ppvp3seVHXSRM44cdSsT9FfNEUUZLOGWVCsiWaRPWM1Znn+mqZ1OfVZ3z3DWEzSp7hRA==
|
integrity sha512-BSHWgDSAiKs50o2Re8ppvp3seVHXSRM44cdSsT9FfNEUUZLOGWVCsiWaRPWM1Znn+mqZ1OfVZ3z3DWEzSp7hRA==
|
||||||
|
|
||||||
|
assert@^2.0.0:
|
||||||
|
version "2.1.0"
|
||||||
|
resolved "https://registry.yarnpkg.com/assert/-/assert-2.1.0.tgz#6d92a238d05dc02e7427c881fb8be81c8448b2dd"
|
||||||
|
integrity sha512-eLHpSK/Y4nhMJ07gDaAzoX/XAKS8PSaojml3M0DM4JpV1LAi5JOJ/p6H/XWrl8L+DzVEvVCW1z3vWAaB9oTsQw==
|
||||||
|
dependencies:
|
||||||
|
call-bind "^1.0.2"
|
||||||
|
is-nan "^1.3.2"
|
||||||
|
object-is "^1.1.5"
|
||||||
|
object.assign "^4.1.4"
|
||||||
|
util "^0.12.5"
|
||||||
|
|
||||||
ast-types@0.15.2:
|
ast-types@0.15.2:
|
||||||
version "0.15.2"
|
version "0.15.2"
|
||||||
resolved "https://registry.npmjs.org/ast-types/-/ast-types-0.15.2.tgz"
|
resolved "https://registry.npmjs.org/ast-types/-/ast-types-0.15.2.tgz"
|
||||||
@ -3492,6 +3522,11 @@ babel-preset-jest@^29.6.3:
|
|||||||
babel-plugin-jest-hoist "^29.6.3"
|
babel-plugin-jest-hoist "^29.6.3"
|
||||||
babel-preset-current-node-syntax "^1.0.0"
|
babel-preset-current-node-syntax "^1.0.0"
|
||||||
|
|
||||||
|
badgin@^1.1.5:
|
||||||
|
version "1.2.3"
|
||||||
|
resolved "https://registry.yarnpkg.com/badgin/-/badgin-1.2.3.tgz#994b5f519827d7d5422224825b2c8faea2bc43ad"
|
||||||
|
integrity sha512-NQGA7LcfCpSzIbGRbkgjgdWkjy7HI+Th5VLxTJfW5EeaAf3fnS+xWQaQOCYiny+q6QSvxqoSO04vCx+4u++EJw==
|
||||||
|
|
||||||
balanced-match@^1.0.0:
|
balanced-match@^1.0.0:
|
||||||
version "1.0.2"
|
version "1.0.2"
|
||||||
resolved "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz"
|
resolved "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz"
|
||||||
@ -3721,7 +3756,7 @@ calendarize@^1.1.1:
|
|||||||
resolved "https://registry.npmjs.org/calendarize/-/calendarize-1.1.1.tgz"
|
resolved "https://registry.npmjs.org/calendarize/-/calendarize-1.1.1.tgz"
|
||||||
integrity sha512-C2JyBAtNp2NG4DX4fA1EILggLt/5PlYzvQR0crHktoAPBc9TlIfdhzg7tWekCbe+pH6+9qoK+FhPbi+vYJJlqw==
|
integrity sha512-C2JyBAtNp2NG4DX4fA1EILggLt/5PlYzvQR0crHktoAPBc9TlIfdhzg7tWekCbe+pH6+9qoK+FhPbi+vYJJlqw==
|
||||||
|
|
||||||
call-bind@^1.0.2, call-bind@^1.0.5, call-bind@^1.0.6, call-bind@^1.0.7:
|
call-bind@^1.0.0, call-bind@^1.0.2, call-bind@^1.0.5, call-bind@^1.0.6, call-bind@^1.0.7:
|
||||||
version "1.0.7"
|
version "1.0.7"
|
||||||
resolved "https://registry.npmjs.org/call-bind/-/call-bind-1.0.7.tgz"
|
resolved "https://registry.npmjs.org/call-bind/-/call-bind-1.0.7.tgz"
|
||||||
integrity sha512-GHTSNSYICQ7scH7sZ+M2rFopRoLh8t2bLSW6BbgrtLsahOIB5iyAVJf9GjWK3cYTDaMj4XdBpM1cA6pIS0Kv2w==
|
integrity sha512-GHTSNSYICQ7scH7sZ+M2rFopRoLh8t2bLSW6BbgrtLsahOIB5iyAVJf9GjWK3cYTDaMj4XdBpM1cA6pIS0Kv2w==
|
||||||
@ -4413,7 +4448,7 @@ define-lazy-prop@^2.0.0:
|
|||||||
resolved "https://registry.npmjs.org/define-lazy-prop/-/define-lazy-prop-2.0.0.tgz"
|
resolved "https://registry.npmjs.org/define-lazy-prop/-/define-lazy-prop-2.0.0.tgz"
|
||||||
integrity sha512-Ds09qNh8yw3khSjiJjiUInaGX9xlqZDY7JVryGxdxV7NPeuqQfplOpQ66yJFZut3jLa5zOwkXw1g9EI2uKh4Og==
|
integrity sha512-Ds09qNh8yw3khSjiJjiUInaGX9xlqZDY7JVryGxdxV7NPeuqQfplOpQ66yJFZut3jLa5zOwkXw1g9EI2uKh4Og==
|
||||||
|
|
||||||
define-properties@^1.2.0, define-properties@^1.2.1:
|
define-properties@^1.1.3, define-properties@^1.2.0, define-properties@^1.2.1:
|
||||||
version "1.2.1"
|
version "1.2.1"
|
||||||
resolved "https://registry.npmjs.org/define-properties/-/define-properties-1.2.1.tgz"
|
resolved "https://registry.npmjs.org/define-properties/-/define-properties-1.2.1.tgz"
|
||||||
integrity sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==
|
integrity sha512-8QmQKqEASLd5nx0U1B1okLElbUuuttJ/AnYmRXbbbGDWh6uS208EjD4Xqq/I9wK7u0v6O08XhTWnt5XtEbR6Dg==
|
||||||
@ -4964,6 +4999,18 @@ expo-dev-menu@5.0.21:
|
|||||||
expo-dev-menu-interface "1.8.3"
|
expo-dev-menu-interface "1.8.3"
|
||||||
semver "^7.5.4"
|
semver "^7.5.4"
|
||||||
|
|
||||||
|
expo-device@~6.0.2:
|
||||||
|
version "6.0.2"
|
||||||
|
resolved "https://registry.yarnpkg.com/expo-device/-/expo-device-6.0.2.tgz#9bc3eccd16509c2819c225cc2ca8f7c3e3bdd11e"
|
||||||
|
integrity sha512-sCt91CuTmAuMXX4SlFOn4lIos2UIr8vb0jDstDDZXys6kErcj0uynC7bQAMreU5uRUTKMAl4MAMpKt9ufCXPBw==
|
||||||
|
dependencies:
|
||||||
|
ua-parser-js "^0.7.33"
|
||||||
|
|
||||||
|
expo-eas-client@~0.12.0:
|
||||||
|
version "0.12.0"
|
||||||
|
resolved "https://registry.yarnpkg.com/expo-eas-client/-/expo-eas-client-0.12.0.tgz#e8b6f7d33873e6f630f37f7bfc41646ae7b0b2a9"
|
||||||
|
integrity sha512-Jkww9Cwpv0z7DdLYiRX0r4fqBEcI9cKqTn7cHx63S09JaZ2rcwEE4zYHgrXwjahO+tU2VW8zqH+AJl6RhhW4zA==
|
||||||
|
|
||||||
expo-file-system@~17.0.1:
|
expo-file-system@~17.0.1:
|
||||||
version "17.0.1"
|
version "17.0.1"
|
||||||
resolved "https://registry.npmjs.org/expo-file-system/-/expo-file-system-17.0.1.tgz"
|
resolved "https://registry.npmjs.org/expo-file-system/-/expo-file-system-17.0.1.tgz"
|
||||||
@ -5034,6 +5081,20 @@ expo-modules-core@1.12.24:
|
|||||||
dependencies:
|
dependencies:
|
||||||
invariant "^2.2.4"
|
invariant "^2.2.4"
|
||||||
|
|
||||||
|
expo-notifications@~0.28.18:
|
||||||
|
version "0.28.18"
|
||||||
|
resolved "https://registry.yarnpkg.com/expo-notifications/-/expo-notifications-0.28.18.tgz#a3e5488429079d664885e975985dd2d6bdb52a5b"
|
||||||
|
integrity sha512-oRvr8rYhbbKNhVgcO+fj5g5g6vS0umGcElpeMSWa0KudUfOOgV6nNLvv5M89393z2Ahd7wPK4bnK8lygc0nCPQ==
|
||||||
|
dependencies:
|
||||||
|
"@expo/image-utils" "^0.5.0"
|
||||||
|
"@ide/backoff" "^1.0.0"
|
||||||
|
abort-controller "^3.0.0"
|
||||||
|
assert "^2.0.0"
|
||||||
|
badgin "^1.1.5"
|
||||||
|
expo-application "~5.9.0"
|
||||||
|
expo-constants "~16.0.0"
|
||||||
|
fs-extra "^9.1.0"
|
||||||
|
|
||||||
expo-router@~3.5.20:
|
expo-router@~3.5.20:
|
||||||
version "3.5.23"
|
version "3.5.23"
|
||||||
resolved "https://registry.npmjs.org/expo-router/-/expo-router-3.5.23.tgz"
|
resolved "https://registry.npmjs.org/expo-router/-/expo-router-3.5.23.tgz"
|
||||||
@ -5061,6 +5122,11 @@ expo-status-bar@~1.12.1:
|
|||||||
resolved "https://registry.npmjs.org/expo-status-bar/-/expo-status-bar-1.12.1.tgz"
|
resolved "https://registry.npmjs.org/expo-status-bar/-/expo-status-bar-1.12.1.tgz"
|
||||||
integrity sha512-/t3xdbS8KB0prj5KG5w7z+wZPFlPtkgs95BsmrP/E7Q0xHXTcDcQ6Cu2FkFuRM+PKTb17cJDnLkawyS5vDLxMA==
|
integrity sha512-/t3xdbS8KB0prj5KG5w7z+wZPFlPtkgs95BsmrP/E7Q0xHXTcDcQ6Cu2FkFuRM+PKTb17cJDnLkawyS5vDLxMA==
|
||||||
|
|
||||||
|
expo-structured-headers@~3.8.0:
|
||||||
|
version "3.8.0"
|
||||||
|
resolved "https://registry.yarnpkg.com/expo-structured-headers/-/expo-structured-headers-3.8.0.tgz#11797a4c3a7a6770b21126cecffcda148030e361"
|
||||||
|
integrity sha512-R+gFGn0x5CWl4OVlk2j1bJTJIz4KO8mPoCHpRHmfqMjmrMvrOM0qQSY3V5NHXwp1yT/L2v8aUmFQsBRIdvi1XA==
|
||||||
|
|
||||||
expo-system-ui@~3.0.7:
|
expo-system-ui@~3.0.7:
|
||||||
version "3.0.7"
|
version "3.0.7"
|
||||||
resolved "https://registry.npmjs.org/expo-system-ui/-/expo-system-ui-3.0.7.tgz"
|
resolved "https://registry.npmjs.org/expo-system-ui/-/expo-system-ui-3.0.7.tgz"
|
||||||
@ -5074,6 +5140,27 @@ expo-updates-interface@~0.16.2:
|
|||||||
resolved "https://registry.npmjs.org/expo-updates-interface/-/expo-updates-interface-0.16.2.tgz"
|
resolved "https://registry.npmjs.org/expo-updates-interface/-/expo-updates-interface-0.16.2.tgz"
|
||||||
integrity sha512-929XBU70q5ELxkKADj1xL0UIm3HvhYhNAOZv5DSk7rrKvLo7QDdPyl+JVnwZm9LrkNbH4wuE2rLoKu1KMgZ+9A==
|
integrity sha512-929XBU70q5ELxkKADj1xL0UIm3HvhYhNAOZv5DSk7rrKvLo7QDdPyl+JVnwZm9LrkNbH4wuE2rLoKu1KMgZ+9A==
|
||||||
|
|
||||||
|
expo-updates@~0.25.27:
|
||||||
|
version "0.25.27"
|
||||||
|
resolved "https://registry.yarnpkg.com/expo-updates/-/expo-updates-0.25.27.tgz#4aff889fea2aa221d8341a902646288f84c48b9e"
|
||||||
|
integrity sha512-1hyYZqBEXcAiEuSRPJ6dINTndGlWi6/bwlyYGjSnyoYfu/vzZQrJ+XA8JUP4EvJ3b0g8a0UOIjlDJ9ke9kMcfg==
|
||||||
|
dependencies:
|
||||||
|
"@expo/code-signing-certificates" "0.0.5"
|
||||||
|
"@expo/config" "~9.0.0-beta.0"
|
||||||
|
"@expo/config-plugins" "~8.0.8"
|
||||||
|
"@expo/fingerprint" "^0.10.2"
|
||||||
|
"@expo/spawn-async" "^1.7.2"
|
||||||
|
arg "4.1.0"
|
||||||
|
chalk "^4.1.2"
|
||||||
|
expo-eas-client "~0.12.0"
|
||||||
|
expo-manifests "~0.14.0"
|
||||||
|
expo-structured-headers "~3.8.0"
|
||||||
|
expo-updates-interface "~0.16.2"
|
||||||
|
fast-glob "^3.3.2"
|
||||||
|
fbemitter "^3.0.0"
|
||||||
|
ignore "^5.3.1"
|
||||||
|
resolve-from "^5.0.0"
|
||||||
|
|
||||||
expo-web-browser@~13.0.0, expo-web-browser@~13.0.3:
|
expo-web-browser@~13.0.0, expo-web-browser@~13.0.3:
|
||||||
version "13.0.3"
|
version "13.0.3"
|
||||||
resolved "https://registry.npmjs.org/expo-web-browser/-/expo-web-browser-13.0.3.tgz"
|
resolved "https://registry.npmjs.org/expo-web-browser/-/expo-web-browser-13.0.3.tgz"
|
||||||
@ -5997,7 +6084,7 @@ ieee754@^1.1.13:
|
|||||||
resolved "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz"
|
resolved "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz"
|
||||||
integrity sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==
|
integrity sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==
|
||||||
|
|
||||||
ignore@^5.2.0:
|
ignore@^5.2.0, ignore@^5.3.1:
|
||||||
version "5.3.2"
|
version "5.3.2"
|
||||||
resolved "https://registry.npmjs.org/ignore/-/ignore-5.3.2.tgz"
|
resolved "https://registry.npmjs.org/ignore/-/ignore-5.3.2.tgz"
|
||||||
integrity sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==
|
integrity sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g==
|
||||||
@ -6240,6 +6327,14 @@ is-invalid-path@^0.1.0:
|
|||||||
dependencies:
|
dependencies:
|
||||||
is-glob "^2.0.0"
|
is-glob "^2.0.0"
|
||||||
|
|
||||||
|
is-nan@^1.3.2:
|
||||||
|
version "1.3.2"
|
||||||
|
resolved "https://registry.yarnpkg.com/is-nan/-/is-nan-1.3.2.tgz#043a54adea31748b55b6cd4e09aadafa69bd9e1d"
|
||||||
|
integrity sha512-E+zBKpQ2t6MEo1VsonYmluk9NxGrbzpeeLC2xIViuO2EjU2xsXsBPwTr3Ykv9l08UYEVEdWeRZNouaZqF6RN0w==
|
||||||
|
dependencies:
|
||||||
|
call-bind "^1.0.0"
|
||||||
|
define-properties "^1.1.3"
|
||||||
|
|
||||||
is-negative-zero@^2.0.3:
|
is-negative-zero@^2.0.3:
|
||||||
version "2.0.3"
|
version "2.0.3"
|
||||||
resolved "https://registry.npmjs.org/is-negative-zero/-/is-negative-zero-2.0.3.tgz"
|
resolved "https://registry.npmjs.org/is-negative-zero/-/is-negative-zero-2.0.3.tgz"
|
||||||
@ -7959,12 +8054,20 @@ object-inspect@^1.13.1:
|
|||||||
resolved "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.2.tgz"
|
resolved "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.2.tgz"
|
||||||
integrity sha512-IRZSRuzJiynemAXPYtPe5BoI/RESNYR7TYm50MC5Mqbd3Jmw5y790sErYw3V6SryFJD64b74qQQs9wn5Bg/k3g==
|
integrity sha512-IRZSRuzJiynemAXPYtPe5BoI/RESNYR7TYm50MC5Mqbd3Jmw5y790sErYw3V6SryFJD64b74qQQs9wn5Bg/k3g==
|
||||||
|
|
||||||
|
object-is@^1.1.5:
|
||||||
|
version "1.1.6"
|
||||||
|
resolved "https://registry.yarnpkg.com/object-is/-/object-is-1.1.6.tgz#1a6a53aed2dd8f7e6775ff870bea58545956ab07"
|
||||||
|
integrity sha512-F8cZ+KfGlSGi09lJT7/Nd6KJZ9ygtvYC0/UYYLI9nmQKLMnydpB9yvbv9K1uSkEu7FU9vYPmVwLg328tX+ot3Q==
|
||||||
|
dependencies:
|
||||||
|
call-bind "^1.0.7"
|
||||||
|
define-properties "^1.2.1"
|
||||||
|
|
||||||
object-keys@^1.1.1:
|
object-keys@^1.1.1:
|
||||||
version "1.1.1"
|
version "1.1.1"
|
||||||
resolved "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz"
|
resolved "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz"
|
||||||
integrity sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==
|
integrity sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==
|
||||||
|
|
||||||
object.assign@^4.1.5:
|
object.assign@^4.1.4, object.assign@^4.1.5:
|
||||||
version "4.1.5"
|
version "4.1.5"
|
||||||
resolved "https://registry.npmjs.org/object.assign/-/object.assign-4.1.5.tgz"
|
resolved "https://registry.npmjs.org/object.assign/-/object.assign-4.1.5.tgz"
|
||||||
integrity sha512-byy+U7gp+FVwmyzKPYhW2h5l3crpmGsxl7X2s8y43IgxvG4g3QZ6CffDtsNQy1WsmZpQbO+ybo0AlW7TY6DcBQ==
|
integrity sha512-byy+U7gp+FVwmyzKPYhW2h5l3crpmGsxl7X2s8y43IgxvG4g3QZ6CffDtsNQy1WsmZpQbO+ybo0AlW7TY6DcBQ==
|
||||||
@ -10149,6 +10252,11 @@ typical@^2.6.0:
|
|||||||
resolved "https://registry.npmjs.org/typical/-/typical-2.6.1.tgz"
|
resolved "https://registry.npmjs.org/typical/-/typical-2.6.1.tgz"
|
||||||
integrity sha512-ofhi8kjIje6npGozTip9Fr8iecmYfEbS06i0JnIg+rh51KakryWF4+jX8lLKZVhy6N+ID45WYSFCxPOdTWCzNg==
|
integrity sha512-ofhi8kjIje6npGozTip9Fr8iecmYfEbS06i0JnIg+rh51KakryWF4+jX8lLKZVhy6N+ID45WYSFCxPOdTWCzNg==
|
||||||
|
|
||||||
|
ua-parser-js@^0.7.33:
|
||||||
|
version "0.7.39"
|
||||||
|
resolved "https://registry.yarnpkg.com/ua-parser-js/-/ua-parser-js-0.7.39.tgz#c71efb46ebeabc461c4612d22d54f88880fabe7e"
|
||||||
|
integrity sha512-IZ6acm6RhQHNibSt7+c09hhvsKy9WUr4DVbeq9U8o71qxyYtJpQeDxQnMrVqnIFMLcQjHO0I9wgfO2vIahht4w==
|
||||||
|
|
||||||
ua-parser-js@^1.0.35:
|
ua-parser-js@^1.0.35:
|
||||||
version "1.0.38"
|
version "1.0.38"
|
||||||
resolved "https://registry.npmjs.org/ua-parser-js/-/ua-parser-js-1.0.38.tgz"
|
resolved "https://registry.npmjs.org/ua-parser-js/-/ua-parser-js-1.0.38.tgz"
|
||||||
@ -10313,7 +10421,7 @@ util-deprecate@^1.0.1, util-deprecate@~1.0.1:
|
|||||||
resolved "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz"
|
resolved "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz"
|
||||||
integrity sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==
|
integrity sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==
|
||||||
|
|
||||||
util@^0.12.3:
|
util@^0.12.3, util@^0.12.5:
|
||||||
version "0.12.5"
|
version "0.12.5"
|
||||||
resolved "https://registry.npmjs.org/util/-/util-0.12.5.tgz"
|
resolved "https://registry.npmjs.org/util/-/util-0.12.5.tgz"
|
||||||
integrity sha512-kZf/K6hEIrWHI6XqOFUiiMa+79wE/D8Q+NCNAWclkyg3b4d2k7s0QGepNjiABc+aR3N1PAyHL7p6UcLY6LmrnA==
|
integrity sha512-kZf/K6hEIrWHI6XqOFUiiMa+79wE/D8Q+NCNAWclkyg3b4d2k7s0QGepNjiABc+aR3N1PAyHL7p6UcLY6LmrnA==
|
||||||
|
|||||||
Reference in New Issue
Block a user