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

[Feature] 근거리 통신 모듈에 URL을 이용한 통신 메서드 추가 #103

Merged
merged 5 commits into from
Nov 20, 2024
Merged
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
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
import Foundation

public protocol NearbyNetworkInterface {
var delegate: NearbyNetworkDelegate? { get set }
var connectionDelegate: NearbyNetworkConnectionDelegate? { get set }
Copy link
Collaborator

Choose a reason for hiding this comment

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

그러니까 근거리통신 연결 로직을 NearbyNetworkConnectionDelegate가,
근거리통신 송수신 로직을 NearbyNetworkReceiptDelegate가 담당하게 되는게 맞나요 ??

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

똑똑한 조이 맞습니다!!


/// 주변 기기를 검색합니다.
func startSearching()
Expand All @@ -33,15 +33,15 @@ public protocol NearbyNetworkInterface {
/// 연결된 기기들에게 데이터를 송신합니다.
/// - Parameter data: 송신할 데이터
func send(data: Data)
}

public protocol NearbyNetworkDelegate: AnyObject {
/// 데이터를 수신했을 때 실행됩니다.
/// 연결된 기기들에게 파일을 송신합니다.
/// - Parameters:
/// - data: 수신된 데이터
/// - connection: 데이터를 송신한 기기
func nearbyNetwork(_ sender: NearbyNetworkInterface, didReceive data: Data, from connection: NetworkConnection)
/// - fileURL: 파일의 URL
/// - info: 파일에 대한 정보
func send(fileURL: URL, info: DataInformationDTO) async
}

public protocol NearbyNetworkConnectionDelegate: AnyObject {
/// 주변 기기에게 연결 요청을 받았을 때 실행됩니다.
/// - Parameters:
/// - connectionHandler: 연결 요청 처리 Handler
Expand All @@ -55,3 +55,19 @@ public protocol NearbyNetworkDelegate: AnyObject {
/// 주변 기기와의 연결에 실패했을 때 실행됩니다.
func nearbyNetworkCannotConnect(_ sender: NearbyNetworkInterface)
}

public protocol NearbyNetworkReceiptDelegate: AnyObject {
Copy link
Collaborator

Choose a reason for hiding this comment

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

connection, receipt 적절한 기준으로 잘 나눈거같아용

/// 데이터를 수신했을 때 실행됩니다.
/// - Parameters:
/// - data: 수신된 데이터
func nearbyNetwork(_ sender: NearbyNetworkInterface, didReceive data: Data)

/// 파일을 수신했을 때 실행됩니다.
/// - Parameters:
/// - URL: 수신한 파일의 URL
/// - info: 파일에 대한 정보
func nearbyNetwork(
_ sender: NearbyNetworkInterface,
didReceiveURL URL: URL,
info: DataInformationDTO)
Comment on lines +69 to +72
Copy link
Member

Choose a reason for hiding this comment

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

style: 닫히는 괄호가 밑으로 내려와야 하는 것 같습니다!

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

요 부분은 저희 같이 이야기 나눈대로 현상유지하도록 하겠습니다 :)

}
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,6 @@
import Foundation

public struct DataInformationDTO: Codable {
public let identifier: UUID
public let id: UUID
public let type: AirplaINDataType
}
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ public final class WhiteboardRepository: WhiteboardRepositoryInterface {

public init(nearbyNetworkInterface: NearbyNetworkInterface) {
self.nearbyNetwork = nearbyNetworkInterface
self.nearbyNetwork.delegate = self
self.nearbyNetwork.connectionDelegate = self
}

public func startPublishing(with info: [Profile]) {
Expand All @@ -33,14 +33,7 @@ public final class WhiteboardRepository: WhiteboardRepositoryInterface {
}
}

extension WhiteboardRepository: NearbyNetworkDelegate {
public func nearbyNetwork(
_ sender: any NearbyNetworkInterface,
didReceive data: Data,
from connection: NetworkConnection) {
// TODO: -
}

extension WhiteboardRepository: NearbyNetworkConnectionDelegate {
public func nearbyNetwork(
_ sender: any NearbyNetworkInterface,
didReceive connectionHandler: @escaping (
Expand Down
24 changes: 24 additions & 0 deletions NearbyNetwork/NearbyNetwork.xcodeproj/project.pbxproj
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,8 @@
objects = {

/* Begin PBXBuildFile section */
00549AD62CEDDDB700DF8F6C /* MCSessionState+.swift in Sources */ = {isa = PBXBuildFile; fileRef = 00549AD52CEDDDB100DF8F6C /* MCSessionState+.swift */; };
00549AD82CEDDDCF00DF8F6C /* MCSession+.swift in Sources */ = {isa = PBXBuildFile; fileRef = 00549AD72CEDDDCF00DF8F6C /* MCSession+.swift */; };
0080E86A2CE19EC40095B958 /* NearbyNetworkService.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0080E8672CE19EC40095B958 /* NearbyNetworkService.swift */; };
5B7C6EBF2CDB6C6E0024704A /* DataSource.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 5B7C6EBE2CDB6C6E0024704A /* DataSource.framework */; };
5B7C6EC02CDB6C6E0024704A /* DataSource.framework in Embed Frameworks */ = {isa = PBXBuildFile; fileRef = 5B7C6EBE2CDB6C6E0024704A /* DataSource.framework */; settings = {ATTRIBUTES = (CodeSignOnCopy, RemoveHeadersOnCopy, ); }; };
Expand All @@ -27,6 +29,8 @@
/* End PBXCopyFilesBuildPhase section */

/* Begin PBXFileReference section */
00549AD52CEDDDB100DF8F6C /* MCSessionState+.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "MCSessionState+.swift"; sourceTree = "<group>"; };
00549AD72CEDDDCF00DF8F6C /* MCSession+.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "MCSession+.swift"; sourceTree = "<group>"; };
0080E8672CE19EC40095B958 /* NearbyNetworkService.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NearbyNetworkService.swift; sourceTree = "<group>"; };
5B7C6E652CDB6A560024704A /* NearbyNetwork.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = NearbyNetwork.framework; sourceTree = BUILT_PRODUCTS_DIR; };
5B7C6EBE2CDB6C6E0024704A /* DataSource.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; path = DataSource.framework; sourceTree = BUILT_PRODUCTS_DIR; };
Expand All @@ -44,9 +48,27 @@
/* End PBXFrameworksBuildPhase section */

/* Begin PBXGroup section */
00549AD32CEDDDA300DF8F6C /* Common */ = {
isa = PBXGroup;
children = (
00549AD42CEDDDA800DF8F6C /* Extension */,
);
path = Common;
sourceTree = "<group>";
};
00549AD42CEDDDA800DF8F6C /* Extension */ = {
isa = PBXGroup;
children = (
00549AD52CEDDDB100DF8F6C /* MCSessionState+.swift */,
00549AD72CEDDDCF00DF8F6C /* MCSession+.swift */,
);
path = Extension;
sourceTree = "<group>";
};
0080E8682CE19EC40095B958 /* Sources */ = {
isa = PBXGroup;
children = (
00549AD32CEDDDA300DF8F6C /* Common */,
0080E8672CE19EC40095B958 /* NearbyNetworkService.swift */,
);
path = Sources;
Expand Down Expand Up @@ -190,6 +212,8 @@
isa = PBXSourcesBuildPhase;
buildActionMask = 2147483647;
files = (
00549AD62CEDDDB700DF8F6C /* MCSessionState+.swift in Sources */,
00549AD82CEDDDCF00DF8F6C /* MCSession+.swift in Sources */,
0080E86A2CE19EC40095B958 /* NearbyNetworkService.swift in Sources */,
);
runOnlyForDeploymentPostprocessing = 0;
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
//
// MCSession+.swift
// NearbyNetwork
//
// Created by 이동현 on 11/20/24.
//

import MultipeerConnectivity

// MARK: - Swift Concurrency로 wrapping
extension MCSession {
func sendResource(
at resourceURL: URL,
withName resourceName: String,
toPeer peer: MCPeerID
) async throws {
typealias Continuation = CheckedContinuation<Void, Error>

try await withCheckedThrowingContinuation { (continuation: Continuation) in
Copy link
Member

Choose a reason for hiding this comment

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

이것을 통해 swift Concurrency처럼 사용할 수 있게 해주는 군요..!

이부분은 공부를 해봐야할 것 같습니다..!ㅜㅜ

Copy link
Collaborator

Choose a reason for hiding this comment

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

꺆 !!!!!!!!!!!!!! 쏘 어렵 ... 내일 설명해주기 .......................................

self.sendResource(
at: resourceURL,
withName: resourceName,
toPeer: peer) { error in
if let error {
continuation.resume(throwing: error)
} else {
continuation.resume()
}
}
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
//
// MCSessionState+.swift
// NearbyNetwork
//
// Created by 이동현 on 11/20/24.
//

import MultipeerConnectivity

extension MCSessionState {
var description: String {
switch self {
case .notConnected:
return "연결 끊김"
case .connecting:
return "연결 중"
case .connected:
return "연결 됨"
@unknown default:
return "알 수 없음"
}
}
}
67 changes: 42 additions & 25 deletions NearbyNetwork/NearbyNetwork/Sources/NearbyNetworkService.swift
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,8 @@ import MultipeerConnectivity
import OSLog

public final class NearbyNetworkService: NSObject {
public weak var delegate: NearbyNetworkDelegate?
public weak var connectionDelegate: NearbyNetworkConnectionDelegate?
public weak var receiptDelegate: NearbyNetworkReceiptDelegate?
private let peerID: MCPeerID
private let session: MCSession
private var serviceAdvertiser: MCNearbyServiceAdvertiser
Expand All @@ -20,7 +21,7 @@ public final class NearbyNetworkService: NSObject {
private var foundPeers: [MCPeerID: NetworkConnection] = [:] {
didSet {
let foundPeers: [NetworkConnection] = foundPeers.values.map { $0 }
delegate?.nearbyNetwork(self, didFind: foundPeers)
connectionDelegate?.nearbyNetwork(self, didFind: foundPeers)
}
}
private let logger = Logger()
Expand Down Expand Up @@ -77,9 +78,8 @@ extension NearbyNetworkService: NearbyNetworkInterface {
.first { $0.value == connection }?
.key
// TODO: Error 수정
guard let peerID else {
throw NSError()
}
guard let peerID else { throw NSError() }

serviceBrowser.invitePeer(
peerID,
to: session,
Expand All @@ -97,6 +97,30 @@ extension NearbyNetworkService: NearbyNetworkInterface {
logger.log(level: .error, "데이터 전송 실패")
}
}

public func send(fileURL: URL, info: DataSource.DataInformationDTO) async {
let infoJsonData = try? JSONEncoder().encode(info)

guard
let infoJsonData,
let infoJsonString = String(data: infoJsonData, encoding: .utf8)
else { return }

await withTaskGroup(of: Void.self) { taskGroup in
session.connectedPeers.forEach { peer in
taskGroup.addTask {
do {
try await self.session.sendResource(
at: fileURL,
withName: infoJsonString,
toPeer: peer)
} catch {
self.logger.log(level: .error, "\(peer)에게 file 데이터 전송 실패")
}
}
}
}
Comment on lines +109 to +122
Copy link
Member

Choose a reason for hiding this comment

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

이부분도 공부해보겠습니다!

Copy link
Collaborator

Choose a reason for hiding this comment

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

다시봐도 어렵네유

}
}

// MARK: - MCSessionDelegate
Expand Down Expand Up @@ -131,7 +155,7 @@ extension NearbyNetworkService: MCSessionDelegate {
logger.log(level: .error, "\(peerID.displayName)와 연결되어 있지 않음")
return
}
delegate?.nearbyNetwork(self, didReceive: data, from: connection)
receiptDelegate?.nearbyNetwork(self, didReceive: data)
}

public func session(
Expand Down Expand Up @@ -159,7 +183,16 @@ extension NearbyNetworkService: MCSessionDelegate {
at localURL: URL?,
withError error: (any Error)?
) {
logger.log(level: .error, "\(peerID.displayName)로부터 데이터 수신을 완료함")
guard
let localURL,
let jsonData = resourceName.data(using: .utf8),
let dto = try? JSONDecoder().decode(DataInformationDTO.self, from: jsonData)
else{ return }

receiptDelegate?.nearbyNetwork(
self,
didReceiveURL: localURL,
info: dto)
}
}

Expand All @@ -171,7 +204,7 @@ extension NearbyNetworkService: MCNearbyServiceAdvertiserDelegate {
withContext context: Data?,
invitationHandler: @escaping (Bool, MCSession?) -> Void
) {
delegate?.nearbyNetwork(self, didReceive: { [weak self] isAccepted in
connectionDelegate?.nearbyNetwork(self, didReceive: { [weak self] isAccepted in
invitationHandler(isAccepted, self?.session)
})
}
Expand All @@ -181,7 +214,7 @@ extension NearbyNetworkService: MCNearbyServiceAdvertiserDelegate {
didNotStartAdvertisingPeer error: any Error
) {
logger.log(level: .error, "Advertising 실패 \(error.localizedDescription)")
delegate?.nearbyNetworkCannotConnect(self)
connectionDelegate?.nearbyNetworkCannotConnect(self)
}
}

Expand All @@ -203,19 +236,3 @@ extension NearbyNetworkService: MCNearbyServiceBrowserDelegate {
foundPeers[peerID] = nil
}
}

// MARK: - MCSessionState
extension MCSessionState {
var description: String {
switch self {
case .notConnected:
return "연결 끊김"
case .connecting:
return "연결 중"
case .connected:
return "연결 됨"
@unknown default:
return "알 수 없음"
}
}
}
2 changes: 1 addition & 1 deletion Persistence/Persistence/Souces/FilePersistence.swift
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@ public struct FilePersistence: FilePersistenceInterface {
return write(
to: directoryURL,
with: data,
fileName: dataInfo.identifier.uuidString)
fileName: dataInfo.id.uuidString)
}

public func load(path: URL) -> Data? {
Expand Down