2016-06-30 00:08:53 +01:00
/ * *
* React Native FS
* @ flow
* /
2015-05-08 20:05:37 +03:00
'use strict' ;
2015-10-19 14:40:05 +01:00
// This file supports both iOS and Android
2015-09-30 18:32:58 -07:00
var RNFSManager = require ( 'react-native' ) . NativeModules . RNFSManager ;
2016-07-18 22:46:13 +01:00
2015-11-20 00:16:13 +00:00
var NativeAppEventEmitter = require ( 'react-native' ) . NativeAppEventEmitter ; // iOS
var DeviceEventEmitter = require ( 'react-native' ) . DeviceEventEmitter ; // Android
2015-05-08 20:05:37 +03:00
var base64 = require ( 'base-64' ) ;
2015-10-22 01:25:52 +01:00
var utf8 = require ( 'utf8' ) ;
2015-05-08 20:05:37 +03:00
2016-08-10 19:53:24 +01:00
var RNFSFileTypeRegular = RNFSManager . RNFSFileTypeRegular ;
var RNFSFileTypeDirectory = RNFSManager . RNFSFileTypeDirectory ;
2015-05-08 20:05:37 +03:00
2015-11-20 00:16:13 +00:00
var jobId = 0 ;
var getJobId = ( ) => {
jobId += 1 ;
return jobId ;
} ;
2016-08-11 14:07:25 -07:00
var normalizeFilePath = ( path : string ) => ( path . startsWith ( 'file://' ) ? path . slice ( 7 ) : path ) ;
2016-08-01 19:36:15 +01:00
type MkdirOptions = {
2016-08-28 09:51:04 +01:00
NSURLIsExcludedFromBackupKey ? : boolean ; // iOS only
2016-08-01 19:36:15 +01:00
} ;
2016-06-30 00:08:53 +01:00
type ReadDirItem = {
2017-05-02 00:46:21 +02:00
ctime : ? Date ; // The creation date of the file (iOS only)
mtime : Date ; // The last modified date of the file
2016-06-30 00:08:53 +01:00
name : string ; // The name of the item
path : string ; // The absolute path to the item
size : string ; // Size in bytes
isFile : ( ) => boolean ; // Is the file just a file?
isDirectory : ( ) => boolean ; // Is the file a directory?
} ;
type StatResult = {
name : string ; // The name of the item
path : string ; // The absolute path to the item
size : string ; // Size in bytes
mode : number ; // UNIX file mode
2016-12-29 16:58:13 -05:00
ctime : number ; // Created date
utime : number ; // Updated date
2016-06-30 00:08:53 +01:00
isFile : ( ) => boolean ; // Is the file just a file?
isDirectory : ( ) => boolean ; // Is the file a directory?
} ;
type Headers = { [ name : string ] : string } ;
type Fields = { [ name : string ] : string } ;
type DownloadFileOptions = {
fromUrl : string ; // URL to download file from
toFile : string ; // Local filesystem path to save the file to
headers ? : Headers ; // An object of headers to be passed to the server
2016-08-28 09:51:04 +01:00
background ? : boolean ; // iOS only
2016-06-30 00:08:53 +01:00
progressDivider ? : number ;
2017-06-01 16:45:06 +05:30
readTimeout ? : number ;
connectionTimeout ? : number ;
2016-06-30 00:08:53 +01:00
begin ? : ( res : DownloadBeginCallbackResult ) => void ;
progress ? : ( res : DownloadProgressCallbackResult ) => void ;
} ;
type DownloadBeginCallbackResult = {
jobId : number ; // The download job ID, required if one wishes to cancel the download. See `stopDownload`.
statusCode : number ; // The HTTP status code
contentLength : number ; // The total size in bytes of the download resource
headers : Headers ; // The HTTP response headers from the server
} ;
type DownloadProgressCallbackResult = {
jobId : number ; // The download job ID, required if one wishes to cancel the download. See `stopDownload`.
contentLength : number ; // The total size in bytes of the download resource
bytesWritten : number ; // The number of bytes written to the file so far
} ;
type DownloadResult = {
jobId : number ; // The download job ID, required if one wishes to cancel the download. See `stopDownload`.
statusCode : number ; // The HTTP status code
bytesWritten : number ; // The number of bytes written to the file
} ;
type UploadFileOptions = {
toUrl : string ; // URL to upload file to
files : UploadFileItem [ ] ; // An array of objects with the file information to be uploaded.
2016-06-30 11:45:11 +01:00
headers ? : Headers ; // An object of headers to be passed to the server
fields ? : Fields ; // An object of fields to be passed to the server
method ? : string ; // Default is 'POST', supports 'POST' and 'PUT'
2016-06-30 00:08:53 +01:00
begin ? : ( res : UploadBeginCallbackResult ) => void ;
progress ? : ( res : UploadProgressCallbackResult ) => void ;
} ;
type UploadFileItem = {
name : string ; // Name of the file, if not defined then filename is used
filename : string ; // Name of file
filepath : string ; // Path to file
filetype : string ; // The mimetype of the file to be uploaded, if not defined it will get mimetype from `filepath` extension
} ;
type UploadBeginCallbackResult = {
jobId : number ; // The upload job ID, required if one wishes to cancel the upload. See `stopUpload`.
} ;
type UploadProgressCallbackResult = {
jobId : number ; // The upload job ID, required if one wishes to cancel the upload. See `stopUpload`.
totalBytesExpectedToSend : number ; // The total number of bytes that will be sent to the server
totalBytesSent : number ; // The number of bytes sent to the server
} ;
type UploadResult = {
jobId : number ; // The upload job ID, required if one wishes to cancel the upload. See `stopUpload`.
statusCode : number ; // The HTTP status code
headers : Headers ; // The HTTP response headers from the server
body : string ; // The HTTP response body
} ;
type FSInfoResult = {
totalSpace : number ; // The total amount of storage space on the device (in bytes).
freeSpace : number ; // The amount of available storage space on the device (in bytes).
} ;
2016-12-06 13:04:09 +00:00
/ * *
* Generic function used by readFile and readFileAssets
* /
function readFileGeneric ( filepath : string , encodingOrOptions : ? string , command : Function ) {
var options = {
encoding : 'utf8'
} ;
if ( encodingOrOptions ) {
if ( typeof encodingOrOptions === 'string' ) {
options . encoding = encodingOrOptions ;
} else if ( typeof encodingOrOptions === 'object' ) {
options = encodingOrOptions ;
}
}
return command ( normalizeFilePath ( filepath ) ) . then ( ( b64 ) => {
var contents ;
if ( options . encoding === 'utf8' ) {
contents = utf8 . decode ( base64 . decode ( b64 ) ) ;
} else if ( options . encoding === 'ascii' ) {
contents = base64 . decode ( b64 ) ;
} else if ( options . encoding === 'base64' ) {
contents = b64 ;
} else {
throw new Error ( 'Invalid encoding type "' + String ( options . encoding ) + '"' ) ;
}
return contents ;
} ) ;
}
/ * *
* Generic function used by readDir and readDirAssets
* /
function readDirGeneric ( dirpath : string , command : Function ) {
return command ( normalizeFilePath ( dirpath ) ) . then ( files => {
return files . map ( file => ( {
2017-04-27 13:07:19 +02:00
ctime : file . ctime && new Date ( file . ctime * 1000 ) || null ,
mtime : new Date ( file . mtime * 1000 ) ,
2016-12-06 13:04:09 +00:00
name : file . name ,
path : file . path ,
size : file . size ,
isFile : ( ) => file . type === RNFSFileTypeRegular ,
isDirectory : ( ) => file . type === RNFSFileTypeDirectory ,
} ) ) ;
} ) ;
}
2015-05-08 20:05:37 +03:00
var RNFS = {
2016-08-05 18:48:44 -07:00
mkdir ( filepath : string , options : MkdirOptions = { } ) : Promise < void > {
2016-08-11 14:07:25 -07:00
return RNFSManager . mkdir ( normalizeFilePath ( filepath ) , options ) . then ( ( ) => void 0 ) ;
2016-08-01 19:36:15 +01:00
} ,
moveFile ( filepath : string , destPath : string ) : Promise < void > {
2016-08-11 14:07:25 -07:00
return RNFSManager . moveFile ( normalizeFilePath ( filepath ) , normalizeFilePath ( destPath ) ) . then ( ( ) => void 0 ) ;
2016-08-01 19:36:15 +01:00
} ,
copyFile ( filepath : string , destPath : string ) : Promise < void > {
2016-08-11 14:07:25 -07:00
return RNFSManager . copyFile ( normalizeFilePath ( filepath ) , normalizeFilePath ( destPath ) ) . then ( ( ) => void 0 ) ;
2016-08-01 19:36:15 +01:00
} ,
pathForBundle ( bundleNamed : string ) : Promise < string > {
return RNFSManager . pathForBundle ( bundleNamed ) ;
} ,
2017-01-31 15:40:59 +02:00
pathForGroup ( groupName : string ) : Promise < string > {
return RNFSManager . pathForGroup ( groupName ) ;
} ,
2016-08-01 19:36:15 +01:00
getFSInfo ( ) : Promise < FSInfoResult > {
return RNFSManager . getFSInfo ( ) ;
} ,
unlink ( filepath : string ) : Promise < void > {
2016-08-11 14:07:25 -07:00
return RNFSManager . unlink ( normalizeFilePath ( filepath ) ) . then ( ( ) => void 0 ) ;
2016-08-01 19:36:15 +01:00
} ,
exists ( filepath : string ) : Promise < boolean > {
2016-08-11 14:07:25 -07:00
return RNFSManager . exists ( normalizeFilePath ( filepath ) ) ;
2016-08-01 19:36:15 +01:00
} ,
stopDownload ( jobId : number ) : void {
RNFSManager . stopDownload ( jobId ) ;
} ,
stopUpload ( jobId : number ) : void {
RNFSManager . stopUpload ( jobId ) ;
} ,
2016-06-30 00:08:53 +01:00
readDir ( dirpath : string ) : Promise < ReadDirItem [ ] > {
2016-12-06 13:04:09 +00:00
return readDirGeneric ( dirpath , RNFSManager . readDir ) ;
} ,
// Android-only
readDirAssets ( dirpath : string ) : Promise < ReadDirItem [ ] > {
if ( ! RNFSManager . readDirAssets ) {
throw new Error ( 'readDirAssets is not available on this platform' ) ;
}
return readDirGeneric ( dirpath , RNFSManager . readDirAssets ) ;
} ,
// Android-only
existsAssets ( filepath : string ) {
if ( ! RNFSManager . existsAssets ) {
throw new Error ( 'existsAssets is not available on this platform' ) ;
}
return RNFSManager . existsAssets ( filepath ) ;
2015-05-08 20:05:37 +03:00
} ,
2015-10-22 01:25:52 +01:00
// Node style version (lowercase d). Returns just the names
2016-06-30 00:08:53 +01:00
readdir ( dirpath : string ) : Promise < string [ ] > {
2016-08-11 14:07:25 -07:00
return RNFS . readDir ( normalizeFilePath ( dirpath ) ) . then ( files => {
2016-06-30 00:08:53 +01:00
return files . map ( file => file . name ) ;
} ) ;
2015-10-22 01:25:52 +01:00
} ,
2016-06-30 00:08:53 +01:00
stat ( filepath : string ) : Promise < StatResult > {
2016-08-11 14:07:25 -07:00
return RNFSManager . stat ( normalizeFilePath ( filepath ) ) . then ( ( result ) => {
2016-06-30 00:08:53 +01:00
return {
'ctime' : new Date ( result . ctime * 1000 ) ,
'mtime' : new Date ( result . mtime * 1000 ) ,
'size' : result . size ,
'mode' : result . mode ,
2016-08-10 19:53:24 +01:00
isFile : ( ) => result . type === RNFSFileTypeRegular ,
isDirectory : ( ) => result . type === RNFSFileTypeDirectory ,
2016-06-30 00:08:53 +01:00
} ;
2016-07-18 22:46:13 +01:00
} ) ;
2016-01-28 21:36:31 +08:00
} ,
2015-05-08 20:05:37 +03:00
2016-07-27 00:15:41 +01:00
readFile ( filepath : string , encodingOrOptions ? : any ) : Promise < string > {
2016-12-06 13:04:09 +00:00
return readFileGeneric ( filepath , encodingOrOptions , RNFSManager . readFile ) ;
} ,
2016-07-27 00:15:41 +01:00
2016-12-06 13:04:09 +00:00
// Android only
readFileAssets ( filepath : string , encodingOrOptions ? : any ) : Promise < string > {
if ( ! RNFSManager . readFileAssets ) {
throw new Error ( 'readFileAssets is not available on this platform' ) ;
2016-07-27 00:15:41 +01:00
}
2016-12-06 13:04:09 +00:00
return readFileGeneric ( filepath , encodingOrOptions , RNFSManager . readFileAssets ) ;
2016-06-30 00:08:53 +01:00
} ,
2016-11-16 12:33:24 -08:00
hash ( filepath : string , algorithm : string ) : Promise < string > {
return RNFSManager . hash ( filepath , algorithm ) ;
} ,
2016-12-06 13:04:09 +00:00
// Android only
copyFileAssets ( filepath : string , destPath : string ) {
if ( ! RNFSManager . copyFileAssets ) {
throw new Error ( 'copyFileAssets is not available on this platform' ) ;
}
return RNFSManager . copyFileAssets ( normalizeFilePath ( filepath ) , normalizeFilePath ( destPath ) ) . then ( ( ) => void 0 ) ;
} ,
2017-04-28 00:59:29 +02:00
// iOS only
// Copies fotos from asset-library (camera-roll) to a specific location
2017-05-01 14:48:06 -07:00
// with a given width or height
2017-04-28 00:59:29 +02:00
// @see: https://developer.apple.com/reference/photos/phimagemanager/1616964-requestimageforasset
copyAssetsFileIOS ( imageUri : string , destPath : string , width : number , height : number ,
scale : number = 1.0 , compression : number = 1.0 , resizeMode : string = 'contain' ) : Promise < string > {
return RNFSManager . copyAssetsFileIOS ( imageUri , destPath , width , height , scale , compression , resizeMode ) ;
} ,
2016-07-27 00:15:41 +01:00
writeFile ( filepath : string , contents : string , encodingOrOptions ? : any ) : Promise < void > {
2016-06-30 00:08:53 +01:00
var b64 ;
2016-07-27 00:15:41 +01:00
var options = {
encoding : 'utf8'
} ;
if ( encodingOrOptions ) {
if ( typeof encodingOrOptions === 'string' ) {
options . encoding = encodingOrOptions ;
} else if ( typeof encodingOrOptions === 'object' ) {
options = encodingOrOptions ;
}
}
2016-06-30 00:08:53 +01:00
2016-07-27 00:15:41 +01:00
if ( options . encoding === 'utf8' ) {
2016-06-30 00:08:53 +01:00
b64 = base64 . encode ( utf8 . encode ( contents ) ) ;
2016-07-27 00:15:41 +01:00
} else if ( options . encoding === 'ascii' ) {
2016-06-30 00:08:53 +01:00
b64 = base64 . encode ( contents ) ;
2016-07-27 00:15:41 +01:00
} else if ( options . encoding === 'base64' ) {
2016-06-30 00:08:53 +01:00
b64 = contents ;
} else {
2016-07-27 00:15:41 +01:00
throw new Error ( 'Invalid encoding type "' + options . encoding + '"' ) ;
2016-06-30 00:08:53 +01:00
}
2016-08-11 14:07:25 -07:00
return RNFSManager . writeFile ( normalizeFilePath ( filepath ) , b64 ) . then ( ( ) => void 0 ) ;
2015-05-08 20:05:37 +03:00
} ,
2016-07-27 00:15:41 +01:00
appendFile ( filepath : string , contents : string , encodingOrOptions ? : any ) : Promise < void > {
2015-10-22 01:25:52 +01:00
var b64 ;
2016-07-27 00:15:41 +01:00
var options = {
encoding : 'utf8'
} ;
if ( encodingOrOptions ) {
if ( typeof encodingOrOptions === 'string' ) {
options . encoding = encodingOrOptions ;
} else if ( typeof encodingOrOptions === 'object' ) {
options = encodingOrOptions ;
}
}
2015-10-22 01:25:52 +01:00
2016-07-27 00:15:41 +01:00
if ( options . encoding === 'utf8' ) {
2015-10-22 01:25:52 +01:00
b64 = base64 . encode ( utf8 . encode ( contents ) ) ;
2016-07-27 00:15:41 +01:00
} else if ( options . encoding === 'ascii' ) {
2015-10-22 01:25:52 +01:00
b64 = base64 . encode ( contents ) ;
2016-07-27 00:15:41 +01:00
} else if ( options . encoding === 'base64' ) {
2015-10-22 01:25:52 +01:00
b64 = contents ;
} else {
2016-07-27 00:15:41 +01:00
throw new Error ( 'Invalid encoding type "' + options . encoding + '"' ) ;
2015-10-22 01:25:52 +01:00
}
2016-08-11 14:07:25 -07:00
return RNFSManager . appendFile ( normalizeFilePath ( filepath ) , b64 ) ;
2015-05-09 00:17:10 +03:00
} ,
2017-04-29 12:38:10 +02:00
write ( filepath : string , contents : string , position ? : number , encodingOrOptions ? : any ) : Promise < void > {
var b64 ;
var options = {
encoding : 'utf8'
} ;
if ( encodingOrOptions ) {
if ( typeof encodingOrOptions === 'string' ) {
options . encoding = encodingOrOptions ;
} else if ( typeof encodingOrOptions === 'object' ) {
options = encodingOrOptions ;
}
}
if ( options . encoding === 'utf8' ) {
b64 = base64 . encode ( utf8 . encode ( contents ) ) ;
} else if ( options . encoding === 'ascii' ) {
b64 = base64 . encode ( contents ) ;
} else if ( options . encoding === 'base64' ) {
b64 = contents ;
} else {
throw new Error ( 'Invalid encoding type "' + options . encoding + '"' ) ;
}
if ( position === undefined ) {
position = - 1 ;
}
return RNFSManager . write ( normalizeFilePath ( filepath ) , b64 , position ) . then ( ( ) => void 0 ) ;
} ,
2016-08-10 20:29:14 +01:00
downloadFile ( options : DownloadFileOptions ) : { jobId : number , promise : Promise < DownloadResult > } {
2016-06-02 00:49:01 +01:00
if ( typeof options !== 'object' ) throw new Error ( 'downloadFile: Invalid value for argument `options`' ) ;
if ( typeof options . fromUrl !== 'string' ) throw new Error ( 'downloadFile: Invalid value for property `fromUrl`' ) ;
if ( typeof options . toFile !== 'string' ) throw new Error ( 'downloadFile: Invalid value for property `toFile`' ) ;
if ( options . headers && typeof options . headers !== 'object' ) throw new Error ( 'downloadFile: Invalid value for property `headers`' ) ;
if ( options . background && typeof options . background !== 'boolean' ) throw new Error ( 'downloadFile: Invalid value for property `background`' ) ;
2016-06-08 17:52:08 +01:00
if ( options . progressDivider && typeof options . progressDivider !== 'number' ) throw new Error ( 'downloadFile: Invalid value for property `progressDivider`' ) ;
2017-06-01 16:45:06 +05:30
if ( options . readTimeout && typeof options . readTimeout !== 'number' ) throw new Error ( 'downloadFile: Invalid value for property `readTimeout`' ) ;
if ( options . connectionTimeout && typeof options . connectionTimeout !== 'number' ) throw new Error ( 'downloadFile: Invalid value for property `connectionTimeout`' ) ;
2016-06-02 00:49:01 +01:00
2015-11-20 00:16:13 +00:00
var jobId = getJobId ( ) ;
2016-05-14 23:19:27 +02:00
var subscriptions = [ ] ;
2016-05-30 23:13:50 +01:00
2016-06-02 00:49:01 +01:00
if ( options . begin ) {
subscriptions . push ( NativeAppEventEmitter . addListener ( 'DownloadBegin-' + jobId , options . begin ) ) ;
2015-11-23 16:29:25 +00:00
}
2016-06-02 00:49:01 +01:00
if ( options . progress ) {
subscriptions . push ( NativeAppEventEmitter . addListener ( 'DownloadProgress-' + jobId , options . progress ) ) ;
2015-11-20 00:16:13 +00:00
}
2016-06-02 00:49:01 +01:00
var bridgeOptions = {
jobId : jobId ,
fromUrl : options . fromUrl ,
2016-08-11 14:07:25 -07:00
toFile : normalizeFilePath ( options . toFile ) ,
2016-06-02 00:49:01 +01:00
headers : options . headers || { } ,
background : ! ! options . background ,
2017-06-01 16:45:06 +05:30
progressDivider : options . progressDivider || 0 ,
readTimeout : options . readTimeout || 15000 ,
connectionTimeout : options . connectionTimeout || 5000
2016-06-02 00:49:01 +01:00
} ;
2016-08-10 20:29:14 +01:00
return {
jobId ,
promise : RNFSManager . downloadFile ( bridgeOptions ) . then ( res => {
subscriptions . forEach ( sub => sub . remove ( ) ) ;
return res ;
} )
} ;
2015-11-23 17:08:52 +00:00
} ,
2016-08-10 20:29:14 +01:00
uploadFiles ( options : UploadFileOptions ) : { jobId : number , promise : Promise < UploadResult > } {
if ( ! RNFSManager . uploadFiles ) {
return {
jobId : - 1 ,
promise : Promise . reject ( new Error ( '`uploadFiles` is unsupported on this platform' ) )
} ;
}
2016-05-30 23:13:50 +01:00
var jobId = getJobId ( ) ;
2016-05-30 23:35:34 +01:00
var subscriptions = [ ] ;
2016-05-30 23:13:50 +01:00
if ( typeof options !== 'object' ) throw new Error ( 'uploadFiles: Invalid value for argument `options`' ) ;
if ( typeof options . toUrl !== 'string' ) throw new Error ( 'uploadFiles: Invalid value for property `toUrl`' ) ;
if ( ! Array . isArray ( options . files ) ) throw new Error ( 'uploadFiles: Invalid value for property `files`' ) ;
if ( options . headers && typeof options . headers !== 'object' ) throw new Error ( 'uploadFiles: Invalid value for property `headers`' ) ;
if ( options . fields && typeof options . fields !== 'object' ) throw new Error ( 'uploadFiles: Invalid value for property `fields`' ) ;
if ( options . method && typeof options . method !== 'string' ) throw new Error ( 'uploadFiles: Invalid value for property `method`' ) ;
2016-06-30 00:08:53 +01:00
if ( options . begin ) {
subscriptions . push ( NativeAppEventEmitter . addListener ( 'UploadBegin-' + jobId , options . begin ) ) ;
}
2016-10-03 17:28:15 -07:00
if ( options . beginCallback && options . beginCallback instanceof Function ) {
2016-06-30 00:08:53 +01:00
// Deprecated
2016-05-30 23:35:34 +01:00
subscriptions . push ( NativeAppEventEmitter . addListener ( 'UploadBegin-' + jobId , options . beginCallback ) ) ;
2016-05-30 23:13:50 +01:00
}
2016-06-30 00:08:53 +01:00
if ( options . progress ) {
subscriptions . push ( NativeAppEventEmitter . addListener ( 'UploadProgress-' + jobId , options . progress ) ) ;
}
2016-10-03 17:28:15 -07:00
if ( options . progressCallback && options . progressCallback instanceof Function ) {
2016-06-30 00:08:53 +01:00
// Deprecated
2016-05-30 23:35:34 +01:00
subscriptions . push ( NativeAppEventEmitter . addListener ( 'UploadProgress-' + jobId , options . progressCallback ) ) ;
2016-05-30 23:13:50 +01:00
}
var bridgeOptions = {
jobId : jobId ,
toUrl : options . toUrl ,
files : options . files ,
headers : options . headers || { } ,
fields : options . fields || { } ,
method : options . method || 'POST'
} ;
2016-08-10 20:29:14 +01:00
return {
jobId ,
promise : RNFSManager . uploadFiles ( bridgeOptions ) . then ( res => {
subscriptions . forEach ( sub => sub . remove ( ) ) ;
return res ;
} )
} ;
2016-05-30 23:13:50 +01:00
} ,
2016-08-10 19:53:24 +01:00
MainBundlePath : RNFSManager . RNFSMainBundlePath ,
CachesDirectoryPath : RNFSManager . RNFSCachesDirectoryPath ,
DocumentDirectoryPath : RNFSManager . RNFSDocumentDirectoryPath ,
ExternalDirectoryPath : RNFSManager . RNFSExternalDirectoryPath ,
2016-08-10 19:57:37 +01:00
ExternalStorageDirectoryPath : RNFSManager . RNFSExternalStorageDirectoryPath ,
2016-08-10 19:53:24 +01:00
TemporaryDirectoryPath : RNFSManager . RNFSTemporaryDirectoryPath ,
LibraryDirectoryPath : RNFSManager . RNFSLibraryDirectoryPath ,
PicturesDirectoryPath : RNFSManager . RNFSPicturesDirectoryPath
2016-07-18 22:46:13 +01:00
2015-05-08 20:05:37 +03:00
} ;
module . exports = RNFS ;