Tài liệu này trình bày cách tích hợp Outline SDK vào các ứng dụng di động của bạn, tập trung vào thư viện MobileProxy để đơn giản hoá việc quản lý proxy cục bộ.
MobileProxy là một thư viện dựa trên Go, được thiết kế để đơn giản hoá việc tích hợp các chức năng của proxy vào ứng dụng di động. Nó sử dụng Go Mobile để tạo các thư viện di động, cho phép bạn định cấu hình các thư viện mạng của ứng dụng để định tuyến lưu lượng truy cập thông qua một proxy cục bộ.
Ứng dụng không có MobileProxy

Ứng dụng có MobileProxy

Bước 1: Tạo thư viện di động MobileProxy
Sử dụng gomobile để biên dịch mã Go thành các thư viện cho Android và iOS.
Sao chép kho lưu trữ Outline SDK:
git clone https://github.com/Jigsaw-Code/outline-sdk.git cd outline-sdk/xTạo tệp nhị phân Go Mobile bằng
go build:go build -o "$(pwd)/out/" golang.org/x/mobile/cmd/gomobile golang.org/x/mobile/cmd/gobindThêm tính năng hỗ trợ Psiphon
Bạn có thể thêm tính năng hỗ trợ để sử dụng mạng Psiphon bằng cách làm theo các bước bổ sung sau:
- Liên hệ với nhóm Psiphon để lấy một cấu hình cho phép bạn truy cập vào mạng của họ. Bạn có thể cần phải ký hợp đồng.
- Thêm cấu hình Psiphon đã nhận vào phần
fallbackcủa cấu hìnhSmartDialer. Tạo Mobile Proxy bằng cờ
-tags psiphon:go build -tags psiphon -o "$(pwd)/out/" golang.org/x/mobile/cmd/gomobile golang.org/x/mobile/cmd/gobindĐăng ký Psiphon bằng Trình quay số thông minh trong mã gốc của bạn.
Cần có cờ
-tags psiphonvì cơ sở mã Psiphon được cấp phép theo GPL, có thể áp đặt các hạn chế về giấy phép đối với mã của riêng bạn. Bạn nên cân nhắc việc xin một giấy phép đặc biệt của họ.Tạo thư viện di động và thêm thư viện đó vào dự án của bạn:
Android
PATH="$(pwd)/out:$PATH" gomobile bind -ldflags='-s -w' -target=android -androidapi=21 -o "$(pwd)/out/mobileproxy.aar" github.com/Jigsaw-Code/outline-sdk/x/mobileproxyTrong Android Studio, hãy chọn File > Import Project… (Tệp > Nhập dự án...) để nhập gói
out/mobileproxy.aarđã tạo. Để được trợ giúp thêm, hãy xem phần Xây dựng và triển khai cho Android của Go Mobile.iOS
PATH="$(pwd)/out:$PATH" gomobile bind -ldflags='-s -w' -target=ios -iosversion=11.0 -o "$(pwd)/out/mobileproxy.xcframework" github.com/Jigsaw-Code/outline-sdk/x/mobileproxyKéo gói
out/mobileproxy.xcframeworkvào dự án Xcode. Để biết thêm thông tin trợ giúp, hãy xem bài viết Tạo và triển khai cho iOS của Go Mobile.
Bước 2: Chạy MobileProxy
- Khởi động và bắt đầu proxy cục bộ
MobileProxytrong thời gian chạy của ứng dụng. Bạn có thể sử dụng cấu hình truyền tải tĩnh hoặc Smart Proxy để chọn chiến lược động.
Cấu hình phương tiện truyền tải tĩnh: Sử dụng hàm
RunProxyvới địa chỉ cục bộ và cấu hình phương tiện truyền tải.Android
import mobileproxy.* val dialer = StreamDialer("split:3") // Use port zero to let the system pick an open port for you. val proxy = Mobileproxy.runProxy("localhost:0", dialer) // Configure your networking library using proxy.host() and proxy.port() or proxy.address(). // ... // Stop running the proxy. proxy.stop()iOS
import Mobileproxy let dialer = MobileproxyStreamDialer("split:3") // Use port zero to let the system pick an open port for you. let proxy = MobileproxyRunProxy("localhost:0", dialer) // Configure your networking library using proxy.host() and proxy.port() or proxy.address(). // ... // Stop running the proxy. proxy.stop()Smart Proxy: Smart Proxy sẽ tự động chọn các chiến lược DNS và TLS dựa trên các miền kiểm thử được chỉ định. Bạn cần chỉ định chiến lược cấu hình ở định dạng YAML (ví dụ).
Android
val testDomains = Mobileproxy.newListFromLines("www.youtube.com\ni.ytimg.com") val strategiesConfig = "..." // Config YAML. val dialer = Mobileproxy.newSmartStreamDialer(testDomains, strategiesConfig, Mobileproxy.newStderrLogWriter()) // Use port zero to let the system pick an open port for you. val proxy = Mobileproxy.runProxy("localhost:0", dialer) // Configure your networking library using proxy.host() and proxy.port() or proxy.address(). // ... // Stop running the proxy. proxy.stop()iOS
import Mobileproxy var dialerError: NSError? let testDomains = MobileproxyNewListFromLines("www.youtube.com\ni.ytimg.com") let strategiesConfig = "..." // Config YAML. let dialer = MobileproxyNewSmartStreamDialer( testDomains, strategiesConfig, MobileproxyNewStderrLogWriter(), &dialerError ) var proxyError: NSError? // Use port zero to let the system pick an open port for you. MobileproxyRunProxy("localhost:0", dialer, &proxyError) // Configure your networking library using proxy.host() and proxy.port() or proxy.address(). // ... // Stop running the proxy. proxy.stop()
- Sau đó, nếu bạn đang sử dụng psiphon, hãy đăng ký Psiphon bằng các lựa chọn Smart Dialer trong mã gốc của bạn.
Android:
import mobileproxy.Mobileproxy
import psiphon.Psiphon
// ...
val testDomains = Mobileproxy.newListFromLines("www.google.com\ni.ytimg.com")
// You can get a Psiphon config from the Psiphon team at sponsor@psiphon.ca.
val psiphonConfig = "<YOUR_PSIPHON_CONFIG_JSON_HERE>"
val config = """
dns:
- {system: {}}
tls:
- ""
fallback:
- {"psiphon": \(psiphonConfig)}
"""
val options = Mobileproxy.newSmartDialerOptions(testDomains, config)
// Register Psiphon
Psiphon.registerConfig(options, "psiphon")
try {
// Create the dialer
val dialer = options.newStreamDialer()
// ... use the dialer
} catch (e: Exception) {
// Handle error
}
iOS:
import Mobileproxy
import Psiphon
// ...
let testDomains = MobileproxyNewListFromLines("www.google.com\ni.ytimg.com")
// You can get a Psiphon config from the Psiphon team at sponsor@psiphon.ca.
let psiphonConfig = "<YOUR_PSIPHON_CONFIG_JSON_HERE>"
let config = """
dns:
- {system: {}}
tls:
- ""
fallback:
- {"psiphon": \(psiphonConfig)}
"""
let options = MobileproxyNewSmartDialerOptions(testDomains, config)
// Register Psiphon
PsiphonRegisterConfig(options, "psiphon")
do {
// Create the dialer
let dialer = try options.newStreamDialer()
// ... use the dialer
} catch {
// Handle error
}
Bước 3: Định cấu hình ứng dụng HTTP và thư viện mạng
Định cấu hình các thư viện mạng để sử dụng địa chỉ và cổng proxy cục bộ.
Dart/Flutter HttpClient
Đặt proxy bằng HttpClient.findProxy.
HttpClient client = HttpClient();
client.findProxy = (Uri uri) {
return "PROXY " + proxy.address();
};
OkHttp (Android)
Đặt proxy bằng OkHttpClient.Builder.proxy.
val proxyConfig = Proxy(Proxy.Type.HTTP, InetSocketAddress(proxy.host(), proxy.port()))
val client = OkHttpClient.Builder().proxy(proxyConfig).build()
JVM (Java, Kotlin)
Định cấu hình proxy để sử dụng với các thuộc tính hệ thống:
System.setProperty("http.proxyHost", proxy.host())
System.setProperty("http.proxyPort", String.valueOf(proxy.port()))
System.setProperty("https.proxyHost", proxy.host())
System.setProperty("https.proxyPort", String.valueOf(proxy.port()))
Khung hiển thị web Android
Áp dụng cấu hình proxy cho tất cả các khung hiển thị web trong ứng dụng của bạn bằng thư viện androidx.webview:
ProxyController.getInstance()
.setProxyOverride(
ProxyConfig.Builder()
.addProxyRule(this.proxy!!.address())
.build(),
{}, // execution context for the following callback - do anything needed here once the proxy is applied, like refreshing web views
{} // callback to be called once the ProxyConfig is applied
)
Chế độ xem web trên iOS
Kể từ iOS 17, bạn có thể thêm cấu hình proxy vào WKWebView bằng cách sử dụng thuộc tính WKWebsiteDataStore:
let configuration = WKWebViewConfiguration()
let endpoint = NWEndpoint.hostPort(host: NWEndpoint.Host(proxyHost), port: NWEndpoint.Port(proxyPort)!)
let proxyConfig = ProxyConfiguration.init(httpCONNECTProxy: endpoint)
let websiteDataStore = WKWebsiteDataStore.default()
websiteDataStore.proxyConfigurations = [proxyConfig]
let webview = WKWebView(configuration: configuration)
Nâng cao: Tạo thư viện di động tuỳ chỉnh
Đối với các trường hợp sử dụng nâng cao, bạn có thể tạo thư viện di động của riêng mình:
- Tạo thư viện Go: Phát triển một gói Go bao bọc các chức năng SDK cần thiết.
- Tạo thư viện di động: Sử dụng
gomobile bindđể tạo Android Archive (AAR) và Apple Framework. Ví dụ: - Tích hợp vào ứng dụng: Thêm thư viện đã tạo vào ứng dụng di động của bạn.