Skip to content

Commit 2563617

Browse files
authored
Merge pull request #696 from amvanbaren/bugfix/issue-695
Unable to delete namespace logo
2 parents e0947cb + 395c3c6 commit 2563617

File tree

6 files changed

+105
-13
lines changed

6 files changed

+105
-13
lines changed

server/src/main/java/org/eclipse/openvsx/ExtensionValidator.java

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@
2727
import org.eclipse.openvsx.entities.ExtensionVersion;
2828
import org.eclipse.openvsx.json.NamespaceDetailsJson;
2929
import org.eclipse.openvsx.util.TargetPlatform;
30+
import org.eclipse.openvsx.util.TimeUtil;
3031
import org.eclipse.openvsx.util.VersionAlias;
3132
import org.springframework.stereotype.Component;
3233

@@ -88,7 +89,7 @@ public List<Issue> validateNamespaceDetails(NamespaceDetailsJson json) {
8889
var detectedType = tika.detect(in, json.logo);
8990
var logoType = MimeTypes.getDefaultMimeTypes().getRegisteredMimeType(detectedType);
9091
if(logoType != null) {
91-
json.logo = "logo-" + json.name + logoType.getExtension();
92+
json.logo = "logo-" + json.name + "-" + System.currentTimeMillis() + logoType.getExtension();
9293
if(!logoType.getType().equals(MediaType.image("png")) && !logoType.getType().equals(MediaType.image("jpg"))) {
9394
issues.add(new Issue("Namespace logo should be of png or jpg type"));
9495
}

server/src/main/java/org/eclipse/openvsx/UserService.java

Lines changed: 35 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -9,18 +9,12 @@
99
********************************************************************************/
1010
package org.eclipse.openvsx;
1111

12-
import java.util.Arrays;
13-
import java.util.Objects;
14-
import java.util.UUID;
15-
16-
import javax.persistence.EntityManager;
17-
import javax.transaction.Transactional;
18-
1912
import com.google.common.base.Joiner;
13+
import org.apache.commons.io.IOUtils;
2014
import org.eclipse.openvsx.cache.CacheService;
2115
import org.eclipse.openvsx.entities.*;
22-
import org.eclipse.openvsx.json.NamespaceDetailsJson;
2316
import org.eclipse.openvsx.json.AccessTokenJson;
17+
import org.eclipse.openvsx.json.NamespaceDetailsJson;
2418
import org.eclipse.openvsx.json.ResultJson;
2519
import org.eclipse.openvsx.repositories.RepositoryService;
2620
import org.eclipse.openvsx.security.IdPrincipal;
@@ -35,6 +29,14 @@
3529
import org.springframework.security.oauth2.core.user.OAuth2User;
3630
import org.springframework.stereotype.Component;
3731

32+
import javax.persistence.EntityManager;
33+
import javax.transaction.Transactional;
34+
import java.io.ByteArrayInputStream;
35+
import java.io.IOException;
36+
import java.nio.file.Files;
37+
import java.util.Objects;
38+
import java.util.UUID;
39+
3840
import static org.eclipse.openvsx.cache.CacheService.CACHE_NAMESPACE_DETAILS_JSON;
3941
import static org.eclipse.openvsx.util.UrlUtil.createApiUrl;
4042

@@ -234,23 +236,44 @@ public ResultJson updateNamespaceDetails(NamespaceDetailsJson details) {
234236
if(!Objects.equals(details.socialLinks, namespace.getSocialLinks())) {
235237
namespace.setSocialLinks(details.socialLinks);
236238
}
237-
if(!Arrays.equals(details.logoBytes, namespace.getLogoBytes())) {
238-
if (details.logoBytes != null) {
239-
if (namespace.getLogoBytes() != null) {
239+
if(details.logoBytes == null) {
240+
details.logoBytes = new byte[0];
241+
}
242+
243+
boolean contentEquals;
244+
var oldLogo = storageUtil.downloadNamespaceLogo(namespace);
245+
try (
246+
var newLogoInput = new ByteArrayInputStream(details.logoBytes);
247+
var oldLogoInput = Files.newInputStream(oldLogo)
248+
) {
249+
contentEquals = IOUtils.contentEquals(newLogoInput, oldLogoInput);
250+
} catch (IOException e) {
251+
throw new RuntimeException(e);
252+
}
253+
254+
if(!contentEquals) {
255+
if (details.logoBytes.length > 0) {
256+
if (namespace.getLogoStorageType() != null) {
240257
storageUtil.removeNamespaceLogo(namespace);
241258
}
242259

243260
namespace.setLogoName(details.logo);
244261
namespace.setLogoBytes(details.logoBytes);
245262
storeNamespaceLogo(namespace);
246-
} else if (namespace.getLogoBytes() != null) {
263+
} else if (namespace.getLogoStorageType() != null) {
247264
storageUtil.removeNamespaceLogo(namespace);
248265
namespace.setLogoName(null);
249266
namespace.setLogoBytes(null);
250267
namespace.setLogoStorageType(null);
251268
}
252269
}
253270

271+
try {
272+
Files.delete(oldLogo);
273+
} catch (IOException e) {
274+
throw new RuntimeException(e);
275+
}
276+
254277
return ResultJson.success("Updated details for namespace " + details.name);
255278
}
256279

server/src/main/java/org/eclipse/openvsx/storage/AzureBlobStorageService.java

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@
2626
import java.io.ByteArrayInputStream;
2727
import java.io.IOException;
2828
import java.net.URI;
29+
import java.nio.file.Files;
2930
import java.nio.file.Path;
3031

3132
@Component
@@ -189,4 +190,15 @@ public URI getNamespaceLogoLocation(Namespace namespace) {
189190
protected String getBlobName(Namespace namespace) {
190191
return UrlUtil.createApiUrl("", namespace.getName(), "logo", namespace.getLogoName()).substring(1); // remove first '/'
191192
}
193+
194+
@Override
195+
public Path downloadNamespaceLogo(Namespace namespace) {
196+
try {
197+
var logoFile = Files.createTempFile("namespace-logo", ".png");
198+
getContainerClient().getBlobClient(getBlobName(namespace)).downloadToFile(logoFile.toString(), true);
199+
return logoFile;
200+
} catch (IOException e) {
201+
throw new RuntimeException(e);
202+
}
203+
}
192204
}

server/src/main/java/org/eclipse/openvsx/storage/GoogleCloudStorageService.java

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@
2222
import org.springframework.beans.factory.annotation.Value;
2323
import org.springframework.stereotype.Component;
2424

25+
import java.io.FileOutputStream;
2526
import java.io.IOException;
2627
import java.net.URI;
2728
import java.nio.ByteBuffer;
@@ -185,4 +186,24 @@ protected String getObjectId(Namespace namespace) {
185186
return UrlUtil.createApiUrl("", namespace.getName(), "logo", namespace.getLogoName()).substring(1); // remove first '/'
186187
}
187188

189+
@Override
190+
public Path downloadNamespaceLogo(Namespace namespace) {
191+
Path logoFile;
192+
try {
193+
logoFile = Files.createTempFile("namespace-logo", ".png");
194+
} catch (IOException e) {
195+
throw new RuntimeException(e);
196+
}
197+
198+
try (
199+
var reader = getStorage().reader(BlobId.of(bucketId, getObjectId(namespace)));
200+
var output = new FileOutputStream(logoFile.toFile());
201+
) {
202+
output.getChannel().transferFrom(reader, 0, Long.MAX_VALUE);
203+
} catch (IOException e) {
204+
throw new RuntimeException(e);
205+
}
206+
207+
return logoFile;
208+
}
188209
}

server/src/main/java/org/eclipse/openvsx/storage/IStorageService.java

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -56,4 +56,6 @@ public interface IStorageService {
5656
* Returns the public access location of a namespace logo.
5757
*/
5858
URI getNamespaceLogoLocation(Namespace namespace);
59+
60+
Path downloadNamespaceLogo(Namespace namespace);
5961
}

server/src/main/java/org/eclipse/openvsx/storage/StorageUtilService.java

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,9 @@
3030

3131
import javax.persistence.EntityManager;
3232
import javax.transaction.Transactional;
33+
import java.io.IOException;
3334
import java.net.URI;
35+
import java.nio.file.Files;
3436
import java.nio.file.Path;
3537
import java.util.*;
3638
import java.util.concurrent.TimeUnit;
@@ -221,6 +223,37 @@ public URI getNamespaceLogoLocation(Namespace namespace) {
221223
}
222224
}
223225

226+
public Path downloadNamespaceLogo(Namespace namespace) {
227+
if(namespace.getLogoStorageType() == null) {
228+
return createNamespaceLogoFile();
229+
}
230+
231+
switch (namespace.getLogoStorageType()) {
232+
case STORAGE_GOOGLE:
233+
return googleStorage.downloadNamespaceLogo(namespace);
234+
case STORAGE_AZURE:
235+
return azureStorage.downloadNamespaceLogo(namespace);
236+
case STORAGE_DB:
237+
try {
238+
var logoFile = createNamespaceLogoFile();
239+
Files.write(logoFile, namespace.getLogoBytes());
240+
return logoFile;
241+
} catch (IOException e) {
242+
throw new RuntimeException(e);
243+
}
244+
default:
245+
return createNamespaceLogoFile();
246+
}
247+
}
248+
249+
private Path createNamespaceLogoFile() {
250+
try {
251+
return Files.createTempFile("namespace-logo", ".png");
252+
} catch (IOException e) {
253+
throw new RuntimeException(e);
254+
}
255+
}
256+
224257
private String getFileUrl(String name, ExtensionVersion extVersion, String serverUrl) {
225258
return UrlUtil.createApiFileUrl(serverUrl, extVersion, name);
226259
}

0 commit comments

Comments
 (0)