Azure Graph Api - Change Password does not work - c#

I have the following code in order to update the password profile on azure:
ActiveDirectoryClient client = AuthenticationHelper.GetActiveDirectoryClient();
IUser toUpdate = await client.Users.GetByObjectId(user.ObjectId).ExecuteAsync();
toUpdate.PasswordProfile = new PasswordProfile()
{
ForceChangePasswordNextLogin = false,
Password = password
};
toUpdate.UpdateAsync().Wait();
Apparently I am able to change the user password in Azure (Cloud) but it is not write back to local Active Directory. I have reviewed the settings in Azure Coennect and the PasswordWriteBack option is checked.

Before you can enable and use the Password Writeback, you must make sure you complete the following prerequisites:
You have an Azure AD tenant with Azure AD Premium enabled
Password reset has been configured and enabled in your tenant
Please refer the document here about the detail of PasswordWriteBack.

Related

ChangePassword operation throws exception "Unsupported User Type 'Unknown'" in GraphAPI

Users are registered using Active Directory B2C workflows so they appear as Members
What I am trying to do is to change users passwords like explained here
So my code looks like following:
var options = new TokenCredentialOptions
{
AuthorityHost = AzureAuthorityHosts.AzurePublicCloud
};
var userNamePasswordCredential = new UsernamePasswordCredential(
email, currentPassword, "my tenant id", "my client id", options);
var authentication = await userNamePasswordCredential.AuthenticateAsync();
var scopes = new[] { "User.Read" };
var graphClient = new GraphServiceClient(userNamePasswordCredential, scopes);
var user = await graphClient.Me
.Request()
.GetAsync();
await graphClient.Me
.ChangePassword(currentPassword, newPassword)
.Request()
.PostAsync();
I have tried multiple things but I always get the same exception:
The exception is the following:
MsalClientException: Unsupported User Type 'Unknown'. Please see
https://aka.ms/msal-net-up.
AuthenticationFailedException: UsernamePasswordCredential
authentication failed: Unsupported User Type 'Unknown'. Please see
https://aka.ms/msal-net-up.
So my question is, is it possible to auto change the password for users registered in ADB2C?
If so, what is causing the exception?
I know I can change password of users updating PasswordProfile as admin but I want to somehow verify they know their current password.
You cannot use an Azure AD B2C account to authenticate to Microsoft Graph API.
You must create a normal Azure AD Account from the AAD Users blade in the Azure Portal for this operation. Which means, this will not work for B2C users at all.
For Change Password flows, create a self service change-password flow that users can go through themselves.
Or, you must create an API endpoint which the B2C protected application can call. And the API must use client_credentials flow to call Graph API and perform the Update User operation on the password profile.

Unable to get access token from Google for Service Account

I'm trying to configure an application able to work with Gmail API. As you know to work with it we must have an access token. There are several way of requesting this token, but for my needs it should be a service account, because in future this program code will be inside the Windows Service... (so, there is no opportunity to receive the token manually by redirecting from Google URL, only a web-request and response is a way out)
So, what I have done already:
Created new project (in Google Cloud Platform);
Created new service account in this project (according to the steps mentioned here: https://developers.google.com/identity/protocols/oauth2/service-account#creatinganaccount );
Generated and downloaded *.P12 key;
Enabled domain-wide delegation [before step 4 as were suggested in many similar questions];
Authorized the scope "https://mail.google.com/" in G Suite admin account for correct Client Id (according to the steps mentioned here: https://developers.google.com/identity/protocols/oauth2/service-account#delegatingauthority );
Used such simple code for authorization and requesting token:
const string serviceAccountEmail = "***test#oauthtester-271011.iam.gserviceaccount.com";
const string serviceAccountCertPath = #"C:\Users\user\Documents\Visual Studio 2017\Projects\OAuthTester\OAuthTester\bin\Debug\oauthtester-271011-bd2cced31ea5.p12";
const string serviceAccountCertPassword = "notasecret";
const string userEmail = "***oauthtest#***.com";
X509Certificate2 certificate = new X509Certificate2(
serviceAccountCertPath,
serviceAccountCertPassword,
X509KeyStorageFlags.Exportable);
ServiceAccountCredential credential = new ServiceAccountCredential(
new ServiceAccountCredential.Initializer(serviceAccountEmail)
{
Scopes = new[] { GoogleScope.ImapAndSmtp.Name }, //"https://mail.google.com/"
User = userEmail
}.FromCertificate(certificate));
credential.RequestAccessTokenAsync(CancellationToken.None).Wait();
Unfortunately, I'm facing with an error:
Client is unauthorized to retrieve access tokens using this method, or client not authorized for any of the scopes requested.
I have also tried:
To change serviceAccountEmail to ClientId;
To create, remove and add again the Authorized access in G Suite for the same Client Id;
To delete and create another service account and then Authorize new Client Id in G Suite.
Unfortunately, each time I'm facing with the same error. Maybe somebody guesses what I do wrong?

Azure REST Api Authentication using C#

I would like to be able to get information about one of my Azure SQL databases using this call: https://learn.microsoft.com/en-gb/rest/api/sql/manageddatabases/manageddatabases_get
When I use the Try It button and login to my account it works perfectly, however I can't get my C# function app to get an authentication token so it can work in C#. I've spent 3 days on this. I have tried the Keyvault way but haven't managed to set up the permissions correctly. Forgetting Keyvault, the nearest I've got I think is by using this code but I don't know what my app password is:
// I am using:
// tenant id is the Azure AD client id
// client id is the application id of my function app in Azure AD
public static string GetAccessToken(string tenantId, string clientId, string clientSecret)
{
var authContextUrl = "https://login.windows.net/" + tenantId;
var authenticationContext = new AuthenticationContext(authContextUrl);
var credential = new ClientCredential(clientId, clientSecret );
var result = authenticationContext.AcquireTokenAsync(resource: "https://management.azure.com/", clientCredential: credential).Result;
if (result == null)
{
throw new InvalidOperationException("Failed to obtain the JWT token");
}
var token = result.AccessToken;
return token;
}
When I use the Try It button and login to my account it works perfectly
When you click the Try it, you use the user credential with username and user_password to authenticate. And the code you provided is using App registered in Azure AD to authenticate, and it would work well with the following steps you have followed.
1.As silent said, you need to create a Service Principle in Azure Active Directory. You could refer to this article.
2.The Sign in value about TenantId, clientId and clientSecret you could refer to this link.
3.Finally, you would access to Azure SQL Database, you need to add permission to you Azure AD App. Click the App you registered in Azure AD before and click Settings, and add Require Permission. After adding API access, Grant Permission.
I found an answer that worked for me (after 3 days of trying different things and trying to read articles about it on the web - its not very well documented I don't think).
This link contains some powershell steps:
https://msftstack.wordpress.com/2016/01/03/how-to-call-the-azure-resource-manager-rest-api-from-c/
These are the steps I tried in PowerShell
Login-AzureRmAccount
Get-AzureRmSubscription
Select-AzureRmSubscription –SubscriptionID “id”
$SecurePassword=ConvertTo-SecureString <my password> –asplaintext –force
$azureAdApplication = New-AzureRmADApplication -DisplayName “my ARM App” -HomePage
“https://<a home page>” -IdentifierUris “https://<a home page>” -Password $SecurePassword
New-AzureRmADServicePrincipal -ApplicationId $azureAdApplication.ApplicationId
New-AzureRmRoleAssignment -RoleDefinitionName Contributor -ServicePrincipalName $azureAdApplication.ApplicationId
Get-AzureRmSubscription
$subscription = Get-AzureRmSubscription –SubscriptionId "id"
$creds=get-credential
(enter application id and password at this point)
Login-AzureRmAccount -Credential $creds -ServicePrincipal -Tenant $subscription.TenantId

EWS Use credentials from logged in user

I have a ASP MVC web application which uses Form Authentication. Users Have to log in with their AD username and password. I only store the AD username in a cookie not the password.
In this application users need to add contacts to outlook. I'm using EWS and the code works perfectly if I use my own AD username and password.
Code sample:
var eS = new ExchangeService
{
Credentials = new WebCredentials("Username", "Password", "Domain"),
TraceEnabled = true,
};
eS.AutodiscoverUrl("email");
var contact = new Microsoft.Exchange.WebServices.Data.Contact(eS)
{
GivenName = "Nanou",
Surname = "Ponette",
};
contact.PhoneNumbers[PhoneNumberKey.BusinessPhone] = "00000000000";
contact.Save();
The question I have is how can I make this work for every user that logs in?
You should be able to use Impersonation and Kerberos delegation see http://blogs.msdn.com/b/emeamsgdev/archive/2012/11/05/exchange-web-services-from-a-web-application-using-windows-authentication.aspx which has a sample for what you need to do.
Cheers
Glen

Authenticate user by ADFS (Active Directory Federation Service)

I need to check whether particular user exist OR not in Active Directory by ADFS.
So, I want my ADFS to check user Authentication by UserName/Password.
Could anybody please provide the sample code OR tutorial for the same.
Thanks in advance!
To use Username/Password authentication you can use the
trust/13/UsernameMixed
endpoint of the ADFS 2.0.
This does NOT check if the user exists in the Active Directory!
In code you request the token like this:
WSTrustChannelFactory adfsfactory = new WSTrustChannelFactory(new UserNameWSTrustBinding(SecurityMode.TransportWithMessageCredential),
StsEndpoint);
adfsfactory.TrustVersion = TrustVersion.WSTrust13;
// Username and Password here...
factory.Credentials.UserName.UserName = "domain\username";
factory.Credentials.UserName.Password = "password";
IWSTrustChannelContract channel = adfsfactory.CreateChannel();
// request the token
SecurityToken token = channel.Issue(rst);
Then create the channel factory for your service using your token:
var binding = new WS2007FederationHttpBinding(WSFederationHttpSecurityMode.Message);
var factory = new ChannelFactory<IYourInterface >(binding, "your service address");
factory.ConfigureChannelFactory();
IYourInterface channel = factory.CreateChannelWithIssuedToken(token);
Hope this helps!
The AD FS 2.0 sign-in pages support username/password authentication out of the box. No code or customizations necessary.
As per #Marnix, this is out the box behavior.
However, just to point out:
Authenticating the user is NOT the same as checking whether a particular user exists in Active Directory.
e.g. the user could be locked out. He still exists in AD but will not be able to authenticate.

Categories