Skip to content

Commit

Permalink
Merged with master
Browse files Browse the repository at this point in the history
  • Loading branch information
insidegui committed Jun 2, 2023
2 parents 0b9863c + d57b449 commit 6e31563
Show file tree
Hide file tree
Showing 10 changed files with 162 additions and 17 deletions.
9 changes: 5 additions & 4 deletions Packages/ConfCore/ConfCore/StorageMigrator.swift
Original file line number Diff line number Diff line change
Expand Up @@ -27,9 +27,10 @@ final class StorageMigrator {
32: migrateSessionModels,
34: migrateOldTranscriptModels,
37: migrateIdentifiersWithoutReplacement,
43: migrateTracks,
43: resetTracks,
44: removeInvalidLiveAssets,
57: resetFeaturedSections
57: resetFeaturedSections,
59: resetTracks
]

init(migration: Migration, oldVersion: UInt64) {
Expand Down Expand Up @@ -162,8 +163,8 @@ final class StorageMigrator {
}
}

private static func migrateTracks(with migration: Migration, oldVersion: SchemaVersion, log: OSLog) {
os_log("migrateTracks", log: log, type: .info)
private static func resetTracks(with migration: Migration, oldVersion: SchemaVersion, log: OSLog) {
os_log("resetTracks", log: log, type: .info)

migration.deleteData(forType: "Track")
}
Expand Down
4 changes: 4 additions & 0 deletions WWDC.xcodeproj/project.pbxproj
Original file line number Diff line number Diff line change
Expand Up @@ -187,6 +187,7 @@
F4578D9F2A26A218005B311A /* WWDCAppCommand.swift in Sources */ = {isa = PBXBuildFile; fileRef = F4578D9E2A26A218005B311A /* WWDCAppCommand.swift */; };
F474DEC926737EFA00B28B31 /* SharePlayManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = F474DEC826737EFA00B28B31 /* SharePlayManager.swift */; };
F474DECD2673801500B28B31 /* WatchWWDCActivity.swift in Sources */ = {isa = PBXBuildFile; fileRef = F474DECC2673801500B28B31 /* WatchWWDCActivity.swift */; };
F4777ABA2A2A2F6C00A09179 /* WWDCAgentRemover.swift in Sources */ = {isa = PBXBuildFile; fileRef = F4777AB92A2A2F6C00A09179 /* WWDCAgentRemover.swift */; };
F4A882842673AC8500BAB7F5 /* TitleBarButtonsViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = F4A882832673AC8500BAB7F5 /* TitleBarButtonsViewController.swift */; };
F4A882882673AD2D00BAB7F5 /* SharePlayStatusView.swift in Sources */ = {isa = PBXBuildFile; fileRef = F4A882862673AD2D00BAB7F5 /* SharePlayStatusView.swift */; };
F4CCF942265ED24500A69E62 /* AppCommandsReceiver.swift in Sources */ = {isa = PBXBuildFile; fileRef = F4CCF941265ED24500A69E62 /* AppCommandsReceiver.swift */; };
Expand Down Expand Up @@ -455,6 +456,7 @@
F4578D9E2A26A218005B311A /* WWDCAppCommand.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = WWDCAppCommand.swift; sourceTree = "<group>"; };
F474DEC826737EFA00B28B31 /* SharePlayManager.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SharePlayManager.swift; sourceTree = "<group>"; };
F474DECC2673801500B28B31 /* WatchWWDCActivity.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WatchWWDCActivity.swift; sourceTree = "<group>"; };
F4777AB92A2A2F6C00A09179 /* WWDCAgentRemover.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WWDCAgentRemover.swift; sourceTree = "<group>"; };
F4A882832673AC8500BAB7F5 /* TitleBarButtonsViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TitleBarButtonsViewController.swift; sourceTree = "<group>"; };
F4A882862673AD2D00BAB7F5 /* SharePlayStatusView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = SharePlayStatusView.swift; sourceTree = "<group>"; };
F4CCF941265ED24500A69E62 /* AppCommandsReceiver.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppCommandsReceiver.swift; sourceTree = "<group>"; };
Expand Down Expand Up @@ -593,6 +595,7 @@
children = (
01B3EB491EEDD23100DE1003 /* AppCoordinator+SessionTableViewContextMenuActions.swift */,
DDA50E3424AA5090007C77C6 /* Boot.swift */,
F4777AB92A2A2F6C00A09179 /* WWDCAgentRemover.swift */,
DD36A4AF1E478C6A00B2EA88 /* AppDelegate.swift */,
DDCE7ED81EA7A86600C7A3CA /* AppCoordinator.swift */,
F4CCF941265ED24500A69E62 /* AppCommandsReceiver.swift */,
Expand Down Expand Up @@ -1407,6 +1410,7 @@
DDF32EAB1EBE2E240028E39D /* WWDCTableRowView.swift in Sources */,
DD7E2902247FEA3900A58370 /* EventHeroViewController.swift in Sources */,
DDC927FE20B7A259004C784D /* NSImage+Compression.swift in Sources */,
F4777ABA2A2A2F6C00A09179 /* WWDCAgentRemover.swift in Sources */,
DD7A2103218111470052FD07 /* WWDCProgressIndicator.swift in Sources */,
DD7F38681EABE4E4002D8C00 /* SessionViewModel.swift in Sources */,
DD9564231ED27FBE00051D07 /* NSImage+Thumbnail.swift in Sources */,
Expand Down
2 changes: 2 additions & 0 deletions WWDC/Boot.swift
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,8 @@ final class Boot {
return
}

WWDCAgentRemover.removeWWDCAgentIfNeeded()

do {
let supportPath = try PathUtil.appSupportPathCreatingIfNeeded()
let filePath = supportPath + "/ConfCore.realm"
Expand Down
2 changes: 1 addition & 1 deletion WWDC/Constants.swift
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ import Foundation

struct Constants {

static let coreSchemaVersion: UInt64 = 58
static let coreSchemaVersion: UInt64 = 59

static let thumbnailHeight: CGFloat = 150

Expand Down
36 changes: 35 additions & 1 deletion WWDC/ExploreTabContent.swift
Original file line number Diff line number Diff line change
Expand Up @@ -72,13 +72,47 @@ extension ExploreTabContent.Item {
imageURL: URL(string: "https://wwdc.io/images/placeholder.jpg")!
)
]
static let placeholderItems2: [ExploreTabContent.Item] = [
.init(
id: "4",
title: "Placeholder Item Regular",
subtitle: "Placeholder Description 4",
overlayText: "24m",
overlaySymbol: "play",
imageURL: URL(string: "https://wwdc.io/images/placeholder.jpg")!
),
.init(
id: "5",
title: "Placeholder",
subtitle: "Placeholder Item Description 5",
overlayText: "37m",
overlaySymbol: "play",
imageURL: URL(string: "https://wwdc.io/images/placeholder.jpg")!
),
.init(
id: "6",
title: "Placeholder Item Longer Title",
subtitle: "Placeholder Item Description 6",
overlayText: "37m",
overlaySymbol: "play",
imageURL: URL(string: "https://wwdc.io/images/placeholder.jpg")!
),
.init(
id: "7",
title: "Placeholder",
subtitle: "Item Description 7",
overlayText: "35m",
overlaySymbol: "play",
imageURL: URL(string: "https://wwdc.io/images/placeholder.jpg")!
)
]
}

extension ExploreTabContent {
static let placeholder: ExploreTabContent = {
ExploreTabContent(id: "1", sections: [
Section(id: "placeholder-1", title: "Placeholder Section First", icon: .symbol("app.badge.checkmark"), items: ExploreTabContent.Item.placeholderItems),
Section(id: "placeholder-2", title: "Placeholder Section Second Longer Title", icon: .symbol("app.badge.checkmark"), items: ExploreTabContent.Item.placeholderItems),
Section(id: "placeholder-2", title: "Placeholder Section Second Longer Title", icon: .symbol("app.badge.checkmark"), items: ExploreTabContent.Item.placeholderItems2),
Section(id: "placeholder-3", title: "Placeholder Short", icon: .symbol("app.badge.checkmark"), items: ExploreTabContent.Item.placeholderItems)
])
}()
Expand Down
8 changes: 7 additions & 1 deletion WWDC/ExploreTabItemView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,13 @@ struct ExploreTabItemView: View {
item.progress != nil ? .topTrailing : .bottomTrailing
}

private var hasOverlay: Bool { item.overlayText != nil || item.overlaySymbol != nil }
@Environment(\.redactionReasons)
private var redactionReasons

private var hasOverlay: Bool {
guard redactionReasons.isEmpty else { return false }
return item.overlayText != nil || item.overlaySymbol != nil
}

var body: some View {
VStack(alignment: .leading, spacing: 8) {
Expand Down
16 changes: 15 additions & 1 deletion WWDC/ExploreTabProvider.swift
Original file line number Diff line number Diff line change
Expand Up @@ -71,7 +71,7 @@ final class ExploreTabProvider: ObservableObject {

private var disposeBag = DisposeBag()

private struct SourceData {
fileprivate struct SourceData {
var featuredSections: Results<FeaturedSection>
var continueWatching: [Session]
var recentFavorites: [Session]
Expand Down Expand Up @@ -101,6 +101,8 @@ final class ExploreTabProvider: ObservableObject {
}

private func update(with data: SourceData) {
guard !data.shouldDisplayPlaceholderUI else { return }

let continueWatchingSection = ExploreTabContent.Section(
id: "continue-watching",
title: "Continue Watching",
Expand Down Expand Up @@ -293,3 +295,15 @@ extension WWDCFiltersState {
)
}
}

private extension ExploreTabProvider.SourceData {
/// `true` when all sections except for "Topics" are empty.
/// This addresses migration from previous versions without an Explore tab,
/// where the local database has topics but no other data relevant to the explore tab.
var shouldDisplayPlaceholderUI: Bool {
featuredSections.isEmpty
&& continueWatching.isEmpty
&& recentFavorites.isEmpty
&& liveEventSession == nil
}
}
19 changes: 11 additions & 8 deletions WWDC/ExploreTabRootView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -4,15 +4,18 @@ struct ExploreTabRootView: View {
@EnvironmentObject private var provider: ExploreTabProvider

var body: some View {
if let content = provider.content {
ExploreTabContentView(content: content, scrollOffset: $provider.scrollOffset)
#if DEBUG
.contextMenu { Button("Export JSON…", action: content.exportJSON) }
#endif
} else {
ExploreTabContentView(content: .placeholder, scrollOffset: .constant(.zero))
.redacted(reason: .placeholder)
ZStack {
if let content = provider.content {
ExploreTabContentView(content: content, scrollOffset: $provider.scrollOffset)
#if DEBUG
.contextMenu { Button("Export JSON…", action: content.exportJSON) }
#endif
} else {
ExploreTabContentView(content: .placeholder, scrollOffset: .constant(.zero))
.redacted(reason: .placeholder)
}
}
.animation(.spring(), value: provider.content?.sections.flatMap(\.items).count)
}

}
Expand Down
2 changes: 1 addition & 1 deletion WWDC/Main.xcconfig
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
#include "TeamID.xcconfig"

MARKETING_VERSION = 7.4
CURRENT_PROJECT_VERSION = 1034
CURRENT_PROJECT_VERSION = 1036

MACOSX_DEPLOYMENT_TARGET = 12.0

Expand Down
81 changes: 81 additions & 0 deletions WWDC/WWDCAgentRemover.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,81 @@
import Cocoa
import OSLog

/// Handles removal of the legacy `WWDCAgent` helper process,
/// which is no longer available but may cause database migration
/// issues on first launch of version 7.4.
struct WWDCAgentRemover {

private static let logger = Logger(subsystem: "io.wwdc.app", category: "WWDCAgentRemover")

private static let agentBundleID = "io.wwdc.app.WWDCAgent"

private static let agentLaunchdServiceID: String = { "gui/\(getuid())/\(agentBundleID)" }()

private static var performedLegacyAgentRemoval: Bool {
get { UserDefaults.standard.bool(forKey: #function) }
set {
UserDefaults.standard.set(newValue, forKey: #function)
UserDefaults.standard.synchronize()
}
}

static func removeWWDCAgentIfNeeded() {
guard !performedLegacyAgentRemoval else { return }

/// Set the flag regardless of the removal result.
/// The idea is to avoid potential launch issues caused
/// by repeated attempts in case removal fails for some obscure reason.
defer { performedLegacyAgentRemoval = true }

guard let agent = NSRunningApplication.runningApplications(withBundleIdentifier: agentBundleID).first else {
logger.debug("Couldn't find \(agentBundleID, privacy: .public) process, skipping legacy agent removal")
return
}

unregisterAgent()

guard !agent.isTerminated else {
logger.debug("Legacy agent process is present, but already terminated")
return
}

if !agent.forceTerminate() {
logger.warning("Force terminate failed for \(agentBundleID, privacy: .public)")
} else {
logger.debug("Successfully terminated legacy agent")
}
}

private static func unregisterAgent() {
logger.debug("Requesting removal of service \(agentLaunchdServiceID, privacy: .public)")

let proc = Process()
proc.executableURL = URL(fileURLWithPath: "/bin/launchctl")
proc.arguments = [
"bootout",
agentLaunchdServiceID
]
let outPipe = Pipe()
let errPipe = Pipe()
proc.standardOutput = outPipe
proc.standardError = errPipe

do {
try proc.run()

proc.waitUntilExit()

guard proc.terminationStatus == 0 else {
let output = (try? errPipe.fileHandleForReading.readToEnd().flatMap { String(decoding: $0, as: UTF8.self) }) ?? "<nil>"
logger.error("launchctl operation failed with exit code \(proc.terminationStatus, privacy: .public): \(output, privacy: .public)")
return
}

logger.debug("launchctl operation succeeded")
} catch {
logger.fault("Failed to run launchctl: \(error, privacy: .public)")
}
}

}

0 comments on commit 6e31563

Please sign in to comment.