Nextcloud Login refactoring
This commit is contained in:
44
Nextcloud Cookbook iOS Client/Data/AuthManager.swift
Normal file
44
Nextcloud Cookbook iOS Client/Data/AuthManager.swift
Normal file
@@ -0,0 +1,44 @@
|
||||
//
|
||||
// AuthManager.swift
|
||||
// Nextcloud Cookbook iOS Client
|
||||
//
|
||||
// Created by Vincent Meilinger on 30.05.25.
|
||||
//
|
||||
|
||||
import Foundation
|
||||
import KeychainSwift
|
||||
|
||||
class AuthManager {
|
||||
static let shared = AuthManager()
|
||||
let keychain = KeychainSwift()
|
||||
|
||||
var authString: String? = nil
|
||||
|
||||
private let nextcloudUsernameKey = "nextcloud_username"
|
||||
private let nextcloudAuthStringKey = "nextcloud_auth_string" // Stored as base64
|
||||
|
||||
func saveNextcloudCredentials(username: String, appPassword: String) {
|
||||
keychain.set(username, forKey: nextcloudUsernameKey)
|
||||
|
||||
let loginString = "\(username):\(appPassword)"
|
||||
if let loginData = loginString.data(using: .utf8) {
|
||||
keychain.set(loginData.base64EncodedString(), forKey: nextcloudAuthStringKey)
|
||||
}
|
||||
}
|
||||
|
||||
func getNextcloudCredentials() -> (username: String?, authString: String?) {
|
||||
let username = keychain.get(nextcloudUsernameKey)
|
||||
let authString = keychain.get(nextcloudAuthStringKey)
|
||||
|
||||
return (username, authString)
|
||||
}
|
||||
|
||||
func loadAuthString() {
|
||||
authString = keychain.get(nextcloudAuthStringKey)
|
||||
}
|
||||
|
||||
func deleteNextcloudCredentials() {
|
||||
keychain.delete(nextcloudUsernameKey)
|
||||
keychain.delete(nextcloudAuthStringKey)
|
||||
}
|
||||
}
|
||||
@@ -51,7 +51,7 @@ class Recipe {
|
||||
var name: String
|
||||
var keywords: [String]
|
||||
@Attribute(.externalStorage) var image: RecipeImage?
|
||||
var thumbnail: RecipeThumbnail?
|
||||
@Attribute(.externalStorage) var thumbnail: RecipeThumbnail?
|
||||
var dateCreated: String? = nil
|
||||
var dateModified: String? = nil
|
||||
var prepTime: String
|
||||
@@ -70,6 +70,16 @@ class Recipe {
|
||||
@Transient
|
||||
var ingredientMultiplier: Double = 1.0
|
||||
|
||||
var prepTimeDurationComponent: DurationComponents {
|
||||
DurationComponents.fromPTString(prepTime)
|
||||
}
|
||||
var cookTimeDurationComponent: DurationComponents {
|
||||
DurationComponents.fromPTString(cookTime)
|
||||
}
|
||||
var totalTimeDurationComponent: DurationComponents {
|
||||
DurationComponents.fromPTString(totalTime)
|
||||
}
|
||||
|
||||
|
||||
init(
|
||||
id: String,
|
||||
@@ -109,50 +119,24 @@ class Recipe {
|
||||
self.ingredientMultiplier = ingredientMultiplier
|
||||
}
|
||||
|
||||
required init(from decoder: Decoder) throws {
|
||||
let container = try decoder.container(keyedBy: CodingKeys.self)
|
||||
id = try container.decode(String.self, forKey: .id)
|
||||
name = try container.decode(String.self, forKey: .name)
|
||||
keywords = try container.decode([String].self, forKey: .keywords)
|
||||
dateCreated = try container.decodeIfPresent(String.self, forKey: .dateCreated)
|
||||
dateModified = try container.decodeIfPresent(String.self, forKey: .dateModified)
|
||||
prepTime = try container.decode(String.self, forKey: .prepTime)
|
||||
cookTime = try container.decode(String.self, forKey: .cookTime)
|
||||
totalTime = try container.decode(String.self, forKey: .totalTime)
|
||||
recipeDescription = try container.decode(String.self, forKey: .recipeDescription)
|
||||
url = try container.decodeIfPresent(String.self, forKey: .url)
|
||||
yield = try container.decode(Int.self, forKey: .yield)
|
||||
category = try container.decode(String.self, forKey: .category)
|
||||
tools = try container.decode([String].self, forKey: .tools)
|
||||
ingredients = try container.decode([String].self, forKey: .ingredients)
|
||||
instructions = try container.decode([String].self, forKey: .instructions)
|
||||
nutrition = try container.decode([String: String].self, forKey: .nutrition)
|
||||
}
|
||||
}
|
||||
|
||||
extension Recipe: Codable {
|
||||
enum CodingKeys: String, CodingKey {
|
||||
case id, name, keywords, dateCreated, dateModified, prepTime, cookTime, totalTime, recipeDescription, url, yield, category, tools, ingredients, instructions, nutrition
|
||||
}
|
||||
|
||||
func encode(to encoder: Encoder) throws {
|
||||
var container = encoder.container(keyedBy: CodingKeys.self)
|
||||
try container.encode(id, forKey: .id)
|
||||
try container.encode(name, forKey: .name)
|
||||
try container.encode(keywords, forKey: .keywords)
|
||||
try container.encode(dateCreated, forKey: .dateCreated)
|
||||
try container.encode(dateModified, forKey: .dateModified)
|
||||
try container.encode(prepTime, forKey: .prepTime)
|
||||
try container.encode(cookTime, forKey: .cookTime)
|
||||
try container.encode(totalTime, forKey: .totalTime)
|
||||
try container.encode(recipeDescription, forKey: .recipeDescription)
|
||||
try container.encode(url, forKey: .url)
|
||||
try container.encode(yield, forKey: .yield)
|
||||
try container.encode(category, forKey: .category)
|
||||
try container.encode(tools, forKey: .tools)
|
||||
try container.encode(ingredients, forKey: .ingredients)
|
||||
try container.encode(instructions, forKey: .instructions)
|
||||
try container.encode(nutrition, forKey: .nutrition)
|
||||
init() {
|
||||
self.id = UUID().uuidString
|
||||
self.name = String(localized: "New Recipe")
|
||||
self.keywords = []
|
||||
self.dateCreated = nil
|
||||
self.dateModified = nil
|
||||
self.prepTime = "0"
|
||||
self.cookTime = "0"
|
||||
self.totalTime = "0"
|
||||
self.recipeDescription = ""
|
||||
self.url = ""
|
||||
self.yield = 1
|
||||
self.category = ""
|
||||
self.tools = []
|
||||
self.ingredients = []
|
||||
self.instructions = []
|
||||
self.nutrition = [:]
|
||||
self.ingredientMultiplier = 1
|
||||
}
|
||||
}
|
||||
// MARK: - Recipe Stub
|
||||
|
||||
Reference in New Issue
Block a user