소스 검색

Merge branch 'develop' of https://github.com/siard-y/cryptomator into feature/gdrive-presets

Jan-Peter Klein 7 달 전
부모
커밋
e6890e8fa5

+ 3 - 2
src/main/java/module-info.java

@@ -2,7 +2,8 @@ import ch.qos.logback.classic.spi.Configurator;
 import org.cryptomator.common.locationpresets.DropboxLinuxLocationPresetsProvider;
 import org.cryptomator.common.locationpresets.DropboxMacLocationPresetsProvider;
 import org.cryptomator.common.locationpresets.DropboxWindowsLocationPresetsProvider;
-import org.cryptomator.common.locationpresets.GoogleDriveLocationPresetsProvider;
+import org.cryptomator.common.locationpresets.GoogleDriveMacLocationPresetsProvider;
+import org.cryptomator.common.locationpresets.GoogleDriveWindowsLocationPresetsProvider;
 import org.cryptomator.common.locationpresets.ICloudMacLocationPresetsProvider;
 import org.cryptomator.common.locationpresets.ICloudWindowsLocationPresetsProvider;
 import org.cryptomator.common.locationpresets.LeitzcloudLocationPresetsProvider;
@@ -56,7 +57,7 @@ open module org.cryptomator.desktop {
 	provides Configurator with LogbackConfiguratorFactory;
 	provides LocationPresetsProvider with //
 			DropboxWindowsLocationPresetsProvider, DropboxMacLocationPresetsProvider, DropboxLinuxLocationPresetsProvider, //
-			GoogleDriveLocationPresetsProvider, //
+			GoogleDriveMacLocationPresetsProvider, GoogleDriveWindowsLocationPresetsProvider, //
 			ICloudWindowsLocationPresetsProvider, ICloudMacLocationPresetsProvider, //
 			LeitzcloudLocationPresetsProvider, //
 			MegaLocationPresetsProvider, //

+ 107 - 0
src/main/java/org/cryptomator/common/locationpresets/GoogleDriveMacLocationPresetsProvider.java

@@ -0,0 +1,107 @@
+package org.cryptomator.common.locationpresets;
+
+import org.cryptomator.integrations.common.CheckAvailability;
+import org.cryptomator.integrations.common.OperatingSystem;
+
+import java.io.IOException;
+import java.io.UncheckedIOException;
+import java.nio.file.DirectoryStream;
+import java.nio.file.Files;
+import java.nio.file.Path;
+import java.util.Arrays;
+import java.util.List;
+import java.util.function.Predicate;
+import java.util.regex.Pattern;
+import java.util.stream.Stream;
+
+import static org.cryptomator.integrations.common.OperatingSystem.Value.MAC;
+
+@OperatingSystem(MAC)
+public final class GoogleDriveMacLocationPresetsProvider implements LocationPresetsProvider {
+	private static final Path LOCATION = LocationPresetsProvider.resolveLocation("~/Library/CloudStorage/").toAbsolutePath();
+	private static final Predicate<String> PATTERN = Pattern.compile("^GoogleDrive-[^/]+$").asMatchPredicate();
+
+	private static final List<Path> FALLBACK_LOCATIONS = Arrays.asList( //
+			LocationPresetsProvider.resolveLocation("~/GoogleDrive/My Drive"), //
+			LocationPresetsProvider.resolveLocation("~/Google Drive/My Drive"), //
+			LocationPresetsProvider.resolveLocation("~/GoogleDrive"), //
+			LocationPresetsProvider.resolveLocation("~/Google Drive") //
+	);
+
+	@Override
+	public Stream<LocationPreset> getLocations() {
+		if(isLocationPresent()) {
+			return getCloudStorageDirLocations();
+		} else if(FALLBACK_LOCATIONS.stream().anyMatch(Files::isDirectory)) {
+			return getFallbackLocation();
+		} else {
+			return Stream.of();
+		}
+	}
+
+	@CheckAvailability
+	public static boolean isPresent() {
+		return isLocationPresent() || FALLBACK_LOCATIONS.stream().anyMatch(Files::isDirectory);
+	}
+
+	public static boolean isLocationPresent() {
+		try (DirectoryStream<Path> stream = Files.newDirectoryStream(LOCATION, "GoogleDrive-*")) {
+			return stream.iterator().hasNext();
+		} catch (IOException e) {
+			return false;
+		}
+	}
+
+	/**
+	 * Returns Google Drive preset String.
+	 *
+	 * @param accountPath The path to the Google Drive account directory (e.g. {@code ~/Library/CloudStorage/GoogleDrive-username})
+	 * @param drivePath The path to the Google Drive file directory, within the account directory. (e.g. {@code ~/Library/CloudStorage/GoogleDrive-username/drive_name})
+	 * @return {@code String}. For example: "Google Drive - username - drive_name"
+	 */
+	private String getDriveLocationString(Path accountPath, Path drivePath) {
+		String accountName = accountPath.getFileName().toString().replace("GoogleDrive-", "");
+		String driveName = drivePath.getFileName().toString();
+
+		return STR."Google Drive - \{accountName} - \{driveName}";
+	}
+
+	/**
+	 * Handles searching through {@code ~/Library/CloudStorage/} for directories with the "{@code GoogleDrive-*}" pattern,
+	 * and returns the corresponding presets.
+	 *
+	 * @return {@code Stream<LocationPreset>}. Displays as "{@code Google Drive - username - drive_name}"
+	 */
+	private Stream<LocationPreset> getCloudStorageDirLocations() {
+		try (var dirStream = Files.list(LOCATION)) {
+			var presets = dirStream.filter(path -> Files.isDirectory(path) && PATTERN.test(path.getFileName().toString()))
+					.flatMap(accountPath -> {
+						try {
+							return Files.list(accountPath)
+									.filter(Files::isDirectory)
+									.map(drivePath -> new LocationPreset(getDriveLocationString(accountPath, drivePath), drivePath));
+						} catch (IOException e) {
+							throw new RuntimeException(e);
+						}
+					}).toList();
+			return presets.stream();
+		}
+		catch (IOException | UncheckedIOException e) {
+			return Stream.of();
+		}
+	}
+
+	/**
+	 * Uses {@code FALLBACK_LOCATIONS} for directories as fallback, if {@code ~/Library/CloudStorage/} isn't present.
+	 * Returns the corresponding presets.
+	 *
+	 * @return {@code Stream<LocationPreset>}. Displays as "{@code Google Drive}"
+	 */
+	private Stream<LocationPreset> getFallbackLocation() {
+		return FALLBACK_LOCATIONS.stream() //
+				.filter(Files::isDirectory) //
+				.map(location -> new LocationPreset("Google Drive", location))
+				.findFirst()
+				.stream();
+	}
+}

+ 1 - 4
src/main/java/org/cryptomator/common/locationpresets/GoogleDriveLocationPresetsProvider.java

@@ -9,13 +9,11 @@ import java.util.Arrays;
 import java.util.List;
 import java.util.stream.Stream;
 
-import static org.cryptomator.integrations.common.OperatingSystem.Value.MAC;
 import static org.cryptomator.integrations.common.OperatingSystem.Value.WINDOWS;
 
 @OperatingSystem(WINDOWS)
-@OperatingSystem(MAC)
 @CheckAvailability
-public final class GoogleDriveLocationPresetsProvider implements LocationPresetsProvider {
+public final class GoogleDriveWindowsLocationPresetsProvider implements LocationPresetsProvider {
 
 	private static final List<Path> LOCATIONS = Arrays.asList( //
 			LocationPresetsProvider.resolveLocation("~/GoogleDrive/My Drive"), //
@@ -37,5 +35,4 @@ public final class GoogleDriveLocationPresetsProvider implements LocationPresets
 				.findFirst() //
 				.stream();
 	}
-
 }