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

fix: Suggestions in the macOS Safari extension #710

Merged
merged 2 commits into from
Jul 2, 2023
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
30 changes: 12 additions & 18 deletions core/Sources/BookmarksCore/Model/ItemViewModel.swift
Original file line number Diff line number Diff line change
Expand Up @@ -18,14 +18,16 @@
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
// SOFTWARE.

#if os(macOS)

import Combine
import SwiftUI

import Interact

class ItemViewModel: ObservableObject, Runnable {

let store: Store
let extensionModel: SafariExtensionModel
let pinboard: Pinboard

let tab: Tab
Expand All @@ -36,13 +38,11 @@ class ItemViewModel: ObservableObject, Runnable {
@Published var suggestions: [String] = []

@Published var tokens: [String] = []
@Published var input: String = ""
@Published var newSuggestions: [String] = []

var cancellables: [AnyCancellable] = []

init(store: Store, pinboard: Pinboard, tab: Tab) {
self.store = store
init(extensionModel: SafariExtensionModel, pinboard: Pinboard, tab: Tab) {
self.extensionModel = extensionModel
self.pinboard = pinboard
self.tab = tab
self.title = tab.title
Expand All @@ -69,14 +69,6 @@ class ItemViewModel: ObservableObject, Runnable {
}
}

$input
.debounce(for: 0.1, scheduler: DispatchQueue.main)
.filter { !$0.isEmpty }
.receive(on: DispatchQueue.main)
.map { [store] in store.suggestions(prefix: $0, existing: [], count: 1) }
.assign(to: \.newSuggestions, on: self)
.store(in: &cancellables)

}

func stop() {
Expand All @@ -91,15 +83,15 @@ class ItemViewModel: ObservableObject, Runnable {
post.tags = tokens
_ = try await pinboard.postsAdd(post)
DispatchQueue.main.async {
self.store.close(self.tab)
self.extensionModel.close(self.tab)
}
} else {
let post = Pinboard.Post(href: self.tab.url,
description: title,
tags: tokens)
_ = try await pinboard.postsAdd(post)
DispatchQueue.main.async {
self.store.close(self.tab)
self.extensionModel.close(self.tab)
}
}
} catch {
Expand All @@ -110,18 +102,20 @@ class ItemViewModel: ObservableObject, Runnable {

func close() {
withAnimation {
store.close(tab)
extensionModel.close(tab)
}
}

func remove() {
withAnimation {
store.close(tab)
extensionModel.close(tab)
}
}

func activate() {
store.activate(tab)
extensionModel.activate(tab)
}

}

#endif
32 changes: 9 additions & 23 deletions core/Sources/BookmarksCore/Model/SafariExtensionModel.swift
Original file line number Diff line number Diff line change
Expand Up @@ -23,13 +23,16 @@
import SafariServices
import SwiftUI

public class SafariExtensionModel: ObservableObject, Store {
public class SafariExtensionModel: ObservableObject {

let settings = Settings()
let tagsModel: TagsModel

@Published public var tabs: [Tab] = []

var tags = Trie()
private static let database: Database = {
try! Database(path: Database.sharedStoreURL)
}()

public var pinboard: Pinboard? {
guard let apiKey = settings.pinboardApiKey else {
Expand All @@ -39,29 +42,12 @@ public class SafariExtensionModel: ObservableObject, Store {
}

public init() {

}

public func update() {
// TODO: Show the authentication state to the user.
guard let pinboard = pinboard else {
return
}
Task {
do {
let tags = try await pinboard.tagsGet()
let trie = Trie(words: tags.keys.map({ $0.lowercased() }))
DispatchQueue.main.async {
self.tags = trie
}
} catch {
NSLog("Failed to get tags with error \(error)")
}
}
self.tagsModel = TagsModel(database: Self.database)
tagsModel.start()
}

public func suggestions(prefix: String, existing: [String], count: Int) -> [String] {
tags.suggestions(for: prefix, count: count)
@MainActor public func suggestions(prefix: String, existing: [String], count: Int) -> [String] {
return tagsModel.suggestions(candidate: prefix, existing: existing, count: count)
}

public func close(_ tab: Tab) {
Expand Down
30 changes: 0 additions & 30 deletions core/Sources/BookmarksCore/Model/Store.swift

This file was deleted.

10 changes: 5 additions & 5 deletions core/Sources/BookmarksCore/Views/ItemView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -26,14 +26,14 @@ import WrappingHStack

public struct ItemView: View {

let store: Store
var extensionModel: SafariExtensionModel

@StateObject var model: ItemViewModel
@State var title: String? = nil

public init(store: Store, pinboard: Pinboard, tab: Tab) {
self.store = store
_model = StateObject(wrappedValue: ItemViewModel(store: store, pinboard: pinboard, tab: tab))
public init(extensionModel: SafariExtensionModel, pinboard: Pinboard, tab: Tab) {
self.extensionModel = extensionModel
_model = StateObject(wrappedValue: ItemViewModel(extensionModel: extensionModel, pinboard: pinboard, tab: tab))
}

struct LayoutMetrics {
Expand Down Expand Up @@ -62,7 +62,7 @@ public struct ItemView: View {
Divider()

TokenView("Add tags...", tokens: $model.tokens) { candidate, existing, count in
return store.suggestions(prefix: candidate, existing: existing, count: count)
return extensionModel.suggestions(prefix: candidate, existing: existing, count: count)
}
.padding(.horizontal, 6)

Expand Down
2 changes: 1 addition & 1 deletion macos/SafariExtension/ContentView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ struct ContentView: View {
List {
if let pinboard = extensionModel.pinboard {
ForEach(Array(extensionModel.tabs)) { tab in
ItemView(store: extensionModel, pinboard: pinboard, tab: tab)
ItemView(extensionModel: extensionModel, pinboard: pinboard, tab: tab)
Divider()
}
} else {
Expand Down