Skip to content

Commit 31d51cf

Browse files
committed
Updated GCDWebUploader to latest APIs
1 parent 35ce178 commit 31d51cf

File tree

2 files changed

+84
-58
lines changed

2 files changed

+84
-58
lines changed

GCDWebUploader/GCDWebUploader.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -54,4 +54,6 @@
5454
@interface GCDWebUploader (Subclassing)
5555
- (BOOL)shouldUploadFileAtPath:(NSString*)path withTemporaryFile:(NSString*)tempPath; // Default implementation returns YES
5656
- (BOOL)shouldMoveItemFromPath:(NSString*)fromPath toPath:(NSString*)toPath; // Default implementation returns YES
57+
- (BOOL)shouldDeleteItemAtPath:(NSString*)path; // Default implementation returns YES
58+
- (BOOL)shouldCreateDirectoryAtPath:(NSString*)path; // Default implementation returns YES
5759
@end

GCDWebUploader/GCDWebUploader.m

Lines changed: 82 additions & 58 deletions
Original file line numberDiff line numberDiff line change
@@ -33,10 +33,13 @@
3333
#endif
3434

3535
#import "GCDWebUploader.h"
36+
3637
#import "GCDWebServerDataRequest.h"
3738
#import "GCDWebServerMultiPartFormRequest.h"
3839
#import "GCDWebServerURLEncodedFormRequest.h"
40+
3941
#import "GCDWebServerDataResponse.h"
42+
#import "GCDWebServerErrorResponse.h"
4043
#import "GCDWebServerFileResponse.h"
4144

4245
@interface GCDWebUploader () {
@@ -93,7 +96,7 @@ - (id)initWithUploadDirectory:(NSString*)path {
9396
return nil;
9497
}
9598
_uploadDirectory = [[path stringByStandardizingPath] copy];
96-
GCDWebUploader* __unsafe_unretained uploader = self;
99+
GCDWebUploader* __unsafe_unretained server = self;
97100

98101
// Resource files
99102
[self addGETHandlerForBasePath:@"/" directoryPath:[siteBundle resourcePath] indexFilename:nil cacheAge:3600 allowRangeRequests:NO];
@@ -110,7 +113,7 @@ - (id)initWithUploadDirectory:(NSString*)path {
110113
NSString* device = [(id)SCDynamicStoreCopyComputerName(NULL, NULL) autorelease];
111114
#endif
112115
#endif
113-
NSString* title = uploader.title;
116+
NSString* title = server.title;
114117
if (title == nil) {
115118
title = [[NSBundle mainBundle] objectForInfoDictionaryKey:@"CFBundleDisplayName"];
116119
#if !TARGET_OS_IPHONE
@@ -119,19 +122,19 @@ - (id)initWithUploadDirectory:(NSString*)path {
119122
}
120123
#endif
121124
}
122-
NSString* header = uploader.header;
125+
NSString* header = server.header;
123126
if (header == nil) {
124127
header = title;
125128
}
126-
NSString* prologue = uploader.prologue;
129+
NSString* prologue = server.prologue;
127130
if (prologue == nil) {
128131
prologue = [siteBundle localizedStringForKey:@"PROLOGUE" value:@"" table:nil];
129132
}
130-
NSString* epilogue = uploader.epilogue;
133+
NSString* epilogue = server.epilogue;
131134
if (epilogue == nil) {
132135
epilogue = [siteBundle localizedStringForKey:@"EPILOGUE" value:@"" table:nil];
133136
}
134-
NSString* footer = uploader.footer;
137+
NSString* footer = server.footer;
135138
if (footer == nil) {
136139
NSString* name = [[NSBundle mainBundle] objectForInfoDictionaryKey:@"CFBundleDisplayName"];
137140
NSString* version = [[NSBundle mainBundle] objectForInfoDictionaryKey:@"CFBundleShortVersionString"];
@@ -159,19 +162,20 @@ - (id)initWithUploadDirectory:(NSString*)path {
159162
[self addHandlerForMethod:@"GET" path:@"/list" requestClass:[GCDWebServerRequest class] processBlock:^GCDWebServerResponse *(GCDWebServerRequest* request) {
160163

161164
NSString* relativePath = [[request query] objectForKey:@"path"];
162-
NSString* absolutePath = [uploader.uploadDirectory stringByAppendingPathComponent:relativePath];
165+
NSString* absolutePath = [server.uploadDirectory stringByAppendingPathComponent:relativePath];
163166
BOOL isDirectory;
164167
if ([[NSFileManager defaultManager] fileExistsAtPath:absolutePath isDirectory:&isDirectory]) {
165168
if (isDirectory) {
166-
BOOL showHidden = uploader.showHiddenFiles;
167-
NSArray* contents = [[NSFileManager defaultManager] contentsOfDirectoryAtPath:absolutePath error:NULL];
169+
BOOL showHidden = server.showHiddenFiles;
170+
NSError* error = nil;
171+
NSArray* contents = [[NSFileManager defaultManager] contentsOfDirectoryAtPath:absolutePath error:&error];
168172
if (contents) {
169173
NSMutableArray* array = [NSMutableArray array];
170174
for (NSString* item in [contents sortedArrayUsingSelector:@selector(localizedStandardCompare:)]) {
171175
if (showHidden || ![item hasPrefix:@"."]) {
172176
NSDictionary* attributes = [[NSFileManager defaultManager] attributesOfItemAtPath:[absolutePath stringByAppendingPathComponent:item] error:NULL];
173177
NSString* type = [attributes objectForKey:NSFileType];
174-
if ([type isEqualToString:NSFileTypeRegular] && [uploader _checkFileExtension:item]) {
178+
if ([type isEqualToString:NSFileTypeRegular] && [server _checkFileExtension:item]) {
175179
[array addObject:@{
176180
@"path": [relativePath stringByAppendingPathComponent:item],
177181
@"name": item,
@@ -187,13 +191,13 @@ - (id)initWithUploadDirectory:(NSString*)path {
187191
}
188192
return [GCDWebServerDataResponse responseWithJSONObject:array];
189193
} else {
190-
return [GCDWebServerResponse responseWithStatusCode:500];
194+
return [GCDWebServerErrorResponse responseWithServerError:kGCDWebServerHTTPStatusCode_InternalServerError underlyingError:error message:@"Failed listing directory \"%@\"", relativePath];
191195
}
192196
} else {
193-
return [GCDWebServerResponse responseWithStatusCode:400];
197+
return [GCDWebServerErrorResponse responseWithClientError:kGCDWebServerHTTPStatusCode_BadRequest message:@"\"%@\" is not a directory", relativePath];
194198
}
195199
} else {
196-
return [GCDWebServerResponse responseWithStatusCode:404];
200+
return [GCDWebServerErrorResponse responseWithClientError:kGCDWebServerHTTPStatusCode_NotFound message:@"\"%@\" does not exist", relativePath];
197201
}
198202

199203
}];
@@ -202,21 +206,21 @@ - (id)initWithUploadDirectory:(NSString*)path {
202206
[self addHandlerForMethod:@"GET" path:@"/download" requestClass:[GCDWebServerRequest class] processBlock:^GCDWebServerResponse *(GCDWebServerRequest* request) {
203207

204208
NSString* relativePath = [[request query] objectForKey:@"path"];
205-
NSString* absolutePath = [uploader.uploadDirectory stringByAppendingPathComponent:relativePath];
209+
NSString* absolutePath = [server.uploadDirectory stringByAppendingPathComponent:relativePath];
206210
BOOL isDirectory;
207211
if ([[NSFileManager defaultManager] fileExistsAtPath:absolutePath isDirectory:&isDirectory]) {
208212
if (isDirectory) {
209-
return [GCDWebServerResponse responseWithStatusCode:400];
213+
return [GCDWebServerErrorResponse responseWithClientError:kGCDWebServerHTTPStatusCode_BadRequest message:@"\"%@\" is a directory", relativePath];
210214
} else {
211-
if ([uploader.delegate respondsToSelector:@selector(webUploader:didDownloadFileAtPath: )]) {
215+
if ([server.delegate respondsToSelector:@selector(webUploader:didDownloadFileAtPath: )]) {
212216
dispatch_async(dispatch_get_main_queue(), ^{
213-
[uploader.delegate webUploader:uploader didDownloadFileAtPath:absolutePath];
217+
[server.delegate webUploader:server didDownloadFileAtPath:absolutePath];
214218
});
215219
}
216220
return [GCDWebServerFileResponse responseWithFile:absolutePath isAttachment:YES];
217221
}
218222
} else {
219-
return [GCDWebServerResponse responseWithStatusCode:404];
223+
return [GCDWebServerErrorResponse responseWithClientError:kGCDWebServerHTTPStatusCode_NotFound message:@"\"%@\" does not exist", relativePath];
220224
}
221225

222226
}];
@@ -229,26 +233,26 @@ - (id)initWithUploadDirectory:(NSString*)path {
229233
NSString* contentType = (range.location != NSNotFound ? @"application/json" : @"text/plain; charset=utf-8");
230234

231235
GCDWebServerMultiPartFile* file = [[(GCDWebServerMultiPartFormRequest*)request files] objectForKey:@"files[]"];
232-
if ((![file.fileName hasPrefix:@"."] || uploader.showHiddenFiles) && [uploader _checkFileExtension:file.fileName]) {
236+
if ((![file.fileName hasPrefix:@"."] || server.showHiddenFiles) && [server _checkFileExtension:file.fileName]) {
233237
NSString* relativePath = [(GCDWebServerMultiPartArgument*)[[(GCDWebServerURLEncodedFormRequest*)request arguments] objectForKey:@"path"] string];
234-
NSString* absolutePath = [uploader _uniquePathForPath:[[uploader.uploadDirectory stringByAppendingPathComponent:relativePath] stringByAppendingPathComponent:file.fileName]];
235-
if ([uploader shouldUploadFileAtPath:absolutePath withTemporaryFile:file.temporaryPath]) {
238+
NSString* absolutePath = [server _uniquePathForPath:[[server.uploadDirectory stringByAppendingPathComponent:relativePath] stringByAppendingPathComponent:file.fileName]];
239+
if ([server shouldUploadFileAtPath:absolutePath withTemporaryFile:file.temporaryPath]) {
236240
NSError* error = nil;
237241
if ([[NSFileManager defaultManager] moveItemAtPath:file.temporaryPath toPath:absolutePath error:&error]) {
238-
if ([uploader.delegate respondsToSelector:@selector(webUploader:didUploadFileAtPath:)]) {
242+
if ([server.delegate respondsToSelector:@selector(webUploader:didUploadFileAtPath:)]) {
239243
dispatch_async(dispatch_get_main_queue(), ^{
240-
[uploader.delegate webUploader:uploader didUploadFileAtPath:absolutePath];
244+
[server.delegate webUploader:server didUploadFileAtPath:absolutePath];
241245
});
242246
}
243247
return [GCDWebServerDataResponse responseWithJSONObject:@{} contentType:contentType];
244248
} else {
245-
return [GCDWebServerResponse responseWithStatusCode:500];
249+
return [GCDWebServerErrorResponse responseWithServerError:kGCDWebServerHTTPStatusCode_InternalServerError underlyingError:error message:@"Failed moving uploaded file to \"%@\"", relativePath];
246250
}
247251
} else {
248-
return [GCDWebServerResponse responseWithStatusCode:403];
252+
return [GCDWebServerErrorResponse responseWithClientError:kGCDWebServerHTTPStatusCode_Forbidden message:@"Uploading file \"%@\" to \"%@\" is not allowed", file.fileName, relativePath];
249253
}
250254
} else {
251-
return [GCDWebServerResponse responseWithStatusCode:400];
255+
return [GCDWebServerErrorResponse responseWithClientError:kGCDWebServerHTTPStatusCode_Forbidden message:@"Uploaded file name \"%@\" is not allowed", file.fileName];
252256
}
253257

254258
}];
@@ -257,37 +261,39 @@ - (id)initWithUploadDirectory:(NSString*)path {
257261
[self addHandlerForMethod:@"POST" path:@"/move" requestClass:[GCDWebServerURLEncodedFormRequest class] processBlock:^GCDWebServerResponse *(GCDWebServerRequest* request) {
258262

259263
NSString* oldRelativePath = [[(GCDWebServerURLEncodedFormRequest*)request arguments] objectForKey:@"oldPath"];
260-
NSString* oldAbsolutePath = [uploader.uploadDirectory stringByAppendingPathComponent:oldRelativePath];
264+
NSString* oldAbsolutePath = [server.uploadDirectory stringByAppendingPathComponent:oldRelativePath];
261265
BOOL isDirectory;
262266
if ([[NSFileManager defaultManager] fileExistsAtPath:oldAbsolutePath isDirectory:&isDirectory]) {
263267
NSString* newRelativePath = [[(GCDWebServerURLEncodedFormRequest*)request arguments] objectForKey:@"newPath"];
264-
if (!uploader.showHiddenFiles) {
268+
if (!server.showHiddenFiles) {
265269
for (NSString* component in [newRelativePath pathComponents]) {
266270
if ([component hasPrefix:@"."]) {
267-
return [GCDWebServerResponse responseWithStatusCode:400];
271+
return [GCDWebServerErrorResponse responseWithClientError:kGCDWebServerHTTPStatusCode_BadRequest message:@"Item path \"%@\" is not allowed", newRelativePath];
268272
}
269273
}
270274
}
271-
if (!isDirectory && ![uploader _checkFileExtension:newRelativePath]) {
272-
return [GCDWebServerResponse responseWithStatusCode:400];
275+
if (!isDirectory && ![server _checkFileExtension:newRelativePath]) {
276+
return [GCDWebServerErrorResponse responseWithClientError:kGCDWebServerHTTPStatusCode_Forbidden message:@"Item path \"%@\" is not allowed", newRelativePath];
273277
}
274-
NSString* newAbsolutePath = [uploader _uniquePathForPath:[uploader.uploadDirectory stringByAppendingPathComponent:newRelativePath]];
275-
if ([uploader shouldMoveItemFromPath:oldAbsolutePath toPath:newAbsolutePath]) {
276-
if ([[NSFileManager defaultManager] moveItemAtPath:oldAbsolutePath toPath:newAbsolutePath error:NULL]) {
277-
if ([uploader.delegate respondsToSelector:@selector(webUploader:didMoveItemFromPath:toPath:)]) {
278+
NSString* newAbsolutePath = [server _uniquePathForPath:[server.uploadDirectory stringByAppendingPathComponent:newRelativePath]];
279+
if ([server shouldMoveItemFromPath:oldAbsolutePath toPath:newAbsolutePath]) {
280+
[[NSFileManager defaultManager] createDirectoryAtPath:[newAbsolutePath stringByDeletingLastPathComponent] withIntermediateDirectories:YES attributes:nil error:NULL];
281+
NSError* error = nil;
282+
if ([[NSFileManager defaultManager] moveItemAtPath:oldAbsolutePath toPath:newAbsolutePath error:&error]) {
283+
if ([server.delegate respondsToSelector:@selector(webUploader:didMoveItemFromPath:toPath:)]) {
278284
dispatch_async(dispatch_get_main_queue(), ^{
279-
[uploader.delegate webUploader:uploader didMoveItemFromPath:oldAbsolutePath toPath:newAbsolutePath];
285+
[server.delegate webUploader:server didMoveItemFromPath:oldAbsolutePath toPath:newAbsolutePath];
280286
});
281287
}
282288
return [GCDWebServerDataResponse responseWithJSONObject:@{}];
283289
} else {
284-
return [GCDWebServerResponse responseWithStatusCode:500];
290+
return [GCDWebServerErrorResponse responseWithServerError:kGCDWebServerHTTPStatusCode_InternalServerError underlyingError:error message:@"Failed moving \"%@\" to \"%@\"", oldRelativePath, newRelativePath];
285291
}
286292
} else {
287-
return [GCDWebServerResponse responseWithStatusCode:403];
293+
return [GCDWebServerErrorResponse responseWithClientError:kGCDWebServerHTTPStatusCode_Forbidden message:@"Moving \"%@\" to \"%@\" is not allowed", oldRelativePath, newRelativePath];
288294
}
289295
} else {
290-
return [GCDWebServerResponse responseWithStatusCode:404];
296+
return [GCDWebServerErrorResponse responseWithClientError:kGCDWebServerHTTPStatusCode_NotFound message:@"\"%@\" does not exist", oldRelativePath];
291297
}
292298

293299
}];
@@ -296,20 +302,25 @@ - (id)initWithUploadDirectory:(NSString*)path {
296302
[self addHandlerForMethod:@"POST" path:@"/delete" requestClass:[GCDWebServerURLEncodedFormRequest class] processBlock:^GCDWebServerResponse *(GCDWebServerRequest* request) {
297303

298304
NSString* relativePath = [[(GCDWebServerURLEncodedFormRequest*)request arguments] objectForKey:@"path"];
299-
NSString* absolutePath = [uploader.uploadDirectory stringByAppendingPathComponent:relativePath];
305+
NSString* absolutePath = [server.uploadDirectory stringByAppendingPathComponent:relativePath];
300306
if ([[NSFileManager defaultManager] fileExistsAtPath:absolutePath]) {
301-
if ([[NSFileManager defaultManager] removeItemAtPath:absolutePath error:NULL]) {
302-
if ([uploader.delegate respondsToSelector:@selector(webUploader:didDeleteItemAtPath:)]) {
303-
dispatch_async(dispatch_get_main_queue(), ^{
304-
[uploader.delegate webUploader:uploader didDeleteItemAtPath:absolutePath];
305-
});
307+
if ([server shouldDeleteItemAtPath:absolutePath]) {
308+
NSError* error = nil;
309+
if ([[NSFileManager defaultManager] removeItemAtPath:absolutePath error:&error]) {
310+
if ([server.delegate respondsToSelector:@selector(webUploader:didDeleteItemAtPath:)]) {
311+
dispatch_async(dispatch_get_main_queue(), ^{
312+
[server.delegate webUploader:server didDeleteItemAtPath:absolutePath];
313+
});
314+
}
315+
return [GCDWebServerDataResponse responseWithJSONObject:@{}];
316+
} else {
317+
return [GCDWebServerErrorResponse responseWithServerError:kGCDWebServerHTTPStatusCode_InternalServerError underlyingError:error message:@"Failed deleting \"%@\"", relativePath];
306318
}
307-
return [GCDWebServerDataResponse responseWithJSONObject:@{}];
308319
} else {
309-
return [GCDWebServerResponse responseWithStatusCode:500];
320+
return [GCDWebServerErrorResponse responseWithClientError:kGCDWebServerHTTPStatusCode_Forbidden message:@"Deleting \"%@\" is not allowed", relativePath];
310321
}
311322
} else {
312-
return [GCDWebServerResponse responseWithStatusCode:404];
323+
return [GCDWebServerErrorResponse responseWithClientError:kGCDWebServerHTTPStatusCode_NotFound message:@"\"%@\" does not exist", relativePath];
313324
}
314325

315326
}];
@@ -318,23 +329,28 @@ - (id)initWithUploadDirectory:(NSString*)path {
318329
[self addHandlerForMethod:@"POST" path:@"/create" requestClass:[GCDWebServerURLEncodedFormRequest class] processBlock:^GCDWebServerResponse *(GCDWebServerRequest* request) {
319330

320331
NSString* relativePath = [[(GCDWebServerURLEncodedFormRequest*)request arguments] objectForKey:@"path"];
321-
if (!uploader.showHiddenFiles) {
332+
if (!server.showHiddenFiles) {
322333
for (NSString* component in [relativePath pathComponents]) {
323334
if ([component hasPrefix:@"."]) {
324-
return [GCDWebServerResponse responseWithStatusCode:400];
335+
return [GCDWebServerErrorResponse responseWithClientError:kGCDWebServerHTTPStatusCode_Forbidden message:@"Directory path \"%@\" is not allowed", relativePath];
325336
}
326337
}
327338
}
328-
NSString* absolutePath = [uploader _uniquePathForPath:[uploader.uploadDirectory stringByAppendingPathComponent:relativePath]];
329-
if ([[NSFileManager defaultManager] createDirectoryAtPath:absolutePath withIntermediateDirectories:YES attributes:nil error:NULL]) {
330-
if ([uploader.delegate respondsToSelector:@selector(webUploader:didCreateDirectoryAtPath:)]) {
331-
dispatch_async(dispatch_get_main_queue(), ^{
332-
[uploader.delegate webUploader:uploader didCreateDirectoryAtPath:absolutePath];
333-
});
339+
NSString* absolutePath = [server _uniquePathForPath:[server.uploadDirectory stringByAppendingPathComponent:relativePath]];
340+
if ([server shouldCreateDirectoryAtPath:absolutePath]) {
341+
NSError* error = nil;
342+
if ([[NSFileManager defaultManager] createDirectoryAtPath:absolutePath withIntermediateDirectories:YES attributes:nil error:&error]) {
343+
if ([server.delegate respondsToSelector:@selector(webUploader:didCreateDirectoryAtPath:)]) {
344+
dispatch_async(dispatch_get_main_queue(), ^{
345+
[server.delegate webUploader:server didCreateDirectoryAtPath:absolutePath];
346+
});
347+
}
348+
return [GCDWebServerDataResponse responseWithJSONObject:@{}];
349+
} else {
350+
return [GCDWebServerErrorResponse responseWithServerError:kGCDWebServerHTTPStatusCode_InternalServerError underlyingError:error message:@"Failed creating directory \"%@\"", relativePath];
334351
}
335-
return [GCDWebServerDataResponse responseWithJSONObject:@{}];
336352
} else {
337-
return [GCDWebServerResponse responseWithStatusCode:500];
353+
return [GCDWebServerErrorResponse responseWithClientError:kGCDWebServerHTTPStatusCode_Forbidden message:@"Creating directory \"%@\" is not allowed", relativePath];
338354
}
339355

340356
}];
@@ -371,4 +387,12 @@ - (BOOL)shouldMoveItemFromPath:(NSString*)fromPath toPath:(NSString*)toPath {
371387
return YES;
372388
}
373389

390+
- (BOOL)shouldDeleteItemAtPath:(NSString*)path {
391+
return YES;
392+
}
393+
394+
- (BOOL)shouldCreateDirectoryAtPath:(NSString*)path {
395+
return YES;
396+
}
397+
374398
@end

0 commit comments

Comments
 (0)