Skip to content

Commit 77afa09

Browse files
authored
fix: validate URI scheme and improve error messages (#22)
Reject bare file paths (e.g. /var/mobile/...) with a clear error message indicating that a scheme (file://, ph://, content://) is required. - iOS: add scheme validation in read and write methods - Android: add scheme validation in write, improve read error message - Add JSDoc to read() and write() - Update README with URI format note Closes #9
1 parent ee244cb commit 77afa09

4 files changed

Lines changed: 41 additions & 2 deletions

File tree

README.md

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,9 @@ const tags = await Exify.read(uri)
3434
console.log(tags)
3535
```
3636

37+
> [!IMPORTANT]
38+
> The `uri` must include a scheme (e.g. `file://`, `ph://`, `content://`). Bare file paths like `/var/mobile/.../image.jpg` are not supported and will throw an error.
39+
3740
> [!NOTE]
3841
> On Android 10+, GPS data is redacted from `content://` URIs by default. The library automatically requests `ACCESS_MEDIA_LOCATION` at runtime to access unredacted location data. Your app must have media read access (`READ_MEDIA_IMAGES` or `READ_EXTERNAL_STORAGE`) granted first.
3942
> If you're already using a library like [`expo-media-library`](https://docs.expo.dev/versions/latest/sdk/media-library/) that grants `ACCESS_MEDIA_LOCATION`, exify will use the existing grant.

android/src/main/java/com/lodev09/exify/ExifyModule.kt

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -34,8 +34,8 @@ class ExifyModule(
3434
val scheme = photoUri.scheme
3535

3636
if (scheme == null) {
37-
RNLog.w(context, "Exify: Invalid URI: $uri")
38-
promise.reject(ERROR_TAG, "Invalid URI: $uri")
37+
RNLog.w(context, "Exify: URI must include a scheme (e.g. file://): $uri")
38+
promise.reject(ERROR_TAG, "URI must include a scheme (e.g. file://): $uri")
3939
return
4040
}
4141

@@ -108,6 +108,13 @@ class ExifyModule(
108108
promise: Promise,
109109
) {
110110
val photoUri = Uri.parse(uri)
111+
112+
if (photoUri.scheme == null) {
113+
RNLog.w(context, "Exify: URI must include a scheme (e.g. file://): $uri")
114+
promise.reject(ERROR_TAG, "URI must include a scheme (e.g. file://): $uri")
115+
return
116+
}
117+
111118
val params = Arguments.createMap()
112119

113120
try {

ios/Exify.mm

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -226,6 +226,16 @@ - (void)read:(NSString *)uri
226226
resolve(tags);
227227
}];
228228
} else {
229+
if ([uri hasPrefix:@"/"] || ![uri containsString:@"://"]) {
230+
RCTLogWarn(@"Exify: URI must include a scheme (e.g. file://): %@", uri);
231+
reject(@"Error",
232+
[NSString stringWithFormat:@"URI must include a scheme (e.g. "
233+
@"file://): %@",
234+
uri],
235+
nil);
236+
return;
237+
}
238+
229239
NSURL *url = [NSURL URLWithString:uri];
230240
if (!url) {
231241
RCTLogWarn(@"Exify: Invalid URI: %@", uri);
@@ -317,6 +327,16 @@ - (void)write:(NSString *)uri
317327
});
318328
}];
319329
} else {
330+
if ([uri hasPrefix:@"/"] || ![uri containsString:@"://"]) {
331+
RCTLogWarn(@"Exify: URI must include a scheme (e.g. file://): %@", uri);
332+
reject(@"Error",
333+
[NSString stringWithFormat:@"URI must include a scheme (e.g. "
334+
@"file://): %@",
335+
uri],
336+
nil);
337+
return;
338+
}
339+
320340
NSURL *url = [NSURL URLWithString:uri];
321341
if (!url) {
322342
reject(@"Error", @"Invalid URL", nil);

src/index.ts

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,19 @@
11
import Exify from './NativeExify';
22
import type { ExifTags, ExifyWriteResult } from './types';
33

4+
/**
5+
* Read Exif metadata from an image.
6+
* @param uri Image URI with a scheme (e.g. `file://`, `ph://`, `content://`). Bare file paths are not supported.
7+
*/
48
export function read(uri: string): Promise<ExifTags | null> {
59
return Exify.read(uri) as Promise<ExifTags | null>;
610
}
711

12+
/**
13+
* Write Exif metadata into an image.
14+
* @param uri Image URI with a scheme (e.g. `file://`, `ph://`, `content://`). Bare file paths are not supported.
15+
* @param tags Exif tags to write.
16+
*/
817
export function write(uri: string, tags: ExifTags): Promise<ExifyWriteResult> {
918
return Exify.write(uri, tags as Object) as Promise<ExifyWriteResult>;
1019
}

0 commit comments

Comments
 (0)