Cookie jar
parent
0e746091b8
commit
f02c233292
@ -0,0 +1,34 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2016 Francisco José Montiel Navarro.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
package org.koitharu.kotatsu.core.http.persistentcookiejar
|
||||||
|
|
||||||
|
import okhttp3.CookieJar
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This interface extends [okhttp3.CookieJar] and adds methods to clear the cookies.
|
||||||
|
*/
|
||||||
|
interface ClearableCookieJar : CookieJar {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Clear all the session cookies while maintaining the persisted ones.
|
||||||
|
*/
|
||||||
|
fun clearSession()
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Clear all the cookies from persistence and from the cache.
|
||||||
|
*/
|
||||||
|
fun clear()
|
||||||
|
}
|
||||||
@ -0,0 +1,87 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2016 Francisco José Montiel Navarro.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
package org.koitharu.kotatsu.core.http.persistentcookiejar
|
||||||
|
|
||||||
|
import org.koitharu.kotatsu.core.http.persistentcookiejar.persistence.CookiePersistor
|
||||||
|
import okhttp3.Cookie
|
||||||
|
import okhttp3.HttpUrl
|
||||||
|
import org.koitharu.kotatsu.core.http.persistentcookiejar.cache.CookieCache
|
||||||
|
import java.util.*
|
||||||
|
|
||||||
|
class PersistentCookieJar(
|
||||||
|
private val cache: CookieCache,
|
||||||
|
private val persistor: CookiePersistor
|
||||||
|
) : ClearableCookieJar {
|
||||||
|
|
||||||
|
init {
|
||||||
|
cache.addAll(persistor.loadAll())
|
||||||
|
}
|
||||||
|
|
||||||
|
@Synchronized
|
||||||
|
override fun saveFromResponse(url: HttpUrl, cookies: List<Cookie>) {
|
||||||
|
cache.addAll(cookies)
|
||||||
|
persistor.saveAll(filterPersistentCookies(cookies))
|
||||||
|
}
|
||||||
|
|
||||||
|
@Synchronized
|
||||||
|
override fun loadForRequest(url: HttpUrl): List<Cookie> {
|
||||||
|
val cookiesToRemove: MutableList<Cookie> = ArrayList()
|
||||||
|
val validCookies: MutableList<Cookie> = ArrayList()
|
||||||
|
val it = cache.iterator()
|
||||||
|
while (it.hasNext()) {
|
||||||
|
val currentCookie = it.next()
|
||||||
|
if (isCookieExpired(currentCookie)) {
|
||||||
|
cookiesToRemove.add(currentCookie)
|
||||||
|
it.remove()
|
||||||
|
} else if (currentCookie.matches(url)) {
|
||||||
|
validCookies.add(currentCookie)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
persistor.removeAll(cookiesToRemove)
|
||||||
|
return validCookies
|
||||||
|
}
|
||||||
|
|
||||||
|
@Synchronized
|
||||||
|
override fun clearSession() {
|
||||||
|
cache.clear()
|
||||||
|
cache.addAll(persistor.loadAll())
|
||||||
|
}
|
||||||
|
|
||||||
|
@Synchronized
|
||||||
|
override fun clear() {
|
||||||
|
cache.clear()
|
||||||
|
persistor.clear()
|
||||||
|
}
|
||||||
|
|
||||||
|
private companion object {
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun filterPersistentCookies(cookies: List<Cookie>): List<Cookie> {
|
||||||
|
val persistentCookies: MutableList<Cookie> = ArrayList()
|
||||||
|
for (cookie in cookies) {
|
||||||
|
if (cookie.persistent) {
|
||||||
|
persistentCookies.add(cookie)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return persistentCookies
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun isCookieExpired(cookie: Cookie): Boolean {
|
||||||
|
return cookie.expiresAt < System.currentTimeMillis()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -0,0 +1,35 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2016 Francisco José Montiel Navarro.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
package org.koitharu.kotatsu.core.http.persistentcookiejar.cache
|
||||||
|
|
||||||
|
import okhttp3.Cookie
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A CookieCache handles the volatile cookie session storage.
|
||||||
|
*/
|
||||||
|
interface CookieCache : MutableIterable<Cookie> {
|
||||||
|
/**
|
||||||
|
* Add all the new cookies to the session, existing cookies will be overwritten.
|
||||||
|
*
|
||||||
|
* @param newCookies
|
||||||
|
*/
|
||||||
|
fun addAll(newCookies: Collection<Cookie>)
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Clear all the cookies from the session.
|
||||||
|
*/
|
||||||
|
fun clear()
|
||||||
|
}
|
||||||
@ -0,0 +1,60 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2016 Francisco José Montiel Navarro.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
package org.koitharu.kotatsu.core.http.persistentcookiejar.cache
|
||||||
|
|
||||||
|
import okhttp3.Cookie
|
||||||
|
import java.util.*
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This class decorates a Cookie to re-implements equals() and hashcode() methods in order to identify
|
||||||
|
* the cookie by the following attributes: name, domain, path, secure & hostOnly.
|
||||||
|
*
|
||||||
|
*
|
||||||
|
*
|
||||||
|
* This new behaviour will be useful in determining when an already existing cookie in session must be overwritten.
|
||||||
|
*/
|
||||||
|
internal class IdentifiableCookie(val cookie: Cookie) {
|
||||||
|
|
||||||
|
override fun equals(other: Any?): Boolean {
|
||||||
|
if (other !is IdentifiableCookie) return false
|
||||||
|
return other.cookie.name == cookie.name && other.cookie.domain == cookie.domain
|
||||||
|
&& other.cookie.path == cookie.path && other.cookie.secure == cookie.secure
|
||||||
|
&& other.cookie.hostOnly == cookie.hostOnly
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun hashCode(): Int {
|
||||||
|
var hash = 17
|
||||||
|
hash = 31 * hash + cookie.name.hashCode()
|
||||||
|
hash = 31 * hash + cookie.domain.hashCode()
|
||||||
|
hash = 31 * hash + cookie.path.hashCode()
|
||||||
|
hash = 31 * hash + if (cookie.secure) 0 else 1
|
||||||
|
hash = 31 * hash + if (cookie.hostOnly) 0 else 1
|
||||||
|
return hash
|
||||||
|
}
|
||||||
|
|
||||||
|
companion object {
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun decorateAll(cookies: Collection<Cookie>): List<IdentifiableCookie> {
|
||||||
|
val identifiableCookies: MutableList<IdentifiableCookie> = ArrayList(cookies.size)
|
||||||
|
for (cookie in cookies) {
|
||||||
|
identifiableCookies.add(IdentifiableCookie(cookie))
|
||||||
|
}
|
||||||
|
return identifiableCookies
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@ -0,0 +1,57 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2016 Francisco José Montiel Navarro.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
package org.koitharu.kotatsu.core.http.persistentcookiejar.cache
|
||||||
|
|
||||||
|
import okhttp3.Cookie
|
||||||
|
import org.koitharu.kotatsu.core.http.persistentcookiejar.cache.IdentifiableCookie.Companion.decorateAll
|
||||||
|
import java.util.*
|
||||||
|
import java.util.concurrent.ConcurrentHashMap
|
||||||
|
|
||||||
|
class SetCookieCache : CookieCache {
|
||||||
|
|
||||||
|
private val cookies: MutableSet<IdentifiableCookie> = Collections.newSetFromMap(ConcurrentHashMap())
|
||||||
|
|
||||||
|
override fun addAll(newCookies: Collection<Cookie>) {
|
||||||
|
for (cookie in decorateAll(newCookies)) {
|
||||||
|
cookies.remove(cookie)
|
||||||
|
cookies.add(cookie)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun clear() {
|
||||||
|
cookies.clear()
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun iterator(): MutableIterator<Cookie> = SetCookieCacheIterator()
|
||||||
|
|
||||||
|
private inner class SetCookieCacheIterator internal constructor() : MutableIterator<Cookie> {
|
||||||
|
|
||||||
|
private val iterator = cookies.iterator()
|
||||||
|
|
||||||
|
override fun hasNext(): Boolean {
|
||||||
|
return iterator.hasNext()
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun next(): Cookie {
|
||||||
|
return iterator.next().cookie
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun remove() {
|
||||||
|
iterator.remove()
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -0,0 +1,44 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2016 Francisco José Montiel Navarro.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
package org.koitharu.kotatsu.core.http.persistentcookiejar.persistence
|
||||||
|
|
||||||
|
import okhttp3.Cookie
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A CookiePersistor handles the persistent cookie storage.
|
||||||
|
*/
|
||||||
|
interface CookiePersistor {
|
||||||
|
|
||||||
|
fun loadAll(): List<Cookie>
|
||||||
|
/**
|
||||||
|
* Persist all cookies, existing cookies will be overwritten.
|
||||||
|
*
|
||||||
|
* @param cookies cookies persist
|
||||||
|
*/
|
||||||
|
fun saveAll(cookies: Collection<Cookie>)
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Removes indicated cookies from persistence.
|
||||||
|
*
|
||||||
|
* @param cookies cookies to remove from persistence
|
||||||
|
*/
|
||||||
|
fun removeAll(cookies: Collection<Cookie>)
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Clear all cookies from persistence.
|
||||||
|
*/
|
||||||
|
fun clear()
|
||||||
|
}
|
||||||
@ -0,0 +1,150 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2016 Francisco José Montiel Navarro.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
package org.koitharu.kotatsu.core.http.persistentcookiejar.persistence
|
||||||
|
|
||||||
|
import android.util.Log
|
||||||
|
import okhttp3.Cookie
|
||||||
|
import java.io.*
|
||||||
|
|
||||||
|
class SerializableCookie : Serializable {
|
||||||
|
|
||||||
|
@Transient
|
||||||
|
private var cookie: Cookie? = null
|
||||||
|
|
||||||
|
fun encode(cookie: Cookie?): String? {
|
||||||
|
this.cookie = cookie
|
||||||
|
val byteArrayOutputStream = ByteArrayOutputStream()
|
||||||
|
var objectOutputStream: ObjectOutputStream? = null
|
||||||
|
try {
|
||||||
|
objectOutputStream = ObjectOutputStream(byteArrayOutputStream)
|
||||||
|
objectOutputStream.writeObject(this)
|
||||||
|
} catch (e: IOException) {
|
||||||
|
Log.d(TAG, "IOException in encodeCookie", e)
|
||||||
|
return null
|
||||||
|
} finally {
|
||||||
|
if (objectOutputStream != null) {
|
||||||
|
try { // Closing a ByteArrayOutputStream has no effect, it can be used later (and is used in the return statement)
|
||||||
|
objectOutputStream.close()
|
||||||
|
} catch (e: IOException) {
|
||||||
|
Log.d(TAG, "Stream not closed in encodeCookie", e)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return byteArrayToHexString(byteArrayOutputStream.toByteArray())
|
||||||
|
}
|
||||||
|
|
||||||
|
fun decode(encodedCookie: String): Cookie? {
|
||||||
|
val bytes = hexStringToByteArray(encodedCookie)
|
||||||
|
val byteArrayInputStream = ByteArrayInputStream(
|
||||||
|
bytes)
|
||||||
|
var cookie: Cookie? = null
|
||||||
|
var objectInputStream: ObjectInputStream? = null
|
||||||
|
try {
|
||||||
|
objectInputStream = ObjectInputStream(byteArrayInputStream)
|
||||||
|
cookie = (objectInputStream.readObject() as SerializableCookie).cookie
|
||||||
|
} catch (e: IOException) {
|
||||||
|
Log.d(TAG, "IOException in decodeCookie", e)
|
||||||
|
} catch (e: ClassNotFoundException) {
|
||||||
|
Log.d(TAG, "ClassNotFoundException in decodeCookie", e)
|
||||||
|
} finally {
|
||||||
|
if (objectInputStream != null) {
|
||||||
|
try {
|
||||||
|
objectInputStream.close()
|
||||||
|
} catch (e: IOException) {
|
||||||
|
Log.d(TAG, "Stream not closed in decodeCookie", e)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return cookie
|
||||||
|
}
|
||||||
|
|
||||||
|
@Throws(IOException::class)
|
||||||
|
private fun writeObject(out: ObjectOutputStream) {
|
||||||
|
out.writeObject(cookie!!.name)
|
||||||
|
out.writeObject(cookie!!.value)
|
||||||
|
out.writeLong(if (cookie!!.persistent) cookie!!.expiresAt else NON_VALID_EXPIRES_AT)
|
||||||
|
out.writeObject(cookie!!.domain)
|
||||||
|
out.writeObject(cookie!!.path)
|
||||||
|
out.writeBoolean(cookie!!.secure)
|
||||||
|
out.writeBoolean(cookie!!.httpOnly)
|
||||||
|
out.writeBoolean(cookie!!.hostOnly)
|
||||||
|
}
|
||||||
|
|
||||||
|
@Throws(IOException::class, ClassNotFoundException::class)
|
||||||
|
private fun readObject(`in`: ObjectInputStream) {
|
||||||
|
val builder = Cookie.Builder()
|
||||||
|
builder.name((`in`.readObject() as String))
|
||||||
|
builder.value((`in`.readObject() as String))
|
||||||
|
val expiresAt = `in`.readLong()
|
||||||
|
if (expiresAt != NON_VALID_EXPIRES_AT) {
|
||||||
|
builder.expiresAt(expiresAt)
|
||||||
|
}
|
||||||
|
val domain = `in`.readObject() as String
|
||||||
|
builder.domain(domain)
|
||||||
|
builder.path((`in`.readObject() as String))
|
||||||
|
if (`in`.readBoolean()) builder.secure()
|
||||||
|
if (`in`.readBoolean()) builder.httpOnly()
|
||||||
|
if (`in`.readBoolean()) builder.hostOnlyDomain(domain)
|
||||||
|
cookie = builder.build()
|
||||||
|
}
|
||||||
|
|
||||||
|
private companion object {
|
||||||
|
|
||||||
|
private val TAG = SerializableCookie::class.java.simpleName
|
||||||
|
|
||||||
|
const val serialVersionUID = -8594045714036645534L
|
||||||
|
private const val NON_VALID_EXPIRES_AT = -1L
|
||||||
|
/**
|
||||||
|
* Using some super basic byte array <-> hex conversions so we don't
|
||||||
|
* have to rely on any large Base64 libraries. Can be overridden if you
|
||||||
|
* like!
|
||||||
|
*
|
||||||
|
* @param bytes byte array to be converted
|
||||||
|
* @return string containing hex values
|
||||||
|
*/
|
||||||
|
@JvmStatic
|
||||||
|
private fun byteArrayToHexString(bytes: ByteArray): String {
|
||||||
|
val sb = StringBuilder(bytes.size * 2)
|
||||||
|
for (element in bytes) {
|
||||||
|
val v: Int = element.toInt() and 0xff
|
||||||
|
if (v < 16) {
|
||||||
|
sb.append('0')
|
||||||
|
}
|
||||||
|
sb.append(Integer.toHexString(v))
|
||||||
|
}
|
||||||
|
return sb.toString()
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Converts hex values from strings to byte array
|
||||||
|
*
|
||||||
|
* @param hexString string of hex-encoded values
|
||||||
|
* @return decoded byte array
|
||||||
|
*/
|
||||||
|
@JvmStatic
|
||||||
|
private fun hexStringToByteArray(hexString: String): ByteArray {
|
||||||
|
val len = hexString.length
|
||||||
|
val data = ByteArray(len / 2)
|
||||||
|
var i = 0
|
||||||
|
while (i < len) {
|
||||||
|
data[i / 2] = ((Character.digit(hexString[i], 16) shl 4) + Character
|
||||||
|
.digit(hexString[i + 1], 16)).toByte()
|
||||||
|
i += 2
|
||||||
|
}
|
||||||
|
return data
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -0,0 +1,74 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2016 Francisco José Montiel Navarro.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
package org.koitharu.kotatsu.core.http.persistentcookiejar.persistence
|
||||||
|
|
||||||
|
import android.annotation.SuppressLint
|
||||||
|
import android.content.Context
|
||||||
|
import android.content.SharedPreferences
|
||||||
|
import okhttp3.Cookie
|
||||||
|
import java.util.*
|
||||||
|
|
||||||
|
@SuppressLint("CommitPrefEdits")
|
||||||
|
class SharedPrefsCookiePersistor(private val sharedPreferences: SharedPreferences) :
|
||||||
|
CookiePersistor {
|
||||||
|
|
||||||
|
constructor(context: Context) : this(context.getSharedPreferences("cookies", Context.MODE_PRIVATE))
|
||||||
|
|
||||||
|
override fun loadAll(): List<Cookie> {
|
||||||
|
val cookies: MutableList<Cookie> = ArrayList(sharedPreferences.all.size)
|
||||||
|
for ((_, value) in sharedPreferences.all) {
|
||||||
|
val serializedCookie = value as? String
|
||||||
|
if (serializedCookie != null) {
|
||||||
|
val cookie = SerializableCookie().decode(serializedCookie)
|
||||||
|
if (cookie != null) {
|
||||||
|
cookies.add(cookie)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return cookies
|
||||||
|
}
|
||||||
|
|
||||||
|
@SuppressLint("ApplySharedPref")
|
||||||
|
override fun saveAll(cookies: Collection<Cookie>) {
|
||||||
|
val editor = sharedPreferences.edit()
|
||||||
|
for (cookie in cookies) {
|
||||||
|
editor.putString(createCookieKey(cookie), SerializableCookie().encode(cookie))
|
||||||
|
}
|
||||||
|
editor.commit()
|
||||||
|
}
|
||||||
|
|
||||||
|
@SuppressLint("ApplySharedPref")
|
||||||
|
override fun removeAll(cookies: Collection<Cookie>) {
|
||||||
|
val editor = sharedPreferences.edit()
|
||||||
|
for (cookie in cookies) {
|
||||||
|
editor.remove(createCookieKey(cookie))
|
||||||
|
}
|
||||||
|
editor.commit()
|
||||||
|
}
|
||||||
|
|
||||||
|
@SuppressLint("ApplySharedPref")
|
||||||
|
override fun clear() {
|
||||||
|
sharedPreferences.edit().clear().commit()
|
||||||
|
}
|
||||||
|
|
||||||
|
private companion object {
|
||||||
|
|
||||||
|
fun createCookieKey(cookie: Cookie): String {
|
||||||
|
return (if (cookie.secure) "https" else "http") + "://" + cookie.domain + cookie.path + "|" + cookie.name
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
Loading…
Reference in New Issue