release
Raz 1 year ago
parent 6bf9bdf634
commit 1dd2b1ee5d
  1. 2
      PadelClub/Data/Coredata/PadelClubApp.xcdatamodeld/Model_1_1.xcdatamodel/contents
  2. 23
      PadelClub/Data/Coredata/Persistence.swift
  3. 13
      PadelClub/Data/MonthData.swift
  4. 18
      PadelClub/Extensions/URL+Extensions.swift
  5. 1
      PadelClub/PadelClubApp.swift
  6. 19
      PadelClub/Utils/SourceFileManager.swift
  7. 15
      PadelClub/ViewModel/SearchViewModel.swift
  8. 3
      PadelClub/Views/Navigation/MainView.swift
  9. 5
      PadelClub/Views/Shared/SelectablePlayerListView.swift

@ -1,5 +1,5 @@
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<model type="com.apple.IDECoreDataModeler.DataModel" documentVersion="1.0" lastSavedToolsVersion="22757" systemVersion="23E214" minimumToolsVersion="Automatic" sourceLanguage="Swift" userDefinedModelVersionIdentifier="">
<model type="com.apple.IDECoreDataModeler.DataModel" documentVersion="1.0" lastSavedToolsVersion="22757" systemVersion="23E214" minimumToolsVersion="Automatic" sourceLanguage="Swift" userDefinedModelVersionIdentifier="v1.1">
<entity name="ImportedPlayer" representedClassName=".ImportedPlayer" syncable="YES" codeGenerationType="class">
<attribute name="assimilation" attributeType="String"/>
<attribute name="bestRank" optional="YES" attributeType="String"/>

@ -17,6 +17,20 @@ class PersistenceController: NSObject {
}
private static var _model: NSManagedObjectModel?
static func getModelVersion() -> String? {
if let versions = _model?.versionIdentifiers {
let currentVersion = versions.compactMap { $0 as? String }.joined(separator: ",")
//print("Current Model Version: \(currentVersion)")
// Compare the current model version with the saved version
return currentVersion
}
return nil
}
private static func model(name: String) throws -> NSManagedObjectModel {
if _model == nil {
_model = try loadModel(name: name, bundle: Bundle.main)
@ -47,10 +61,17 @@ class PersistenceController: NSObject {
let fileManager = FileManager.default
var firstLaunch = false
if fileManager.fileExists(atPath: localStoreFolderURL.path()) == false {
if fileManager.fileExists(atPath: localStoreFolderURL.appendingPathComponent("local.sqlite").path) == false {
firstLaunch = true
}
do {
let contents = try fileManager.contentsOfDirectory(atPath: localStoreFolderURL.path)
print("Directory contents: \(contents)")
} catch {
print("Failed to list directory contents: \(error)")
}
for folderURL in [localStoreFolderURL] where !fileManager.fileExists(atPath: folderURL.path) {
do {
try fileManager.createDirectory(at: folderURL, withIntermediateDirectories: true, attributes: nil)

@ -26,16 +26,14 @@ final class MonthData : ModelObject, Storable {
var femaleCount: Int? = nil
var anonymousCount: Int? = nil
var incompleteMode: Bool = false
var dataModelIdentifier: String?
var fileModelIdentifier: String?
init(monthKey: String) {
self.monthKey = monthKey
self.creationDate = Date()
}
fileprivate func _updateCreationDate() {
self.creationDate = Date()
}
required init(from decoder: Decoder) throws {
let container = try decoder.container(keyedBy: CodingKeys.self)
id = try container.decode(String.self, forKey: ._id)
@ -47,6 +45,8 @@ final class MonthData : ModelObject, Storable {
femaleCount = try container.decodeIfPresent(Int.self, forKey: ._femaleCount)
anonymousCount = try container.decodeIfPresent(Int.self, forKey: ._anonymousCount)
incompleteMode = try container.decodeIfPresent(Bool.self, forKey: ._incompleteMode) ?? false
dataModelIdentifier = try container.decodeIfPresent(String.self, forKey: ._dataModelIdentifier) ?? nil
fileModelIdentifier = try container.decodeIfPresent(String.self, forKey: ._fileModelIdentifier) ?? nil
}
@ -69,7 +69,8 @@ final class MonthData : ModelObject, Storable {
await MainActor.run {
let lastDataSource = URL.importDateFormatter.string(from: fromDate)
let currentMonthData : MonthData = DataStore.shared.monthData.first(where: { $0.monthKey == lastDataSource }) ?? MonthData(monthKey: lastDataSource)
currentMonthData._updateCreationDate()
currentMonthData.dataModelIdentifier = PersistenceController.getModelVersion()
currentMonthData.fileModelIdentifier = fileURL?.fileModelIdentifier()
currentMonthData.maleUnrankedValue = incompleteMode ? fftImportingMaleUnrankValue : lastDataSourceMaleUnranked?.0
currentMonthData.incompleteMode = incompleteMode
currentMonthData.maleCount = incompleteMode ? fftImportingUncomplete : lastDataSourceMaleUnranked?.1
@ -97,5 +98,7 @@ final class MonthData : ModelObject, Storable {
case _femaleCount = "femaleCount"
case _anonymousCount = "anonymousCount"
case _incompleteMode = "incompleteMode"
case _dataModelIdentifier = "dataModelIdentifier"
case _fileModelIdentifier = "fileModelIdentifier"
}
}

@ -107,6 +107,24 @@ extension URL {
return nil
}
func fileModelIdentifier() -> String? {
// Read the contents of the file
guard let fileContents = try? String(contentsOfFile: path(), encoding: .utf8) else {
return nil
}
// Split the contents by newline characters
let lines = fileContents.components(separatedBy: .newlines)
if let line = lines.first(where: {
$0.hasPrefix("file-model-version:")
}) {
return line.replacingOccurrences(of: "file-model-version:", with: "")
}
return nil
}
func fftImportingUncomplete() -> Int? {
// Read the contents of the file
guard let fileContents = try? String(contentsOfFile: path(), encoding: .utf8) else {

@ -76,6 +76,7 @@ struct PadelClubApp: App {
.onAppear {
networkMonitor.checkConnection()
self._onAppear()
print(PersistenceController.getModelVersion())
}
.task {

@ -225,6 +225,25 @@ class SourceFileManager {
return importDate.isEarlierThan(date)
}
static func getSortOption() -> [SortOption] {
if canFilterByAge() {
return SortOption.allCases
} else {
return [.name, .rank, .tournamentCount, .points]
}
}
static func canFilterByAge() -> Bool {
let currentMonthData = DataStore.shared.monthData.first(where: { data in
data.monthKey == DataStore.shared.appSettings.lastDataSource
})
let currentModelVersion = PersistenceController.getModelVersion()
if let currentMonthData, currentMonthData.fileModelIdentifier == currentModelVersion, currentModelVersion != nil {
return true
}
return false
}
}
enum SourceFile: String, CaseIterable {

@ -421,16 +421,23 @@ enum DataSet: Int, Identifiable {
}
var tokens: [SearchToken] {
var _tokens : [SearchToken] = []
switch self {
case .national:
return [.club, .ligue, .rankMoreThan, .rankLessThan, .rankBetween, .age]
_tokens = [.club, .ligue, .rankMoreThan, .rankLessThan, .rankBetween]
case .ligue:
return [.club, .rankMoreThan, .rankLessThan, .rankBetween, .age]
_tokens = [.club, .rankMoreThan, .rankLessThan, .rankBetween]
case .club:
return [.rankMoreThan, .rankLessThan, .rankBetween, .age]
_tokens = [.rankMoreThan, .rankLessThan, .rankBetween]
case .favoritePlayers, .favoriteClubs:
return [.rankMoreThan, .rankLessThan, .rankBetween, .age]
_tokens = [.rankMoreThan, .rankLessThan, .rankBetween]
}
if SourceFileManager.canFilterByAge() {
_tokens.append(.age)
}
return _tokens
}
}

@ -257,11 +257,14 @@ struct MainView: View {
if let current = monthData.last {
Task {
let updated = await SourceFileManager.shared.fetchData(fromDate: mostRecentDateImported)
let fileURL = SourceFileManager.shared.allFiles(true).first(where: { $0.dateFromPath == mostRecentDateImported && $0.index == 0 })
print("file updated", updated)
if let updated, updated == 1 {
await _startImporting(importingDate: mostRecentDateImported)
} else if current.incompleteMode == false || updated == 0 {
await _calculateMonthData(dataSource: current.monthKey)
} else if current.dataModelIdentifier != PersistenceController.getModelVersion() && current.dataModelIdentifier != fileURL?.fileModelIdentifier() {
await _startImporting(importingDate: mostRecentDateImported)
}
}
}

@ -74,7 +74,7 @@ struct SelectablePlayerListView: View {
.pickerStyle(.segmented)
Menu {
Section {
ForEach(SortOption.allCases) { option in
ForEach(SourceFileManager.getSortOption()) { option in
Toggle(isOn: .init(get: {
return searchViewModel.sortOption == option
}, set: { value in
@ -90,6 +90,8 @@ struct SelectablePlayerListView: View {
Text("Trier par")
}
Divider()
if SourceFileManager.canFilterByAge() {
Section {
Picker(selection: $searchViewModel.selectedAgeCategory) {
ForEach(FederalTournamentAge.allCases) { ageCategory in
@ -103,6 +105,7 @@ struct SelectablePlayerListView: View {
Text("Catégorie d'âge")
}
Divider()
}
Section {
Toggle(isOn: .init(get: {
return searchViewModel.hideAssimilation == false

Loading…
Cancel
Save