Square API + OAuth2:如何将我的重定向 URL 设置到我的 iOS 应用程序?
Square API + OAuth2: How do I set my redirect URL to my iOS app?
我正尝试通过 Square 在我的 iOS 应用程序中实施 OAuth2,但它说当我通过弹出的浏览器成功登录时,我的 redirect_uri 出现错误。
我正在使用 OAuthSwift pod。这是我到目前为止设置 URL 方案的内容,以便重定向应该打开我的 iOS 应用程序:
方形仪表板配置:
AppDelegate:
class AppDelegate: UIResponder, UIApplicationDelegate {
var window: UIWindow?
func application(_ app: UIApplication, open url: URL, options: [UIApplicationOpenURLOptionsKey : Any] = [:]) -> Bool {
print("hollaaaaaaaaaaaaaaaaa") // i never see this printed
OAuthSwift.handle(url: url)
return true
}
}
目标:
打开浏览器的控制器:
class OAuthViewController: UIViewController {
@IBAction func signInButtonTapped(_ sender: AnyObject) {
print("tapped");
let oauthswift = OAuth2Swift(
consumerKey: "my token",
consumerSecret: "my secret",
authorizeUrl: "https://connect.squareup.com/oauth2/authorize?client_id=my_id",
responseType: "token"
)
oauthswift.authorize(
withCallbackURL: URL(string: "com.edmund.ios/oauth-callback")!, // doesn't seem to do anything honestly... I think the Square dashboard setting has precedence over this.
scope: "MERCHANT_PROFILE_READ%20PAYMENTS_READ%20ITEMS_READ%20ORDERS_READ",
state: "",
success: { (credential, response, parameters) -> Void in
print(credential)
},
failure: { error in
print(error.localizedDescription)
}
)
}
}
当您引导用户完成应用程序的 oauth 流程时,您必须指定一个 redirect_uri 参数,该参数与您在 Square 开发人员门户中指定的值相匹配。注意这个redirect_uri必须以http或https开头,并且对应你服务器上的一个网页。
如果您将方形端点重定向到您的服务器,如果您确定它们在 iOS 上 运行,您可以使用您的 URL 方案重新打开您的应用程序并传递任何参数你希望
可以重定向到 ios 应用吗?完全可以
在这里,我将指导您实现这一目标的简单方法。
方形 oAuth 实现可以通过 2 个简单的简单步骤实现,无需使用任何第三方库。
这种方法的好处
- 您始终停留在应用程序中(因为我们使用应用程序内浏览器)
- 无需在应用程序中添加 URI 架构(因为我们永远不会离开应用程序)
- 第 1 步:添加一个视图控制器并附加一个 WKWebview;
- 第 2 步:加载身份验证请求 URL 并侦听重定向 URI;
重定向发生后,您可以关闭控制器并继续使用访问令牌。
重定向 URI
您必须在方形仪表板中设置重定向 URI;
(Example: "http://localhost/square-oauth-callback")
但您可以自由设置任何有效的 URL。
我们在我们的应用程序中监控此 url。
在您的应用程序中实现以下代码
import Foundation
import UIKit
import WebKit
class SquareAuthenticationViewController: UIViewController {
// MARK: Connection Objects
@IBOutlet weak var webView: WKWebView!
// MARK: Life Cycle
override func viewDidLoad() {
super.viewDidLoad()
configureView()
initiateAuthentication()
}
func configureView() {
webView.navigationDelegate = self
}
func initiateAuthentication() {
// Validation
guard let url = getPath() else {
return
}
// Prepare request
let request = URLRequest(url: url)
webView.load(request)
}
func getPath() -> URL? {
let clientId = "Your Suare Application Id"
let scope = ["MERCHANT_PROFILE_READ",
"CUSTOMERS_READ",
"CUSTOMERS_WRITE",
"EMPLOYEES_READ",
"EMPLOYEES_WRITE",
"ITEMS_READ",
"PAYMENTS_READ"].joined(separator: " ")
let queryClientId = URLQueryItem(name: "client_id" , value: clientId.addingPercentEncoding(withAllowedCharacters: .urlQueryAllowed))
let queryScope = URLQueryItem(name: "scope" , value: scope.addingPercentEncoding(withAllowedCharacters: .urlQueryAllowed))
var components = URLComponents()
components.scheme = "https"
components.host = "connect.squareup.com"
components.path = "/oauth2/authorize"
components.percentEncodedQueryItems = [queryClientId, queryScope]
return components.url
}
}
extension SquareAuthenticationViewController: WKNavigationDelegate {
func webView(_ webView: WKWebView, decidePolicyFor navigationAction: WKNavigationAction, decisionHandler: @escaping (WKNavigationActionPolicy) -> Void) {
// here we handle internally the callback url and call method that call handleOpenURL (not app scheme used)
if let url = navigationAction.request.url, url.host == "localhost" , url.path == "/square-oauth-callback" {
print(url)
print(url.valueOf("code"))
//decisionHandler(.cancel)
/* Dismiss your view controller as normal
And proceed with OAuth authorization code
The code you receive here is not the auth token; For auth token you have to make another api call with the code that you received here and you can procced further
*/
/*
Auth Process Flow: https://developer.squareup.com/docs/oauth-api/how-it-works#oauth-access-token-management
Obtain Auth Token: https://developer.squareup.com/reference/square/oauth-api/obtain-token
*/
}
decisionHandler(.allow)
}
}
extension URL {
func valueOf(_ queryParamaterName: String) -> String? {
guard let url = URLComponents(string: self.absoluteString) else { return nil }
return url.queryItems?.first(where: { [=10=].name == queryParamaterName })?.value
}
}
我正尝试通过 Square 在我的 iOS 应用程序中实施 OAuth2,但它说当我通过弹出的浏览器成功登录时,我的 redirect_uri 出现错误。
我正在使用 OAuthSwift pod。这是我到目前为止设置 URL 方案的内容,以便重定向应该打开我的 iOS 应用程序:
方形仪表板配置:
AppDelegate:
class AppDelegate: UIResponder, UIApplicationDelegate {
var window: UIWindow?
func application(_ app: UIApplication, open url: URL, options: [UIApplicationOpenURLOptionsKey : Any] = [:]) -> Bool {
print("hollaaaaaaaaaaaaaaaaa") // i never see this printed
OAuthSwift.handle(url: url)
return true
}
}
目标:
打开浏览器的控制器:
class OAuthViewController: UIViewController {
@IBAction func signInButtonTapped(_ sender: AnyObject) {
print("tapped");
let oauthswift = OAuth2Swift(
consumerKey: "my token",
consumerSecret: "my secret",
authorizeUrl: "https://connect.squareup.com/oauth2/authorize?client_id=my_id",
responseType: "token"
)
oauthswift.authorize(
withCallbackURL: URL(string: "com.edmund.ios/oauth-callback")!, // doesn't seem to do anything honestly... I think the Square dashboard setting has precedence over this.
scope: "MERCHANT_PROFILE_READ%20PAYMENTS_READ%20ITEMS_READ%20ORDERS_READ",
state: "",
success: { (credential, response, parameters) -> Void in
print(credential)
},
failure: { error in
print(error.localizedDescription)
}
)
}
}
当您引导用户完成应用程序的 oauth 流程时,您必须指定一个 redirect_uri 参数,该参数与您在 Square 开发人员门户中指定的值相匹配。注意这个redirect_uri必须以http或https开头,并且对应你服务器上的一个网页。
如果您将方形端点重定向到您的服务器,如果您确定它们在 iOS 上 运行,您可以使用您的 URL 方案重新打开您的应用程序并传递任何参数你希望
可以重定向到 ios 应用吗?完全可以
在这里,我将指导您实现这一目标的简单方法。 方形 oAuth 实现可以通过 2 个简单的简单步骤实现,无需使用任何第三方库。
这种方法的好处
- 您始终停留在应用程序中(因为我们使用应用程序内浏览器)
- 无需在应用程序中添加 URI 架构(因为我们永远不会离开应用程序)
- 第 1 步:添加一个视图控制器并附加一个 WKWebview;
- 第 2 步:加载身份验证请求 URL 并侦听重定向 URI;
重定向发生后,您可以关闭控制器并继续使用访问令牌。
重定向 URI
您必须在方形仪表板中设置重定向 URI;
(Example: "http://localhost/square-oauth-callback")
但您可以自由设置任何有效的 URL。
我们在我们的应用程序中监控此 url。
在您的应用程序中实现以下代码
import Foundation
import UIKit
import WebKit
class SquareAuthenticationViewController: UIViewController {
// MARK: Connection Objects
@IBOutlet weak var webView: WKWebView!
// MARK: Life Cycle
override func viewDidLoad() {
super.viewDidLoad()
configureView()
initiateAuthentication()
}
func configureView() {
webView.navigationDelegate = self
}
func initiateAuthentication() {
// Validation
guard let url = getPath() else {
return
}
// Prepare request
let request = URLRequest(url: url)
webView.load(request)
}
func getPath() -> URL? {
let clientId = "Your Suare Application Id"
let scope = ["MERCHANT_PROFILE_READ",
"CUSTOMERS_READ",
"CUSTOMERS_WRITE",
"EMPLOYEES_READ",
"EMPLOYEES_WRITE",
"ITEMS_READ",
"PAYMENTS_READ"].joined(separator: " ")
let queryClientId = URLQueryItem(name: "client_id" , value: clientId.addingPercentEncoding(withAllowedCharacters: .urlQueryAllowed))
let queryScope = URLQueryItem(name: "scope" , value: scope.addingPercentEncoding(withAllowedCharacters: .urlQueryAllowed))
var components = URLComponents()
components.scheme = "https"
components.host = "connect.squareup.com"
components.path = "/oauth2/authorize"
components.percentEncodedQueryItems = [queryClientId, queryScope]
return components.url
}
}
extension SquareAuthenticationViewController: WKNavigationDelegate {
func webView(_ webView: WKWebView, decidePolicyFor navigationAction: WKNavigationAction, decisionHandler: @escaping (WKNavigationActionPolicy) -> Void) {
// here we handle internally the callback url and call method that call handleOpenURL (not app scheme used)
if let url = navigationAction.request.url, url.host == "localhost" , url.path == "/square-oauth-callback" {
print(url)
print(url.valueOf("code"))
//decisionHandler(.cancel)
/* Dismiss your view controller as normal
And proceed with OAuth authorization code
The code you receive here is not the auth token; For auth token you have to make another api call with the code that you received here and you can procced further
*/
/*
Auth Process Flow: https://developer.squareup.com/docs/oauth-api/how-it-works#oauth-access-token-management
Obtain Auth Token: https://developer.squareup.com/reference/square/oauth-api/obtain-token
*/
}
decisionHandler(.allow)
}
}
extension URL {
func valueOf(_ queryParamaterName: String) -> String? {
guard let url = URLComponents(string: self.absoluteString) else { return nil }
return url.queryItems?.first(where: { [=10=].name == queryParamaterName })?.value
}
}