The OneDrive PowerShell module is available via PowerShellGallery.com. If you want to support and work with me feel free to make changes cloning this repo, change and send me and a pull request.
This OneDrive version (2.0.0 and higher in PowerShellGallery.com) supports:
- OneDrive personal
- OneDrive for Business
Version 2.2.8
- Change: Update of the meta data
Version 2.2.6
- Change: A endpoint change from Microsoft regarding OneDrive personnel is adapted to avoid the error: "AADSTS70011: The provided value for the input parameter 'scope' is not valid. The scope '' is not configured for this tenant" for a refresh token
Version 2.2.5
- Change: A endpoint change from Microsoft regarding OneDrive personnel is adapted to avoid the error: "AADSTS70011: The provided value for the input parameter 'scope' is not valid. The scope '' is not configured for this tenant"
Version 2.2.4
- Bugfix: Cannot access a path on a remote/shared drive
Version 2.2.1
- Upload support for larger files: Add-ODItemLarge Typically files larger then 10 MBytes. Uploading this files is not stable with the standard upload process used by Add-ODItem. Thanks to Benke Tamás (funkeninduktor@gmail.com) for sharing this function
Version 2.2.0
- Downloaded files keeping their time stamps from know Bevor: A downloaded file get the current time as time stamp (created at)
Open PowerShell and
Install-Module -Name OneDrive -Scope CurrentUser -force
You can update the module to a newer version with the same command (-force). After that you have to restart your PowerShell session. If you don’t use PowerShellGet currently, go to the Gallery on https://www.powershellgallery.com/packages/OneDrive and click "Get Started".
Check your installation with
Get-Help -Name OneDrive
Before you start using the OneDrive module you have register your script/application. This differs depending on the OneDrive version to be used.
Read this on my blog: https://www.sepago.de/blog/onedrive-powershell-module-new-version-with-improved-authentication/
-
Go to: https://apps.dev.microsoft.com and login with your Microsoft Account (MSA) and "Add an app" in the category "converged applications"
-
Press "Generate New Password" and save the password (app key)
-
Also save the "Application id"
-
Check "Allow implicit Flow" and enter a "Redirect URL". This is not a real URL. Choose a localhost address and note it. In my case I chose: http://localhost/login
-
Press "Save"
-
Now you have all necessary data for your app / script:
- Client Id: 5dd40b03-0ead-451b-b5e3-f704550e8cca
- AppKey: xqacs8K92MuCJKgciRHQ1Cf
- RedirectURI: http://localhost/login
-
To get an authentication token use:
$Auth=Get-ODAuthentication -ClientID 5dd40b03-0ead-451b-b5e3-f704550e8cca -AppKey "xqacs8K92MuCJKgciRHQ1Cf" -RedirectURI http://localhost/login
Hint: If you create the application in the Azure Portal, make sure to edit the manifest. Change the following values:
"signInAudience": "AzureADandPersonalMicrosoftAccount",
"tags": [
"supportsConvergence:true",
"availableToOtherTenants:true",
"accessTokenVersion:1",
"appModelVersion:2"
],
"tokenEncryptionKeyId": null,
"verifiedPublisher": {
"displayName": null,
"verifiedPublisherId": null,
"addedDateTime": null
}
To use OneDrive for business you have to register your script/app to in Azure Active Directory
-
Add an application in Azure Active Directory inside the Azure portal: https://portal.azure.com/#blade/Microsoft_AAD_IAM/ActiveDirectoryMenuBlade/RegisteredApps
-
Chose "New registration"
-
Give your application a name and configure the redirect URI. The sign-on URL has to be a valid URL but doesn't have to exist. E.g.: http://localhost/1Drive4Business (make later sure that this url is in the reply url list of your application)
-
Click "Register" to create the Azure application.
-
Next go to "Authentication" and enable "ID tokens" - Save the change
-
Click on API permissions and add the following permissions:
-
Azure Active Directory Graph - Delegated permission - User.Read
- SharePoint - Delegated permission - MyFilesRead
- SharePoint - Delegated permission - MyFilesWrite
-
Generate a secrete key for this application and save it for later use. Also save the application Id
-
You should now have the following parameter:
- Client Id: 2831fc52-e1b8-4493-9f3a-a3dad74b2081
- AppKey: TqoSXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX=
- RedirectURI: http://sepago.de/1Drive4Business
-
Additionally you need the resource URL for OneDrive for Business. Normally: https://-my.sharepoint.com/. In our company this is the URL "https://sepagogmbh-my.sharepoint.com/" (the last one / is important).
- Resource ID: https://sepagogmbh-my.sharepoint.com/
-
To get an authentication token use:
$Auth=Get-ODAuthentication -ClientId "2831fc52-e1b8-4493-9f3a-a3dad74b2081" -AppKey "TqoSXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX=" -RedirectURI "http://sepago.de/1Drive4Business" -ResourceId "https://sepagogmbh-my.sharepoint.com/"
An access token is 1 hour valid. You can get a new access token with the refresh token provided by the last authentication. This is necessary if you are creating a script that will work for a long time without further user input. Renew your access token automatically in the program code.
$Auth=Get-ODAuthentication -ClientId "2831fc52-e1b8-4493-9f3a-a3dad74b2081" -AppKey "TqoSXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX=" -RedirectURI "http://sepago.de/1Drive4Business" -ResourceId "https://sepagogmbh-my.sharepoint.com/" -RefreshToken $LastAuth.refresh_token
- Where $LastAuth is your last authentication result (containing the refresh token)
- For OneDrive personal leave the ResourceId empty (-ResourceId "")
Get an authentication code from above and store it in $Auth
Get-ODChildItems -AccessToken $Auth.access_token -ResourceId "https://sepagogmbh-my.sharepoint.com/" -path "/"
Remove-ODItem -AccessToken $Auth.access_token -ResourceId "https://sepagogmbh-my.sharepoint.com/" -path "/Upload"
New-ODFolder -AccessToken $Auth.access_token -ResourceId "https://sepagogmbh-my.sharepoint.com/" -path "/" -FolderName "Upload"
Add-ODItem -AccessToken $Auth.access_token -ResourceId "https://sepagogmbh-my.sharepoint.com/" -LocalFile "D:\DEV\PowerShell\PowerShellGallery-OneDrive\Test\Uploads\IoT Workshop.pptx" -Path "/Upload"
Add-ODItemLarge -AccessToken $Auth.access_token -ResourceId "https://sepagogmbh-my.sharepoint.com/" -LocalFile "D:\DEV\PowerShell\PowerShellGallery-OneDrive\Test\Uploads\IoT Workshop.mp4" -Path "/Upload"
Get-ODDrives -AccessToken $Auth.access_token -ResourceId "https://sepagogmbh-my.sharepoint.com/"
Get-ODItem -AccessToken $Auth.access_token -ResourceId "https://sepagogmbh-my.sharepoint.com/" -Path "/Upload/Doings.txt" -LocalPath "D:\DEV\PowerShell\PowerShellGallery-OneDrive\Test\Downloads"
Get-ODItem -AccessToken $Auth.access_token -ResourceId "https://sepagogmbh-my.sharepoint.com/" -Path "/Upload/Doings.txt" -LocalPath "D:\DEV\PowerShell\PowerShellGallery-OneDrive\Test\Downloads" -LocalFileName "Copy from OneDrive.Doings.txt"
Hint: From version 2.2 downloaded files keep their timestamp.
Remove-ODItem -AccessToken $Auth.access_token -ResourceId "https://sepagogmbh-my.sharepoint.com/" -Path "/Upload/Doings.txt"
Sometimes you have files and folders shared by someone others. You can list this files and download it to your local computer. To access shared files and other OneDrive drives / SharePoint edit your application permission: Add "Read items and all site collection" below application permission to access shared files and other OneDrive drives
$sharedFiles=Get-ODSharedItems -AccessToken $Auth.access_token -ResourceId "https://sepagogmbh-my.sharepoint.com/"
$sharedFiles | Select-Object -Property Name,size,folder
$sharedFile=$sharedFiles[17] # element 17; has to be a file - not a folder
Get-ODItem -AccessToken $Auth.access_token -ResourceId "https://sepagogmbh-my.sharepoint.com/" -ElementId $sharedFile.id -DriveId $sharedFile.remoteItem.parentReference.driveId
This can be a shared folder from a user or from SharePoint
$sharedFolder=$sharedFiles[1] # where element 1 is a folder shared with you
Add-ODItem -AccessToken $at -ResourceId $resourceIdGiven -LocalFile "D:\DEV\PowerShell\PowerShellGallery-OneDrive\Test\Uploads\Doings.txt" -DriveId $sharedFolder.remoteItem.parentReference.driveId -ElementId $sharedFolder.Id
Copy files recursively from OneDrive to a local folder
function Transfer-Files ($path)
{
$Content=@(Get-ODChildItems -AccessToken $at -ResourceId $resourceIdGiven -Path $path)
$CountFiles=@($Content|where {!$_.folder}).count
$CountFolders=@($Content|where {$_.folder}).count
if ($Verbose) {write-host("Current folder: '"+$path+"' (contains folders/files: "+$CountFolders+"/"+$CountFiles+")")}
$global:AllFiles+=$CountFiles
$global:AllFolders+=$CountFolders
$ErrorActionPreference = "Stop"
foreach ($entry in $content)
{
if ($entry.folder)
{
if ($Verbose) {write-host ("Found folder '"+$entry.name+"'")}
$NewPath=($path+"/"+$entry.name).Replace("//","/")
$NewLocalPath=$TargetPath+$NewPath.Replace("/","\")
if ($Verbose) {write-host ("Create local folder '"+$NewLocalPath+"'")}
if (!$demo) {New-Item -ItemType directory -Path $NewLocalPath -force | out-null}
Transfer-Files($NewPath)
} else
{
$LocalPath=$TargetPath+$path.Replace("/","\")
if ($Verbose) {write-host("Download file "+$entry.name+ " to "+$LocalPath)}
if (!$demo) {$ReturnCode=Get-ODItem -AccessToken $at -ResourceId $resourceIdGiven -ElementID $entry.id -LocalPath $LocalPath}
$global:size+=$entry.size
}
}
}
$global:size=0
$global:AllFiles=0
$global:AllFolders=0
$Verbose=$true
$TargetPath="D:\DEV\PowerShell\PowerShellGallery-OneDrive\Test\Downloads\Backup"
Transfer-Files "\Working Folder\Data Analytics"
write-host ("Number of files: "+$global:AllFiles)
write-host ("Number of folders: "+$global:AllFolders)
write-host ("Bytes transfered: {0:N0}" -f $global:Size)
$Drives=Get-ODDrives -AccessToken $Auth.access_token -ResourceId "https://sepagogmbh-my.sharepoint.com/"
$Drives=Get-ODDrives -AccessToken $Auth.access_token -ResourceId "https://sepagogmbh-my.sharepoint.com/"
Get-ODChildItems -AccessToken $at -ResourceId $resourceIdGiven -DriveId $Drives[0].id -Path "/Profilbilder"
Links:
- My blog: https://www.sepago.de/blog/author/marcel-meurer/
- Linked-in: https://www.linkedin.com/in/marcel-meurer-15b46b98/
- Twitter: https://twitter.com/MarcelMeurer
- About me / imprint: https://about.me/marcel.meurer
Feel free to contribute. If you want to stay informed follow this GitHub repo and me on Twitter: https://twitter.com/MarcelMeurer