RORK LABJP
TOOLING — Rork's developer repos keep moving: rork-xcode was updated on July 16, rork-device on July 15, and rork-plist on July 13OPUS46 — Claude Opus 4.6 is live in Rork, and Rork Max is built to assemble apps on top of Claude CodeSIM — A cloud iOS simulator runs in the browser, with one click to install on a device and two clicks to publish to the App StoreMAX — Rork Max emits pure Swift rather than React Native, reaching iPhone, iPad, Apple Watch, Apple TV, Vision Pro, and even iMessageNATIVE — That opens up HealthKit, ARKit and LiDAR, NFC, Dynamic Island, Live Activities, 3D through Metal, and on-device inference with Core MLSEED — Rork raised a $15M seed led by Left Lane Capital, with Peak XV and a16z Speedrun joining the roundTOOLING — Rork's developer repos keep moving: rork-xcode was updated on July 16, rork-device on July 15, and rork-plist on July 13OPUS46 — Claude Opus 4.6 is live in Rork, and Rork Max is built to assemble apps on top of Claude CodeSIM — A cloud iOS simulator runs in the browser, with one click to install on a device and two clicks to publish to the App StoreMAX — Rork Max emits pure Swift rather than React Native, reaching iPhone, iPad, Apple Watch, Apple TV, Vision Pro, and even iMessageNATIVE — That opens up HealthKit, ARKit and LiDAR, NFC, Dynamic Island, Live Activities, 3D through Metal, and on-device inference with Core MLSEED — Rork raised a $15M seed led by Left Lane Capital, with Peak XV and a16z Speedrun joining the round
Articles/Dev Tools
Dev Tools/2026-05-04Intermediate

Microphone and Audio Recording Not Working in Rork — A Symptom-Based Troubleshooting Guide

When microphone or audio recording stops working in a Rork-generated app, the root cause is often not obvious. This guide walks through common failure patterns — permissions, audio mode setup, simulator limits, and async pitfalls — with working code fixes.

microphoneaudio recordingexpo-audio3expo-av6permissions7troubleshooting65iOS109Android43React Native209

You built a voice memo app with Rork, tapped the record button, and nothing happened. No error, no crash — just silence.

Microphone bugs are uniquely frustrating because they often fail silently. Unlike a network request that throws a 404 or a UI crash that prints a stack trace, a microphone that doesn't start gives you almost no feedback. If you're also dealing with camera or location permission issues, the Rork Permissions Troubleshooting Guide covers those patterns in detail. This guide breaks down the most common failure patterns in Rork-generated audio recording code, with practical fixes for each.

First Check: The Simulator Won't Record Audio

Before diving into code, it's worth ruling out the most common false alarm.

The iOS Simulator does not support the microphone. If you're testing recording functionality in Expo Go or the simulator, it will silently fail every time — regardless of how correct your code is.

// This might look like it's working, but on a simulator
// the permission status may stay 'undetermined' indefinitely
const { status } = await Audio.requestPermissionsAsync();
console.log('Permission status:', status);

Always test microphone functionality on a real device using the Rork Companion app, a TestFlight build, or an EAS Development Build. If recording works on device but not simulator, your code is fine — you just need a real device for this feature.

Pattern 1: Recording Crashes Immediately or Produces No Audio

If the app crashes on record, or recording appears to start but captures nothing, the most likely cause is missing native permission declarations.

iOS — Info.plist Entry

Without NSMicrophoneUsageDescription in your app's Info.plist, iOS denies microphone access at the OS level. The app may crash without a clear error message.

// app.json (or app.config.js) — add this under expo.ios
{
  "expo": {
    "ios": {
      "infoPlist": {
        "NSMicrophoneUsageDescription": "Used to record voice memos within the app."
      }
    }
  }
}

Rork's AI often generates the recording component correctly but omits this app.json entry. After adding it, you'll need to create a new EAS Build — an OTA update (eas update) won't pick up native configuration changes.

Android — RECORD_AUDIO Permission

On Android, RECORD_AUDIO must be declared in AndroidManifest.xml. When using expo-audio, the Expo plugin usually handles this automatically, but it's worth verifying.

// app.json — android section
{
  "expo": {
    "android": {
      "permissions": ["RECORD_AUDIO"]
    }
  }
}

After changing this, rebuild with EAS. Runtime permission requests also need to be handled in code — the manifest entry alone isn't enough.

Pattern 2: Permission Dialog Appears, User Approves, Still No Recording

If the user grants microphone permission but recording still doesn't work, the issue is almost always missing Audio Mode configuration.

With expo-audio (the current recommended library as of Expo SDK 51+), you need to set the audio mode before starting a recording. Without this, iOS in particular will silently fail because the audio session isn't configured for recording.

import { useAudioRecorder, AudioModule, RecordingPresets } from 'expo-audio';
 
async function startRecording() {
  // Request permission first
  const { status } = await AudioModule.requestRecordingPermissionsAsync();
  if (status !== 'granted') {
    // Guide user to Settings — iOS won't show the dialog again after denial
    Alert.alert(
      'Microphone Permission Required',
      'Please enable microphone access in Settings to use this feature.',
      [{ text: 'Open Settings', onPress: () => Linking.openSettings() }]
    );
    return;
  }
 
  // ★ This step is frequently missing from Rork-generated code
  await AudioModule.setAudioModeAsync({
    allowsRecordingIOS: true,        // Required for recording on iOS
    playsInSilentModeIOS: true,      // Record even when device is on silent
    interruptionModeIOS: 'doNotMix', // Don't mix with other audio sessions
  });
 
  const recorder = useAudioRecorder(RecordingPresets.HIGH_QUALITY);
  await recorder.record();
}

The key line is allowsRecordingIOS: true. Without it, iOS keeps the audio session in playback mode, and recording simply doesn't start — no error thrown, just no audio captured.

Pattern 3: Works in Expo Go, Fails in TestFlight Build

Expo Go ships with broad permissions pre-granted for development purposes. This means a feature that works in Expo Go may fail in a production build that doesn't have the correct app.json configuration.

Additionally, if Rork generated code using the older expo-av recording API, you may be hitting deprecation-related instability. As of Expo SDK 51, expo-av's audio recording functionality is deprecated in favor of expo-audio.

# Install the current recommended audio package
npx expo install expo-audio
 
# If you're migrating from expo-av, check for this import
# OLD: import { Audio } from 'expo-av';
# NEW: import { useAudioRecorder, AudioModule } from 'expo-audio';

After switching packages, you need a fresh EAS Build — not just an OTA update.

Pattern 4: Recording Starts but File Is Corrupted or Empty

If recording starts but the saved file won't play back (or is 0 bytes), the issue is almost certainly async handling. Rork's AI sometimes generates recording stop logic without properly awaiting the async operations.

// ❌ Common pattern in Rork-generated code — doesn't await stop()
const handleStop = () => {
  recorder.stop();    // Returns a Promise, but we're not awaiting it
  const uri = recorder.getUri();  // Called before recording has actually stopped
  saveFile(uri);      // May save an incomplete or empty file
};
 
// ✅ Correct async pattern
const handleStop = async () => {
  await recorder.stop();           // Wait for recording to fully complete
  const uri = recorder.getUri();   // URI is now valid
  if (uri) {
    await saveToStorage(uri);      // File is complete, safe to save
  }
};

The stop() method is asynchronous — the audio file isn't fully written until the Promise resolves. Accessing the URI before that point often results in an empty or corrupted file.

iOS vs Android Behavioral Differences

Microphone behavior has meaningful differences between platforms that are useful to know when debugging.

iOS:

  • Silent mode blocks recording unless playsInSilentModeIOS: true is set
  • After a user taps "Don't Allow," iOS won't show the permission dialog again — you must redirect to Settings
  • Background recording requires Background Modes capability (audio mode in app.json)

Android:

  • Runtime permission request is required even if declared in the manifest
  • Background recording needs a Foreground Service
  • Some manufacturers (particularly Huawei and Xiaomi) have custom battery optimization that can interrupt background recording

If something works on iOS but not Android, start by verifying that the runtime RECORD_AUDIO permission request is actually being triggered in code (not just declared in the manifest).

Getting Rork AI to Generate Better Recording Code

Vague prompts often produce incomplete recording implementations. Being specific about what you need gets significantly better results.

# Effective prompt for recording functionality
"Create a voice recording component using expo-audio that works on both 
iOS and Android. Include AudioModule.setAudioModeAsync with 
allowsRecordingIOS: true before recording starts. Handle the case where 
the user denies permission with an alert that links to Settings. Use 
proper async/await throughout the start and stop recording flow."

A prompt like "add a record button" tends to produce code missing the Audio Mode setup and permission denial handling. The more you specify what you know is needed, the more complete the output.

If you already have generated code that's not working, pasting the actual error output (or noting "recording starts but the file is empty") alongside the code gives Rork's AI the context it needs to produce a targeted fix.

Testing on a Real Device Without a Full EAS Build

If you want to verify microphone behavior without going through a full EAS Build cycle, Rork's Development Build workflow (via expo-dev-client) is the fastest option. It behaves like a real native build while allowing you to update JavaScript code on the fly.

# Create a development build once
eas build --profile development --platform ios
 
# After installation, use expo start to push JS changes instantly
npx expo start --dev-client

This approach means you only need to rebuild when native configuration changes (like adding NSMicrophoneUsageDescription). For the async and audio mode fixes described above, you can test changes immediately without waiting for a full build.

The Rork Companion app also supports testing many native features, including microphone access — which makes it useful for quick iteration before committing to a formal build.

Where to Start

If recording isn't working and you're not sure why, work through this checklist in order:

  1. Are you testing on a real device? (The simulator won't work)
  2. Is NSMicrophoneUsageDescription in your app.json?
  3. Is AudioModule.setAudioModeAsync({ allowsRecordingIOS: true }) called before record()?
  4. Is stop() properly awaited before accessing the file URI?

These four checks resolve the majority of Rork recording issues. Audio apps — voice diaries, transcription tools, AI voice assistants — are well within Rork's capabilities once the native wiring is in place. For a complete implementation example, the AI Voice Diary App Guide shows how these pieces fit together in a production app.

Share

Thank You for Reading

Rork Lab is ad-free, supported entirely by members like you. We publish practical guides daily with implementation code, benchmarks, and production-ready patterns. If you've found it useful, we'd love to have you on board.

  • Copy-paste ready implementation code
  • New advanced guides published daily
  • $5/mo or $10 for lifetime access
View Membership →

If you found this article helpful, a small tip ($1.50) would mean a lot to us. Your support helps keep this site ad-free and covers server and hosting costs.

Related Articles

Dev Tools2026-05-10
When expo-image-picker won't launch in your Rork app — Info.plist and permission fixes that actually worked
Your Rork-generated app's pick image button works in the simulator but does nothing on TestFlight builds. Walk through the four real-world causes I keep hitting: missing Info.plist keys, wrong permission order, iOS 14 Limited Photo Access, and Android 13+ media permissions.
Dev Tools2026-04-23
Why Your Rork App Can't Save Images to the Camera Roll — A Complete Fix
Image and video saving often breaks the moment a Rork-generated app leaves the simulator. This guide walks through the permission model, expo-media-library quirks, and Android 13+ scoped storage changes that reliably trip people up.
Dev Tools2026-04-18
Rork App Works on iOS but Breaks on Android: A Practical Guide to Fixing Platform Differences
Troubleshoot Rork apps that work on iOS but break on Android. Covers shadows, fonts, permissions, keyboard, and status bar with code examples.
📚RECOMMENDED BOOKS
Build a Large Language Model (From Scratch)
Sebastian Raschka
LLM Dev
Prompt Engineering for LLMs
Berryman & Ziegler
Prompting
AI Engineering
Chip Huyen
AI Eng
* Contains affiliate links
See all →