# sm_load <url or handle>: what Smithereen makes of it, as "type id"
sm_load(){ sm utils.loadRemoteObject "q=$1"| j "r = d.get('response') or {}; print(r.get('type', ''), r.get('id', ''))";}
p_home_has(){ curl -s -H "$PH""$P/api/v1/timelines/home?limit=40"| j "print(next(((s.get('reblog') or s)['id'] for s in d if '$1' in ((s.get('reblog') or s)['content'] or '')), ''))";}
["$(sm users.get fields=screen_name | j "print(d['response'][0]['screen_name'])")"="smuser"]&& ok "Smithereen token for smuser"||{ ko "Smithereen token";return 1;}
PT=$(privapub_token alice_smithereen)
PH="Authorization: Bearer $PT"
[ -n "$PT"]&& ok "PrivaPub token for alice_smithereen"||{ ko "PrivaPub token for alice_smithereen";return 1;}
alice_uri="$(curl -s -H "$PH""$P/api/v1/accounts/verify_credentials"| j "print(d['url'])"| sed 's|/@|/peasants/|')"
&& ok "the two follows make them friends on Smithereen"|| ko "Smithereen does not count them as friends ($(sm friends.areFriends "user_ids=$alice_on_sm"))"
sm_post=$(sm wall.post "message=a Smithereen wall post $run"| j "print(d['response'])")
until_true 45'[ -n "$(p_home_has "a Smithereen wall post $run")" ]'&& ok "smuser's wall post reaches alice's home"|| ko "smuser's wall post never reached alice"
sm_post_on_p=$(p_home_has "a Smithereen wall post $run")
p_post=$(curl -s -X POST -H "$PH"$P/api/v1/statuses -d "status=a PrivaPub post for Smithereen $run&visibility=public")
until_true 45'[ "$(sm wall.getComments "post_id=$sm_post" | j "print(any(\"a PrivaPub comment $run\" in (c.get(\"text\") or \"\") for c in d[\"response\"][\"items\"]))")" = "True" ]'\
&& ok "alice's reply becomes a comment on smuser's post"|| ko "alice's reply never reached Smithereen ($(sm wall.getComments "post_id=$sm_post"| head -c 300))"
echo" likes and reposts"
sm likes.add type=post "item_id=$p_post_on_sm" >/dev/null
until_true 45'[ "$(p_status $p_post_id favourites_count)" = "1" ]'&& ok "smuser's like counts on PrivaPub"|| ko "smuser's like never counted"
curl -s -o /dev/null -X POST -H "$PH""$P/api/v1/statuses/$sm_post_on_p/favourite"
until_true 45'[ "$(sm_sql "select count(*) from likes where object_id=$sm_post and object_type=0")" = "1" ]'\
&& ok "alice's favourite is a like on Smithereen"|| ko "alice's favourite never counted on Smithereen"
# a repost there is a quote: a QuoteRequest to alice, which her policy grants, then the quoting post (its API fails
# without a message, even an empty one)
sm wall.repost "post_id=$p_post_on_sm"message= >/dev/null
until_true 45'[ "$(p_status $p_post_id quotes_count)" = "1" ]'&& ok "smuser's repost quotes alice's post, which lets it"|| ko "smuser's repost never counted as a quote"
curl -s -o /dev/null -X POST -H "$PH""$P/api/v1/statuses/$sm_post_on_p/reblog"
until_true 45'[ "$(sm_sql "select count(*) from wall_posts where repost_of=$sm_post")" = "1" ]'\
&& ok "alice's boost is a repost on Smithereen"|| ko "alice's boost never reached Smithereen"
# smuser follows alice, so it may write on her wall (her actor says her followers may): PrivaPub hosts the post, tells
# alice, lists it on her wall and tells her followers' servers with Add; alice takes it off, which deletes it on Smithereen
sm_wall_post=$(sm wall.post "owner_id=$alice_on_sm""message=a word on alice's wall $run"| j "print(d.get('response', ''))")
[ -n "$sm_wall_post"]&& ok "Smithereen lets smuser write on alice's wall"|| ko "Smithereen refused smuser's post on alice's wall ($(sm wall.post "owner_id=$alice_on_sm""message=x"| head -c 200))"
p_mention(){ curl -s -H "$PH""$P/api/v1/notifications?types[]=mention&limit=40"| j "print(next((n['status']['id'] for n in d if 'a word on alice' in n['status']['content'] and '$run' in n['status']['content']), ''))";}
until_true 45'[ -n "$(p_mention)" ]'&& ok "the post on alice's wall reaches her"|| ko "the post on alice's wall never reached her"
walled=$(p_mention)
["$(curl -s -H "$PH""$P/api/v1/statuses/$walled"| j "print((d['privapub'].get('wall') or {}).get('username'))")"="alice_smithereen"]\
&& ok "as written on her wall"|| ko "PrivaPub does not say it is on alice's wall"
sm messages.send "to=$alice_on_sm""body=a Smithereen message $run" >/dev/null
until_true 45'curl -s -H "$PH" "$P/api/v1/conversations" | grep -q "a Smithereen message $run"'&& ok "smuser's message arrives as a DM"|| ko "smuser's message never reached alice"
dm=$(curl -s -H "$PH""$P/api/v1/conversations"| j "print(next(c['last_status']['id'] for c in d if 'a Smithereen message $run' in c['last_status']['content']))")
curl -s -o /dev/null -X POST -H "$PH"$P/api/v1/statuses -d "status=@smuser@smithereen.test a PrivaPub answer $run&in_reply_to_id=$dm&visibility=direct"
until_true 45'[ "$(sm_sql "select count(*) from mail_messages where text like '"'%a PrivaPub answer $run%'"'")" -ge 1 ]'\
&& ok "alice's answer arrives as a Smithereen message"|| ko "alice's answer never reached Smithereen"
echo" unfollow"
curl -s -o /dev/null -X POST -H "$PH""$P/api/v1/accounts/$sm_on_p/unfollow"