Для некоторых полей, отличных от messageType, условие «IN» работает нормально.
Вот быстрый пример для проверки:
public extension Logger {
static let appSubsystem = Bundle.main.bundleIdentifier!
static func fetch(since date: Date) async throws -> [String] {
let store = try OSLogStore(scope: .currentProcessIdentifier)
let position = store.position(date: date)
// This does NOT work.
// let predicate = NSPredicate(format: "(subsystem == %@) && (messageType IN %@)", Logger.appSubsystem, ["error", "fault"])
// This, however, works.
let predicate = NSPredicate(format: "(subsystem IN %@) && (messageType == %@)", [Logger.appSubsystem], "error")
let entries = try store.getEntries(/* with: [.reverse], */ at: position,
matching: predicate)
var logs: [String] = []
for entry in entries {
try Task.checkCancellation()
if let log = entry as? OSLogEntryLog {
logs.append("""
\(entry.date):\(log.subsystem):\
\(log.category):\(log.level): \
\(entry.composedMessage)\n
""")
} else {
logs.append("\(entry.date): \(entry.composedMessage)\n")
}
}
if logs.isEmpty { logs = ["Nothing found"] }
return logs
}
}
Вот небольшой экран SwiftUI, который поможет воспроизвести проблему.
import SwiftUI
import OSLog
struct LogView: View {
@State private var text = "Loading..."
@State private var task: Task?
@State private var isLoading = false
@State private var selectedLogLevel: OSLogEntryLog.Level = .undefined
private let logLevels: [OSLogEntryLog.Level] = [.undefined, .debug, .info, .notice, .error, .fault]
let logger = Logger(subsystem: Logger.appSubsystem, category: "main")
var body: some View {
VStack {
HStack {
Button(isLoading ? "Cancel" : "Refresh") {
if isLoading {
task?.cancel()
} else {
task = Task {
text = await fetchLogs()
isLoading = false
}
}
}
ProgressView()
.opacity(isLoading ? 1 : 0)
Picker(selection: $selectedLogLevel, label: Text("Choose Log Level")) {
ForEach(logLevels) { logLevel in
Text(logLevel.description)
.tag(logLevel)
}
}
Button("Log") {
logMessage(selectedLogLevel: selectedLogLevel)
}
}
ScrollView {
Text(text)
.textSelection(.enabled)
.fontDesign(.monospaced)
.padding()
}
}
.onAppear {
isLoading = true
task = Task {
text = await fetchLogs()
isLoading = false
}
}
}
}
private extension LogView {
@MainActor
func fetchLogs() async -> String {
let calendar = Calendar.current
guard let hourAgo = calendar.date(byAdding: .hour,
value: -1, to: Date.now) else {
return "Invalid calendar"
}
do {
let logs = try await Logger.fetch(since: hourAgo)
return logs.joined()
} catch {
return error.localizedDescription
}
}
func logMessage(selectedLogLevel: OSLogEntryLog.Level) {
switch(selectedLogLevel) {
case .undefined:
logger.log("Default log message")
case .debug:
logger.debug("Debug log message")
case .info:
logger.info("Info log message")
// case .warning:
// logger.warning("Warning log message")
case .notice:
logger.notice("Notice log message")
case .error:
logger.error("Error log message")
case .fault:
logger.fault("Fault log message")
@unknown default:
logger.log("Default log message")
}
}
}
extension OSLogEntryLog.Level: @retroactive CustomStringConvertible {
public var description: String {
switch self {
case .undefined: "undefined"
case .debug: "debug"
case .info: "info"
case .notice: "notice"
case .error: "error"
case .fault: "fault"
@unknown default: "default"
}
}
}
Подробнее здесь: https://stackoverflow.com/questions/793 ... or-message
Функция OSLogStore `getEntries(with:, at:, match: predicate)` завершается с ошибкой для типов предикатов "messageType IN ⇐ IOS
Программируем под IOS
1737116339
Anonymous
Для некоторых полей, отличных от messageType, условие «IN» работает нормально.
Вот быстрый пример для проверки:
public extension Logger {
static let appSubsystem = Bundle.main.bundleIdentifier!
static func fetch(since date: Date) async throws -> [String] {
let store = try OSLogStore(scope: .currentProcessIdentifier)
let position = store.position(date: date)
// This does NOT work.
// let predicate = NSPredicate(format: "(subsystem == %@) && (messageType IN %@)", Logger.appSubsystem, ["error", "fault"])
// This, however, works.
let predicate = NSPredicate(format: "(subsystem IN %@) && (messageType == %@)", [Logger.appSubsystem], "error")
let entries = try store.getEntries(/* with: [.reverse], */ at: position,
matching: predicate)
var logs: [String] = []
for entry in entries {
try Task.checkCancellation()
if let log = entry as? OSLogEntryLog {
logs.append("""
\(entry.date):\(log.subsystem):\
\(log.category):\(log.level): \
\(entry.composedMessage)\n
""")
} else {
logs.append("\(entry.date): \(entry.composedMessage)\n")
}
}
if logs.isEmpty { logs = ["Nothing found"] }
return logs
}
}
Вот небольшой экран SwiftUI, который поможет воспроизвести проблему.
import SwiftUI
import OSLog
struct LogView: View {
@State private var text = "Loading..."
@State private var task: Task?
@State private var isLoading = false
@State private var selectedLogLevel: OSLogEntryLog.Level = .undefined
private let logLevels: [OSLogEntryLog.Level] = [.undefined, .debug, .info, .notice, .error, .fault]
let logger = Logger(subsystem: Logger.appSubsystem, category: "main")
var body: some View {
VStack {
HStack {
Button(isLoading ? "Cancel" : "Refresh") {
if isLoading {
task?.cancel()
} else {
task = Task {
text = await fetchLogs()
isLoading = false
}
}
}
ProgressView()
.opacity(isLoading ? 1 : 0)
Picker(selection: $selectedLogLevel, label: Text("Choose Log Level")) {
ForEach(logLevels) { logLevel in
Text(logLevel.description)
.tag(logLevel)
}
}
Button("Log") {
logMessage(selectedLogLevel: selectedLogLevel)
}
}
ScrollView {
Text(text)
.textSelection(.enabled)
.fontDesign(.monospaced)
.padding()
}
}
.onAppear {
isLoading = true
task = Task {
text = await fetchLogs()
isLoading = false
}
}
}
}
private extension LogView {
@MainActor
func fetchLogs() async -> String {
let calendar = Calendar.current
guard let hourAgo = calendar.date(byAdding: .hour,
value: -1, to: Date.now) else {
return "Invalid calendar"
}
do {
let logs = try await Logger.fetch(since: hourAgo)
return logs.joined()
} catch {
return error.localizedDescription
}
}
func logMessage(selectedLogLevel: OSLogEntryLog.Level) {
switch(selectedLogLevel) {
case .undefined:
logger.log("Default log message")
case .debug:
logger.debug("Debug log message")
case .info:
logger.info("Info log message")
// case .warning:
// logger.warning("Warning log message")
case .notice:
logger.notice("Notice log message")
case .error:
logger.error("Error log message")
case .fault:
logger.fault("Fault log message")
@unknown default:
logger.log("Default log message")
}
}
}
extension OSLogEntryLog.Level: @retroactive CustomStringConvertible {
public var description: String {
switch self {
case .undefined: "undefined"
case .debug: "debug"
case .info: "info"
case .notice: "notice"
case .error: "error"
case .fault: "fault"
@unknown default: "default"
}
}
}
Подробнее здесь: [url]https://stackoverflow.com/questions/79364678/oslogstore-func-getentrieswith-at-matching-predicate-fails-for-message[/url]
Ответить
1 сообщение
• Страница 1 из 1
Перейти
- Кемерово-IT
- ↳ Javascript
- ↳ C#
- ↳ JAVA
- ↳ Elasticsearch aggregation
- ↳ Python
- ↳ Php
- ↳ Android
- ↳ Html
- ↳ Jquery
- ↳ C++
- ↳ IOS
- ↳ CSS
- ↳ Excel
- ↳ Linux
- ↳ Apache
- ↳ MySql
- Детский мир
- Для души
- ↳ Музыкальные инструменты даром
- ↳ Печатная продукция даром
- Внешняя красота и здоровье
- ↳ Одежда и обувь для взрослых даром
- ↳ Товары для здоровья
- ↳ Физкультура и спорт
- Техника - даром!
- ↳ Автомобилистам
- ↳ Компьютерная техника
- ↳ Плиты: газовые и электрические
- ↳ Холодильники
- ↳ Стиральные машины
- ↳ Телевизоры
- ↳ Телефоны, смартфоны, плашеты
- ↳ Швейные машинки
- ↳ Прочая электроника и техника
- ↳ Фототехника
- Ремонт и интерьер
- ↳ Стройматериалы, инструмент
- ↳ Мебель и предметы интерьера даром
- ↳ Cантехника
- Другие темы
- ↳ Разное даром
- ↳ Давай меняться!
- ↳ Отдам\возьму за копеечку
- ↳ Работа и подработка в Кемерове
- ↳ Давай с тобой поговорим...
Мобильная версия