fix(up-wip): recording permissions

This commit is contained in:
devthejo 2025-10-02 19:29:24 +02:00
parent c5ccfa8d08
commit 749a09aa5e
No known key found for this signature in database
GPG key ID: 00CCA7A92B1D5351
3 changed files with 96 additions and 22 deletions

View file

@ -1,5 +1,5 @@
import React, { useState, useCallback, useEffect, useRef } from "react";
import { View, Text, TouchableOpacity } from "react-native";
import { View, Text, TouchableOpacity, Platform, Alert } from "react-native";
import { MaterialCommunityIcons } from "@expo/vector-icons";
import {
useAudioRecorder,
@ -11,6 +11,14 @@ import {
AudioQuality,
} from "expo-audio";
import {
check,
request,
PERMISSIONS,
RESULTS,
openSettings,
} from "react-native-permissions";
import Countdown from "react-countdown";
import { useAlertState, getLocationState, useSessionState } from "~/stores";
@ -74,6 +82,51 @@ const recordingOptionsFallback = {
const activeOpacity = 0.7;
const withTimeout = (promise, ms = 10000) =>
new Promise((resolve, reject) => {
const id = setTimeout(
() => reject(new Error("Permission request timeout")),
ms,
);
promise
.then((v) => {
clearTimeout(id);
resolve(v);
})
.catch((e) => {
clearTimeout(id);
reject(e);
});
});
const ensureMicPermission = async () => {
if (Platform.OS !== "android") {
return true;
}
try {
const status = await check(PERMISSIONS.ANDROID.RECORD_AUDIO);
if (status === RESULTS.GRANTED) return true;
if (status === RESULTS.BLOCKED) {
try {
Alert.alert(
"Autorisation micro bloquée",
"Veuillez autoriser le micro dans les paramètres de l'application.",
[
{ text: "Annuler", style: "cancel" },
{ text: "Ouvrir les paramètres", onPress: openSettings },
],
);
} catch (_) {}
return false;
}
const res = await request(PERMISSIONS.ANDROID.RECORD_AUDIO);
return res === RESULTS.GRANTED;
} catch (e) {
console.log("Mic permission check failed", e);
return false;
}
};
export default React.memo(function ChatInput({
style,
labelStyle,
@ -146,8 +199,30 @@ export default React.memo(function ChatInput({
const startRecording = useCallback(async () => {
try {
console.log("Requesting permissions..");
await requestRecordingPermissionsAsync();
console.log("Requesting microphone permission..");
const grantedPre = await ensureMicPermission();
if (!grantedPre) {
console.log("Microphone permission not granted or blocked");
return;
}
try {
await withTimeout(requestRecordingPermissionsAsync(), 10000);
} catch (permErr) {
console.log("Microphone permission request failed/timed out:", permErr);
if (Platform.OS === "android") {
try {
Alert.alert(
"Autorisation micro requise",
"Impossible d'obtenir l'autorisation du microphone. Ouvrir les paramètres pour l'accorder.",
[
{ text: "Annuler", style: "cancel" },
{ text: "Ouvrir les paramètres", onPress: openSettings },
],
);
} catch (_) {}
}
return;
}
await setAudioModeAsync({
allowsRecording: true,
interruptionMode: "doNotMix",

View file

@ -46,22 +46,27 @@ export default async () => {
// Handle Android permissions
permissionLogger.debug("Requesting Android notification permissions");
const { status } = await requestNotifications(["alert"]);
const { status } = await requestNotifications(["alert", "sound", "badge"]);
permissionLogger.debug(
"Requesting POST_NOTIFICATIONS permission (Android 13+)",
);
const postNotifications = await request(
PERMISSIONS.ANDROID.POST_NOTIFICATIONS,
);
let postNotifications = RESULTS.UNAVAILABLE;
if (Platform.Version >= 33) {
permissionLogger.debug(
"Requesting POST_NOTIFICATIONS permission (Android 13+)",
);
postNotifications = await request(PERMISSIONS.ANDROID.POST_NOTIFICATIONS);
}
// Determine grant state:
// - Android 13+ requires POST_NOTIFICATIONS granted
// - Below 13, POST_NOTIFICATIONS is unavailable; use requestNotifications result
const isGranted =
status === RESULTS.GRANTED &&
(postNotifications === "granted" || postNotifications === "unavailable");
(Platform.Version >= 33 && postNotifications === RESULTS.GRANTED) ||
(Platform.Version < 33 && status === RESULTS.GRANTED);
permissionLogger.info("Android notification permission result", {
notificationStatus: status,
postNotificationsStatus: postNotifications,
osVersion: Platform.Version,
granted: isGranted,
});

View file

@ -3,23 +3,17 @@ import { useEffect } from "react";
import requestPermissionFcm from "./requestPermissionFcm";
export default async function usePermissionFcm() {
export default function usePermissionFcm() {
const { fcm } = usePermissionsState(["fcm"]);
const { setFcm } = permissionsActions;
useEffect(() => {
// if (fcm) {
// return;
// }
if (fcm) {
return;
}
(async () => {
// const authStatus = await messaging().requestPermission();
// setFcm(
// authStatus === AuthorizationStatus.AUTHORIZED ||
// authStatus === AuthorizationStatus.PROVISIONAL,
// );
const granted = await requestPermissionFcm();
setFcm(granted);
})();
}, [fcm, setFcm]);