Skip to main content

VideoError

Base error class for React Native Video errors. All video-related errors extend this class.
class VideoError<TCode extends VideoErrorCode> extends Error {
  readonly code: TCode;
  readonly message: string;
  readonly stack?: string;
}

Properties

code
VideoErrorCode
required
The error code identifying the specific error type. See VideoErrorCode for possible values.
message
string
required
Human-readable description of the error.
stack
string
Stack trace for debugging (when available).

Error Classes

VideoComponentError

Errors related to the Video component itself:
class VideoComponentError extends VideoError<VideoViewError> {}
Thrown when there are issues with the video view/component.

VideoRuntimeError

Errors that occur during video playback:
class VideoRuntimeError extends VideoError<
  LibraryError | PlayerError | SourceError | UnknownError
> {}
Thrown when there are runtime issues with the library, player, or video source.

VideoErrorCode

Union type of all possible error codes:
type VideoErrorCode =
  | LibraryError
  | PlayerError
  | SourceError
  | VideoViewError
  | UnknownError;

LibraryError

Errors related to the video library itself:
type LibraryError =
  | 'library/deallocated'
  | 'library/application-context-not-found';
library/deallocated
string
The video library has been deallocated/destroyed.
library/application-context-not-found
string
Android: Application context could not be found.

PlayerError

Errors related to the video player:
type PlayerError =
  | 'player/released'
  | 'player/not-initialized'
  | 'player/asset-not-initialized'
  | 'player/invalid-source';
player/released
string
The player has been released and cannot be used.
player/not-initialized
string
The player has not been initialized yet.
player/asset-not-initialized
string
The video asset has not been initialized.
player/invalid-source
string
The provided video source is invalid.

SourceError

Errors related to video source loading:
type SourceError =
  | 'source/invalid-uri'
  | 'source/missing-read-file-permission'
  | 'source/file-does-not-exist'
  | 'source/failed-to-initialize-asset'
  | 'source/unsupported-content-type';
source/invalid-uri
string
The video URI is invalid or malformed.
source/missing-read-file-permission
string
Missing permission to read the video file.
source/file-does-not-exist
string
The video file does not exist at the specified path.
source/failed-to-initialize-asset
string
Failed to initialize the video asset.
source/unsupported-content-type
string
The video content type is not supported.

VideoViewError

Errors related to the video view/component:
type VideoViewError =
  | 'view/not-found'
  | 'view/deallocated'
  | 'view/picture-in-picture-not-supported';
view/not-found
string
The video view could not be found.
view/deallocated
string
The video view has been deallocated.
view/picture-in-picture-not-supported
string
Picture-in-picture mode is not supported on this device/platform.

UnknownError

Unknown or unexpected errors:
type UnknownError = 'unknown/unknown';
unknown/unknown
string
An unknown error occurred.

Error Handling

Basic Error Handling

import { VideoPlayer, VideoError, tryParseNativeVideoError } from 'react-native-video';

try {
  const player = VideoPlayer.create({
    uri: 'https://example.com/video.mp4'
  });
  
  await player.playAsync();
} catch (error) {
  const videoError = tryParseNativeVideoError(error);
  
  if (videoError instanceof VideoError) {
    console.error(`[${videoError.code}]: ${videoError.message}`);
  } else {
    console.error('Unknown error:', error);
  }
}

Handling Specific Error Types

import {
  VideoPlayer,
  VideoComponentError,
  VideoRuntimeError,
  tryParseNativeVideoError
} from 'react-native-video';

try {
  const player = VideoPlayer.create({
    uri: 'https://example.com/video.mp4'
  });
  
  await player.playAsync();
} catch (error) {
  const videoError = tryParseNativeVideoError(error);
  
  if (videoError instanceof VideoComponentError) {
    // Handle component errors
    console.error('Component error:', videoError.message);
    if (videoError.code === 'view/picture-in-picture-not-supported') {
      console.log('PiP not available on this device');
    }
  } else if (videoError instanceof VideoRuntimeError) {
    // Handle runtime errors
    console.error('Runtime error:', videoError.message);
    if (videoError.code === 'source/file-does-not-exist') {
      console.log('Video file not found');
    }
  } else {
    console.error('Unknown error:', error);
  }
}

Handling Specific Error Codes

import { VideoPlayer, VideoError, tryParseNativeVideoError } from 'react-native-video';

const handleVideoError = (error: unknown) => {
  const videoError = tryParseNativeVideoError(error);
  
  if (!(videoError instanceof VideoError)) {
    console.error('Unknown error:', error);
    return;
  }
  
  switch (videoError.code) {
    case 'source/invalid-uri':
      console.error('Invalid video URL');
      break;
      
    case 'source/file-does-not-exist':
      console.error('Video file not found');
      break;
      
    case 'source/missing-read-file-permission':
      console.error('Missing file read permission');
      break;
      
    case 'player/not-initialized':
      console.error('Player not initialized');
      break;
      
    case 'view/picture-in-picture-not-supported':
      console.error('PiP not supported');
      break;
      
    case 'library/deallocated':
      console.error('Video library deallocated');
      break;
      
    default:
      console.error(`Error [${videoError.code}]: ${videoError.message}`);
  }
};

try {
  const player = VideoPlayer.create({
    uri: 'https://example.com/video.mp4'
  });
  await player.playAsync();
} catch (error) {
  handleVideoError(error);
}

User-Friendly Error Messages

import { VideoError, tryParseNativeVideoError } from 'react-native-video';
import { Alert } from 'react-native';

const getUserFriendlyErrorMessage = (error: unknown): string => {
  const videoError = tryParseNativeVideoError(error);
  
  if (!(videoError instanceof VideoError)) {
    return 'An unexpected error occurred while playing the video.';
  }
  
  const errorMessages: Record<string, string> = {
    'source/invalid-uri': 'The video URL is invalid.',
    'source/file-does-not-exist': 'The video file could not be found.',
    'source/missing-read-file-permission': 'Permission to access the video was denied.',
    'source/unsupported-content-type': 'This video format is not supported.',
    'player/invalid-source': 'The video source is invalid.',
    'view/picture-in-picture-not-supported': 'Picture-in-picture is not available on your device.',
  };
  
  return errorMessages[videoError.code] || `Error: ${videoError.message}`;
};

// Usage
try {
  await player.playAsync();
} catch (error) {
  const message = getUserFriendlyErrorMessage(error);
  Alert.alert('Playback Error', message);
}

tryParseNativeVideoError

Utility function to parse native video errors into typed VideoError instances:
function tryParseNativeVideoError<T>(
  nativeError: T
): (VideoRuntimeError | VideoComponentError) | T
Attempts to parse an error from native code into a typed JavaScript VideoError. Returns the original error if it cannot be parsed.

Usage

import { tryParseNativeVideoError, VideoError } from 'react-native-video';

try {
  await player.playAsync();
} catch (error) {
  const parsedError = tryParseNativeVideoError(error);
  
  if (parsedError instanceof VideoError) {
    // Typed error with code and message
    console.log('Error code:', parsedError.code);
    console.log('Error message:', parsedError.message);
  } else {
    // Original unparsed error
    console.error('Unparsed error:', parsedError);
  }
}

Examples

Complete Error Handling Example

import React, { useEffect, useState } from 'react';
import { View, Text, Button, Alert } from 'react-native';
import {
  Video,
  VideoPlayer,
  VideoError,
  VideoRuntimeError,
  tryParseNativeVideoError
} from 'react-native-video';

const VideoPlayerWithErrorHandling = () => {
  const [player, setPlayer] = useState<VideoPlayer | null>(null);
  const [error, setError] = useState<string | null>(null);

  useEffect(() => {
    try {
      const newPlayer = VideoPlayer.create({
        uri: 'https://example.com/video.mp4'
      });
      setPlayer(newPlayer);
    } catch (err) {
      handleError(err);
    }

    return () => {
      player?.release();
    };
  }, []);

  const handleError = (err: unknown) => {
    const videoError = tryParseNativeVideoError(err);
    
    if (videoError instanceof VideoError) {
      setError(`[${videoError.code}]: ${videoError.message}`);
      
      // Show user-friendly alert
      Alert.alert(
        'Playback Error',
        getUserFriendlyMessage(videoError.code),
        [{ text: 'OK' }]
      );
    } else {
      setError('An unknown error occurred');
    }
  };

  const getUserFriendlyMessage = (code: string): string => {
    const messages: Record<string, string> = {
      'source/file-does-not-exist': 'Video file not found. Please check the URL.',
      'source/invalid-uri': 'Invalid video URL.',
      'player/not-initialized': 'Player is not ready yet. Please try again.',
    };
    return messages[code] || 'Unable to play video.';
  };

  const handlePlay = async () => {
    if (!player) return;
    
    try {
      await player.playAsync();
      setError(null);
    } catch (err) {
      handleError(err);
    }
  };

  if (!player) {
    return <Text>Loading player...</Text>;
  }

  return (
    <View>
      <Video
        player={player}
        style={{ width: '100%', height: 300 }}
      />
      
      {error && (
        <View style={{ padding: 16, backgroundColor: '#ffebee' }}>
          <Text style={{ color: '#c62828' }}>{error}</Text>
        </View>
      )}
      
      <Button title="Play" onPress={handlePlay} />
    </View>
  );
};

export default VideoPlayerWithErrorHandling;

Build docs developers (and LLMs) love