Show reasons for tweets being withheld

Fixes #33
This commit is contained in:
Zed 2019-09-08 14:34:26 +02:00
parent 8208676e6e
commit 9ff3ba2005
5 changed files with 30 additions and 7 deletions

View File

@ -107,3 +107,6 @@ proc getTime*(tweet: Tweet): string =
proc getLink*(tweet: Tweet | Quote): string = proc getLink*(tweet: Tweet | Quote): string =
&"/{tweet.profile.username}/status/{tweet.id}" &"/{tweet.profile.username}/status/{tweet.id}"
proc getTombstone*(text: string): string =
text.replace(re"\n* *Learn more", "").stripText().strip(chars={' ', '\n'})

View File

@ -78,8 +78,11 @@ proc parseQuote*(quote: XmlNode): Quote =
result.getQuoteMedia(quote) result.getQuoteMedia(quote)
proc parseTweet*(node: XmlNode): Tweet = proc parseTweet*(node: XmlNode): Tweet =
if "withheld" in node.attr("class"):
return Tweet(tombstone: getTombstone(node.selectText(".Tombstone-label")))
let tweet = node.select(".tweet") let tweet = node.select(".tweet")
if tweet == nil or "withheld-tweet" in tweet.attr("class"): if tweet == nil:
return Tweet() return Tweet()
result = Tweet( result = Tweet(
@ -113,7 +116,8 @@ proc parseTweet*(node: XmlNode): Tweet =
let tombstone = tweet.select(".Tombstone") let tombstone = tweet.select(".Tombstone")
if tombstone != nil: if tombstone != nil:
if "unavailable" in tombstone.innerText(): if "unavailable" in tombstone.innerText():
result.quote = some(Quote()) let quote = Quote(tombstone: getTombstone(node.selectText(".Tombstone-label")))
result.quote = some(quote)
proc parseThread*(nodes: XmlNode): Thread = proc parseThread*(nodes: XmlNode): Thread =
if nodes == nil: return if nodes == nil: return
@ -128,8 +132,13 @@ proc parseThread*(nodes: XmlNode): Thread =
result.content.add parseTweet(n) result.content.add parseTweet(n)
proc parseConversation*(node: XmlNode): Conversation = proc parseConversation*(node: XmlNode): Conversation =
let tweet = node.select(".permalink-tweet-container")
if tweet == nil:
return Conversation(tweet: parseTweet(node.select(".permalink-tweet-withheld")))
result = Conversation( result = Conversation(
tweet: parseTweet(node.select(".permalink-tweet-container")), tweet: parseTweet(tweet),
before: parseThread(node.select(".in-reply-to .stream-items")) before: parseThread(node.select(".in-reply-to .stream-items"))
) )

View File

@ -100,6 +100,9 @@ proc createTimelineRouter*(cfg: Config) =
let conversation = await getTweet(@"name", @"id", getAgent()) let conversation = await getTweet(@"name", @"id", getAgent())
if conversation == nil or conversation.tweet.id.len == 0: if conversation == nil or conversation.tweet.id.len == 0:
if conversation.tweet.tombstone.len > 0:
resp Http404, showError(conversation.tweet.tombstone, cfg.title)
else:
resp Http404, showError("Tweet not found", cfg.title) resp Http404, showError("Tweet not found", cfg.title)
let path = getPath() let path = getPath()

View File

@ -118,6 +118,7 @@ type
hasThread*: bool hasThread*: bool
sensitive*: bool sensitive*: bool
available*: bool available*: bool
tombstone*: string
thumb*: string thumb*: string
badge*: string badge*: string
@ -139,8 +140,9 @@ type
shortTime*: string shortTime*: string
reply*: seq[string] reply*: seq[string]
pinned*: bool pinned*: bool
available*: bool
hasThread*: bool hasThread*: bool
available*: bool
tombstone*: string
stats*: TweetStats stats*: TweetStats
retweet*: Option[Retweet] retweet*: Option[Retweet]
quote*: Option[Quote] quote*: Option[Quote]

View File

@ -191,6 +191,9 @@ proc renderQuote(quote: Quote; prefs: Prefs): VNode =
if not quote.available: if not quote.available:
return buildHtml(tdiv(class="quote unavailable")): return buildHtml(tdiv(class="quote unavailable")):
tdiv(class="unavailable-quote"): tdiv(class="unavailable-quote"):
if quote.tombstone.len > 0:
text quote.tombstone
else:
text "This tweet is unavailable" text "This tweet is unavailable"
buildHtml(tdiv(class="quote")): buildHtml(tdiv(class="quote")):
@ -223,6 +226,9 @@ proc renderTweet*(tweet: Tweet; prefs: Prefs; path: string; class="";
return buildHtml(tdiv(class=divClass)): return buildHtml(tdiv(class=divClass)):
tdiv(class="status-el unavailable"): tdiv(class="status-el unavailable"):
tdiv(class="unavailable-box"): tdiv(class="unavailable-box"):
if tweet.tombstone.len > 0:
text tweet.tombstone
else:
text "This tweet is unavailable" text "This tweet is unavailable"
buildHtml(tdiv(class=divClass)): buildHtml(tdiv(class=divClass)):