From 4af8e15fb771f1becdd617cc059e6c7e672d0dc3 Mon Sep 17 00:00:00 2001 From: Brion Vibber Date: Tue, 14 May 2013 16:16:42 -0700 Subject: [PATCH 1/2] Fix regression in file extension We were appending a file extension and then throwing it away since some refactoring. Oops! --- .../org/wikimedia/commons/StartUploadTask.java | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/commons/src/main/java/org/wikimedia/commons/StartUploadTask.java b/commons/src/main/java/org/wikimedia/commons/StartUploadTask.java index c0adbd220..4bf2b6bfe 100644 --- a/commons/src/main/java/org/wikimedia/commons/StartUploadTask.java +++ b/commons/src/main/java/org/wikimedia/commons/StartUploadTask.java @@ -29,7 +29,13 @@ public class StartUploadTask extends AsyncTask { app = (CommonsApplication)context.getApplicationContext(); - contribution = new Contribution(mediaUri, null, rawTitle, description, -1, null, null, app.getCurrentAccount().name, CommonsApplication.DEFAULT_EDIT_SUMMARY); + String title = rawTitle; + String extension = MimeTypeMap.getSingleton().getExtensionFromMimeType(mimeType); + if(extension != null && !title.toLowerCase().endsWith(extension.toLowerCase())) { + title += "." + extension; + } + + contribution = new Contribution(mediaUri, null, title, description, -1, null, null, app.getCurrentAccount().name, CommonsApplication.DEFAULT_EDIT_SUMMARY); contribution.setTag("mimeType", mimeType); contribution.setSource(source); } @@ -70,12 +76,6 @@ public class StartUploadTask extends AsyncTask { } String mimeType = (String)contribution.getTag("mimeType"); - String extension = MimeTypeMap.getSingleton().getExtensionFromMimeType(mimeType); - - if(extension != null && !title.toLowerCase().endsWith(extension.toLowerCase())) { - title += "." + extension; - } - if(mimeType.startsWith("image/") && contribution.getDateCreated() == null) { Cursor cursor = context.getContentResolver().query(contribution.getLocalUri(), new String[]{MediaStore.Images.ImageColumns.DATE_TAKEN}, null, null, null); From de34019e608f0c7acfab511711717efebc5b501c Mon Sep 17 00:00:00 2001 From: Brion Vibber Date: Tue, 14 May 2013 15:05:59 -0700 Subject: [PATCH 2/2] Name uniqueness checking Follows sequence 'Foo.jpeg', 'Foo 2.jpeg', 'Foo 3.jpeg' etc until one is found that doesn't exist, then we send up the upload. This avoids most typical conflicts scenarios. Still can produce a conflict if you start uploads near-simultaneously, but this is better than none. --- .../org/wikimedia/commons/UploadService.java | 51 ++++++++++++++++++- 1 file changed, 50 insertions(+), 1 deletion(-) diff --git a/commons/src/main/java/org/wikimedia/commons/UploadService.java b/commons/src/main/java/org/wikimedia/commons/UploadService.java index 4e26b709c..02c3f07fa 100644 --- a/commons/src/main/java/org/wikimedia/commons/UploadService.java +++ b/commons/src/main/java/org/wikimedia/commons/UploadService.java @@ -1,7 +1,10 @@ package org.wikimedia.commons; import java.io.*; +import java.util.ArrayList; import java.util.Date; +import java.util.regex.Matcher; +import java.util.regex.Pattern; import android.graphics.*; import android.os.Bundle; @@ -186,6 +189,7 @@ public class UploadService extends HandlerService { this.startForeground(NOTIFICATION_UPLOAD_IN_PROGRESS, curProgressNotification.build()); try { + String filename = findUniqueFilename(contribution.getFilename()); if(!api.validateLogin()) { // Need to revalidate! if(app.revalidateAuthToken()) { @@ -204,7 +208,7 @@ public class UploadService extends HandlerService { String.format(getString(R.string.upload_progress_notification_title_finishing), contribution.getDisplayTitle()), contribution ); - result = api.upload(contribution.getFilename(), file, contribution.getDataLength(), contribution.getPageContents(), contribution.getEditSummary(), notificationUpdater); + result = api.upload(filename, file, contribution.getDataLength(), contribution.getPageContents(), contribution.getEditSummary(), notificationUpdater); Log.d("Commons", "Response is" + Utils.getStringFromDOM(result.getDocument())); @@ -271,4 +275,49 @@ public class UploadService extends HandlerService { contribution.setState(Contribution.STATE_FAILED); contribution.save(); } + + private String findUniqueFilename(String fileName) { + return findUniqueFilename(fileName, 1); + } + + private String findUniqueFilename(String fileName, int sequenceNumber) { + String sequenceFileName; + if (sequenceNumber == 1) { + sequenceFileName = fileName; + } else { + if (fileName.indexOf('.') == -1) { + // We really should have appended a file type suffix already. + // But... we might not. + sequenceFileName = fileName + " " + sequenceNumber; + } else { + Pattern regex = Pattern.compile("^(.*)(\\..+?)$"); + Matcher regexMatcher = regex.matcher(fileName); + sequenceFileName = regexMatcher.replaceAll("$1 " + sequenceNumber + "$2"); + } + } + Log.d("Commons", "checking for uniqueness of name " + sequenceFileName); + + if (fileExistsWithName(sequenceFileName)) { + return findUniqueFilename(fileName, sequenceNumber + 1); + } else { + return sequenceFileName; + } + } + + private boolean fileExistsWithName(String fileName) { + MWApi api = app.getApi(); + ApiResult result; + + try { + result = api.action("query") + .param("prop", "imageinfo") + .param("titles", "File:" + fileName) + .get(); + } catch (IOException e) { + throw new RuntimeException(e); + } + + ArrayList nodes = result.getNodes("/api/query/pages/page/imageinfo"); + return nodes.size() > 0; + } }