Test for announce via c2s

master
Bob Mottram 2019-07-16 20:07:45 +01:00
parent 53d68cd10d
commit a819c4ae57
5 changed files with 149 additions and 22 deletions

View File

@ -14,6 +14,10 @@ from utils import urlPermitted
from utils import getNicknameFromActor
from utils import getDomainFromActor
from posts import sendSignedJson
from posts import getPersonBox
from session import postJson
from webfinger import webfingerHandle
from auth import createBasicAuthHeader
def createAnnounce(session,baseDir: str,federationList: [], \
nickname: str, domain: str, port: int, \
@ -229,3 +233,78 @@ def undoRepeatPost(session,baseDir: str,federationList: [], \
sendThreads,postLog, \
personCache,cachedWebfingers, \
debug)
def sendAnnounceViaServer(session,fromNickname: str,password: str,
fromDomain: str,fromPort: int, \
httpPrefix: str,repeatObjectUrl: str, \
cachedWebfingers: {},personCache: {}, \
debug: bool) -> {}:
"""Creates an announce message via c2s
"""
if not session:
print('WARN: No session for sendAnnounceViaServer')
return 6
withDigest=True
fromDomainFull=fromDomain
if fromPort!=80 and fromPort!=443:
fromDomainFull=fromDomain+':'+str(fromPort)
toUrl = 'https://www.w3.org/ns/activitystreams#Public'
ccUrl = httpPrefix + '://'+fromDomainFull+'/users/'+fromNickname+'/followers'
statusNumber,published = getStatusNumber()
newAnnounceId= \
httpPrefix+'://'+fromDomainFull+'/users/'+fromNickname+'/statuses/'+statusNumber
newAnnounceJson = {
'actor': httpPrefix+'://'+fromDomainFull+'/users/'+fromNickname,
'atomUri': newAnnounceId,
'cc': [ccUrl],
'id': newAnnounceId+'/activity',
'object': repeatObjectUrl,
'published': published,
'to': [toUrl],
'type': 'Announce'
}
handle=httpPrefix+'://'+fromDomainFull+'/@'+fromNickname
# lookup the inbox for the To handle
wfRequest = webfingerHandle(session,handle,httpPrefix,cachedWebfingers)
if not wfRequest:
if debug:
print('DEBUG: announce webfinger failed for '+handle)
return 1
postToBox='outbox'
# get the actor inbox for the To handle
inboxUrl,pubKeyId,pubKey,fromPersonId,sharedInbox,capabilityAcquisition = \
getPersonBox(session,wfRequest,personCache,postToBox)
if not inboxUrl:
if debug:
print('DEBUG: No '+postToBox+' was found for '+handle)
return 3
if not fromPersonId:
if debug:
print('DEBUG: No actor was found for '+handle)
return 4
authHeader=createBasicAuthHeader(fromNickname,password)
headers = {'host': fromDomain, \
'Content-type': 'application/json', \
'Authorization': authHeader}
postResult = \
postJson(session,newAnnounceJson,[],inboxUrl,headers,"inbox:write")
#if not postResult:
# if debug:
# print('DEBUG: POST announce failed for c2s to '+inboxUrl)
# return 5
if debug:
print('DEBUG: c2s POST announce success')
return newAnnounceJson

View File

@ -703,15 +703,9 @@ class PubServer(BaseHTTPRequestHandler):
# https://www.w3.org/TR/activitypub/#object-without-create
if self.outboxAuthenticated:
if self._postToOutbox(messageJson):
if messageJson.get('object'):
#self.send_header('Location', \
if messageJson.get('id'):
self.headers['Location']= \
messageJson['object']['id'].replace('/activity','')
else:
if messageJson.get('id'):
#self.send_header('Location', \
self.headers['Location']= \
messageJson['id'].replace('/activity','')
messageJson['id'].replace('/activity','')
self.send_response(201)
self.end_headers()
self.server.POSTbusy=False

View File

@ -214,8 +214,8 @@ if args.tests:
if args.testsnetwork:
print('Network Tests')
testPostMessageBetweenServers()
testFollowBetweenServers()
#testPostMessageBetweenServers()
#testFollowBetweenServers()
testClientToServer()
sys.exit()

View File

@ -305,8 +305,9 @@ def savePostToBox(baseDir: str,httpPrefix: str,postId: str, \
'/statuses/'+statusNumber
postJsonObject['id']=postId+'/activity'
if postJsonObject.get('object'):
postJsonObject['object']['id']=postId
postJsonObject['object']['atomUri']=postId
if isinstance(postJsonObject['object'], dict):
postJsonObject['object']['id']=postId
postJsonObject['object']['atomUri']=postId
boxDir = createPersonDir(nickname,domain,baseDir,boxname)
filename=boxDir+'/'+postId.replace('/','#')+'.json'
@ -493,19 +494,29 @@ def postIsAddressedToFollowers(baseDir: str,
if not postJsonObject.get('object'):
return False
if not postJsonObject['object'].get('to'):
return False
toList=[]
ccList=[]
if isinstance(postJsonObject['object'], dict):
if not postJsonObject['object'].get('to'):
return False
toList=postJsonObject['object']['to']
if postJsonObject['object'].get('cc'):
ccList=postJsonObject['object']['cc']
else:
if not postJsonObject.get('to'):
return False
toList=postJsonObject['to']
if postJsonObject.get('cc'):
ccList=postJsonObject['cc']
followersUrl=httpPrefix+'://'+domain+'/users/'+nickname+'/followers'
# does the followers url exist in 'to' or 'cc' lists?
addressedToFollowers=False
if followersUrl in postJsonObject['object']['to']:
if followersUrl in toList:
addressedToFollowers=True
if not addressedToFollowers:
if not postJsonObject['object'].get('cc'):
return False
if followersUrl in postJsonObject['object']['cc']:
if followersUrl in ccList:
addressedToFollowers=True
return addressedToFollowers
@ -872,13 +883,22 @@ def sendToNamedAddresses(session,baseDir: str, \
return
if not postJsonObject.get('object'):
return
if not postJsonObject['object'].get('to'):
return
toList=[]
if isinstance(postJsonObject['object'], dict):
if not postJsonObject['object'].get('to'):
return
toList=postJsonObject['object']['to']
recipientsObject=postJsonObject['object']
else:
if not postJsonObject.get('to'):
return
toList=postJsonObject['to']
recipientsObject=postJsonObject
recipients=[]
recipientType=['to','cc']
for rType in recipientType:
for address in postJsonObject['object'][rType]:
for address in recipientsObject[rType]:
if address.endswith('#Public'):
continue
if address.endswith('/followers'):

View File

@ -48,6 +48,7 @@ from auth import authorizeBasic
from auth import storeBasicCredentials
from like import likePost
from announce import announcePublic
from announce import sendAnnounceViaServer
from media import getMediaPath
testServerAliceRunning = False
@ -1043,7 +1044,7 @@ def testClientToServer():
assert len([name for name in os.listdir(outboxPath) if os.path.isfile(os.path.join(outboxPath, name))])==1
print(">>> c2s post arrived in Alice's outbox")
for i in range(30):
if os.path.isdir(inboxPath):
if len([name for name in os.listdir(inboxPath) if os.path.isfile(os.path.join(inboxPath, name))])==1:
@ -1054,6 +1055,39 @@ def testClientToServer():
print(">>> s2s post arrived in Bob's inbox")
print("c2s send success")
print('\n\nGetting message id for the post')
statusNumber=0
outboxPostFilename=None
outboxPostId=None
for name in os.listdir(outboxPath):
if '#statuses#' in name:
statusNumber=int(name.split('#statuses#')[1].replace('.json','').replace('#activity',''))
outboxPostFilename=outboxPath+'/'+name
with open(outboxPostFilename, 'r') as fp:
postJsonObject=commentjson.load(fp)
outboxPostId=postJsonObject['id'].replace('/activity','')
assert outboxPostId
print('message id obtained: '+outboxPostId)
print('\n\nBob repeats the post')
sessionBob = createSession(bobDomain,bobPort,useTor)
password='bobpass'
outboxPath=bobDir+'/accounts/bob@'+bobDomain+'/outbox'
assert len([name for name in os.listdir(outboxPath) if os.path.isfile(os.path.join(outboxPath, name))])==0
sendAnnounceViaServer(sessionBob,'bob',password,
bobDomain,bobPort, \
httpPrefix,outboxPostId, \
cachedWebfingers,personCache, \
True)
for i in range(10):
if os.path.isdir(outboxPath):
if len([name for name in os.listdir(outboxPath) if os.path.isfile(os.path.join(outboxPath, name))])==1:
break
time.sleep(1)
assert len([name for name in os.listdir(outboxPath) if os.path.isfile(os.path.join(outboxPath, name))])==1
print('Post repeated')
# stop the servers
thrAlice.kill()
thrAlice.join()