๐ Recipe ยท SharePoint & OneDrive
List All SharePoint Sites and Their Document Libraries via Microsoft Graph
Enumerate every SharePoint site in your M365 tenant and the document libraries (drives) attached to each, then export the inventory for governance review.
Complexity
Intermediate
Impact
read-only + governance + reporting + sharepoint
Context
Why This Matters
Building a complete inventory of SharePoint sites and their document libraries is a foundational governance task. Admins need this data to:
- Track content sprawl and identify abandoned or duplicate sites.
- Map data residency before running DLP, retention, or sensitivity label rollouts.
- Feed migration, backup, and archival tooling with an accurate source-of-truth list.
- Answer audit questions like "which libraries exist under site X?" or "how many document libraries are in the tenant?"
The SharePoint admin center shows a site list, but it does not expose the per-site drive (document library) URLs in a single exportable view. Microsoft Graph's /sites and /sites/{id}/drives endpoints solve this cleanly and programmatically.
Expected Outcomes
After running this recipe you will have:
- A complete list of SharePoint sites in the tenant (display name, site ID, web URL).
- For each site, the attached document libraries (drive name, drive ID, web URL, drive type).
- A flat CSV report (
SharePoint_Sites_and_Libraries.csv) with one row per library, suitable for Excel, Power BI, or migration tooling. - A repeatable process you can schedule to detect new sites/libraries over time.
Risks & Considerations
Things to watch for
- Search indexing lag โ Newly created sites can take minutes to hours to appear via
/sites?search=*. For freshly provisioned sites, query by hostname or site path directly. - The
search=*wildcard sometimes returns HTTP 500 on some tenants. Usesearch=(empty value) or omit the parameter and page through results as a fallback โ this is the workaround baked into the scripts below. - Result cap โ The search endpoint returns roughly the top 500 sites. Very large tenants should enumerate via
/sites/getAllSites(beta) or via the SharePoint Admin REST API for full coverage. - System / hidden libraries โ The
/drivesendpoint returns document libraries only. Hidden system libraries (Form Templates, Style Library, etc.) are excluded by design. Use/sites/{id}/lists?$filter=list/template eq 'documentLibrary'if you need the complete list. - Read-only scope is enough โ
Sites.Read.Allis sufficient. Do NOT grantSites.FullControl.Allfor an inventory report. - Throttling โ Tenants with hundreds of sites will hit Graph throttling if you fire drive lookups in parallel without backoff. The script includes sequential processing and retry-on-429 handling.
Required Permissions
| Permission | Why It's Needed |
|---|---|
| Sites.Read.All | Read-only access to list all SharePoint sites and enumerate drives (document libraries). Sufficient for an inventory report. |
| Sites.ReadWrite.All | Only needed if you intend to extend this recipe to modify sites or libraries โ NOT required for read-only inventory. |
The fastest way to get this done: just ask Dex. Copy the prompt below and paste it into your Dex conversation.
For IT Admins
Paste into Dex Pro
Collect the list manually from the SharePoint admin center
This approach works for small tenants but does not expose library URLs directly โ you must visit each site to capture them.
Step 1 โ Open the SharePoint admin center
- Sign in to https://admin.microsoft.com as a Global Administrator or SharePoint Administrator.
- In the left nav, expand .
Step 2 โ Export the site list
- In the SharePoint admin center, go to .
- Click Export (top-right toolbar) to download a CSV of all active sites. This gives you site name, URL, template, storage, and owner โ but NOT library URLs.
Step 3 โ Capture document libraries for each site
- For each site in the exported CSV, click the site URL to open it.
- In the site's left navigation, note each item listed under Documents or the Site contents page (gear icon โ ).
- Each document library's URL is of the form
https://<tenant>.sharepoint.com/sites/<site>/<LibraryName>. Copy these into your spreadsheet.
Recommendation: For anything beyond ~5 sites, skip this manual path and use the API or PowerShell recipes below.
Enumerate sites and drives with Microsoft Graph
Two endpoints do the heavy lifting: list sites, then for each site list its drives.
Step 1 โ List all SharePoint sites
GET https://graph.microsoft.com/v1.0/sites?search=&$select=id,displayName,webUrl&$top=999Note: use search= (empty) rather than search=*; the wildcard form returns HTTP 500 on some tenants.
Sample response:
{
"value": [
{
"id": "contoso.sharepoint.com,6bee9a7d-...,348121bc-...",
"displayName": "Mark 8 Project Team",
"webUrl": "https://contoso.sharepoint.com/sites/Mark8ProjectTeam"
}
]
}Step 2 โ List document libraries for each site
GET https://graph.microsoft.com/v1.0/sites/{site-id}/drives?$select=id,name,webUrl,driveTypeSample response:
{
"value": [
{
"id": "b!fZru...",
"name": "Documents",
"webUrl": "https://contoso.sharepoint.com/sites/Mark8ProjectTeam/Shared%20Documents",
"driveType": "documentLibrary"
}
]
}Step 3 โ Handle pagination
If either response contains an @odata.nextLink, follow it until absent. Large tenants will paginate the site list into multiple pages of up to 200โ500 items.
Step 4 โ Watch for 429 throttling
When fanning out drive lookups across many sites, respect Retry-After headers. A 200ms delay between sequential calls keeps most tenants safely under the limit.
PowerShell inventory script
The downloadable script below uses the Microsoft Graph PowerShell SDK to enumerate sites and drives, then writes a CSV report.
Prerequisites
- Microsoft.Graph PowerShell SDK:
Install-Module Microsoft.Graph -Scope CurrentUser Sites.Read.Allconsent granted (delegated or application).
How it works
- Connects to Graph with the
Sites.Read.Allscope. - Calls
Get-MgSite -Search ""and pages through all results. - For each site, calls
Get-MgSiteDriveto list document libraries. - Flattens the data into one row per library and exports to CSV.
- Includes retry logic for HTTP 429 (throttling) and skips sites that return permission errors.
Run it
.\Get-SharePointSitesAndLibraries.ps1 -OutputPath "C:\Reports\SPInventory.csv"The script prints a per-site progress line and a final summary (total sites, total libraries, sites with errors).
Next steps