From 952d4e41efc21f1276e8b03892e1e8079a727a1b Mon Sep 17 00:00:00 2001 From: Allan Wang Date: Sun, 24 Sep 2017 17:53:07 -0400 Subject: Feature/compact formatter (#337) * Make components private and thus jvm fields * Split converter and decoder * Update changelog * Only decode nonquery portions of links * Add comments and fix test --- .../pitchedapps/frost/facebook/FbUrlFormatter.kt | 39 ++++++++++++++++++---- .../com/pitchedapps/frost/facebook/FbUrlTest.kt | 4 +-- 2 files changed, 34 insertions(+), 9 deletions(-) (limited to 'app') diff --git a/app/src/main/kotlin/com/pitchedapps/frost/facebook/FbUrlFormatter.kt b/app/src/main/kotlin/com/pitchedapps/frost/facebook/FbUrlFormatter.kt index cd7d9002..542277b8 100644 --- a/app/src/main/kotlin/com/pitchedapps/frost/facebook/FbUrlFormatter.kt +++ b/app/src/main/kotlin/com/pitchedapps/frost/facebook/FbUrlFormatter.kt @@ -11,16 +11,25 @@ val String.formattedFbUrl: String get() = FbUrlFormatter(this).toString() class FbUrlFormatter(url: String) { - val queries = mutableMapOf() - val cleaned: String + private val queries = mutableMapOf() + private val cleaned: String + /** + * Formats all facebook urls + * + * The order is very important: + * 1. Wrapper links (discardables) are stripped away, resulting in the actual link + * 2. CSS encoding is converted to normal encoding + * 3. Query portions are separated from the cleaned url + * 4. The cleaned url is decoded. Queries are kept as is! + */ init { if (url.isBlank()) cleaned = "" else { var cleanedUrl = url discardable.forEach { cleanedUrl = cleanedUrl.replace(it, "", true) } - val changed = cleanedUrl != url //note that discardables strip away the first ? - decoder.forEach { (k, v) -> cleanedUrl = cleanedUrl.replace(k, v, true) } + val changed = cleanedUrl != url //note that discardables strip away the first '?' + converter.forEach { (k, v) -> cleanedUrl = cleanedUrl.replace(k, v, true) } val qm = cleanedUrl.indexOf(if (changed) "&" else "?") if (qm > -1) { cleanedUrl.substring(qm + 1).split("&").forEach { @@ -29,6 +38,8 @@ class FbUrlFormatter(url: String) { } cleanedUrl = cleanedUrl.substring(0, qm) } + //only decode non query portion of the url + decoder.forEach { (k, v) -> cleanedUrl = cleanedUrl.replace(k, v, true) } discardableQueries.forEach { queries.remove(it) } if (cleanedUrl.startsWith("#!")) cleanedUrl = cleanedUrl.substring(2) if (cleanedUrl.startsWith("/")) cleanedUrl = FB_URL_BASE + cleanedUrl.substring(1) @@ -83,15 +94,29 @@ class FbUrlFormatter(url: String) { "%60" to "`", "%3B" to ";", "%2F" to "/", "%3F" to "?", "%3A" to ":", "%40" to "@", "%3D" to "=", "%26" to "&", "%24" to "$", "%2B" to "+", "%22" to "\"", "%2C" to ",", - "%20" to " ", - //css + "%20" to " " + ) + + @JvmStatic + val cssDecoder = mapOf( "\\3C " to "<", "\\3E " to ">", "\\23 " to "#", "\\25 " to "%", "\\7B " to "{", "\\7D " to "}", "\\7C " to "|", "\\5C " to "\\", "\\5E " to "^", "\\7E " to "~", "\\5B " to "[", "\\5D " to "]", "\\60 " to "`", "\\3B " to ";", "\\2F " to "/", "\\3F " to "?", "\\3A " to ":", "\\40 " to "@", "\\3D " to "=", "\\26 " to "&", "\\24 " to "$", "\\2B " to "+", "\\22 " to "\"", "\\2C " to ",", - "\\20 " to " " + "%20" to " " + ) + + @JvmStatic + val converter = mapOf( + "\\3C " to "%3C", "\\3E " to "%3E", "\\23 " to "%23", "\\25 " to "%25", + "\\7B " to "%7B", "\\7D " to "%7D", "\\7C " to "%7C", "\\5C " to "%5C", + "\\5E " to "%5E", "\\7E " to "%7E", "\\5B " to "%5B", "\\5D " to "%5D", + "\\60 " to "%60", "\\3B " to "%3B", "\\2F " to "%2F", "\\3F " to "%3F", + "\\3A " to "%3A", "\\40 " to "%40", "\\3D " to "%3D", "\\26 " to "%26", + "\\24 " to "%24", "\\2B " to "%2B", "\\22 " to "%22", "\\2C " to "%2C", + "\\20 " to "%20" ) } } \ No newline at end of file diff --git a/app/src/test/kotlin/com/pitchedapps/frost/facebook/FbUrlTest.kt b/app/src/test/kotlin/com/pitchedapps/frost/facebook/FbUrlTest.kt index bb6a8467..3a87a697 100644 --- a/app/src/test/kotlin/com/pitchedapps/frost/facebook/FbUrlTest.kt +++ b/app/src/test/kotlin/com/pitchedapps/frost/facebook/FbUrlTest.kt @@ -45,8 +45,8 @@ class FbUrlTest { @Test fun css() { - val expected = "https://test.com?efg=hi&oh=bye&oe=apple" - val orig = "https\\3a //test.com?efg\\3d hi\\26 oh\\3d bye\\26 oe\\3d apple" + val expected = "https://test.com?efg=hi&oh=bye&oe=apple%3Fornot" + val orig = "https\\3a //test.com?efg=hi&oh=bye&oe=apple\\3F ornot" assertFbFormat(expected, orig) } -- cgit v1.2.3