Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Chat] feature/#244-create thread #266

Merged
merged 24 commits into from
Jun 20, 2022
Merged
Show file tree
Hide file tree
Changes from 22 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
56 changes: 35 additions & 21 deletions Sources/Chat/Chat.swift
Original file line number Diff line number Diff line change
Expand Up @@ -9,19 +9,20 @@ import Combine
class Chat {
private var publishers = [AnyCancellable]()
let registry: Registry
let registryManager: RegistryManager
let engine: Engine
let registryService: RegistryService
let invitationHandlingService: InvitationHandlingService
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I like ***Service naming, let's use more often

let inviteService: InviteService
let kms: KeyManagementService

let socketConnectionStatusPublisher: AnyPublisher<SocketConnectionStatus, Never>

var newThreadPublisherSubject = PassthroughSubject<Thread, Never>()
public var newThreadPublisher: AnyPublisher<Thread, Never> {
var newThreadPublisherSubject = PassthroughSubject<String, Never>()
public var newThreadPublisher: AnyPublisher<String, Never> {
newThreadPublisherSubject.eraseToAnyPublisher()
}

var invitePublisherSubject = PassthroughSubject<Invite, Never>()
public var invitePublisher: AnyPublisher<Invite, Never> {
var invitePublisherSubject = PassthroughSubject<InviteEnvelope, Never>()
public var invitePublisher: AnyPublisher<InviteEnvelope, Never> {
invitePublisherSubject.eraseToAnyPublisher()
}

Expand All @@ -34,16 +35,23 @@ class Chat {
self.registry = registry
self.kms = kms
let serialiser = Serializer(kms: kms)
let networkingInteractor = NetworkingInteractor(relayClient: relayClient, serializer: serialiser)
let inviteStore = CodableStore<Invite>(defaults: keyValueStorage, identifier: StorageDomainIdentifiers.invite.rawValue)
self.registryManager = RegistryManager(registry: registry, networkingInteractor: networkingInteractor, kms: kms, logger: logger, topicToInvitationPubKeyStore: topicToInvitationPubKeyStore)
self.engine = Engine(registry: registry,
let jsonRpcHistory = JsonRpcHistory<ChatRequestParams>(logger: logger, keyValueStore: CodableStore<JsonRpcRecord>(defaults: keyValueStorage, identifier: StorageDomainIdentifiers.jsonRpcHistory.rawValue))
let networkingInteractor = NetworkingInteractor(
relayClient: relayClient,
serializer: serialiser,
logger: logger,
jsonRpcHistory: jsonRpcHistory)
let invitePayloadStore = CodableStore<RequestSubscriptionPayload>(defaults: keyValueStorage, identifier: StorageDomainIdentifiers.invite.rawValue)
self.registryService = RegistryService(registry: registry, networkingInteractor: networkingInteractor, kms: kms, logger: logger, topicToInvitationPubKeyStore: topicToInvitationPubKeyStore)
let codec = ChaChaPolyCodec()
self.invitationHandlingService = InvitationHandlingService(registry: registry,
networkingInteractor: networkingInteractor,
kms: kms,
logger: logger,
topicToInvitationPubKeyStore: topicToInvitationPubKeyStore,
inviteStore: inviteStore,
threadsStore: CodableStore<Thread>(defaults: keyValueStorage, identifier: StorageDomainIdentifiers.threads.rawValue))
kms: kms,
logger: logger,
topicToInvitationPubKeyStore: topicToInvitationPubKeyStore,
invitePayloadStore: invitePayloadStore,
threadsStore: CodableStore<Thread>(defaults: keyValueStorage, identifier: StorageDomainIdentifiers.threads.rawValue), codec: codec)
self.inviteService = InviteService(networkingInteractor: networkingInteractor, kms: kms, logger: logger, codec: codec)
socketConnectionStatusPublisher = relayClient.socketConnectionStatusPublisher
setUpEnginesCallbacks()
}
Expand All @@ -53,7 +61,7 @@ class Chat {
/// - Parameter account: CAIP10 blockchain account
/// - Returns: public key
func register(account: Account) async throws -> String {
try await registryManager.register(account: account)
try await registryService.register(account: account)
}

/// Queries the default keyserver with a blockchain account
Expand All @@ -68,11 +76,14 @@ class Chat {
/// - publicKey: publicKey associated with a peer
/// - openingMessage: oppening message for a chat invite
func invite(publicKey: String, openingMessage: String) async throws {
try await engine.invite(peerPubKey: publicKey, openingMessage: openingMessage)
//TODO - how to provide account?
// in init or in invite method's params
let tempAccount = Account("eip155:1:33e32e32")!
try await inviteService.invite(peerPubKey: publicKey, openingMessage: openingMessage, account: tempAccount)
}

func accept(inviteId: String) async throws {
try await engine.accept(inviteId: inviteId)
try await invitationHandlingService.accept(inviteId: inviteId)
}

/// Sends a chat message to an active chat thread
Expand All @@ -90,10 +101,13 @@ class Chat {
}

private func setUpEnginesCallbacks() {
engine.onInvite = { [unowned self] invite in
invitePublisherSubject.send(invite)
invitationHandlingService.onInvite = { [unowned self] inviteEnvelope in
invitePublisherSubject.send(inviteEnvelope)
}
engine.onNewThread = { [unowned self] newThread in
invitationHandlingService.onNewThread = { [unowned self] newThread in
newThreadPublisherSubject.send(newThread)
}
inviteService.onNewThread = { [unowned self] newThread in
newThreadPublisherSubject.send(newThread)
}
}
Expand Down
94 changes: 0 additions & 94 deletions Sources/Chat/Engine.swift

This file was deleted.

68 changes: 49 additions & 19 deletions Sources/Chat/NetworkingInteractor.swift
Original file line number Diff line number Diff line change
Expand Up @@ -5,12 +5,23 @@ import WalletConnectRelay
import WalletConnectUtils

protocol NetworkInteracting {
func subscribe(topic: String) async throws
var requestPublisher: AnyPublisher<RequestSubscriptionPayload, Never> {get}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

run swiftlint --fix please

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

done

var responsePublisher: AnyPublisher<ChatResponse, Never> {get}
func subscribe(topic: String) async throws
func requestUnencrypted(_ request: JSONRPCRequest<ChatRequestParams>, topic: String) async throws
func request(_ request: JSONRPCRequest<ChatRequestParams>, topic: String) async throws
func respond(topic: String, response: JsonRpcResult) async throws

}

class NetworkingInteractor: NetworkInteracting {
let relayClient: RelayClient
enum Error: Swift.Error {
case failedToInitialiseMethodFromRecord
}
private let jsonRpcHistory: JsonRpcHistory<ChatRequestParams>
private let serializer: Serializing
private let relayClient: RelayClient
private let logger: ConsoleLogging
var requestPublisher: AnyPublisher<RequestSubscriptionPayload, Never> {
requestPublisherSubject.eraseToAnyPublisher()
}
Expand All @@ -20,39 +31,47 @@ class NetworkingInteractor: NetworkInteracting {
responsePublisherSubject.eraseToAnyPublisher()
}
private let responsePublisherSubject = PassthroughSubject<ChatResponse, Never>()

init(relayClient: RelayClient,
serializer: Serializing) {
serializer: Serializing,
logger: ConsoleLogging,
jsonRpcHistory: JsonRpcHistory<ChatRequestParams>
) {
self.relayClient = relayClient
self.serializer = serializer

self.jsonRpcHistory = jsonRpcHistory
self.logger = logger
relayClient.onMessage = { [unowned self] topic, message in
manageSubscription(topic, message)
}
}

func requestUnencrypted(_ request: ChatRequest, topic: String) {
// TODO - remove the method
func requestUnencrypted(_ request: JSONRPCRequest<ChatRequestParams>, topic: String) async throws {
try jsonRpcHistory.set(topic: topic, request: request)
let message = try! request.json()
relayClient.publish(topic: topic, payload: message) {error in
// print(error)
}
try await relayClient.publish(topic: topic, payload: message)
}

func request(_ request: ChatRequest, topic: String) {
func request(_ request: JSONRPCRequest<ChatRequestParams>, topic: String) async throws {
try jsonRpcHistory.set(topic: topic, request: request)
let message = try! serializer.serialize(topic: topic, encodable: request)
relayClient.publish(topic: topic, payload: message) {error in
// print(error)
}
try await relayClient.publish(topic: topic, payload: message)
}

func respond(topic: String, response: JsonRpcResult) async throws {
let message = try serializer.serialize(topic: topic, encodable: response.value)
try await relayClient.publish(topic: topic, payload: message, prompt: false)
}

func subscribe(topic: String) async throws {
try await relayClient.subscribe(topic: topic)
}

private func manageSubscription(_ topic: String, _ message: String) {
if let deserializedJsonRpcRequest: ChatRequest = serializer.tryDeserialize(topic: topic, message: message) {
if let deserializedJsonRpcRequest: JSONRPCRequest<ChatRequestParams> = serializer.tryDeserialize(topic: topic, message: message) {
handleWCRequest(topic: topic, request: deserializedJsonRpcRequest)
} else if let decodedJsonRpcRequest: ChatRequest = tryDecodeRequest(message: message) {
} else if let decodedJsonRpcRequest: JSONRPCRequest<ChatRequestParams> = tryDecodeRequest(message: message) {
handleWCRequest(topic: topic, request: decodedJsonRpcRequest)

} else if let deserializedJsonRpcResponse: JSONRPCResponse<AnyCodable> = serializer.tryDeserialize(topic: topic, message: message) {
Expand All @@ -65,20 +84,31 @@ class NetworkingInteractor: NetworkInteracting {
}


private func tryDecodeRequest(message: String) -> ChatRequest? {
private func tryDecodeRequest(message: String) -> JSONRPCRequest<ChatRequestParams>? {
guard let messageData = message.data(using: .utf8) else {
return nil
}
return try? JSONDecoder().decode(ChatRequest.self, from: messageData)
return try? JSONDecoder().decode(JSONRPCRequest<ChatRequestParams>.self, from: messageData)
}

private func handleWCRequest(topic: String, request: ChatRequest) {
private func handleWCRequest(topic: String, request: JSONRPCRequest<ChatRequestParams>) {
let payload = RequestSubscriptionPayload(topic: topic, request: request)
requestPublisherSubject.send(payload)
}

private func handleJsonRpcResponse(response: JSONRPCResponse<AnyCodable>) {
//todo
do {
let record = try jsonRpcHistory.resolve(response: JsonRpcResult.response(response))
let params = try record.request.params.get(ChatRequestParams.self)
let chatResponse = ChatResponse(
topic: record.topic,
requestMethod: record.request.method,
requestParams: params,
result: JsonRpcResult.response(response))
responsePublisherSubject.send(chatResponse)
} catch {
logger.debug("Handle json rpc response error: \(error)")
}
}

private func handleJsonRpcErrorResponse(response: JSONRPCErrorResponse) {
Expand Down
3 changes: 3 additions & 0 deletions Sources/Chat/ProtocolServices/Common/MessagingService.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@


import Foundation
Loading