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

macOS Session View improvements #275

Merged
merged 12 commits into from
Jul 1, 2024
1 change: 0 additions & 1 deletion Demo/macOS/Pulse_Demo_macOSApp.swift
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@ struct Pulse_Demo_macOSApp: App {
WindowGroup {
ConsoleView(store: .demo)
}
.windowStyle(.hiddenTitleBar)
.windowToolbarStyle(.unified(showsTitle: false))
}
}
2 changes: 1 addition & 1 deletion Sources/Pulse/LoggerStore/LoggerStore.swift
Original file line number Diff line number Diff line change
Expand Up @@ -347,7 +347,7 @@ extension LoggerStore {
}

/// Handles event created by the current store and dispatches it to observers.
func handle(_ event: Event) {
public func handle(_ event: Event) {
guard let event = configuration.willHandleEvent(event) else {
return
}
Expand Down
25 changes: 13 additions & 12 deletions Sources/Pulse/RemoteLogger/RemoteLogger-Connection.swift
Original file line number Diff line number Diff line change
Expand Up @@ -11,12 +11,12 @@ import OSLog
import Pulse
#endif

protocol RemoteLoggerConnectionDelegate: AnyObject {
public protocol RemoteLoggerConnectionDelegate: AnyObject {
func connection(_ connection: RemoteLogger.Connection, didChangeState newState: NWConnection.State)
func connection(_ connection: RemoteLogger.Connection, didReceiveEvent event: RemoteLogger.Connection.Event)
}

extension RemoteLogger {
public extension RemoteLogger {
final class Connection {
var endpoint: NWEndpoint { connection.endpoint }
private let connection: NWConnection
Expand All @@ -31,14 +31,15 @@ extension RemoteLogger {
self.init(NWConnection(to: endpoint, using: parameters))
}

init(_ connection: NWConnection) {
public init(_ connection: NWConnection, delegate: RemoteLoggerConnectionDelegate? = nil) {
self.connection = connection
self.delegate = delegate

let isLogEnabled = UserDefaults.standard.bool(forKey: "com.github.kean.pulse.debug")
self.log = isLogEnabled ? OSLog(subsystem: "com.github.kean.pulse", category: "RemoteLogger") : .disabled
}

func start(on queue: DispatchQueue) {
public func start(on queue: DispatchQueue) {
connection.stateUpdateHandler = { [weak self] state in
guard let self = self else { return }
DispatchQueue.main.async {
Expand All @@ -49,15 +50,15 @@ extension RemoteLogger {
connection.start(queue: queue)
}

enum Event {
public enum Event {
case packet(Packet)
case error(Error)
case completed
}

struct Packet {
let code: UInt8
let body: Data
public struct Packet {
public let code: UInt8
public let body: Data
}

private func receive() {
Expand Down Expand Up @@ -130,7 +131,7 @@ extension RemoteLogger {
}
}

func send(code: UInt8, data: Data) {
public func send(code: UInt8, data: Data) {
do {
let data = try encode(code: code, body: data)
let log = self.log
Expand All @@ -144,7 +145,7 @@ extension RemoteLogger {
}
}

func send<T: Encodable>(code: UInt8, entity: T) {
public func send<T: Encodable>(code: UInt8, entity: T) {
do {
let data = try JSONEncoder().encode(entity)
send(code: code, data: data)
Expand Down Expand Up @@ -206,7 +207,7 @@ extension RemoteLogger {
}
}

func cancel() {
public func cancel() {
connection.cancel()
}
}
Expand Down
8 changes: 6 additions & 2 deletions Sources/Pulse/RemoteLogger/RemoteLogger-Protocol.swift
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ import Network
import Pulse
#endif

extension RemoteLogger {
public extension RemoteLogger {
enum PacketCode: UInt8, Equatable {
// Handshake
case clientHello = 0 // PacketClientHello
Expand Down Expand Up @@ -83,7 +83,7 @@ extension RemoteLogger {
return data
}

static func decode(_ data: Data) throws -> LoggerStore.Event.NetworkTaskCompleted {
public static func decode(_ data: Data) throws -> LoggerStore.Event.NetworkTaskCompleted {
guard data.count >= Manifest.size else {
throw PacketParsingError.notEnoughData // Should never happen
}
Expand Down Expand Up @@ -197,6 +197,10 @@ extension RemoteLogger {

struct ServerHelloResponse: Codable {
let version: String

public init(version: String) {
self.version = version
}
}
}

Expand Down
10 changes: 5 additions & 5 deletions Sources/Pulse/RemoteLogger/RemoteLogger.swift
Original file line number Diff line number Diff line change
Expand Up @@ -322,7 +322,7 @@ public final class RemoteLogger: ObservableObject, RemoteLoggerConnectionDelegat

openConnection(to: server, passcode: passcode)
}

private func connectionDidTimeout(isProtected: Bool) {
os_log("Connection did timeout", log: log)
connectionCompletion?(.failure(self.connectionError ?? .unknown(isProtected: isProtected)))
Expand All @@ -341,7 +341,7 @@ public final class RemoteLogger: ObservableObject, RemoteLoggerConnectionDelegat
}

private func saveServer(named name: String) {
os_log("Save server %{private}@", log: log, name)
os_log("Save server %{private}@", log: log, name)
knownServers.removeAll(where: { $0 == name })
knownServers.append(name)
saveKnownServers()
Expand Down Expand Up @@ -371,7 +371,7 @@ public final class RemoteLogger: ObservableObject, RemoteLoggerConnectionDelegat

// MARK: RemoteLoggerConnectionDelegate

func connection(_ connection: Connection, didChangeState newState: NWConnection.State) {
public func connection(_ connection: Connection, didChangeState newState: NWConnection.State) {
os_log("Connection did change state to %{public}@", log: log, "\(newState)")

switch newState {
Expand All @@ -390,7 +390,7 @@ public final class RemoteLogger: ObservableObject, RemoteLoggerConnectionDelegat
}
}

func connection(_ connection: Connection, didReceiveEvent event: Connection.Event) {
public func connection(_ connection: Connection, didReceiveEvent event: Connection.Event) {
switch event {
case .packet(let packet):
do {
Expand Down Expand Up @@ -730,5 +730,5 @@ extension RemoteLogger.ConnectionState {
}

extension RemoteLogger {
public static let serviceType = "_pulse._tcp"
public static var serviceType = "_pulse._tcp"
}
9 changes: 7 additions & 2 deletions Sources/PulseUI/Features/Console/ConsoleView-macos.swift
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,7 @@ private struct ConsoleMainView: View {

private var contentView: some View {
ConsoleListView()
.frame(minWidth: 200, idealWidth: 400, minHeight: 120, idealHeight: 480)
.frame(minWidth: 400, idealWidth: 500, minHeight: 120, idealHeight: 480)
.toolbar {
ToolbarItemGroup(placement: .navigation) {
contentToolbarNavigationItems
Expand All @@ -60,18 +60,21 @@ private struct ConsoleMainView: View {
Button(action: { isShowingFilters = true }) {
Label("Show Filters", systemImage: "line.3.horizontal.decrease.circle")
}
.help("Show Filters")
.popover(isPresented: $isShowingFilters) {
ConsoleFiltersView().frame(width: 300).fixedSize()
}
Button(action: { isShowingSessions = true }) {
Label("Show Sessions", systemImage: "list.clipboard")
}
.help("Show Sessions")
.popover(isPresented: $isShowingSessions) {
SessionsView().frame(width: 300, height: 420)
}
Button(action: { isShowingSettings = true }) {
Label("Show Settings", systemImage: "gearshape")
}
.help("Show Settings")
.popover(isPresented: $isShowingSettings) {
SettingsView().frame(width: 300, height: 420)
}
Expand All @@ -88,17 +91,19 @@ private struct ConsoleMainView: View {
if !(environment.store.options.contains(.readonly)) {
Toggle(isOn: $isNowEnabled) {
Image(systemName: "clock")
}
}.help("Now Mode: Automatically scrolls to the top of the view to display newly incoming network requests.")
Button(action: { isSharingStore = true }) {
Image(systemName: "square.and.arrow.up")
}
.help("Share a session")
.popover(isPresented: $isSharingStore, arrowEdge: .bottom) {
ShareStoreView(onDismiss: {})
.frame(width: 240).fixedSize()
}
Button(action: { environment.store.removeAll() }) {
Image(systemName: "trash")
}
.help("Clear current session")
}
}
}
Expand Down
6 changes: 3 additions & 3 deletions Sources/PulseUI/Features/Console/ConsoleView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -12,9 +12,9 @@ extension ConsoleView {
///
/// - parameters:
/// - store: The store to display. By default, `LoggerStore/shared`.
/// - mode: The console mode. By default, ``ConsoleMode/all``. If you change
/// the mode to ``ConsoleMode/network``, the console will only display the
/// network messages.
/// - mode: The initial console mode. By default, ``ConsoleMode/all``. If you change
/// the mode to ``ConsoleMode/network``, the console will display the
/// network messages up on appearance.
/// - delegate: The delegate that allows you to customize multiple aspects
/// of the console view.
public init(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -174,7 +174,7 @@ private struct _ConsoleListView: View {
} else {
ConsoleListContentView(proxy: proxy)
}
}
}.scrollContentBackground(.hidden)
}
.environment(\.defaultMinListRowHeight, 1)
}
Expand Down
42 changes: 27 additions & 15 deletions Sources/PulseUI/Features/Sessions/SessionListView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -27,34 +27,42 @@ struct SessionListView: View {
@Environment(\.store) private var store

var body: some View {
if sessions.isEmpty {
Text("No Recorded Sessions")
.frame(maxWidth: .infinity, maxHeight: .infinity)
.foregroundColor(.secondary)
} else {
content
.onAppear { refreshGroups() }
.onChange(of: sessions.count) { _ in refreshGroups() }
VStack(spacing: 0) {
#if os(macOS)
Text("Recorded sessions")
.padding(.vertical, 10)
Divider()
#endif
if sessions.isEmpty {
Text("No Recorded Sessions")
.frame(maxWidth: .infinity, maxHeight: .infinity)
.foregroundColor(.secondary)
} else {
content
.onAppear { refreshGroups() }
.onChange(of: sessions.count) { _ in refreshGroups() }
}
}
}

@ViewBuilder
private var content: some View {
#if os(macOS)
VStack {
VStack(spacing: 0) {
list
HStack {

#if PULSE_STANDALONE_APP
HStack {
NavigatorFilterBar(text: $filterTerm)
.frame(maxWidth: 200)
.help("Show sessions with matching name")
}
#else
SearchBar(title: "Filter", imageName: "line.3.horizontal.decrease.circle", text: $filterTerm)
.frame(maxWidth: 200)
.help("Show sessions with matching name")
Divider()
SearchBar(title: "Filter", imageName: "line.3.horizontal.decrease.circle", text: $filterTerm)
.help("Show sessions with matching name")
.padding(8)
#endif
Spacer()
}.padding(8)
}
#else
list
Expand Down Expand Up @@ -92,10 +100,14 @@ struct SessionListView: View {

private func makeHeader(for startDate: Date, sessions: [LoggerSessionEntity]) -> some View {
HStack {
#if os(macOS)
PlainListSectionHeaderSeparator(title: sectionTitleFormatter.string(from: startDate) + " (\(sessions.count))")
#else
(Text(sectionTitleFormatter.string(from: startDate)) +
Text(" (\(sessions.count))").foregroundColor(.secondary.opacity(0.5)))
.font(.headline)
.padding(.vertical, 6)
#endif

#if os(iOS) || os(visionOS)
if editMode?.wrappedValue.isEditing ?? false {
Expand Down
Loading