11
votes

I'm trying to connect to Sharepoint Online (Sharepoint 365?) content using OAuth2 and the REST API. I need to do this from Python as it is an addition to an existing application. I have already managed to connect the application to Google Drive using OAuth2 and REST, so I think I understand the fundamentals of using OAuth2.

I've tried a number of combinations of places to configure the client_id and client_secret and authenticate and receive access and refresh tokens.

So far I have been able to receive a refresh token and use it to obtain an access token; however, I'm unable to use the access token to access content on the Sharepoint 365 site.

For configuring the client_id and client_secret I associated my Sharepoint site with AAD using the Azure Management Portal. Then I added an application to the Sharepoint AD entry with the client_id and client_secret. In Sharepoint I used appregnew.aspx to register the client_id and verified the application appears in appprincipals.aspx.

I call the authentication service using: .../login.windows.net/common/oauth2/authorize?api-version=1.0&response_type=code&client_id=&redirect_uri=&resource=Microsoft.Sharepoint

and am able to authenticate, receive a code, call back to .../login.windows.net/common/oauth2/token with the code and receive access and refresh tokens.

I serialized those tokens and from a separate process call .../login.windows.net/common/oauth2/token with the refresh_token, client_id, client_secret, and grant_type=refresh_token and receive a new access token.

Finally I call in to Sharepoint service endpoint -my.sharepoint.com/personal//_api/web/files' with the new access token and it fails telling me the resource Microsoft.Sharepoint is invalid (Invalid audience Uri 'Microsoft.SharePoint')

I've been spinning my wheels trying various permutations of where the client_id is configured and this is as far as I've gotten. Since all the documentation and examples seem to depend on using C# libraries such as TokenHelper I feel like I'm missing something key but simple and can't find the required information.

Has anyone connected to Sharepoint Online using Python, Ruby, Java, etc? If so:

  1. Where should the client_id be configured?
  2. What are the endpoints for obtaining the refresh and access tokens?
  3. What is the appropriate audience uri or resource for which to request tokens?

Many thanks!

4

4 Answers

8
votes

I've successfully connected to SharePoint Online using PHP. It looks to me like you're combining two different methods to do so. Here is what I did:

The appregnew.aspx and appprincipals.aspx pages are used for apps for SharePoint but it doesn't look like you're building one.

4
votes

I think you are trying to do OAuth from Sharepoint Online without creating an Add-In inside Sharepoint. This was the exact problem I was facing. I know this is an old question but my answer might be helpful to someone else coming here.

It is possible to do OAuth from any web-app. Here are the step by step instructions in my blog -

https://medium.com/@yash_agarwal2/performing-oauth-and-rest-calls-with-sharepoint-online-without-creating-an-add-in-677e15c8d6ab#.6pf4wp83b

High Level overview -

1) Get client id and secret by registering yourself here - https://sellerdashboard.microsoft.com/Registration

2) Get Access Token, Refresh Token by following steps here -

https://msdn.microsoft.com/en-us/library/office/jj687470.aspx

0
votes

Im probably a bit late to the party, but to whoever stumbles into this one, you can have a look at how the SharePoint Oauth App Client lib does it.

You'll probably want to check the SPSite and SPAccessToken classes.

0
votes

I know this is old by had to deal with similar problem and have 2.5 solutions.

This solution is specifically for the federated logins.

Simple hacky solutions works like a magic for files :)

  1. On Windows 10 - the silliest solution:

    • First login to your sharepoint with Internet Exploer/Edge. Must be IE/Edge.
    • Then in Start-> Run dialog or any Windows Explorer address bar do this: \\<your_sharepoint_site.com>@SSL\rest\of_the\path. Note @SSL after host name.
    • Make sure to replace all the forward slashes with backslashes.
    • This makes sure that your login credentials are captured by the system.
    • Then navigate to "This PC", menu "Computer->Map Network Drive" and paste either that same path from above or your normal URL https://<your_sharepoint_site.com>/rest/of_the/path into Folder text field of Map Network Drive.
    • Now you have Sharepoint folder mapped as regular network drive X:\! Which allows you to treat is just as normal file system folder from any program or programming language.
    • This solution uses WebDav WebClient and by default you will hit a 50MB limit! Worry not follow these steps to release yourself from the shackles of the silly limit.
  2. Simple Hacky.

    • Open your browsers and open the 'Developer Tools'.
    • Navigate to 'Network' tab of 'Developer Tools'
    • With Network tab open login to your sharepoint site.
    • Click on any of the requests and you shall see that every single Request Header has a Cookie with FedAuth=some_very_long_base64_encoded_xml_struct;rtFa=something_else_long.
    • Basically you need these two cookies FedAuth and rtFa.
    • Now with every GET POST (curl, wget etc) request to the Sharepoint just add a new header Cookie with the value FedAuth=<fedauth-cookie-value>;rtFa=<rtFa-cookie-value>.
  3. Programmatic-hacky (example in python on windows), essentially #2 but cookie manipulation all done programmatically.

    • We shall steal the cookie directly from the kid... I mean from the Chrome browser.
    • Navigate to your Sharepoint With the chrome browser and perform all the necessary login actions.
    • Steal the cookie gist. Plagiarized from here.
    • Use the cookie gist.
    • REST of Sharepoint REST API wisdom here and ref here.
  4. Finally open a beer enjoy your day.