Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@
.packages
.pub/
.dart_tool/
.build/
.swiftpm/
pubspec.lock

Podfile
Expand Down Expand Up @@ -41,4 +43,4 @@ build/

.project
.classpath
.settings
.settings
110 changes: 55 additions & 55 deletions example/lib/main.dart
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import 'package:flutter/material.dart';
import 'package:twitter_login/twitter_login.dart';


void main() {
runApp(MyApp());
Expand Down Expand Up @@ -73,77 +73,77 @@ class _MyAppState extends State<MyApp> {

/// Use Twitter API v1.1
Future login() async {
final twitterLogin = TwitterLogin(
/// Consumer API keys
apiKey: apiKey,
// final twitterLogin = TwitterLogin(
// /// Consumer API keys
// // apiKey: apiKey,

/// Consumer API Secret keys
apiSecretKey: apiSecretKey,
// /// Consumer API Secret keys
// // apiSecretKey: apiSecretKey,

/// Registered Callback URLs in TwitterApp
/// Android is a deeplink
/// iOS is a URLScheme
redirectURI: 'example://',
);
// /// Registered Callback URLs in TwitterApp
// /// Android is a deeplink
// /// iOS is a URLScheme
// redirectURI: 'example://',
// );

/// Forces the user to enter their credentials
/// to ensure the correct users account is authorized.
/// If you want to implement Twitter account switching, set [force_login] to true
/// login(forceLogin: true);
final authResult = await twitterLogin.login();
switch (authResult.status) {
case TwitterLoginStatus.loggedIn:
// success
print('====== Login success ======');
print(authResult.authToken);
print(authResult.authTokenSecret);
break;
case TwitterLoginStatus.cancelledByUser:
// cancel
print('====== Login cancel ======');
break;
case TwitterLoginStatus.error:
case null:
// error
print('====== Login error ======');
break;
}
// final authResult = await twitterLogin.login();
// switch (authResult.status) {
// case TwitterLoginStatus.loggedIn:
// // success
// print('====== Login success ======');
// print(authResult.authToken);
// print(authResult.authTokenSecret);
// break;
// case TwitterLoginStatus.cancelledByUser:
// // cancel
// print('====== Login cancel ======');
// break;
// case TwitterLoginStatus.error:
// case null:
// // error
// print('====== Login error ======');
// break;
// }
}

/// Use Twitter API v2.
Future loginV2() async {
final twitterLogin = TwitterLogin(
/// Consumer API keys
apiKey: apiKey,
// final twitterLogin = TwitterLogin(
// /// Consumer API keys
// //apiKey: apiKey,

/// Consumer API Secret keys
apiSecretKey: apiSecretKey,
// /// Consumer API Secret keys
// // apiSecretKey: apiSecretKey,

/// Registered Callback URLs in TwitterApp
/// Android is a deeplink
/// iOS is a URLScheme
redirectURI: 'example://',
);
// /// Registered Callback URLs in TwitterApp
// /// Android is a deeplink
// /// iOS is a URLScheme
// redirectURI: 'example://',
// );

/// Forces the user to enter their credentials
/// to ensure the correct users account is authorized.
/// If you want to implement Twitter account switching, set [force_login] to true
/// login(forceLogin: true);
final authResult = await twitterLogin.loginV2();
switch (authResult.status) {
case TwitterLoginStatus.loggedIn:
// success
print('====== Login success ======');
break;
case TwitterLoginStatus.cancelledByUser:
// cancel
print('====== Login cancel ======');
break;
case TwitterLoginStatus.error:
case null:
// error
print('====== Login error ======');
break;
}
// final authResult = await twitterLogin.loginV2();
// switch (authResult.status) {
// case TwitterLoginStatus.loggedIn:
// // success
// print('====== Login success ======');
// break;
// case TwitterLoginStatus.cancelledByUser:
// // cancel
// print('====== Login cancel ======');
// break;
// case TwitterLoginStatus.error:
// case null:
// // error
// print('====== Login error ======');
// break;
// }
}
}
4 changes: 0 additions & 4 deletions ios/Classes/TwitterLoginPlugin.h

This file was deleted.

15 changes: 0 additions & 15 deletions ios/Classes/TwitterLoginPlugin.m

This file was deleted.

7 changes: 3 additions & 4 deletions ios/twitter_login.podspec
Original file line number Diff line number Diff line change
Expand Up @@ -13,11 +13,10 @@ Flutter Twitter Login Plugin
s.license = { :file => '../LICENSE' }
s.author = { 'Your Company' => 'email@example.com' }
s.source = { :path => '.' }
s.source_files = 'Classes/**/*'
s.source_files = 'twitter_login/Sources/twitter_login/**/*.swift'
s.dependency 'Flutter'
s.platform = :ios, '8.0'
s.platform = :ios, '12.0'

# Flutter.framework does not contain a i386 slice. Only x86_64 simulators are supported.
s.pod_target_xcconfig = { 'DEFINES_MODULE' => 'YES', 'VALID_ARCHS[sdk=iphonesimulator*]' => 'x86_64' }
s.pod_target_xcconfig = { 'DEFINES_MODULE' => 'YES' }
s.swift_version = '5.0'
end
23 changes: 23 additions & 0 deletions ios/twitter_login/Package.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
// swift-tools-version: 5.9
import PackageDescription

let package = Package(
name: "twitter_login",
platforms: [
.iOS("12.0")
],
products: [
.library(name: "twitter-login", targets: ["twitter_login"])
],
dependencies: [
.package(name: "FlutterFramework", path: "../FlutterFramework")
],
targets: [
.target(
name: "twitter_login",
dependencies: [
.product(name: "FlutterFramework", package: "FlutterFramework")
]
)
]
)
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,8 @@ import UIKit
import SafariServices
import AuthenticationServices

public class SwiftTwitterLoginPlugin: NSObject, FlutterPlugin, ASWebAuthenticationPresentationContextProviding {
var session: Any? = nil
public class SwiftTwitterLoginPlugin: NSObject, FlutterPlugin, ASWebAuthenticationPresentationContextProviding {
var session: Any?

public static func register(with registrar: FlutterPluginRegistrar) {
let channel = FlutterMethodChannel(
Expand All @@ -17,61 +17,68 @@ public class SwiftTwitterLoginPlugin: NSObject, FlutterPlugin, ASWebAuthenticati

public func handle(_ call: FlutterMethodCall, result: @escaping FlutterResult) {
switch call.method {
case "authentication":
authentication(call, result: result)
default:
result(nil)
return
case "authentication":
authentication(call, result: result)
default:
result(nil)
}
}

public func authentication(_ call: FlutterMethodCall, result: @escaping FlutterResult) {
let args = call.arguments as! NSDictionary
let url = args["url"] as! String
guard
let args = call.arguments as? NSDictionary,
let urlString = args["url"] as? String,
let url = URL(string: urlString)
else {
result(nil)
return
}
let urlScheme = args["redirectURL"] as? String

// iOS12以降

if #available(iOS 12.0, *) {
var authSession: ASWebAuthenticationSession?
authSession = ASWebAuthenticationSession(
url: URL(string: url)!,
url: url,
callbackURLScheme: urlScheme
) { url, error in
result(url?.absoluteString)
authSession!.cancel()
authSession?.cancel()
self.session = nil
}
self.session = authSession
if #available(iOS 13.0, *) {
authSession?.presentationContextProvider = self
}
if !authSession!.start() {
// TODO: failed
if authSession?.start() != true {
result(nil)
}
// iOS11のみ
} else if #available(iOS 11.0, *) {
var authSession: SFAuthenticationSession?
authSession = SFAuthenticationSession(
url: URL(string: url)!,
url: url,
callbackURLScheme: urlScheme
) { url, error in
result(url?.absoluteString)
authSession!.cancel()
authSession?.cancel()
self.session = nil
}
self.session = authSession
if !authSession!.start() {
// TODO: failed
if authSession?.start() != true {
result(nil)
}
} else {
// iOS10以前は未対応
result("")
return
}
}

@available(iOS 12.0, *)
public func presentationAnchor(for session: ASWebAuthenticationSession) -> ASPresentationAnchor {
return UIApplication.shared.delegate!.window!!
if #available(iOS 13.0, *) {
return UIApplication.shared.connectedScenes
.compactMap { $0 as? UIWindowScene }
.flatMap { $0.windows }
.first { $0.isKeyWindow } ?? UIWindow()
}
return UIApplication.shared.keyWindow ?? UIWindow()
}
}
21 changes: 7 additions & 14 deletions lib/entity/auth_result.dart
Original file line number Diff line number Diff line change
@@ -1,42 +1,35 @@
import 'dart:core';

import 'package:twitter_login/entity/user.dart';
import 'package:twitter_login/src/twitter_login.dart';

/// The result when the Twitter login flow has completed.
/// The login methods always return an instance of this class.
class AuthResult {

/// constructor
AuthResult({
String? authToken,
String? authTokenSecret,
String? authVerifier,
required TwitterLoginStatus status,
String? errorMessage,
User? user,
}) : _authToken = authToken,
_authTokenSecret = authTokenSecret,
_authVerifier = authVerifier,
_status = status,
_errorMessage = errorMessage,
_user = user;
_errorMessage = errorMessage;

/// The access token for using the Twitter APIs
final String? _authToken;

//// The access token secret for using the Twitter APIs
final String? _authTokenSecret;
/// The access token secret for using the Twitter APIs
final String? _authVerifier;

/// The status after a Twitter login flow has completed
final TwitterLoginStatus? _status;

/// The error message when the log in flow completed with an error
final String? _errorMessage;

/// Twitter Account user Info.
final User? _user;

String? get authToken => _authToken;
String? get authTokenSecret => _authTokenSecret;
String? get authVerifier => _authVerifier;
TwitterLoginStatus? get status => _status;
String? get errorMessage => _errorMessage;
User? get user => _user;
}
Loading