about summary refs log tree commit diff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/lib/hooks/useIntentHandler.ts5
-rw-r--r--src/screens/Settings/Settings.tsx38
2 files changed, 36 insertions, 7 deletions
diff --git a/src/lib/hooks/useIntentHandler.ts b/src/lib/hooks/useIntentHandler.ts
index f55217e56..c359b2bd6 100644
--- a/src/lib/hooks/useIntentHandler.ts
+++ b/src/lib/hooks/useIntentHandler.ts
@@ -13,7 +13,6 @@ import {
 } from '#/components/ageAssurance/AgeAssuranceRedirectDialog'
 import {useIntentDialogs} from '#/components/intents/IntentDialogs'
 import {Referrer} from '../../../modules/expo-bluesky-swiss-army'
-import {IS_TESTFLIGHT} from '../app-info.web'
 import {useApplyPullRequestOTAUpdate} from './useOTAUpdates'
 
 type IntentType = 'compose' | 'verify-email' | 'age-assurance' | 'apply-ota'
@@ -97,10 +96,6 @@ export function useIntentHandler() {
           return
         }
         case 'apply-ota': {
-          if (!isNative || !IS_TESTFLIGHT) {
-            return
-          }
-
           const channel = params.get('channel')
           if (!channel) {
             Alert.alert('Error', 'No channel provided to look for.')
diff --git a/src/screens/Settings/Settings.tsx b/src/screens/Settings/Settings.tsx
index 9596c2479..b712c054c 100644
--- a/src/screens/Settings/Settings.tsx
+++ b/src/screens/Settings/Settings.tsx
@@ -1,5 +1,5 @@
 import {useState} from 'react'
-import {LayoutAnimation, Pressable, View} from 'react-native'
+import {Alert, LayoutAnimation, Pressable, View} from 'react-native'
 import {Linking} from 'react-native'
 import {useReducedMotion} from 'react-native-reanimated'
 import {type AppBskyActorDefs, moderateProfile} from '@atproto/api'
@@ -19,7 +19,7 @@ import {
 } from '#/lib/routes/types'
 import {sanitizeDisplayName} from '#/lib/strings/display-names'
 import {sanitizeHandle} from '#/lib/strings/handles'
-import {isNative} from '#/platform/detection'
+import {isIOS, isNative} from '#/platform/detection'
 import {useProfileShadow} from '#/state/cache/profile-shadow'
 import * as persisted from '#/state/persisted'
 import {clearStorage} from '#/state/persisted'
@@ -367,6 +367,7 @@ function DevOptions() {
   const navigation = useNavigation<NavigationProp>()
   const {mutate: deleteChatDeclarationRecord} = useDeleteActorDeclaration()
   const {
+    tryApplyUpdate,
     revertToEmbedded,
     isCurrentlyRunningPullRequestDeployment,
     currentChannel,
@@ -399,6 +400,30 @@ function DevOptions() {
     setActyNotifNudged(false)
   }
 
+  const onPressApplyOta = () => {
+    Alert.prompt(
+      'Apply OTA',
+      'Enter the channel for the OTA you wish to apply.',
+      [
+        {
+          style: 'cancel',
+          text: 'Cancel',
+        },
+        {
+          style: 'default',
+          text: 'Apply',
+          onPress: channel => {
+            tryApplyUpdate(channel ?? '')
+          },
+        },
+      ],
+      'plain-text',
+      isCurrentlyRunningPullRequestDeployment
+        ? currentChannel
+        : 'pull-request-',
+    )
+  }
+
   return (
     <>
       <SettingsList.PressableItem
@@ -459,6 +484,15 @@ function DevOptions() {
           <Trans>Clear all storage data (restart after this)</Trans>
         </SettingsList.ItemText>
       </SettingsList.PressableItem>
+      {isIOS ? (
+        <SettingsList.PressableItem
+          onPress={onPressApplyOta}
+          label={_(msg`Apply Pull Request`)}>
+          <SettingsList.ItemText>
+            <Trans>Apply Pull Request</Trans>
+          </SettingsList.ItemText>
+        </SettingsList.PressableItem>
+      ) : null}
       {isNative && isCurrentlyRunningPullRequestDeployment ? (
         <SettingsList.PressableItem
           onPress={revertToEmbedded}