Add content warnings in wen interface

master
Bob Mottram 2019-07-31 13:44:08 +01:00
parent 616b186337
commit 1dde784bd8
4 changed files with 73 additions and 8 deletions

View File

@ -58,3 +58,19 @@ input[type=text] {
color: var(--text-entry-foreground); color: var(--text-entry-foreground);
background-color: var(--text-entry-background); background-color: var(--text-entry-background);
} }
.cwButton {
border-radius: 4px;
background-color: #999;
border: none;
color: #FFFFFF;
text-align: center;
font-size: 18px;
padding: 2px;
cursor: pointer;
margin: 5px;
}
.cwText {
display: none;
}

View File

@ -6,6 +6,22 @@ body, html {
margin: 0 auto; margin: 0 auto;
} }
.cwButton {
border-radius: 4px;
background-color: #999;
border: none;
color: #FFFFFF;
text-align: center;
font-size: 18px;
padding: 2px;
cursor: pointer;
margin: 5px;
}
.cwText {
display: none;
}
.timeline-banner { .timeline-banner {
background-image: linear-gradient(rgba(0, 0, 0, 0.5), rgba(0, 0, 0, 0.5)), url("banner.png"); background-image: linear-gradient(rgba(0, 0, 0, 0.5), rgba(0, 0, 0, 0.5)), url("banner.png");
height: 10%; height: 10%;

View File

@ -162,6 +162,7 @@ def createPersonBase(baseDir: str,nickname: str,domain: str,port: int, \
'name': nickname, 'name': nickname,
'outbox': httpPrefix+'://'+domain+'/users/'+nickname+'/outbox', 'outbox': httpPrefix+'://'+domain+'/users/'+nickname+'/outbox',
'preferredUsername': ''+nickname, 'preferredUsername': ''+nickname,
'summary': '',
'publicKey': {'id': httpPrefix+'://'+domain+'/users/'+nickname+'#main-key', 'publicKey': {'id': httpPrefix+'://'+domain+'/users/'+nickname+'#main-key',
'owner': httpPrefix+'://'+domain+'/users/'+nickname, 'owner': httpPrefix+'://'+domain+'/users/'+nickname,
'publicKeyPem': publicKeyPem, 'publicKeyPem': publicKeyPem,
@ -406,9 +407,9 @@ def setBio(baseDir: str,nickname: str, domain: str, bio: str) -> bool:
personJson=commentjson.load(fp) personJson=commentjson.load(fp)
if not personJson: if not personJson:
return False return False
if not personJson.get('publicKey'): if not personJson.get('summary'):
return False return False
personJson['publicKey']['summary']=bio personJson['summary']=bio
with open(filename, 'w') as fp: with open(filename, 'w') as fp:
commentjson.dump(personJson, fp, indent=4, sort_keys=False) commentjson.dump(personJson, fp, indent=4, sort_keys=False)
return True return True

View File

@ -20,6 +20,7 @@ from webfinger import webfingerHandle
from posts import getUserUrl from posts import getUserUrl
from posts import parseUserFeed from posts import parseUserFeed
from session import getJson from session import getJson
from auth import createPassword
def htmlGetLoginCredentials(loginParams: str,lastLoginTime: int) -> (str,str): def htmlGetLoginCredentials(loginParams: str,lastLoginTime: int) -> (str,str):
"""Receives login credentials via HTTPServer POST """Receives login credentials via HTTPServer POST
@ -198,6 +199,7 @@ def htmlProfilePosts(baseDir: str,httpPrefix: str, \
4, 'outbox', \ 4, 'outbox', \
authorized, \ authorized, \
ocapAlways) ocapAlways)
profileStr+='<script>'+contentWarningScript()+'</script>'
for item in outboxFeed['orderedItems']: for item in outboxFeed['orderedItems']:
if item['type']=='Create' or item['type']=='Announce': if item['type']=='Create' or item['type']=='Announce':
profileStr+= \ profileStr+= \
@ -280,7 +282,7 @@ def htmlProfile(baseDir: str,httpPrefix: str,authorized: bool, \
domainFull=domain domainFull=domain
if port: if port:
domainFull=domain+':'+str(port) domainFull=domain+':'+str(port)
profileDescription=profileJson['publicKey']['summary'] profileDescription=profileJson['summary']
profileDescription='A test description' profileDescription='A test description'
postsButton='button' postsButton='button'
followingButton='button' followingButton='button'
@ -413,6 +415,20 @@ def individualFollowAsHtml(session,wfRequest: {}, \
'<p>'+titleStr+'</p></a>'+ \ '<p>'+titleStr+'</p></a>'+ \
'</div>\n' '</div>\n'
def contentWarningScript() -> str:
"""Returns a script used for content warnings
"""
script= \
'function showContentWarning(postID) {' \
' var x = document.getElementById(postID);' \
' if (x.style.display === "none") {' \
' x.style.display = "block";' \
' } else {' \
' x.style.display = "none";' \
' }' \
'}'
return script
def individualPostAsHtml(baseDir: str, \ def individualPostAsHtml(baseDir: str, \
session,wfRequest: {},personCache: {}, \ session,wfRequest: {},personCache: {}, \
nickname: str,domain: str,port: int, \ nickname: str,domain: str,port: int, \
@ -535,12 +551,25 @@ def individualPostAsHtml(baseDir: str, \
footerStr+='<span class="'+timeClass+'">'+postJsonObject['object']['published']+'</span>' footerStr+='<span class="'+timeClass+'">'+postJsonObject['object']['published']+'</span>'
footerStr+='</div>' footerStr+='</div>'
if not postJsonObject['object']['sensitive']:
contentStr=postJsonObject['object']['content']+attachmentStr
else:
postID='post'+str(createPassword(8))
contentStr=''
if postJsonObject['object'].get('summary'):
contentStr+='<b>'+postJsonObject['object']['summary']+'</b> '
else:
contentStr+='<b>Sensitive</b> '
contentStr+='<button class="cwButton" onclick="showContentWarning('+"'"+postID+"'"+')">SHOW MORE</button>'
contentStr+='<div class="cwText" id="'+postID+'">'
contentStr+=postJsonObject['object']['content']+attachmentStr
contentStr+='</div>'
return \ return \
'<div class="'+containerClass+'">\n'+ \ '<div class="'+containerClass+'">\n'+ \
avatarDropdown+ \ avatarDropdown+ \
'<p class="post-title">'+titleStr+'</p>'+ \ '<p class="post-title">'+titleStr+'</p>'+ \
postJsonObject['object']['content']+'\n'+ \ contentStr+footerStr+ \
attachmentStr+footerStr+ \
'</div>\n' '</div>\n'
def htmlTimeline(session,baseDir: str,wfRequest: {},personCache: {}, \ def htmlTimeline(session,baseDir: str,wfRequest: {},personCache: {}, \
@ -587,11 +616,13 @@ def htmlTimeline(session,baseDir: str,wfRequest: {},personCache: {}, \
' <a href="'+actor+'/search"><img src="/icons/search.png" title="Search and follow" alt="Search and follow" class="right"/></a>'+ \ ' <a href="'+actor+'/search"><img src="/icons/search.png" title="Search and follow" alt="Search and follow" class="right"/></a>'+ \
followApprovals+ \ followApprovals+ \
'</div>' '</div>'
tlStr+='<script>'+contentWarningScript()+'</script>'
for item in timelineJson['orderedItems']: for item in timelineJson['orderedItems']:
if item['type']=='Create' or item['type']=='Announce': if item['type']=='Create' or item['type']=='Announce':
tlStr+=individualPostAsHtml(baseDir,session,wfRequest,personCache, \ tlStr+=individualPostAsHtml(baseDir,session,wfRequest,personCache, \
nickname,domain,port,item,None,True,showIndividualPostIcons) nickname,domain,port,item,None,True,showIndividualPostIcons)
tlStr+=htmlFooter() tlStr+=htmlFooter()
print(tlStr)
return tlStr return tlStr
def htmlInbox(session,baseDir: str,wfRequest: {},personCache: {}, \ def htmlInbox(session,baseDir: str,wfRequest: {},personCache: {}, \
@ -775,9 +806,8 @@ def htmlProfileAfterSearch(baseDir: str,path: str,httpPrefix: str, \
if profileJson.get('preferredUsername'): if profileJson.get('preferredUsername'):
preferredName=profileJson['preferredUsername'] preferredName=profileJson['preferredUsername']
profileDescription='' profileDescription=''
if profileJson.get('publicKey'): if profileJson.get('summary'):
if profileJson['publicKey'].get('summary'): profileDescription=profileJson['summary']
profileDescription=profileJson['publicKey']['summary']
outboxUrl=None outboxUrl=None
if not profileJson.get('outbox'): if not profileJson.get('outbox'):
if debug: if debug:
@ -816,6 +846,8 @@ def htmlProfileAfterSearch(baseDir: str,path: str,httpPrefix: str, \
' </form>' \ ' </form>' \
'</div>' '</div>'
profileStr+='<script>'+contentWarningScript()+'</script>'
result = [] result = []
i = 0 i = 0
for item in parseUserFeed(session,outboxUrl,asHeader): for item in parseUserFeed(session,outboxUrl,asHeader):