// // account.swift // 74 桌 // // Created by yunli on 2023/5/20. // import Alamofire import SwiftUI struct Constant { var cookiesDefaultsKey: String } let Constants: Constant = .init(cookiesDefaultsKey: "JSESSIONID") class CookieHandler { static let shared: CookieHandler = .init() let defaults = UserDefaults.standard let cookieStorage = HTTPCookieStorage.shared func getCookie(forURL url: String) -> [HTTPCookie] { let computedUrl = URL(string: url) let cookies = cookieStorage.cookies(for: computedUrl!) ?? [] return cookies } func backupCookies(forURL url: String) { var cookieDict = [String: AnyObject]() for cookie in getCookie(forURL: url) { cookieDict[cookie.name] = cookie.properties as AnyObject? } defaults.set(cookieDict, forKey: Constants.cookiesDefaultsKey) } func restoreCookies() { if let cookieDictionary = defaults.dictionary(forKey: Constants.cookiesDefaultsKey) { for (_, cookieProperties) in cookieDictionary { if let cookie = HTTPCookie(properties: cookieProperties as! [HTTPCookiePropertyKey: Any]) { cookieStorage.setCookie(cookie) } } } } } struct Login: Encodable { let user: String let pwd: String let cook: String } struct UserInfo: Encodable { var name: String var o: String } class LoginHandler { static let sharedInstance = LoginHandler() func getCookie(name: String) -> HTTPCookie? { if let cookie = CookieHandler().getCookie(forURL: "https://debug.sdsz.icu:81/").filter({ cookie -> Bool in cookie.name == name }).first { return cookie } return nil } func fetchLoginCookie(action: @escaping (_: String) -> Void) { if let cookie = getCookie(name: "JSESSIONID") { HTTPCookieStorage.shared.deleteCookie(cookie) print(cookie) } let url = "https://debug.sdsz.icu:81/sso/login" AF.request(url, method: .get, parameters: nil, encoding: URLEncoding.default, headers: nil).response { _ in if let cookie = self.getCookie(name: "JSESSIONID") { action(cookie.value) } } } } func doLogin(user: String, password: String, action: @escaping (_: Int) -> Void) { LoginHandler().fetchLoginCookie { (cookie: String) in let login = Login(user: user, pwd: password, cook: cookie) print(login) AF.request("https://debug.sdsz.icu/andlogin", method: .post, parameters: login, encoder: JSONParameterEncoder.default, headers: nil).responseString { res in print("\(res)") if res.value == "success" { action(1) } else { action(0) } } } } func getUserInfo(userInfo: inout UserInfo) { userInfo.name = "向量" } struct loginView: View { @State var username: String = "" @State var password: String = "" @State var btnText: String = "登录" @State var btnColor: Color = .blue @State var inProgress: Bool = false @FocusState private var isFocused: Bool @Binding var isLoggedIn: Int @Binding var userInfo: UserInfo var body: some View { VStack { Form { Section { HStack { Image(systemName: "person.fill").foregroundColor(Color(red: 0.7, green: 0.7, blue: 0.7)) TextField(text: $username, prompt: Text("数字校园号")) { Text("数字校园号") }.focused($isFocused) .keyboardType(.numberPad) } HStack { Image(systemName: "lock.fill").foregroundColor(Color(red: 0.7, green: 0.7, blue: 0.7)) SecureField(text: $password, prompt: Text("密码")) { Text("密码") }.focused($isFocused) } }.onTapGesture { isFocused = false } HStack { Spacer() Button(action: { inProgress = true doLogin(user: username, password: password) { (ret: Int) in isLoggedIn = ret inProgress = false if ret == 0 { btnText = "登录失败" btnColor = .red } else { getUserInfo(userInfo: &userInfo) } } }) { HStack { Text(btnText) if inProgress { ProgressView() } } }.foregroundColor(btnColor).buttonStyle(.bordered) } } } } } struct accountView: View { @State var username: String = "" @State var password: String = "" @FocusState private var isFocused: Bool @Binding var isLoggedIn: Int @Binding var userInfo: UserInfo var body: some View { VStack { Form { Section(header: Text("基本信息")) { HStack { Text("姓名") Spacer() Text(userInfo.name) } HStack { Text("所属班级") Spacer() Text(userInfo.name) } } Section { Button(action: { isLoggedIn = 0 if let cookie = LoginHandler().getCookie(name: "CASTGC") { HTTPCookieStorage.shared.deleteCookie(cookie) print(cookie) } }) { VStack { Text("退出").foregroundColor(.red) } } } } Spacer() } } } struct accountView_Previews: PreviewProvider { @State static var isLoggedIn = 0 @State static var userInfo: UserInfo = .init(name: "", o: "") static var previews: some View { loginView(isLoggedIn: $isLoggedIn, userInfo: $userInfo) } }