summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--activitypub.c88
-rw-r--r--main.c6
-rw-r--r--snac.h2
3 files changed, 96 insertions, 0 deletions
diff --git a/activitypub.c b/activitypub.c
index 634e243..a375584 100644
--- a/activitypub.c
+++ b/activitypub.c
@@ -936,6 +936,94 @@ xs_str *process_tags(snac *snac, const char *content, xs_list **tag)
936} 936}
937 937
938 938
939void collect_replies(snac *user, const char *id)
940/* collects all replies for a post */
941{
942 xs *obj = NULL;
943
944 if (!valid_status(object_get(id, &obj))) {
945 snac_debug(user, 1, xs_fmt("collect_replies: object '%s' is not here", id));
946 return;
947 }
948
949 const char *next = xs_dict_get_path(obj, "replies.first.next");
950 if (!xs_is_string(next)) {
951 snac_debug(user, 1, xs_fmt("collect_replies: object '%s' does not have a replies.first.next URL", id));
952 return;
953 }
954
955 /* pick the first level replies (may be empty) */
956 const xs_list *level0_replies = xs_dict_get_path(obj, "replies.first.items");
957
958 xs *reply_obj = NULL;
959
960 if (!valid_status(object_get(next, &reply_obj))) {
961 if (!valid_status(activitypub_request(user, next, &reply_obj))) {
962 snac_debug(user, 1, xs_fmt("collect_replies: cannot get replies object '%s'", next));
963 return;
964 }
965 }
966
967 const xs_list *level1_replies = xs_dict_get(reply_obj, "items");
968 if (!xs_is_list(level1_replies)) {
969 snac_debug(user, 1, xs_fmt("collect_replies: cannot get reply items from object '%s'", next));
970 return;
971 }
972
973 xs *items = NULL;
974
975 if (xs_is_list(level0_replies))
976 items = xs_list_cat(xs_dup(level0_replies), level1_replies);
977 else
978 items = xs_dup(level1_replies);
979
980 const xs_val *v;
981
982 xs_list_foreach(items, v) {
983 xs *reply = NULL;
984
985 if (xs_is_string(v)) {
986 /* request the object */
987 if (!valid_status(object_get(v, &reply))) {
988 if (!valid_status(activitypub_request(user, v, &reply))) {
989 snac_debug(user, 1, xs_fmt("collect_replies: error requesting object '%s'", v));
990 continue;
991 }
992 }
993 }
994 else
995 if (xs_is_dict(v)) {
996 /* actually the post object */
997 reply = xs_dup(v);
998 }
999
1000 if (!xs_is_dict(reply))
1001 continue;
1002
1003 const char *id = xs_dict_get(reply, "id");
1004 const char *type = xs_dict_get(reply, "type");
1005 const char *attr_to = get_atto(reply);
1006
1007 if (!xs_is_string(id) || !xs_is_string(type) || !xs_is_string(attr_to))
1008 continue;
1009
1010 if (!xs_match(type, POSTLIKE_OBJECT_TYPE))
1011 continue;
1012
1013 if (timeline_here(user, id)) {
1014 snac_debug(user, 1, xs_fmt("collect_replies: item already in timeline %s", id));
1015 continue;
1016 }
1017
1018 enqueue_actor_refresh(user, attr_to, 0);
1019
1020 timeline_add(user, id, reply);
1021
1022 snac_log(user, xs_fmt("new '%s' (collect_replies) %s %s", type, attr_to, id));
1023 }
1024}
1025
1026
939void notify(snac *snac, const char *type, const char *utype, const char *actor, const xs_dict *msg) 1027void notify(snac *snac, const char *type, const char *utype, const char *actor, const xs_dict *msg)
940/* notifies the user of relevant events */ 1028/* notifies the user of relevant events */
941{ 1029{
diff --git a/main.c b/main.c
index c4c298f..1e27302 100644
--- a/main.c
+++ b/main.c
@@ -730,6 +730,12 @@ int main(int argc, char *argv[])
730 return 0; 730 return 0;
731 } 731 }
732 732
733 if (strcmp(cmd, "collect_replies") == 0) { /** **/
734 collect_replies(&snac, url);
735
736 return 0;
737 }
738
733 if (strcmp(cmd, "insert") == 0) { /** **/ 739 if (strcmp(cmd, "insert") == 0) { /** **/
734 int status; 740 int status;
735 xs *data = NULL; 741 xs *data = NULL;
diff --git a/snac.h b/snac.h
index c060363..82c4a98 100644
--- a/snac.h
+++ b/snac.h
@@ -334,6 +334,8 @@ const char *default_avatar_base64(void);
334 334
335xs_str *process_tags(snac *snac, const char *content, xs_list **tag); 335xs_str *process_tags(snac *snac, const char *content, xs_list **tag);
336 336
337void collect_replies(snac *user, const char *id);
338
337const char *get_atto(const xs_dict *msg); 339const char *get_atto(const xs_dict *msg);
338const char *get_in_reply_to(const xs_dict *msg); 340const char *get_in_reply_to(const xs_dict *msg);
339xs_list *get_attachments(const xs_dict *msg); 341xs_list *get_attachments(const xs_dict *msg);