Is it possible to access Office 365 SharePoint/OneDrive API's with App-Only credentials for Multi-Tenant Azure App? - api

We currently have a web service which is accessing the EWS API's for Mail, Calendar, and Contacts. For those, we used the "App-Only"/Client Credential flow to have an app-to-app auth.
Now we'd like to extend our web service to access the SharePoint/OneDrive API's. It looks like the preferred way to access these API's is by making a request to the Discovery service, however it seems that the Discovery service doesn't work with App-Only auth (see: Access Office 365 Discover Service with "app-only" token)
Another approach we've tried is to simply hard-code the SharePoint endpoint URL's.
* Connection #0 to host devunit1-my.sharepoint.com left intact
{
"#odata.context": "https://devunit1-my.sharepoint.com/_api/v2.0/$metadata#me",
"#odata.type": "#microsoft.coreServices.currentUserRequestContext",
"#odata.id": "https://devunit1-my.sharepoint.com/_api/v2.0/me",
"#odata.editLink": "me",
"id": null
}
We can hit the server, but trying to access /files gives us an error:
{
"error": {
"code": "-1, Microsoft.Office.Server.UserProfiles.UserNotFoundException",
"message": "User 'i:0i.t|00000003-0000-0ff1-ce00-000000000000|app#sharepoint' doesn't exist in UPA by UPN or SID, and user with this SID was not found in AD."
}
}
The third way we've tried is by using the Office365 Unified API using /users/<OMITTED User.objectId>/drive which fails giving:
{"odata.error"=>{"code"=>"Request_ResourceNotFound", "message"=>{"lang"=>"en", "value"=>"Resource 'drive' does not exist or one of its queried reference-property objects are not present."}}}
Is there something that we're doing wrong? Is it possible to access SharePoint/OneDrive data (either through the Files API or some other API) with App-Only credentials? If not, is there some work around we can use or do we have to create an entirely separate auth flow just to use the Discovery service?

When working with SharePoint Designer Workflow on SharePoint Online (Office 365) and trying to access to User Profile Service (UPS) make sure you follow the instructions on the following post by providing the Workflow App the necessary permission to the UPS, but make sure you don't run the REST call in an App Step, this caused me a lot of Troubleshooting time as I was getting the error mentioned above "...app#sharepoint doesn't exist in UPA by UPN or SID, and user with this SID was not found in AD."
http://sharepoint-community.net/profiles/blogs/retrieving-user-profile-properties-in-a-sharepoint-2013-workflow
I hope it helps you too. Have fun.

Related

MSGraph Multi-Factor Authentication "interaction_required"

I'm using the Microsoft Graph login endpoint: login.microsoftonline.com/[tenantId]/oauth2/token with a grant type of "password" to log users in:
{
"grant_type": "password",
"client_id": "xxx",
"client_secret": "xxx",
"scope": "openid",
"resource": "https://graph.microsoft.com",
"username": "username",
"password": "********",
}
When I post this with users that are not enrolled in multi-factor authentication on our AD I get back the expected results including an access_token and refresh_token
However on users that are enrolled I get back a HttpStatusCode.BadRequest with an error of "interaction_required"
According to documentation from Microsoft found here:
In this case, your app receives a 400 with an interaction_required
error during access token acquisition or a 403 with
insufficient_claims error when calling Microsoft Graph. In both cases,
the error response contains additional information that can be
presented to the authorize endpoint to challenge the user for
additional information (like multi-factor authentication or device
enrollment).
However I do not see any additional information in the results and can't find much information on next steps. The JSON I get back looks like this:
{
"error":"interaction_required",
"error_description":"AADSTS50079: Due to a configuration change made by your administrator, or because you moved to a new location, you must enroll in multi-factor authentication to access '00000003-0000-0000-c000-000000000000'.\r\nTrace ID: aee10c85-fd12-42ec-be6c-76d546500100\r\nCorrelation ID: 0ee3ebac-f702-4fbc-be76-fd6a291ad488\r\nTimestamp: 2021-09-09 17:45:24Z",
"error_codes":[50079],"timestamp":"2021-09-09 17:45:24Z",
"trace_id":"aee10c85-fd12-42ec-be6c-76d546500100",
"correlation_id":"0ee3ebac-f702-4fbc-be76-fd6a291ad488",
"error_uri":"https://login.microsoftonline.com/error?code=50079",
"suberror":"basic_action"
}
But I am getting back "interaction_required" and confirmed with our AD administrator that they are definitely enrolled. So I am at a bit of a loss for next steps to resolve this.
Cause :User is attempting a authentication method that requires Multi-factor authentication
Try to catch the error you get, and perform a new request according to steps for your flow scenarios by referring from this MS docs
Microsoft Graph has special considerations when building apps in
Conditional Access environments. Since Conditional Access policies are
assigned the specific datasets, Azure AD will enforce Conditional
Access policies based on the data behind Graph - rather than Graph
itself.
(or check below points)
Conditional access policies prevent non-interactive flows to work.
Possible solutions...
Use a interactive flow instead.
If you are using a interactive flow and still getting this error, please make sure openid is one of the scopes during the interactive sign-in. You might be getting the error after the interactive sign-in and trying to exchange the authorization code for a access token...
Example:
https://login.microsoftonline.com/contoso.onmicrosoft.com/oauth2/authorize?client_id=#...#
&response_type=code
&scope=openid groups.read.all
&nonce=1234
&redirect_uri=https://app.contoso.com
Notice "scope=openid groups.read.all" in the request above
Add the client application to the exception list of the Conditional Access Policy
Add the user to the exception list of the Conditional Access Policy
If you are not using conditional access policies and the user is directly enabled for MFA, then as a last thing, disable MFA for the user if solutions above do not work for you.
Or you can use certificate based authentication instead of MFA
References:
login-to-azure-web-application-fails-with-aadsts50079
SO thread

How to use the eBay Browse API just to search for products via one server

I try to migrate from eBay Finding API to Browse API. My technical setting is quiet easy:
A Server searches the Browse API to find products by a keyword. Thats it.
Does anybody know if I need to implement OAuth, a redirection page for eBay-Users to log in etc.? I don't need all those features..
Thanks!
You can use the browse API with the client credential flow that mints the Application access token.
Application tokens are general-use tokens that give access to interfaces that return application data. For example, many GET requests require only an Application token for authorization.
See Documentation
The client credential flow does not require a User to Login via eBay and the redirect etc. However, you can only use the "GET" methods like getItem, getItemByLegacyId or search for example.
If you using NodeJs or Browser you can checkout the "Get Item" example here. (The library will get the Application access token automatically and return the result.)

Answering reviews on google play with service account

I wanna answer my application's reviews with service account. But regarding to api documantation of google play console, for answering review's, i need to have my auth'key. :
GET https://www.googleapis.com/androidpublisher/v3/applications/your_package_name/reviews?
access_token=your_auth_token
But in my json file that i got from "create key" on my service account page, i have nothing like: "auth token". What should i do?
Note: I also have 1 more small question: I wanna list all of my applications for google play. I found some non-offical api's that can retrieve all app's for spesific developer. But for that i need to have people's developer name that i cannot retrieve from any api.
But in my json file that i got from "create key" on my service account page, i have nothing like: "auth token". What should i do?
Your auth token is not in the key file you downloaded it contains what you need to request an access token.
Assuming that you have created service account credentials on Google cloud console. What you have in that file is the credentials you need to create an access token.
Your application calls Google APIs on behalf of the service account, so users aren't directly involved. This scenario is sometimes called "two-legged OAuth," or "2LO." (The related term "three-legged OAuth" refers to scenarios in which your application calls Google APIs on behalf of end users, and in which user consent is sometimes required.)
Requesting an access token using a service account requires a number of steps Preparing to make an authorized API call I recommend you look for a client library in your chosen language coding it yourself is not for the feint at heart.
I wanna list all of my applications for google play.
In order to do that you will need to grant the service account access to your accounts data probably by sharing the data with it. Or you will need to use Oauth2 to authorize your application then you will have access to it.

MS Graph API: OneDrive resource not found

I'm building a Windows service that connects to OneDrive for Business via the Graph API using this method:
https://graph.microsoft.io/en-us/docs/authorization/app_only
I've successfully authenticated my application and have a token for making calls to Graph API. I have given my Azure AD application permissions to both Windows Azure Active Directory and Microsoft Graph (all application and delegated permissions have been selected for both).
My goal is to get the contents of a folder that resides in a specific user's OneDrive. I need to make the following Graph API call:
//graph.microsoft.com/v1.0/users('user-guid')/drive/items/long-item-id-here/children
I can execute this request successfully using Microsoft Graph Explorer (logged in with my Office 365 credentials). When I try to make the same call as an application (using the auth token received above), I get an "itemNotFound" code with the message "The resource could not be found." (request-id:
5e814dce-c4c2-4615-90e6-ea8ab90cbc49). However, I am able to query the root and the "folder.childCount" property shows the correct number of children in the root:
//graph.microsoft.com/v1.0/users('user-guid')/drive/root
I've set the folder's sharing to "All Authenticated Users" and I still receive "The resource could not be found" from the API call.
Any ideas on what I'm missing here?
The marked answer is no longer the case. You can now access OneDrive and SharePoint resources using a Client Credentials grant (aka "App Only").
The applicable scopes are Files.Read.All, Files.ReadWrite.All, Sites.Read.All, Sites.ReadWrite.All
The application is using App-only authorization which is currently not supported for accessing OneDrive for Business through Microsoft Graph API. Please use delegated flow, which is used by Graph Explorer.

Error code 403 in Google+ api

I got "error": {
"errors": [
{
"domain": "usageLimits",
"reason": "dailyLimitExceededUnreg",
"message": "Daily Limit for Unauthenticated Use Exceeded. Continued use requires signup.",
"extendedHelp": "https://code.google.com/apis/console"
}
],
"code": 403,
"message": "Daily Limit for Unauthenticated Use Exceeded. Continued use requires signup."
}
When i try to fetch User Profile in Google+ api by https://www.googleapis.com/plus/v1/people/me URL String.If anyone have any suggestion then please tell me as soon as possible.Thanks in advance for your time.
That message implies that you haven't set up a Google APIs console project.
Create a Google APIs Console project
On the Services pane, enable all of the APIs that your project requires.
On the API Access pane, click Create an OAuth 2.0 client ID. A dialog opens. Fill in your project's information. Click Next
Choose the appropriate application type. Based on the tags you used for this post, I am guessing this is an iOS project so select Installed application.
Enter your bundle ID. You don't need to enter an App Store ID until your app is listed there.
Click Create Client ID.
You will see the client ID and client secret values. You will use these values to enable communication with your project and the Google APIs.
If you aren't already using it, see the Google+ iOS SDK and documentation for a full walk through. The task called "write moments" is similar in implementation and demonstrates how to connect to and use the Google+ REST APIs from within an iOS project that uses the SDK.
You'll need to specify the scope of plus.me to get the profile information.
I got the same error and after much hunting I found that, in my case, the Authorization header with the access token was not set. Set Authorization: "Bearer <YOUR_ACCESS_TOKEN>" in the header of the request of EVERY Google API call.
I just want to add a little information here in the rare case that someone runs into this problem.
I have an organization (ORG). I created a second channel (SC) with some playlists, that referenced videos from ORG.
I made the mistake of assuming that because ORG owned SC, that I could use the same oauth credentials from ORG to access both. I was wrong.
I switched credentials and was confused when I could access the playlists but not the videos. Again, I needed credentials for each one separately to access the resources on the respective channel.
Lame, but that was how it was.
BrettJ's answer will cover most of the bases. However, you will also get this error - even when your credentials are properly authenticated - when the scope is not properly set up. I would check the scope setting in your OAuth dance. Make sure your user is permitted to do the thing your code is trying to help them do.
On top of what BrettJ has mentioned, it is important to send the authorization header for the request done to fetch UserProfile in google+ API.
For example, Add the following header
key: Authorization
value: Bearer ya29.Ci-cA_CywoVdVG#######
For what it's worth, I also got this error when using rclone to sync files and my firewall wasn't configured to allow that traffic.