Google login oauth integration doesn't work in Windows PWA app - windows

I have developed a PWA application with google and microsoft oauth login integration.Now I want the PWA application to run as windows PWA app in windows mobile and desktop applications, so I tried registering the app using AppX as stated in the following link, https://blogs.windows.com/msedgedev/2018/02/06/welcoming-progressive-web-apps-edge-windows-10/#R6xvoOyZeLza5oGW.97
and ran the application in development mode using PowerShell in windows 10 OS version, the microsoft login works great, However when I try to login using google the application starts loading and exits after some time.[the popup to show the login window also doesn't come up].
Could anyone throw a light on what's happening ?.I researched but I couldn't get any solutions.
Edit
The following API is used for login with google, in the client[react]
gapi.load('auth2', () => {
this.auth2 = gapi.auth2.init({
client_id: constant.CLIENT_ID,
cookie_policy: 'single_host_origin',
scope: constant.SCOPE,
});
});
loginWithGoogle = () => {
const options = {
scope: constant.SCOPE,
};
options.prompt = 'select_account';
this.provider = 'google';
this.auth2.grantOfflineAccess(options).then((data) => {
this.loginUser(data.code);
});
}

Maybe is because your browser´s popup blocker, anyway you could use redirection instead popup mode, using ux_mode option (you have to configure the redirection url on OAuth 2.0 client IDs options)
gapi.load('auth2', () => {
this.auth2 = gapi.auth2.init({
ux_mode: 'redirect',
client_id: constant.CLIENT_ID,
cookie_policy: 'single_host_origin',
scope: constant.SCOPE,
});
});

Related

Azure/Msal authentication inside PowerApp Component Framework returns AADSTS50177 error

I created a simple PowerApps Component Framework using the pac pcf init command.
After successfully packaging and importing this skeleton PCF application to my demo tenant I tried to add MSAL authentication to it.
I used the #azure/msal npm package to write a typescript configuration and login without adding React or Angular npm packages. I only used #azure/msal and package added during the pcf create process.
The final goal was to use the token received from the msal authentication make a request on a authorized method in my Wep Api.
The problem is that my Web Api is not located in my demo tenant and the user that is used for msal authentication is from the demo tenant and does not exist on the tenant of my Web Api.
I cannot change the login user in the popup window as it only displays the error message, and the guest user that was added to the demo tenant, that has access to the Web API cannot have Certificates added to it through portal azure or portal office admin center pages.
This is my login configuration(I will omit the tenant names and client id for the work tenant):
import { AuthenticationParameters, Configuration, UserAgentApplication } from '#azure/msal';
import { AuthOptions, CacheOptions, FrameworkOptions } from "#azure/msal/lib-commonjs/Configuration";
public init(context: ComponentFramework.Context<IInputs>, notifyOutputChanged: () => void, state: ComponentFramework.Dictionary, container:HTMLDivElement)
{
// Add control initialization code
const auth: AuthOptions = {
clientId:'clientid',
authority:'https://login.microsoftonline.com/tenantid',
redirectUri:'redirect uri',
validateAuthority: true
};
const cache: CacheOptions = {
cacheLocation:"localStorage"
};
const framework: FrameworkOptions = {
protectedResourceMap: new Map([
['web api url',['https://tenantid/clientid/uniquename (scope)']],
['CRM work sandbox',['CRM work sandbox user impersonation permission(scope)']]
]),
unprotectedResources:[]
};
const config: Configuration = {
auth: auth,
cache: cache,
framework: framework
};
const params: AuthenticationParameters = {
authority: 'https://login.microsoftonline.com/tenantid',
scopes:['offline_access',
'https://tenantid/clientid/uniquename(scope)',
'CRM work sandbox user impersonation permission(scope)'],
redirectUri:'web api redirect uri'
};
const userAgentApplication = new UserAgentApplication(config);
const login = userAgentApplication.loginPopup(params).then(data => {
console.log(data);
let user = userAgentApplication.getAccount();
console.log(user);
if (user) {
// signin successful
console.log('success');
} else {
// signin failure
console.log('fail');
}
}, function (error: string) {
// handle error
console.log('Error' + error);
});
}
The error message displayed:
AADSTS50177: User account 'user name' from identity provider
'https://sts.windows.net/guid/' does not exist in tenant 'name'
and cannot access the application 'client id'(name of registered
app in portal azure) in that tenant. The account needs to be
added as an external user in the tenant first. Sign out and
sign in again with a different Azure Active Directory user account.
Is there a way to test this without adding the pcf or account in my work tenant ?

grantOfflineAccess is not working with scope

I am using google API's in my angular 8 website. I have to integrate Google Drive and YouTube account on different buttons.
YouTube Connect button
Google Drive Connect button
I init gapi as
initGoogleAccounts() {
gapi.load('auth2', () => {
this.googleUser = gapi.auth2.init({
client_id: this.env.google_client_id,
fetch_basic_profile: false,
scope: 'profile'
});
});
}
On Youtube button click
this.googleUser.grantOfflineAccess('https://www.googleapis.com/auth/youtube.force-ssl').then(({code}) => {
this.youtubeCodeConnect(code);
});
But this is not asking for Youtube permissions.
Is there anything which i am doing wrong?

Single sign on in Teams application between tabs and the bot

Using the Bot Framework w/ Microsoft.Bot.Builder v4.6.3
Is it possible to have users sign in only once using the web-based authentication flow, doesn't matter if they sign in via tabs or via bot conversation? If they sign in via a link from a tab, I'd like to have the bot know about this.
I have tried the following for test, omitting any security checks:
All pages are with the following js files imported:
https://statics.teams.microsoft.com/sdk/v1.4.2/js/MicrosoftTeams.min.js
https://cdnjs.cloudflare.com/ajax/libs/oidc-client/1.9.1/oidc-client.min.js
On load, the tab page executes microsoftTeams.initialize();
Add a button to the tab page:
<button onclick="authenticate()">Authenticate</button>
The authenticate function contains the following:
function authenticate() {
microsoftTeams.authentication.authenticate({
url: window.location.origin + "/tabs/tabAuthStart",
width: 600,
height: 535,
successCallback: function (result) {
// The debug function just displays what's sent to it using document.write()
debug(result);
},
failureCallback: function (reason) {
debug(reason);
}
});
}
The tabAuthStart page contains the following script which is executed on page load:
microsoftTeams.initialize();
const mgr = new Oidc.UserManager({
userStore: new Oidc.WebStorageStateStore(),
authority: '<my-identity-server>',
client_id: '<my-id-srv-client>',
redirect_uri: window.location.origin + '/tabs/tabAuthCallback',
response_type: 'id_token token',
scope: '<my-requested-scopes>',
accessTokenExpiringNotificationTime: 10,
automaticSilentRenew: true,
filterProtocolClaims: true,
loadUserInfo: true
});
mgr.signinRedirect();
After a successful sign in at the identity provider, I'm redirected back to /tabs/tabAuthCallback
On load, the /tabs/tabAuthCallback executes the following code:
microsoftTeams.initialize();
var mgr = new Oidc.UserManager({ userStore: new Oidc.WebStorageStateStore(), loadUserInfo: true, filterProtocolClaims: true });
mgr.signinRedirectCallback().then(function (user) {
// I expected something involving a bot to happen after calling this
microsoftTeams.authentication.notifySuccess({
idToken: user.id_token,
accessToken: user.access_token,
tokenType: user.token_type,
expiresIn: user.expires_at
})
}).catch(function (err) {
microsoftTeams.authentication.notifyFailure("UnexpectedFailure: " + err);
});
The pop-up window is closed and the successCallback function from the tab is executed successfully with the user information that I have sent. However, the bot is not in any way notified about this (as far as I know). I have set a breakpoint in the bot controller action resolved by POST /api/messages but it's never hit.
Do I need to handle this manually? I.e. pass the user info to the back-end? But even if so, how do I know which Teams user to associate this user info (i.e. access token) to?
If this is possible to do in a reliable and secure way, would it also be possible in the opposite direction, i.e. having the user token available to the tab if they have already been authenticated from a bot conversation or a messaging extension? Is there a reliable way to identify a Teams user who's navigating tabs, in order to obtain their access token from the back-end, assuming the back-end already obtained them via the authentication mechanism?

Google authentication with Angular2 and ASP.NET core Web API app

I'm creating an web application in Angular2 and i'd like to use Google for the user to login and use the application. Basically, once the user is logged in with Google, he will navigate in the site and make some AJAX call via Angular to the ASP.NET Core Web API.
In my mind, I though that all these calls should contain a JWT (issued by Google) and the ASP.NET Core Web Api would validate the token and then process the request if the token is valid. Simple enough... However, I'm struggling to find out how this could be achieved. All I found is posts talking about how to login via Google in order to use Google APIs. In my case, I don't need any Google API but the login one.
So far, I have this:
export class GoogleAuthenticationService {
private auth: any;
constructor(private userService: UserService) {
}
public bindLoginButton(element: any) {
this.ensureApiIsLoaded().then(() => {
this.auth.attachClickHandler(element, {}, (user) => {
let profile = user.getBasicProfile();
this.userService.set(profile.getName(), profile.getEmail(), user.getAuthResponse().id_token, AuthenticationType.Google);
});
});
}
// TODO: Better type definition of the promise
private ensureApiIsLoaded() {
return new Promise((resolve, reject) => {
gapi.load('auth2', () => {
this.auth = gapi.auth2.init({
client_id: "CLIENT_ID",
cookiepolicy: 'single_host_origin',
scope: 'profile email'
});
resolve();
});
});
}
}
Basically, I'm just initializing "gapi" with my client ID, then I define some properties in the "UserService". This works pretty well. Moreover, I'm using the value returned by user.getAuthResponse().id_token for every call to my web service (I did this following this article). The next step was to try and validate the token in C# (like the sample in Java) but I didn't find any valid resources talking about that and the class used in the Java code does not exists in C#...
Is it that complicated or am I just on the wrong path and this is totally not how the web application is supposed to work. Could someone give me some pointers about this scenario that is, according to me, quite common.

Google Sign-In gives error when swiching to secondary Youtube accounts

I am currently trying to use gapi.auth2 from Google Sign-In for Websites API and this is the code I have:
-- load the library with:
<script src="https://apis.google.com/js/platform.js?onload=onLoadGapiCallback" async defer></script>
-- initialize an auth2 variable:
var auth2;
window.onLoadGapiCallback = () => {
gapi.load('auth2', () => {
auth2 = gapi.auth2.init({
'client_id': 'CLIENT_ID',
'scope': 'profile email https://www.googleapis.com/auth/youtube.readonly'
});
});
};
-- and when a botton is clicked do:
auth2.signIn().then(() => {
console.log('auth is:', auth2.currentUser.get().getAuthResponse().access_token);
});
This works well, it initializes the auth2 variable, when I click the button, it shows the SingIn prompt and I choose one of my Google Accounts. The problem is from now on when I have to choose a YouTube account, if I choose other account than the main one, I'll get an Exception Object like this one:
{type: "tokenFailed", idpId: "google", error: "USER_LOGGED_OUT"}
also there's an XHR request being sent lastly that has this response:
{"error":"USER_LOGGED_OUT","detail":"No active session found."}
So it only works if I choose the main account, but I cannot choose other YouTube accounts.
What am I missing here?
I've looked into all these docs but none helped me:
Getting profile information
Google Sign-In JavaScript client reference
Monitoring the user's session state
Update:
Running the code from this example (but with this scope: 'profile email https://www.googleapis.com/auth/youtube.readonly') will only work if I choose the first Youtube account for each Google account. If I choose any other Youtube account, I'll get this alert error:

Resources