Chiwda
Chiwda

Reputation: 1344

How do I find the OneDrive (SkyDrive) and GoogleDrive folders without the API?

Thanks to this article,

How do I programmatically locate my Dropbox folder using C#?

I can programmtically find the Dropbox folder. Now, without installing and using various APIs, how can I do the same for GoogleDrive and MS SkyDrive?

Vb.Net or C# solutions are OK...

Upvotes: 3

Views: 4513

Answers (4)

Uwe Keim
Uwe Keim

Reputation: 40736

OneDrive / SkyDrive

The solution of Chiwda led my to the right direction but was not directly working on my machine (Windows 8.1 German), because the registry key was not present.

Instead, this worked:

private static string getOneDriveFolderPath()
{
    var value1 = Registry.GetValue(
        @"HKEY_CURRENT_USER\Software\Microsoft\SkyDrive", 
        @"UserFolder", null);

    var path1 = value1 as string;
    if (path1 != null && Directory.Exist(path1)) return path1;

    var value2 = Registry.GetValue(
        @"HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\SkyDrive",
        @"UserFolder", null);

    var path2 = value2 as string;
    if (path2 != null && Directory.Exists(path2)) return path2;

    var value3 = Registry.GetValue(
        @"HKEY_CURRENT_USER\Software\Microsoft\OneDrive",
        @"UserFolder", null);

    var path3 = value3 as string;
    if (path3 != null && Directory.Exists(path3)) return path3;

    return null;
}

The code first tries the path in Chiwda's answer than tries the path that was present on my machine.

Upvotes: 2

Uwe Keim
Uwe Keim

Reputation: 40736

Google Drive

Again, Chiwda's solution showed me the right way. Google Drive needs to have an SQLite library available in order to read the path to the local folder.

My code:

private static string checkGetGoogleDriveLocation()
{
    var appDataPath = Environment.GetFolderPath(
                          Environment.SpecialFolder.LocalApplicationData);
    var dbPath = Path.Combine(appDataPath, 
                     @"Google\Drive\user_default\sync_config.db");

    if (!File.Exists(dbPath)) return null;

    var tmp = dbPath + Guid.NewGuid();
    File.CopyFile(dbPath, tmp);

    var folderPath = tryGetFolderFromGoogleDriveDB(tmp);
    if (string.IsNullOrEmpty(folderPath) || !Directory.Exists(folderPath)) return null;

    File.Delete(folderPath);

    return folderPath;
}

I've implemented the tryGetFolderFromGoogleDriveDB function with the help of the "sqlite-net" NuGet package which is also available on GitHub:

private static string tryGetFolderFromGoogleDriveDB(string dbFilePath)
{
    using (var conn = new SQLiteConnection(dbFilePath, SQLiteOpenFlags.ReadOnly))
    {
        var cmd = conn.CreateCommand(
            @"select data_value from data where entry_key='local_sync_root_path'");
        return cmd.ExecuteScalar<string>();
    }
}

Please note that the sqlite-net package does P/Invoke the native sqlite3.dll file so you have to ensure that it is stored in the same folder as your executable you are using this code with.

Upvotes: 1

bmgh1985
bmgh1985

Reputation: 789

Not quite what you will be able to use, but you may be able to reverse-engineer it for VB.net. A solution I have used for VBA to save some documents to a users Dropbox folder. It looks for it in default installation location and if it does not find it, then prompts for the folder. Most people will leave the default location anyway IMO, so its rare that it will miss it. From memory, SkyDrive and Google Drive follow the same default location patterns too, so a small tweak should be able to find all of them.

Sub finddropbox()
Dim strOS, localdrive, dropboxfolder As String
Dim folderSelect As FileDialog
Dim objWMIService, colOperatingSystems, objOperatingSystem

strComputer = "."    
Set objWMIService = GetObject("winmgmts:" & "{impersonationLevel=impersonate}!\\" & strComputer & "\root\cimv2")
Set colOperatingSystems = objWMIService.ExecQuery("Select * from Win32_OperatingSystem")

For Each objOperatingSystem In colOperatingSystems
    strOS = objOperatingSystem.Caption
Next

If InStr(strOS, "XP") Then
    localdrive = Environ("USERPROFILE") & "\My Documents\"
Else
    localdrive = Environ("USERPROFILE")
End If

dropboxfolder = localdrive & "Dropbox\"
If Dir(dropboxfolder, vbDirectory) = vbNullString Then
    Set folderSelect = Application.FileDialog(msoFileDialogFolderPicker)
        With folderSelect
            .Title = "Select Dropbox Folder"
            .AllowMultiSelect = False
            .InitialFileName = Environ("SYSTEMDRIVE")
            If .Show = -1 Then
                dropboxfolder = .SelectedItems(1)
            End If
       End With
End If

Debug.Print dropboxfolder

End Sub

Upvotes: 0

Chiwda
Chiwda

Reputation: 1344

I found part of the answer here...

How do I programmatically locate my Google Drive folder using C#?

Here is my code for three of the main Webfolder services

Dim StoreFolder As String = ""
' Dropbox
Dim dbPath As String = System.IO.Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData), "Dropbox\\host.db")
Dim lines() As String = System.IO.File.ReadAllLines(dbPath)
Dim dbBase64Text As Byte() = Convert.FromBase64String(lines(1))
StoreFolder = System.Text.ASCIIEncoding.ASCII.GetString(dbBase64Text)

' SkyDrive
StoreFolder = My.Computer.Registry.GetValue("HKEY_CURRENT_USER\Software\Microsoft\SkyDrive", "UserFolder", Nothing)

' Google Drive
Dim dbPath As String = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), "Google\\Drive\\sync_config.db")
File.Copy(dbPath, "temp.db", True)
StoreFolder = File.ReadAllText("temp.db", System.Text.Encoding.ASCII)
StoreFolder = StoreFolder.Substring(StoreFolder.IndexOf("local_sync_root_pathvalue") + 29)
StoreFolder = StoreFolder.Substring(0, StoreFolder.IndexOf(Char.ConvertFromUtf32(24)))

Upvotes: 2

Related Questions