TDLibKit is a native Swift wrapper for TDLib with support for iOS, macOS, watchOS and even tvOS.
Powered by pre-built multi-platform TDLibFramework implementation of TDLib and generated sources with tl2swift
- Install Latest Xcode
- Add
https://github.com/Swiftgram/TDLibKit
as SPM dependency inProject > Swift Packages
. This could take a while cause it downloads ~300mb zip file with binary from TDLibFramework dependency - Add
TDLibKit
as your target dependency. - Code!
Integration requires similar to TDLibFramework Cocoapods & Flutter guide adaptation.
Library provides multiple API interfaces based on different approaches
- Async/Await syntax & do/catch. Available for iOS 13.0+, macOS 10.15+, watchOS 6.0+, tvOS 13.0+
- Completion handlers & closures
import TDLibKit
let client = TdClientImpl()
let api = TdApi(client: client)
Only for methods with "Can be called synchronously" in docs
let query = SetLogVerbosityLevel(newVerbosityLevel: 5)
do {
let result = try api.client.execute(query: DTO(query))
if let resultDict = result {
print("Response: \(resultDict)")
} else {
print("Empty result")
}
} catch {
print("Error in SetLogVerbosityLevel request \(error.localizedDescription)")
}
You must run at least empty updates handler to get responses for async requests.
api.client.run { _ in }
do {
let chatHistory = try await api.getChatHistory(
chatId: chatId,
fromMessageId: 0,
limit: 50,
offset: 0,
onlyLocal: false // Request remote messages from server
)
for message in chatHistory.messages {
switch message.content {
case .messageText(let text):
print(text.text.text)
case .messageAnimation:
print("<Animation>")
case .messagePhoto(let photo):
print("<Photo>\n\(photo.caption.text)")
case .messageSticker(let sticker):
print(sticker.sticker.emoji)
case .messageVideo(let video):
print("<Video>\n\(video.caption.text)")
// ...
default:
print("Unknown message content \(message.content)")
}
}
} catch {
print("Error in getChatHistory \(error)")
}
try? api.getChatHistory(
chatId: chatId,
fromMessageId: 0,
limit: 50,
offset: 0,
onlyLocal: false, // Request remote messages from server
completion: { result in
// Handle Errors
if case .failure(let error) = result {
print("Error in getChatHistory request \(error.localizedDescription)")
} else if let messages = try? result.get().messages {
// Handle messages
for message in messages {
switch message.content {
case .messageText(let text):
print(text.text.text)
case .messageAnimation:
print("<Animation>")
case .messagePhoto(let photo):
print("<Photo>\n\(photo.caption.text)")
case .messageSticker(let sticker):
print(sticker.sticker.emoji)
case .messageVideo(let video):
print("<Video>\n\(video.caption.text)")
// ...
default:
print("Unknown message content \(message.content)")
}
}
}
}
)
api.client.run {
do {
let update = try api.decoder.decode(Update.self, from: $0)
switch update {
case .updateNewMessage(let newMsg):
switch newMsg.message.content {
case .messageText(let text):
print("Text Message: \(text.text.text)")
default:
break
}
case .updateMessageEdited:
break
// ... etc
default:
print("Unhandled Update \(update)")
break
}
} catch {
print("Error in update handler \(error.localizedDescription)")
}
}
You can pass additional parameter with Logger
type to log "send, receive, execute" and custom entries.
import TDLibKit
public final class StdOutLogger: Logger {
let queue: DispatchQueue
public init() {
queue = DispatchQueue(label: "Logger", qos: .userInitiated)
}
public func log(_ message: String, type: LoggerMessageType?) {
queue.async {
var fisrtLine = "---------------------------"
if let type = type {
fisrtLine = ">> \(type.description): ---------------"
}
print("""
\(fisrtLine)
\(message)
---------------------------
""")
}
}
}
let client = TdClientImpl(completionQueue: .main, logger: StdOutLogger())
You can find more about build process in Github Actions file.
- Anton Glezman for Build Guide , TL Scheme parser and basic implementation
- Leo Mehlig for TDLib-iOS and contributions to run TDLib on Swift
- Telegram Team for TDLib