SharePoint Online: Upload a Folder using PowerShell

Requirement: Upload a Folder to SharePoint Online using PowerShell

How to upload a Folder to SharePoint Online Document Library?

You can upload a folder and its contents to SharePoint either using the web browser – upload button in the toolbar or dragging and dropping the folder onto the library from Windows Explorer. Here is how to upload a folder with its sub-folders and files to a SharePoint Online document library:

  • Navigate to your SharePoint Online library >> Click on “Upload” from the toolbar, choose the “Folder” option. You’ll get a Browse dialog box to select a folder from your computer.
    How to Upload a Folder to SharePoint Online?
  • Select a folder to copy that entire folder to SharePoint Online library.

This will upload the folder and its contents from the local computer to SharePoint Online. Please note, this option doesn’t work in IE 11. (But works in Edge, Google Chrome, and Firefox browsers!). You can also upload a folder with files and sub-folders to SharePoint Online modern libraries, just by Drag and Drop!

PowerShell to upload a Folder to SharePoint Online (Including Folder, Sub-Folders, and Files):

We can also use PowerShell to copy a folder to SharePoint Online from the local disk. This script will be helpful for users who would like to upload folders of data from their personal computer into Sharepoint Online using PowerShell. The process can take some time, depending on the size of your files and internet connection speed. Let’s upload a folder to SharePoint Online using PowerShell. Here is my source:

upload folder to sharepoint online powershell
Prerequisites: Make sure you have installed SharePoint Online Client
Components SDK in your machine to use client-side assemblies. You can download it from https://www.microsoft.com/en-us/download/details.aspx?id=42038

PowerShell is a powerful tool for those looking to automate tedious tasks on the Microsoft platform. This article will cover uploading a folder from your local computer onto Sharepoint Online using PowerShell commands. Here is how to upload a Folder to SharePoint Online Document Library using PowerShell:

#Load SharePoint CSOM Assemblies
Add-Type -Path "C:\Program Files\Common Files\Microsoft Shared\Web Server Extensions\16\ISAPI\Microsoft.SharePoint.Client.dll"
Add-Type -Path "C:\Program Files\Common Files\Microsoft Shared\Web Server Extensions\16\ISAPI\Microsoft.SharePoint.Client.Runtime.dll"

#Function to Check if Folder Exists. If not, Create the Folder
Function Ensure-SPOFolder()
{
    param
    (
        [Parameter(Mandatory=$true)] [string] $FolderRelativeURL
    )

    #Check Folder Exists
    Try { 
        $Folder = $Web.GetFolderByServerRelativeUrl($FolderRelativeURL)
        $Ctx.Load($Folder)
        $Ctx.ExecuteQuery() 
 
        #Write-host -f Green "Folder Already Exists!"
    }
    Catch {
        #Create New Sub-Folder
        $Folder=$Web.Folders.Add($FolderRelativeURL)
        $Ctx.ExecuteQuery()
        Write-host -f Green "Created Folder at "$FolderRelativeURL
    }
}

#Function to Upload a File to a SharePoint Online
Function Upload-SPOFile()    
{
    param
    (
        [Parameter(Mandatory=$true)] [string] $SourceFilePath,
        [Parameter(Mandatory=$true)] [string] $TargetFileURL
    )
    
    #Get the file from disk
    $FileStream = ([System.IO.FileInfo] (Get-Item $SourceFilePath)).OpenRead()
    #Get File Name from source file path
    $SourceFileName = Split-path $SourceFilePath -leaf
   
    #Upload the File to SharePoint Library
    $FileCreationInfo = New-Object Microsoft.SharePoint.Client.FileCreationInformation
    $FileCreationInfo.Overwrite = $true
    $FileCreationInfo.ContentStream = $FileStream
    $FileCreationInfo.URL = $TargetFileURL
    $FileUploaded = $TargetFolder.Files.Add($FileCreationInfo)
  
    $Ctx.ExecuteQuery()  
    #Close file stream
    $FileStream.Close()
    Write-host "File '$TargetFileURL' Uploaded Successfully!" -ForegroundColor Green
}
 
#Main Function to upload a Local Folder to SharePoint Online Document Library Folder
Function Upload-SPOFolder()
{ 
    param
    (
        [Parameter(Mandatory=$true)] [string] $SourceFolderPath,
        [Parameter(Mandatory=$true)] [Microsoft.SharePoint.Client.Folder] $TargetFolder        
    )

    #Get All Files and Sub-Folders from Source
    Get-ChildItem $SourceFolderPath -Recurse | ForEach-Object {
        If ($_.PSIsContainer -eq $True) 
        {
            $FolderRelativeURL = $TargetFolder.ServerRelativeURL+$_.FullName.Replace($SourceFolderPath,[string]::Empty).Replace("\","/")
            If($FolderRelativeURL) 
            {
                Write-host -f Yellow "Ensuring Folder '$FolderRelativeURL' Exists..."
                Ensure-SPOFolder -FolderRelativeURL $FolderRelativeURL
            }  
        }
        Else
        {
            $FolderRelativeUrl = $TargetFolder.ServerRelativeURL + $_.DirectoryName.Replace($SourceFolderPath,[string]::Empty).Replace("\","/")
            $FileRelativeURL = $FolderRelativeUrl+"/"+$_.Name
            Write-host -f Yellow "Uploading File '$_' to URL "$FileRelativeURL
            Upload-SPOFile -SourceFilePath $_.FullName -TargetFileURL $FileRelativeURL
        }
    }
}

#Set parameter values
$SiteURL="https://crescent.sharepoint.com/sites/marketing"
$LibraryName="Documents"
$SourceFolderPath="C:\Users\salaudeen\Desktop\Marketing\Documents"
 
#Setup Credentials to connect
$Cred= Get-Credential
$Credentials = New-Object Microsoft.SharePoint.Client.SharePointOnlineCredentials($Cred.Username, $Cred.Password)
 
#Setup the context
$Ctx = New-Object Microsoft.SharePoint.Client.ClientContext($SiteURL)
$Ctx.Credentials = $Credentials
      
#Get the Target Folder to Upload
$Web = $Ctx.Web
$Ctx.Load($Web)
$List = $Web.Lists.GetByTitle($LibraryName)
$Ctx.Load($List)
$Ctx.Load($List.RootFolder)
$Ctx.ExecuteQuery() 
 
#Call the function to Upload All files & folders from local folder to SharePoint Online
Upload-SPOFolder -SourceFolderPath $SourceFolderPath -TargetFolder $List.RootFolder

This PowerShell uploads the given folder, sub-folder, and files to SharePoint Online.

powershell to upload folder structure to sharepoint online

Here is the PnP PowerShell version of this script which uploads a folder with its subfolders and files: Upload Multiple Files to SharePoint Online using PnP PowerShell

Salaudeen Rajack

Salaudeen Rajack is a SharePoint Architect with Two decades of SharePoint Experience. He loves sharing his knowledge and experiences with the SharePoint community, through his real-world articles!

10 thoughts on “SharePoint Online: Upload a Folder using PowerShell

  • Thanks so much for sharing this script. I’d be interested in a version that prompts for user credentials, as this would be most handy!

    Reply
    • Do you mean, script to *Not* prompt for credentials? You can Hard-code your credentials, use an encrypted password file, or use AppID and AppSecret methods.

      Reply
  • Hello Sir,

    I need help. I am working on one utility where I want to copy folder from local machine to Sharepoint online. This utility will be run by all users in our company, so whichever user will run the utility folder from his local machine should get copied to sharepoint. Can i use your script to achieve the same ? You have mentioned prerequisites of installing SharePoint online client SDK, do I need to install this SDK on all users machine before using this tool ?

    Reply
  • What would we need to add to the script in order for it to delete the source file after successful upload to Sharepoint?
    Also, this only seems to work to the root of a document library. What do we need to do to point it at a sub folder? (for example – right now this works perfectly –> https://mysharepointsite.sharepoint.com/sites/MyTeamSite/TestDocLibrary….. But how do I upload to this target –> https://mysharepointsite.sharepoint.com/sites/MyTeamSite/TestDocLibrary/SubFolder1/SubFolder2???)

    Reply
  • How would i get the code to Skip a Folder? i have tried to add a | Where {$_.name -NotLike “*Archives*”}

    to a few lines but it produces an error. (it still uploads) but searches every sub folder taking a LONG time to upload the files.

    Reply
  • Thank you so much. Saved me a ton of time and your script worked perfectly.

    Reply
  • You saved me!

    But, there is an interesting task:
    How to Upload a Folders to SharePoint Online SubFolder using PowerShell (Url = “https://test.sharepoint.com/Sites/Libary/Folder/SubFolder”)?

    Thank you for your time and effort in advance!

    Reply
    • Sure, Use this script to get the sub folder:

      $FolderServerRelativeUrl= "/Sites/Marketing/Shared Documents/2017"    
      
      #Get the Folder by Server Relative URL
      $Folder = $Web.GetFolderByServerRelativeUrl($FolderServerRelativeUrl)
      $Ctx.Load($Folder)
      $Ctx.ExecuteQuery() 
      
      Reply
    • Thank you!

      But, I still get an error. If you can and have time, check please:

      #Set parameter values
      $SiteURL="https://test.sharepoint.com/teams/Ukraine/"
      #$LibraryName="TempBackup"
      $FolderServerRelativeUrl="/Ukraine/TempBackup/ADVANCE/APPROVED/"
      $SourceFolderPath="D:\Files\public\ADVANCEFORMULARS"
      $Username = "logon_name"
      $Password = Get-Content "password_path.txt" | ConvertTo-SecureString 
      
      #Load SharePoint CSOM Assemblies
      Add-Type -Path "C:\Program Files\Common Files\Microsoft Shared\Web Server Extensions\ISAPI\Microsoft.SharePoint.Client.dll"
      Add-Type -Path "C:\Program Files\Common Files\Microsoft Shared\Web Server Extensions\ISAPI\Microsoft.SharePoint.Client.Runtime.dll"
      
      #Setup Credentials to connect
      $Creds = New-Object Microsoft.SharePoint.Client.SharePointOnlineCredentials($Username, $Password)
      $Credentials = $Creds
      
      #Setup the context
      $Ctx = New-Object Microsoft.SharePoint.Client.ClientContext($SiteURL)
      $Ctx.Credentials = $Credentials
      
      #Function to Check if Folder Exists. If not, Create the Folder
      Function Ensure-SPOFolder()
      {
      param
      (
      [Parameter(Mandatory=$true)] [string] $FolderServerRelativeURL
      ) 
      
      #Check Folder Exists
      Try {
      $Folder = $SPWeb.GetFolderByServerRelativeUrl($FolderServerRelativeURL)
      $Ctx.Load($Folder)
      $Ctx.ExecuteQuery()
      
      #Write-host -f Green "Folder Already Exists!"
      }
      Catch {
      #Create New Sub-Folder
      $Folder=$SPWeb.Folders.Add($FolderServerRelativeURL)
      $Ctx.ExecuteQuery()
      Write-host -f Green "Created Folder at "$FolderServerRelativeURL
      }
      }
      
      #Function to Upload a File to a SharePoint Online
      Function Upload-SPOFile()   
      {
      param
      (
      [Parameter(Mandatory=$true)] [string] $SourceFilePath,
      [Parameter(Mandatory=$true)] [string] $TargetFileURL
      )
      
      #Get the file from disk
      $FileStream = ([System.IO.FileInfo] (Get-Item $SourceFilePath)).OpenRead()
      #Get File Name from source file path
      $SourceFileName = Split-path $SourceFilePath -leaf
      
      #Upload the File to SharePoint Library
      $FileCreationInfo = New-Object Microsoft.SharePoint.Client.FileCreationInformation
      $FileCreationInfo.Overwrite = $true
      $FileCreationInfo.ContentStream = $FileStream
      $FileCreationInfo.URL = $TargetFileURL
      $FileUploaded = $TargetFolder.Files.Add($FileCreationInfo)
         
      $Ctx.ExecuteQuery() 
      #Close file stream
      $FileStream.Close()
      Write-host "File '$TargetFileURL' Uploaded Successfully!" -ForegroundColor Green
      }
      
      #Main Function to upload a Local Folder to SharePoint Online Document Library Folder
      Function Upload-SPOFolder()
      {
      param
      (
      [Parameter(Mandatory=$true)] [string] $SourceFolderPath,
      [Parameter(Mandatory=$true)] [Microsoft.SharePoint.Client.Folder] $TargetFolder       
      )
      
      #Get All Files and Sub-Folders from Source
      Get-ChildItem $SourceFolderPath -Recurse | ForEach-Object {
      If ($_.PSIsContainer -eq $True)
      {
      $FolderServerRelativeURL = $TargetFolder.ServerRelativeURL+$_.FullName.Replace($SourceFolderPath,"").Replace("","/")
      If($FolderServerRelativeURL)
      {
      Write-host -f Yellow "Ensuring Folder '$FolderServerRelativeURL' Exists..."
      Ensure-SPOFolder -FolderServerRelativeURL $FolderServerRelativeURL
      } 
      }
      Else
      {
      $FolderServerRelativeUrl = $TargetFolder.ServerRelativeURL + $_.DirectoryName.Replace($SourceFolderPath,"").Replace("","/")
      $FileRelativeURL = $FolderServerRelativeUrl+"/"+$_.Name
      Write-host -f Yellow "Uploading File '$_' to URL "$FileRelativeURL
      Upload-SPOFile -SourceFilePath $_.FullName -TargetFileURL $FileRelativeURL
      }
      }
      }
      
      #Get the Target Folder to Upload
      $Web = $Ctx.Web
      $Ctx.Load($Web)
      $List = $Web.Lists.GetByTitle($FolderServerRelativeUrl)
      $Ctx.Load($List)
      $Ctx.Load($List.RootFolder)
      $Ctx.ExecuteQuery()
      
      #Call the function to Upload All files and folders from local folder to SharePoint Online
      Upload-SPOFolder -SourceFolderPath $SourceFolderPath -TargetFolder $List.RootFolder
      
      Reply

Leave a Reply