tôi sau bài viết này trên Logins xã hội với AngularJS và ASP.Net WebAPI (đó là khá tốt):AngularJS và ASP.Net WebAPI Đăng nhập xã hội trên một trình duyệt di động
ASP.NET Web API 2 external logins with Facebook and Google in AngularJS app
Khá nhiều, mã hoạt động tốt khi bạn đang chạy đăng nhập xã hội thông qua trình duyệt trên máy tính để bàn (ví dụ: Chrome, FF, IE, Edge). Đăng nhập xã hội mở trong cửa sổ mới (không phải tab) và bạn có thể sử dụng tài khoản Google hoặc Facebook của mình và sau khi đăng nhập qua bất kỳ tài khoản nào, bạn được chuyển hướng đến trang gọi lại (authComplete.html) và trang gọi lại có tệp JS được định nghĩa (authComplete.js) sẽ đóng cửa sổ và thực hiện lệnh trên cửa sổ chính.
bộ điều khiển angularJS trong đó kêu gọi url đăng nhập bên ngoài và mở ra một cửa sổ popup (không tab) trên các trình duyệt máy tính để bàn:
loginController.js
'use strict';
app.controller('loginController', ['$scope', '$location', 'authService', 'ngAuthSettings', function ($scope, $location, authService, ngAuthSettings) {
$scope.loginData = {
userName: "",
password: "",
useRefreshTokens: false
};
$scope.message = "";
$scope.login = function() {
authService.login($scope.loginData).then(function (response) {
$location.path('/orders');
},
function (err) {
$scope.message = err.error_description;
});
};
$scope.authExternalProvider = function (provider) {
var redirectUri = location.protocol + '//' + location.host + '/authcomplete.html';
var externalProviderUrl = ngAuthSettings.apiServiceBaseUri + "api/Account/ExternalLogin?provider=" + provider
+ "&response_type=token&client_id=" + ngAuthSettings.clientId
+ "&redirect_uri=" + redirectUri;
window.$windowScope = $scope;
var oauthWindow = window.open(externalProviderUrl, "Authenticate Account", "location=0,status=0,width=600,height=750");
};
$scope.authCompletedCB = function (fragment) {
$scope.$apply(function() {
if (fragment.haslocalaccount == 'False') {
authService.logOut();
authService.externalAuthData = {
provider: fragment.provider,
userName: fragment.external_user_name,
externalAccessToken: fragment.external_access_token
};
$location.path('/associate');
}
else {
//Obtain access token and redirect to orders
var externalData = { provider: fragment.provider, externalAccessToken: fragment.external_access_token };
authService.obtainAccessToken(externalData).then(function (response) {
$location.path('/orders');
},
function (err) {
$scope.message = err.error_description;
});
}
});
}
}]);
authComplete.html
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<title></title>
</head>
<body>
<script src="scripts/authComplete.js"></script>
</body>
</html>
authComplete.js
window.common = (function() {
var common = {};
common.getFragment = function getFragment() {
if (window.location.hash.indexOf("#") === 0) {
return parseQueryString(window.location.hash.substr(1));
} else {
return {};
}
};
function parseQueryString(queryString) {
var data = {},
pairs, pair, separatorIndex, escapedKey, escapedValue, key, value;
if (queryString === null) {
return data;
}
pairs = queryString.split("&");
for (var i = 0; i < pairs.length; i++) {
pair = pairs[i];
separatorIndex = pair.indexOf("=");
if (separatorIndex === -1) {
escapedKey = pair;
escapedValue = null;
} else {
escapedKey = pair.substr(0, separatorIndex);
escapedValue = pair.substr(separatorIndex + 1);
}
key = decodeURIComponent(escapedKey);
value = decodeURIComponent(escapedValue);
data[key] = value;
}
return data;
}
return common;
})();
var fragment = common.getFragment();
window.location.hash = fragment.state || '';
window.opener.$windowScope.authCompletedCB(fragment);
window.close();
Vấn đề tôi đang gặp là khi tôi chạy các ứng dụng trên thiết bị di động (Safari, Chrome for Mobile), cửa sổ đăng nhập xã hội sẽ mở trong một tab mới và chức năng JS mà được dự định để vượt qua trở lại mảnh vỡ đến cửa sổ ứng dụng chính không thực hiện nad tab mới không đóng.
Bạn thực sự có thể thử hành vi này trên cả hai máy tính để bàn và trình duyệt di động thông qua ứng dụng:
http://ngauthenticationapi.azurewebsites.net/
Những gì tôi đã cố gắng cho đến nay trong bối cảnh này là trong bộ điều khiển đăng nhập, tôi sửa đổi chức năng để rằng url đăng nhập bên ngoài mở ra trong cùng một cửa sổ:
$scope.authExternalProvider = function (provider) {
var redirectUri = location.protocol + '//' + location.host + '/authcomplete.html';
var externalProviderUrl = ngAuthSettings.apiServiceBaseUri + "api/Account/ExternalLogin?provider=" + provider
+ "&response_type=token&client_id=" + ngAuthSettings.clientId
+ "&redirect_uri=" + redirectUri;
window.location = externalProviderUrl;
};
Và sửa đổi chức năng authComplete.js common.getFragment để trở về trang đăng nhập, bằng cách thêm các thẻ truy cập được cung cấp bởi các xã hội đăng nhập như là chuỗi truy vấn:
common.getFragment = function getFragment() {
if (window.location.hash.indexOf("#") === 0) {
var hash = window.location.hash.substr(1);
var redirectUrl = location.protocol + '//' + location.host + '/#/login?ext=' + hash;
window.location = redirectUrl;
} else {
return {};
}
};
Và trong bộ điều khiển đăng nhập, tôi đã thêm một chức năng để phân tích các chuỗi truy vấn và cố gắng gọi $ scope.authCompletedCB (fragment) chức năng như:
var vm = this;
var fragment = null;
vm.testFn = function (fragment) {
$scope.$apply(function() {
if (fragment.haslocalaccount == 'False') {
authenticationService.logOut();
authenticationService.externalAuthData = {
provider: fragment.provider,
userName: fragment.external_user_name,
externalAccessToken: fragment.external_access_token
};
$location.path('/associate');
}
else {
//Obtain access token and redirect to orders
var externalData = { provider: fragment.provider, externalAccessToken: fragment.external_access_token };
authenticationService.obtainAccessToken(externalData).then(function (response) {
$location.path('/home');
},
function (err) {
$scope.message = err.error_description;
});
}
});
}
init();
function parseQueryString(queryString) {
var data = {},
pairs, pair, separatorIndex, escapedKey, escapedValue, key, value;
if (queryString === null) {
return data;
}
pairs = queryString.split("&");
for (var i = 0; i < pairs.length; i++) {
pair = pairs[i];
separatorIndex = pair.indexOf("=");
if (separatorIndex === -1) {
escapedKey = pair;
escapedValue = null;
} else {
escapedKey = pair.substr(0, separatorIndex);
escapedValue = pair.substr(separatorIndex + 1);
}
key = decodeURIComponent(escapedKey);
value = decodeURIComponent(escapedValue);
data[key] = value;
}
return data;
}
function init() {
var idx = window.location.hash.indexOf("ext=");
if (window.location.hash.indexOf("#") === 0) {
fragment = parseQueryString(window.location.hash.substr(idx));
vm.testFn(fragment);
}
}
Nhưng rõ ràng này đem lại cho tôi một lỗi liên quan đến góc (mà tôi không có đầu mối tại thời điểm này):
https://docs.angularjs.org/error/$rootScope/inprog?p0=$digest
vì vậy, khá nhiều đó là một ngõ cụt đối với tôi ở giai đoạn này.
Bất kỳ ý tưởng hoặc đầu vào nào sẽ được đánh giá cao.
Gracias!
Cập nhật: Tôi đã quản lý để giải quyết lỗi Góc về rootscope bị ném, nhưng thật đáng buồn, giải quyết vấn đề đó không khắc phục được vấn đề chính. Nếu tôi cố mở thông tin đăng nhập xã hội trên cùng một tab trình duyệt nơi ứng dụng của tôi, Google có thể đăng nhập và quay lại ứng dụng và chuyển mã thông báo bắt buộc. Đó là một câu chuyện khác cho Facebook, nơi trong bảng điều khiển công cụ của nhà phát triển, có một cảnh báo dường như ngăn Facebook hiển thị trang đăng nhập.
Khá nhiều, phương pháp ban đầu mà cửa sổ mới (hoặc tab) được mở là con đường phía trước nhưng việc sửa lỗi tương tự cho trình duyệt di động dường như đang trở nên khó khăn hơn.
tôi sẽ dành thời gian để kiểm tra này ra sau đó vào ngày . – Batuta
Bạn không cần, 'localStorage' là một phần của HTML5 API trong trình duyệt, trên thực tế là trên cửa sổ', bạn có thể truy cập nó từ bất cứ nơi nào bằng cách sử dụng 'window.localStorage' – udidu
Chỉ cần thử điều này ngay bây giờ và tôi đang nhận được một số lỗi rootscope Lỗi: $ rootScope: inprog Hành động đã được tiến hành – Batuta