5

I am working on a webapi webservice that is proteted by Azure Active Directory. The webservice cumminucates heavily with Office 365 (SharePoint / Yammer) based on the user that is signed in.

To test the web api endpoints I am writing an Console App that let me sign in with my AAD credentials and then calls the endpoints. It works, but looking for something to replace this way of testing the web api. Would be great if it’s more repeatable and that I don’t have to fill in my credentials each time. I was looking for a unit test project but can’t get the Azure AD sign in to work.

Any tips how to make this easier?

Dave Smits
  • 1,871
  • 14
  • 22

2 Answers2

2

The easiest way would be to define the test runner as an application in Azure AD and have it call the API with its own client id and secret.

To do that there are a few things you would need to do:

  1. Add appRoles to your API in its manifest in Azure AD. These are application permissions.
  2. Define your test runner, and have it require the necessary application permissions for your API.
  3. In your test runner you should now be able to get an access token with the client id and secret of the test runner, no user authentication required.

Some setup is needed for app permissions on the API side as well, authorization must also look at the role claims.

You can find an example for defining app permissions and also handling them here: http://www.dushyantgill.com/blog/2014/12/10/roles-based-access-control-in-cloud-applications-using-azure-ad/.

More on defining app permissions: https://stackoverflow.com/a/27852592/1658906.

More info on the application manifest in AAD: https://learn.microsoft.com/en-us/azure/active-directory/develop/active-directory-application-manifest.

EDIT: If you must make calls on behalf of the user in the API, then this of course won't work.

In that case, I would suggest creating a user account with the necessary access for the purpose of running the tests. It would be best not to hard-code its credentials, but store them elsewhere.

Community
  • 1
  • 1
juunas
  • 54,244
  • 13
  • 113
  • 149
  • 1
    I don't think it;s going to work. I had to emphases it more, but SharePoint doesnt seem to accept the App authentication approach; – Dave Smits Feb 19 '17 at 18:11
  • 1
    Right, if you must make calls on behalf of a user, then the only option is to create a user account for testing. – juunas Feb 19 '17 at 18:43
0

If you don't want to "fill in my credentials each time", one workaround is using the Resource Owner Password Credentials Grant flow. This flow is flexible to gain a token easily. In the Console App, you could directly use user account and password to get the access token for your protected web API . The code below is for your reference :

 static  void Main(string[] args)
    {

        test().Wait();
    }


    public static async Task test()
    {

        using (HttpClient client = new HttpClient())
        {
            var tokenEndpoint = @"https://login.windows.net/a703965c-e057-4bf6-bf74-1d7d82964996/oauth2/token";
            var accept = "application/json";

            client.DefaultRequestHeaders.Add("Accept", accept);
            string postBody = @"resource=https%3A%2F%2Fgraph.microsoft.com%2F  //here could be your own web api 
            &client_id=<client id>
            &grant_type=password
            &username=nanyu@xxxxxxx.onmicrosoft.com
            &password=<password>
            &scope=openid";

            using (var response = await client.PostAsync(tokenEndpoint, new StringContent(postBody, Encoding.UTF8, "application/x-www-form-urlencoded")))
            {

                if (response.IsSuccessStatusCode)
                {
                    var jsonresult = JObject.Parse(await response.Content.ReadAsStringAsync());
                    var token = (string)jsonresult["access_token"];
                }
            }
        }
    }

But the problem is that flow will expose the username and password directly in the code, it brings potential attack risk as well and we will always avoid handling the user credential directly. So make sure you just use this flow for testing in a secure environment. You could refer to this article for more details.

Community
  • 1
  • 1
Nan Yu
  • 26,101
  • 9
  • 68
  • 148
  • 1
    If you go this route, please be sure to read Vittorio's blog post on the limitations of this flow: http://www.cloudidentity.com/blog/2014/07/08/using-adal-net-to-authenticate-users-via-usernamepassword/ – dstrockis Feb 21 '17 at 20:47