Azure Access Control Service (ACS) - ACS50001: Relying party with identifier 'https://[namespace].accesscontrol.windows.net/' was not found - acs

I have an ACS namespace with a WS-Federation identity provider set up. Since I'm using Visual Studio 2012, I used the Identity and Access Tool to create the relying party. The tool uses the realm and return url values that I give it when it creates the relying party (I use the Azure cloud service url where I'm deploying my project - i.e. http://myapp.cloudapp.net). There is only one rule in the rule group for my relying party after I run the tool - Pass through all claims for [Relying Party]. I tested the ACS for my app with just that one rule, and also after generating all the rules for the WS-Federation identity provider.
Regardless of the rules in the rule group, I get the error in the title of my question. My browser is redirected to ACS, however for some reason it can't find the correct relying party. I have created an ACS namespace, identity provider, and relying party in two different Azure accounts, with exactly the same result.
I've also tried publishing my project to the Azure cloud service with both http and https endpoints, and both endpoints yield the same result.
The WS-Federation identity provider's federation metadata is coming from Windows Azure Active Directory.
UPDATE
FederationConfiguration section from web.config:
<federationConfiguration>
<cookieHandler requireSsl="false" />
<wsFederation passiveRedirectEnabled="true" issuer="https://[MyNamespace].accesscontrol.windows.net/v2/wsfederation" realm="http://[MyApp].cloudapp.net/" requireHttps="false" />
</federationConfiguration>
UPDATE 2:
Still no solution. It looks like the issue stems from the fact that I set up my own ACS identity provider, and downloaded the federation metadata from Windows Azure Active Directory (WAAD) for that identity provider. That essentially chains 2 ACS instances together. When my app redirects to my ACS, it passes my app's url as the realm. Then, my ACS redirects to the identity provider, WAAD, and passes its own url as the realm. That's why the error I get back has the strange characteristic of a relying party identifier = the url of my own ACS admin portal. I'm not sure why it's not passing the realm all the way through from my app to WAAD.

Well, the answer to this was much more obscure than I had expected - I had to run the following powershell script against my CRM Online WAAD:
Connect-MsolService
Import-Module MSOnlineExtended -Force
$replyUrl = New-MsolServicePrincipalAddresses –Address "https://lefederateur.accesscontrol.windows.net/"
New-MsolServicePrincipal –ServicePrincipalNames #(“https://lefederateur.accesscontrol.windows.net/”) -DisplayName “LeFederateur ACS Namespace” -Addresses $replyUrl
This told WAAD to recognize my ACS namespace, so it wouldn't throw the error saying the ACS namespace was not a valid relying party identifier. Read the whole process here:
http://www.cloudidentity.com/blog/2012/11/07/provisioning-a-directory-tenant-as-an-identity-provider-in-an-acs-namespace/
Thanks to Azure support, I'm now past the error.

Go into the Azure ACS Management Portal. Open Relying Party Applications, and select the relying party you have configured for this app. Make sure that the field "Realm" matches exactly what you have for Realm in the web.config under <federationConfiguration><wsFederation realm=""/>.

All you require is to setup access to ACS in Active directory
After installing powershell Azure Commandlets, run the below commands as mentioned by Andrew
Connect-MsolService
Import-Module MSOnlineExtended -Force
$replyUrl = New-MsolServicePrincipalAddresses –Address "https://xxx.accesscontrol.windows.net/"
New-MsolServicePrincipal –ServicePrincipalNames #("https://xxx.accesscontrol.windows.net/") -DisplayName "xxx ACS Namespace" -Addresses $replyUrl

In case anyone else stumbles on this, double check your realm code here:
wsFederation passiveRedirectEnabled="true" issuer="must match endpoint" realm="must match audience URI " requireHttps="true"
AND
<add key="ida:Realm" value="must match audience uri" />
<add key="ida:AudienceUri" value="must match audience uri" />
my issue was a / at the end of my URI that I added instinctively - i.e. https://somuri.com/ - whereas the portal setting was https://someuri.com
Removal of the / worked.

Related

Exception using Azure Managed Service Identity across tenants

I'm building an Azure web app for a client that will be provisioned into many other directories for their customers. This app will call a web API in my client's directory, which will then call back to another web API in the customer's directory. Something like this:
Other Customer AAD1 --------- My client AAD2
App --------------------------------> Web API 2
Web API 1 <-------------------------- Web API 2
We have been able to get the first call to work. This requires a corresponding App Registation for Web API 2 in AAD1. We figure that we could get the callback to work by following the same pattern, with a registration for Web API1 in AAD2. However, that might be a LOT of these 'proxy' registration in my client's AAD, so we're looking at alternatives.
We are exploring using Managed Service Identity, which we think will allow us to get tokens that are valid for resources in other tenants. If there's a better way, I'm certainly interested in knowing about it.
I've followed the code example from here using the Microsoft.Azure.Services.AppAuthentication library: https://learn.microsoft.com/en-us/azure/app-service/app-service-managed-service-identity#obtaining-tokens-for-azure-resources
// In Web API 2
using Microsoft.Azure.Services.AppAuthentication;
// ...
var azureServiceTokenProvider = new AzureServiceTokenProvider();
string accessToken = await azureServiceTokenProvider.GetAccessTokenAsync(
"https://<App ID URI for Web API1>");
Web API2 is configured to have a Managed Service Identity.
I'm currently running this on my local machine, and I've installed Azure CLI and I'm logged in. I've tried 'az account get-access-token', and I get a valid token.
When Web API2 tries to get the token to be able to call Web API1, I get an exception:
Parameters: Connectionstring: [No connection string specified], Resource: , Authority: . Exception Message: Tried the following 2 methods to get an access token, but none of them worked.
Parameters: Connectionstring: [No connection string specified], Resource: , Authority: . Exception Message: Tried to get token using Managed Service Identity. Unable to connect to the Managed Service Identity (MSI) endpoint. Please check that you are running on an Azure resource that has MSI setup.
Parameters: Connectionstring: [No connection string specified], Resource: , Authority: . Exception Message: Tried to get token using Azure CLI. Access token could not be acquired. ERROR: Get Token request returned http error: 400 and server response: {"error":"invalid_grant","error_description":"AADSTS65001: The user or administrator has not consented to use the application with ID '04b07795-8ddb-461a-bbee-02f9e1bf7b46' named 'Web API 1'. Send an interactive authorization request for this user and resource.\r\nTrace ID: f5bb0d4d-6f92-4fdd-81b7-e82a78720a00\r\nCorrelation ID: 04f92114-8d9d-40c6-b292-965168d6a919\r\nTimestamp: 2017-10-19 16:39:22Z","error_codes":[65001],"timestamp":"2017-10-19 16:39:22Z","trace_id":"f5bb0d4d-6f92-4fdd-81b7-e82a78720a00","correlation_id":"04f92114-8d9d-40c6-b292-965168d6a919"}
What's interesting is that there's no application with ID '04b07795-8ddb-461a-bbee-02f9e1bf7b46' in either AAD1 or AAD2. Is this a known Azure app? I thought that it might be the Service Management API, but I'm not sure.
In any case, I'm not sure of the proper way to grant permission. I've tried building different content URLs like this into my browser, but none of them seem to have done the trick:
https://login.microsoftonline.com/(AAD1 ID)/adminconsent
?client_id=(App ID)
&redirect_uri=https://localhost:44341
&resource=(App ID URI for Web API1)
&prompt=admin_consent
https://login.microsoftonline.com/(AAD1 ID)/adminconsent
?client_id=04b07795-8ddb-461a-bbee-02f9e1bf7b46
&redirect_uri=https://localhost:44341
&resource=(App ID URI for Web API1)
&prompt=admin_consent
(This last one tells me that the reply URL is incorrect; since it's not one of my apps, I can't find the reply URL)
Note that the tenant is AAD1.
Am I missing something, or am I not using this feature correctly?
Thanks in advance.
AzureServiceTokenProvider uses Azure CLI (among other options) for local development. For a scenario where a service calls an Azure Service, this works using the developer identity from Azure CLI, since Azure services allow access to both users and applications.
For a scenario where a service calls another custom service (like your scenario), you need to use a service principal for local development. For this, you have two options:
Login to Azure CLI using a service principal.
First, create a service principal for local development
https://learn.microsoft.com/en-us/cli/azure/create-an-azure-service-principal-azure-cli?view=azure-cli-latest
Then login to Azure CLI using it.
az login --service-principal -u 25922285-eab9-4262-ba61-8083533a929b --password <<pwd>> --tenant 72f988bf-86f1-41af-91ab-2d7cd011db47 --allow-no-subscriptions
Use the --allow-no-subscriptions argument since this service principal may not have access to any subscription.
Now, AzureServiceTokenProvider will get a token using this service principal for local development.
Specify service principal details in an environment variable. AzureServiceTokenProvider will use the specified service principal for local development. Please see the section Running the application using a service principal in local development environment in this sample on how to do that. https://github.com/Azure-Samples/app-service-msi-keyvault-dotnet
Note: Ths is only for local development. AzureServiceTokenProvider will use MSI when deployed to App Service.

The authentication endpoint Kerberos was not found on the configured Secure Token Service

I've encountered a challenge regarding internet-facing deployment installation for CRM using a AD FS server. After the setup is complete, users are able to access the CRM server - but when trying to run custom pages the following error message is prompted:
"The authentication endpoint Kerberos was not found on the configured Secure Token Service!"
I've found several solutions on the internet for this issue:
First I found a KB article from Microsoft providing a possible
solution, this involves updating MEX endpoints by running a provided
PowerShell script.
(https://support.microsoft.com/en-us/help/2828015/configuring-ad-fs-2.1-with-microsoft-dynamics-crm-2011).
But this doesn't seem to be the issue.
Another solution could be to update the CRM rollup version (currently have version 14 installed, latest is version 18) - this is something that I want to avoid as it might lead to further issues.
Have anybody else encountered a similar issue, and in that case how did you solve it?
I have just spent last few days to figure this exact same error message and it turned out that it was the "Domain" attribute in crm connection string. Copied my answer to my own question at the Microsoft Dynamics CRM community forum here:
"Well, I found the culprit - it was the Domain attribute in the connection string:
For connecting from outside the domain, it does not like to have a Domain in the connection string:
Connection string format 1 (without Domain attribute): "Authentication Type=Passport;Server=https://devcrm.myco.com;Username=devuser#myco.com;Password=pwd" - this works both inside and outside the domain "myco.com"
Connection string format 2 (with Domain attribute): "Authentication Type=Passport;Server=https://devcrm.myco.com;Domain=myco;Username=devuser#myco.com;Password=pwd" - this only works inside the domain myco.com but NOT outside (exception: The authentication endpoint Kerberos was not found on the configured Secure Token Service!)

The key is in the Xrm.Client.CrmConnection.ClientCredential:
If Domain is NOT specified in the connection string, when connecting from outside domain, Xrm.Client.CrmConnection.ClientCredentials.UserName is populated whereas the ClientCredentials.Windows.ClientCredentials.UserName is empty.
But if the Domain is specified, Xrm.Client.CrmConnection.ClientCredentials.UserName becomes null and Xrm.Client.CrmConnection.ClientCredentials.Windows.ClientCredentials.UserName populated, which led to the service trying to authenticate user as a Windows AD user so of course it would fail when running app from outside Windows domain. And it explains why the same app works inside the domain even with Domain specified in the connection string.
For more detail, refer here for my original post asking for help in Dynamics CRM Forum

How to specify Logout Service in the PingFederateSLOURL in mod_pf configuration

We are using PingFederate as Service Provider and are using Opentokenadapter.
We are also using mod_pf apache library provided by PingFederate.
Is there any way we can configure "Logout Service (present in OpenToken Adapter )" in the mod_pf configuration? Is there any query parameter for it just like we have for PartnerIdpId, TargetResource etc?
The Apache Integration Kit's mod_pf.conf refers to the /sp/startSLO.ping application endpoint. In that configuration file is where you will configure various bits for the integration... You can review the /sp/startSLO.ping options as listed here:
https://documentation.pingidentity.com/pingfederate/pf81/index.shtml#concept_spServices.html#concept_spServices
The "Logout Service", as defined in the adapter, is where the browser will be sent to for an SLO that will destroy any current session within the SP Application. By spec, that application must return BACK to PingFederate, so that PingFederate can respond back to the IdP with a success/fail. If you plan to support SLO, then this "service" must exist. It's "goal" will be close the session, and redirect back to PingFederate with a success.

OpenAM J2EE agent installation bringing down tomcat

OpenAM version -12 , Agent version 3.5 and 3.3 , tomcat version 7
I have tried to follow the link https://forums.alfresco.com/forum/installation-upgrades-configuration-integration/authentication-ldap-sso/sso-openam-06052012 to set up my J2EE Agent. Let me paste the steps after asking the question(see at the end)
but I am getting the error as asked below
Not able to configure J2ee agent on adding my customized data store for users
I have tried to use 3.5 version installed and uninstalled multiple times and tried previous version.
There is a nice discussion on this topic at http://database.developer-works.com/article/16009911/%22Cannot+obtain+Application+SSO+token%22+error
but it did not help me much.
I am using LDAP so I have used LDAP realm and subjects are showing up ok. Also I am observing that the policy tab has changed quite a bit from how it is described in the Blogs.
Now with the roadblock I am not sure how to proceed as the error is not giving me any clue what to do. I even added the file named AMConfig.properties in the classpath with username and password of the agent and tried the username and password of the OpenAM admin too as suggested in the discussion mentioned. but that too did not help.
The issue is the Tomcat now is not starting and giving error that AMConfig.properties properties are needed
I know the OpenAM Realm setup is good as I am able to login via this realm to another application (Liferay) where I just have to give the URL for use OpenAM integration. but after uninstallation of the agent the tomcat starts without any error and i am able to login to the application
-------------------Step copied from 1st link(modified)--------------------------
1. Configure your OpenAM agent (tried both 3.5 and 3.3 version on tomcat 7)
a. Log into OpenAM as the admin user and navigate to "Access Control -> (Your Realm) - where in my case LDAP Realm (other application using it without issue)
b. Select Policies -> New Policy
c. Enter Share as the policy name and then create 2 new URL Policy agent rules
d. 1st Resource Name = http://:/share/*
e. 2nd Resource Name = http://alfresco.domain.com:8080/share/*?*
f. Add a subjects - already part of LDAP Realm
g. Now select Agents -> J2EE - > (your J2EE agent)
h. Select the Application tab
i. Login Processing -> Login Form URI - add /share/page/dologin
j. Logout Processing -> Application Logout URL - add Map Key = share - Corresponding Map Value = /share/page/dologout
k. Not Enforced URI Processing - Add 2 entries - /share and /share/
l. Profile Attributes Processing - Select HTTP_HEADER and add Map Key = uid - Corresponding Map Value = SsoUserHeader (This is what I called my header in the alfresco-global.properties file - see below)
Auth chain
authentication.chain=external1:external,alfrescoNtlm1:alfrescoNtlm
alfresco.authentication.allowGuestLogin=true
SSO settings
external.authentication.enabled=true
external.authentication.defaultAdministratorUserNames=admin
external.authentication.proxyUserName=
external.authentication.proxyHeader=SsoUserHeader
NOTE- It does not seem possible to configure SSO where the Guest login has been disabled. There are webscripts used on the Alfresco repository that need guest login.
That concludes the setup for Alfresco and OpenAM
For Share you need to have the following section uncommented in your share-config-custom.xml
alfresco/web-extension/alfresco-system.p12
pkcs12
alfresco-system
alfrescoCookie
Alfresco Connector
Connects to an Alfresco instance using cookie-based authentication
org.alfresco.web.site.servlet.SlingshotAlfrescoConnector
alfrescoHeader
Alfresco Connector
Connects to an Alfresco instance using header and cookie-based authentication
org.alfresco.web.site.servlet.SlingshotAlfrescoConnector
SsoUserHeader
alfresco
Alfresco - user access
Access to Alfresco Repository WebScripts that require user authentication
alfrescoHeader
http://alfreso.domain.com:8080/alfresco/wcs
user
true
Notice I am not using the SSL cert and in my alfrescoHeader connector I have used SsoUserHeader (as setup in OpenAM) and the endpoint uses the alfrescoHeader connector
Now you need to add the OpenAM filter to the Share web.xml file
Add the following filter just before the Share SSO authentication support filter
Agent
com.sun.identity.agents.filter.AmAgentFilter
Add the following filter mapping to the filter-mapping section
Agent
REQUEST
INCLUDE
FORWARD
ERROR
----- End ----------
The error message is a bit misleading: the Cannot obtain application SSO token in general means that the agent was unable to authenticate itself. When you install the agent, the agent asks for a profile name and a password file, those values need to correspond to the agent profile configured within OpenAM.
To test if you can authenticate as the user, you could simply try to authenticate as the agent by making the following request:
curl -d "username=profilename&password=password&uri=realm=/%26module=Application" http://aldaris.sch.bme.hu:8080/openam/identity/authenticate
In the above command the realm value needs to be the same as the value for the "com.sun.identity.agents.config.organization.name" property defined in OpenSSOAgentBootstrap.properties (under the agent's install directory).
Having bad username/password combination is only one of the possible root causes for this exception though. It is also possible that during startup the agent was unable to connect to OpenAM to authenticate itself. In those cases the problem could be:
network error, firewall issues preventing the agent from contacting OpenAM
SSL trust issues: agent's JVM does not trust the certificate of OpenAM's container (only problem if you've installed the agent by providing OpenAM's HTTPS URL and the certificate is self-signed or just simply not trusted by the JVM)

ADFS Skip Home Realm Discovery using integrated auth

My scenario:
I've got a .net web application where people log into the app with forms authentication, and my forms authentication code sends certain users off to ADFS to be verified. I have multiple federations, including my own Active Directory server for internal users. So, for users that need to be sent to ADFS for authentication, I do something like this:
WSFederationAuthenticationModule instance = FederatedAuthentication.WSFederationAuthenticationModule;
SignInRequestMessage request = instance.CreateSignInRequest(Guid.NewGuid().ToString(), instance.Realm, true);
request.AuthenticationType = "urn:federation:authentication:windows";
//maybe you just don't need to specify the homerealm for ad, because there can only be one AD (integrated) trust?
//request.HomeRealm = "I-no-idea-what-to-put-here-for-AD";
Response.Redirect(request.WriteQueryString());
When you do this, you set the .HomeRealm property which populates the whr attribute for you on the query string. This should make AD FS skip the HRD (Home Realm Discovery) page. For most of my federations (remote STSs) it's very clear what value I need to put in the property, you can pull the value from the dropdown box on the HRD page itself, or you can go into the AD FS management tool and pull the value from the trust properties. For the AD trust, however, there is no value in the dropdown list (empty string), and you can't go to properties in the management console. So the question is really this: if I want to preselect the AD trust through the whr parameter, what do I set the HomeRealm Property to?
P.S. you'll see the comment there: "maybe you just don't need to specify the homerealm for ad, because there can only be one AD (integrated) trust?" I think this might be the case, but I haven't proved it yet. I will answer this later if my guess is correct.
From the code in the original question:
request.AuthenticationType = "urn:federation:authentication:windows";
That particular line didn't appear to have any effect. Also, the hope that no HomeRealm need be specified was also in vain. It turns out that you must, in fact, specify the HomeRealm. After searching google for some time, I found many statements hinting that the Active Directory trust was the same as trusting the ADFS server itself. So as a wild shot in the dark I tried putting in the URI of the ADFS server, and, much to my pleasure and surprise, this worked.
So, to be more clear, if you go to the web.config of the relying party you should have something set up similar to this:
<issuerNameRegistry type="System.IdentityModel.Tokens.ValidatingIssuerNameRegistry, System.IdentityModel.Tokens.ValidatingIssuerNameRegistry">
<authority name="http://testadfs.test.com/adfs/services/trust">
<keys>
<add thumbprint="XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX" />
</keys>
<validIssuers>
<add name="http://testadfs.test.com/adfs/services/trust" />
</validIssuers>
</authority>
</issuerNameRegistry>
I ended up setting the value of request.HomeRealm to the value that you see there in the validIssuers and authority elements. This gave me the desired effect of causing ADFS to automatically select the Active Directory claims provider trust.
I should be clear that my ADFS server is NOT the domain controller, and yet this still works.

Resources