diff --git a/java-api/src/org/servalproject/servaldna/AbstractId.java b/java-api/src/org/servalproject/servaldna/AbstractId.java index d73d85c5..0700270c 100644 --- a/java-api/src/org/servalproject/servaldna/AbstractId.java +++ b/java-api/src/org/servalproject/servaldna/AbstractId.java @@ -85,6 +85,10 @@ public abstract class AbstractId { this.binary = binary; } + protected boolean isEquivalent(Object other){ + return other.getClass() == this.getClass(); + } + @Override public boolean equals(Object other) { // must be the exact same type with the same binary contents to be considered equal @@ -92,7 +96,7 @@ public abstract class AbstractId { return false; if (other==this) return true; - if (other.getClass() == this.getClass()) { + if (isEquivalent(other)) { AbstractId oBinary = (AbstractId) other; for (int i = 0; i < this.binary.length; i++) if (this.binary[i] != oBinary.binary[i]) diff --git a/java-api/src/org/servalproject/servaldna/ServalDClient.java b/java-api/src/org/servalproject/servaldna/ServalDClient.java index 1ace6e6d..c8b6e16f 100644 --- a/java-api/src/org/servalproject/servaldna/ServalDClient.java +++ b/java-api/src/org/servalproject/servaldna/ServalDClient.java @@ -220,12 +220,8 @@ public class ServalDClient implements ServalDHttpConnectionFactory { return list; } - public int meshmbFollow(Subscriber id, SigningKey peer) throws ServalDInterfaceException, IOException { - return MeshMBCommon.follow(this, id, peer); - } - - public int meshmbIgnore(Subscriber id, SigningKey peer) throws ServalDInterfaceException, IOException { - return MeshMBCommon.ignore(this, id, peer); + public int meshmbAlterSubscription(Subscriber id, MeshMBCommon.SubscriptionAction action, SigningKey peer) throws ServalDInterfaceException, IOException { + return MeshMBCommon.alterSubscription(this, id, action, peer); } public MeshMBSubscriptionList meshmbSubscriptions(Subscriber identity) throws IOException, ServalDInterfaceException { diff --git a/java-api/src/org/servalproject/servaldna/SigningKey.java b/java-api/src/org/servalproject/servaldna/SigningKey.java index ab896665..f5b23cbc 100644 --- a/java-api/src/org/servalproject/servaldna/SigningKey.java +++ b/java-api/src/org/servalproject/servaldna/SigningKey.java @@ -29,4 +29,9 @@ public class SigningKey extends AbstractId { public String getMimeType() { return "serval-mesh/id"; } + + @Override + protected boolean isEquivalent(Object other){ + return SigningKey.class.isInstance(other); + } } diff --git a/java-api/src/org/servalproject/servaldna/meshmb/MeshMBCommon.java b/java-api/src/org/servalproject/servaldna/meshmb/MeshMBCommon.java index 391fc7da..da5e54a3 100644 --- a/java-api/src/org/servalproject/servaldna/meshmb/MeshMBCommon.java +++ b/java-api/src/org/servalproject/servaldna/meshmb/MeshMBCommon.java @@ -17,6 +17,12 @@ public class MeshMBCommon { public static final String SERVICE = "MeshMB1"; + public enum SubscriptionAction{ + Follow, + Ignore, + Block + } + public static int sendMessage(ServalDHttpConnectionFactory connector, SigningKey id, String text) throws IOException, ServalDInterfaceException { HttpURLConnection conn = connector.newServalDHttpConnection("/restful/meshmb/" + id.toHex() + "/sendmessage"); PostHelper helper = new PostHelper(conn); @@ -28,15 +34,8 @@ public class MeshMBCommon { return conn.getResponseCode(); } - public static int ignore(ServalDHttpConnectionFactory connector, Subscriber id, SigningKey peer) throws ServalDInterfaceException, IOException { - HttpURLConnection conn = connector.newServalDHttpConnection("/restful/meshmb/" + id.signingKey.toHex() + "/ignore/" + peer.toHex()); - conn.setRequestMethod("POST"); - conn.connect(); - return conn.getResponseCode(); - } - - public static int follow(ServalDHttpConnectionFactory connector, Subscriber id, SigningKey peer) throws ServalDInterfaceException, IOException { - HttpURLConnection conn = connector.newServalDHttpConnection("/restful/meshmb/" + id.signingKey.toHex() + "/follow/" + peer.toHex()); + public static int alterSubscription(ServalDHttpConnectionFactory connector, Subscriber id, SubscriptionAction action, SigningKey peer) throws ServalDInterfaceException, IOException { + HttpURLConnection conn = connector.newServalDHttpConnection("/restful/meshmb/" + id.signingKey.toHex() + "/"+action.toString().toLowerCase()+"/" + peer.toHex()); conn.setRequestMethod("POST"); conn.connect(); return conn.getResponseCode(); diff --git a/java-api/src/org/servalproject/servaldna/meshmb/MeshMBSubscriptionList.java b/java-api/src/org/servalproject/servaldna/meshmb/MeshMBSubscriptionList.java index b2160124..f8142354 100644 --- a/java-api/src/org/servalproject/servaldna/meshmb/MeshMBSubscriptionList.java +++ b/java-api/src/org/servalproject/servaldna/meshmb/MeshMBSubscriptionList.java @@ -1,6 +1,7 @@ package org.servalproject.servaldna.meshmb; import org.servalproject.json.JSONTableScanner; +import org.servalproject.json.JSONTokeniser; import org.servalproject.servaldna.AbstractJsonList; import org.servalproject.servaldna.ServalDHttpConnectionFactory; import org.servalproject.servaldna.ServalDInterfaceException; @@ -23,9 +24,10 @@ public class MeshMBSubscriptionList extends AbstractJsonListfeeds->root, (void**)&metadata, ack.binary, ack.binary_length, NULL, NULL)==TREE_FOUND){ + if (metadata->details.blocked) + continue; bundle_id = &metadata->bundle_id; i->metadata = metadata; }else{ @@ -240,6 +244,8 @@ static int activity_ack(struct meshmb_feeds *feeds, struct message_ply_ack *ack) static int update_stats(struct meshmb_feeds *feeds, struct feed_metadata *metadata, struct message_ply_read *reader) { + if (metadata->details.blocked) + return 0; if (!metadata->details.ply.found){ // get the current size from the db sqlite_retry_state retry = SQLITE_RETRY_STATE_DEFAULT; @@ -329,7 +335,7 @@ static int update_stats(struct meshmb_feeds *feeds, struct feed_metadata *metada return 1; } -// TODO, might be quicker to fetch all meshmb bundles and test if they are in the feed list +// TODO, might sometimes be quicker to fetch all meshmb bundles and test if they are in the feed list static int update_stats_tree(void **record, void *context) { struct feed_metadata *metadata = (struct feed_metadata *)*record; @@ -346,7 +352,8 @@ int meshmb_bundle_update(struct meshmb_feeds *feeds, rhizome_manifest *m, struct { struct feed_metadata *metadata; if (strcmp(m->service, RHIZOME_SERVICE_MESHMB) == 0 - && tree_find(&feeds->root, (void**)&metadata, m->keypair.public_key.binary, sizeof m->keypair.public_key.binary, NULL, NULL)==TREE_FOUND){ + && tree_find(&feeds->root, (void**)&metadata, m->keypair.public_key.binary, sizeof m->keypair.public_key.binary, NULL, NULL)==TREE_FOUND + && !metadata->details.blocked){ metadata->details.ply.found = 1; if (metadata->details.ply.size != m->filesize){ @@ -384,21 +391,24 @@ static int write_metadata(void **record, void *context) len += sizeof (rhizome_bid_t); bcopy(metadata->details.ply.author.binary, &buffer[len], sizeof (sid_t)); len += sizeof (sid_t); - buffer[len++]=0;// flags? - len+=pack_uint(&buffer[len], metadata->size); - len+=pack_uint(&buffer[len], metadata->size - metadata->last_message_offset); - len+=pack_uint(&buffer[len], metadata->size - metadata->last_seen); - len+=pack_uint(&buffer[len], metadata->details.timestamp); - if (name_len > 1) - strncpy_nul((char *)&buffer[len], metadata->details.name, name_len); - else - buffer[len]=0; - len+=name_len; - if (msg_len > 1) - strncpy_nul((char *)&buffer[len], metadata->details.last_message, msg_len); - else - buffer[len]=0; - len+=msg_len; + uint8_t flags = (metadata->details.blocked ? FLAG_BLOCKED : 0); + buffer[len++]=flags; + if (!metadata->details.blocked){ + len+=pack_uint(&buffer[len], metadata->size); + len+=pack_uint(&buffer[len], metadata->size - metadata->last_message_offset); + len+=pack_uint(&buffer[len], metadata->size - metadata->last_seen); + len+=pack_uint(&buffer[len], metadata->details.timestamp); + if (name_len > 1) + strncpy_nul((char *)&buffer[len], metadata->details.name, name_len); + else + buffer[len]=0; + len+=name_len; + if (msg_len > 1) + strncpy_nul((char *)&buffer[len], metadata->details.last_message, msg_len); + else + buffer[len]=0; + len+=msg_len; + } assert(len < sizeof buffer); DEBUGF(meshmb, "Write %zu bytes of metadata for %s/%s", len, @@ -525,10 +535,12 @@ static int read_metadata(struct meshmb_feeds *feeds, struct rhizome_read *read) break; uint64_t delta=0; - uint64_t size; - uint64_t last_message_offset; - uint64_t last_seen; - uint64_t timestamp; + uint64_t size=0; + uint64_t last_message_offset=0; + uint64_t last_seen=0; + uint64_t timestamp=0; + const char *name=NULL; + const char *msg=NULL; int unpacked; const rhizome_bid_t *bid = (const rhizome_bid_t *)&buffer[0]; @@ -541,39 +553,41 @@ static int read_metadata(struct meshmb_feeds *feeds, struct rhizome_read *read) if (offset >= (unsigned)bytes) goto error; - //uint8_t flags = buffer[offset++]; - offset++; - if (offset >= (unsigned)bytes) - goto error; + uint8_t flags = buffer[offset++]; - if ((unpacked = unpack_uint(buffer+offset, bytes-offset, &size)) == -1) - goto error; - offset += unpacked; - - if ((unpacked = unpack_uint(buffer+offset, bytes-offset, &delta)) == -1) - goto error; - offset += unpacked; - last_message_offset = size - delta; - - if ((unpacked = unpack_uint(buffer+offset, bytes-offset, &delta)) == -1) - goto error; - offset += unpacked; - last_seen = size - delta; - - if ((unpacked = unpack_uint(buffer+offset, bytes-offset, ×tamp)) == -1) - goto error; - offset += unpacked; - - const char *name = (const char *)&buffer[offset]; - while(buffer[offset++]){ + if (!(flags & FLAG_BLOCKED)){ if (offset >= (unsigned)bytes) goto error; - } - const char *msg = (const char *)&buffer[offset]; - while(buffer[offset++]){ - if (offset >= (unsigned)bytes) + if ((unpacked = unpack_uint(buffer+offset, bytes-offset, &size)) == -1) goto error; + offset += unpacked; + + if ((unpacked = unpack_uint(buffer+offset, bytes-offset, &delta)) == -1) + goto error; + offset += unpacked; + last_message_offset = size - delta; + + if ((unpacked = unpack_uint(buffer+offset, bytes-offset, &delta)) == -1) + goto error; + offset += unpacked; + last_seen = size - delta; + + if ((unpacked = unpack_uint(buffer+offset, bytes-offset, ×tamp)) == -1) + goto error; + offset += unpacked; + + name = (const char *)&buffer[offset]; + while(buffer[offset++]){ + if (offset >= (unsigned)bytes) + goto error; + } + + msg = (const char *)&buffer[offset]; + while(buffer[offset++]){ + if (offset >= (unsigned)bytes) + goto error; + } } DEBUGF(meshmb, "Seeking backwards %"PRIu64", %u, %zu", read->offset, offset, bytes); @@ -583,6 +597,7 @@ static int read_metadata(struct meshmb_feeds *feeds, struct rhizome_read *read) if (tree_find(&feeds->root, (void**)&result, bid->binary, sizeof *bid, alloc_feed, feeds)<0) return WHY("Failed to allocate metadata"); + result->details.blocked = (flags & FLAG_BLOCKED) ? 1 : 0; result->last_message_offset = last_message_offset; result->last_seen = last_seen; result->size = size; @@ -675,8 +690,6 @@ int meshmb_follow(struct meshmb_feeds *feeds, rhizome_bid_t *bid) struct feed_metadata *metadata; DEBUGF(meshmb, "Attempting to follow %s", alloca_tohex_rhizome_bid_t(*bid)); - // TODO load the manifest and check the service! - if (tree_find(&feeds->root, (void**)&metadata, bid->binary, sizeof *bid, alloc_feed, feeds)!=TREE_FOUND) return WHYF("Failed to follow feed"); @@ -687,6 +700,30 @@ int meshmb_follow(struct meshmb_feeds *feeds, rhizome_bid_t *bid) return 0; } +int meshmb_block(struct meshmb_feeds *feeds, rhizome_bid_t *bid) +{ + struct feed_metadata *metadata; + DEBUGF(meshmb, "Attempting to block %s", alloca_tohex_rhizome_bid_t(*bid)); + + if (tree_find(&feeds->root, (void**)&metadata, bid->binary, sizeof *bid, alloc_feed, feeds)!=TREE_FOUND) + return WHYF("Failed to block feed"); + if (metadata->details.name){ + free((void*)metadata->details.name); + metadata->details.name = NULL; + } + if (metadata->details.last_message){ + free((void*)metadata->details.last_message); + metadata->details.last_message = NULL; + } + if (is_all_matching(metadata->details.ply.author.binary, sizeof metadata->details.ply.author, 0)) + crypto_sign_to_sid(bid, &metadata->details.ply.author); + if (!metadata->details.blocked) + feeds->dirty = 1; + metadata->details.blocked = 1; + metadata->details.timestamp = 0; + return 0; +} + int meshmb_ignore(struct meshmb_feeds *feeds, rhizome_bid_t *bid) { DEBUGF(meshmb, "Attempting to ignore %s", alloca_tohex_rhizome_bid_t(*bid)); diff --git a/meshmb.h b/meshmb.h index eeb85592..cbcdf96f 100644 --- a/meshmb.h +++ b/meshmb.h @@ -14,6 +14,7 @@ struct meshmb_feed_details{ const char *name; const char *last_message; time_s_t timestamp; + bool_t blocked:1; }; // threaded feed iterator state @@ -41,6 +42,7 @@ int meshmb_flush(struct meshmb_feeds *feeds); // set / clear follow flag for this feed int meshmb_follow(struct meshmb_feeds *feeds, rhizome_bid_t *bid); int meshmb_ignore(struct meshmb_feeds *feeds, rhizome_bid_t *bid); +int meshmb_block(struct meshmb_feeds *feeds, rhizome_bid_t *bid); // enumerate feeds, starting from restart_from typedef int (*meshmb_callback) (struct meshmb_feed_details *details, void *context); diff --git a/meshmb_cli.c b/meshmb_cli.c index b83d68ce..2cc720b6 100644 --- a/meshmb_cli.c +++ b/meshmb_cli.c @@ -212,8 +212,8 @@ static int app_meshmb_find(const struct cli_parsed *parsed, struct cli_context * } DEFINE_CMD(app_meshmb_follow, 0, - "Start or stop following a broadcast feed", - "meshmb", "follow|ignore" KEYRING_PIN_OPTIONS, "", ""); + "Follow, block or ignore a broadcast feed", + "meshmb", "follow|ignore|block" KEYRING_PIN_OPTIONS, "", ""); static int app_meshmb_follow(const struct cli_parsed *parsed, struct cli_context *UNUSED(context)) { const char *peerhex; @@ -221,6 +221,7 @@ static int app_meshmb_follow(const struct cli_parsed *parsed, struct cli_context return -1; int follow = cli_arg(parsed, "follow", NULL, NULL, NULL) == 0; + int block = cli_arg(parsed, "block", NULL, NULL, NULL) == 0; identity_t peer; if (str_to_identity_t(&peer, peerhex) == -1) @@ -230,7 +231,9 @@ static int app_meshmb_follow(const struct cli_parsed *parsed, struct cli_context int ret = -1; if (feeds){ - if (follow){ + if (block){ + ret = meshmb_block(feeds, &peer); + }else if (follow){ ret = meshmb_follow(feeds, &peer); }else{ ret = meshmb_ignore(feeds, &peer); @@ -263,6 +266,7 @@ static int list_callback(struct meshmb_feed_details *details, void *context) cli_put_long(enum_context->context, enum_context->rowcount, ":"); cli_put_string(enum_context->context, alloca_tohex_rhizome_bid_t(details->ply.bundle_id), ":"); cli_put_string(enum_context->context, alloca_tohex_sid_t(details->ply.author), ":"); + cli_put_string(enum_context->context, details->blocked ? "true" : "false", ":"); cli_put_string(enum_context->context, details->name, ":"); cli_put_long(enum_context->context, details->timestamp ? (long)(gettime() - details->timestamp) : (long)-1, ":"); cli_put_string(enum_context->context, details->last_message, "\n"); @@ -270,7 +274,7 @@ static int list_callback(struct meshmb_feed_details *details, void *context) } DEFINE_CMD(app_meshmb_list, 0, - "List the feeds that you are currently following", + "List the feeds that you are currently following or blocking", "meshmb", "list", "following" KEYRING_PIN_OPTIONS, ""); static int app_meshmb_list(const struct cli_parsed *parsed, struct cli_context *context) { @@ -282,6 +286,7 @@ static int app_meshmb_list(const struct cli_parsed *parsed, struct cli_context * "_id", "id", "author", + "blocked", "name", "age", "last_message" diff --git a/meshmb_restful.c b/meshmb_restful.c index 88b96d32..36b30b4d 100644 --- a/meshmb_restful.c +++ b/meshmb_restful.c @@ -20,6 +20,10 @@ struct meshmb_session{ struct meshmb_feeds *feeds; }; +#define FLAG_FOLLOW (1) +#define FLAG_IGNORE (2) +#define FLAG_BLOCK (3) + static struct meshmb_session *sessions = NULL; static struct meshmb_session *open_session(const identity_t *identity){ @@ -484,40 +488,25 @@ static int restful_meshmb_newsince_find(httpd_request *r, const char *remainder) */ -static int restful_meshmb_follow(httpd_request *r, const char *remainder) +static int restful_meshmb_follow_ignore(httpd_request *r, const char *remainder) { if (*remainder) return 404; assert(r->finalise_union == NULL); struct meshmb_session *session = open_session(&r->bid); - int ret; + int ret=-1; - if (session - && meshmb_follow(session->feeds, &r->u.meshmb_feeds.bundle_id)!=-1 - && meshmb_flush(session->feeds)!=-1){ - http_request_simple_response(&r->http, 201, "TODO, detailed response"); - ret = 201; - }else{ - http_request_simple_response(&r->http, 500, "TODO, detailed response"); - ret = 500; + if (session){ + switch(r->ui64){ + case FLAG_FOLLOW: ret = meshmb_follow(session->feeds, &r->u.meshmb_feeds.bundle_id); break; + case FLAG_IGNORE: ret = meshmb_ignore(session->feeds, &r->u.meshmb_feeds.bundle_id); break; + case FLAG_BLOCK: ret = meshmb_block (session->feeds, &r->u.meshmb_feeds.bundle_id); break; + default: + FATAL("Unexpected value"); + } } - if (session) - close_session(session); - return ret; -} - -static int restful_meshmb_ignore(httpd_request *r, const char *remainder) -{ - if (*remainder) - return 404; - assert(r->finalise_union == NULL); - - struct meshmb_session *session = open_session(&r->bid); - int ret; - - if (session - && meshmb_ignore(session->feeds, &r->u.meshmb_feeds.bundle_id)!=-1 + if (ret!=-1 && meshmb_flush(session->feeds)!=-1){ http_request_simple_response(&r->http, 201, "TODO, detailed response"); ret = 201; @@ -545,7 +534,7 @@ static int restful_feedlist_enum(struct meshmb_feed_details *details, void *cont strbuf_json_hex(state->buffer, details->ply.bundle_id.binary, sizeof details->ply.bundle_id.binary); strbuf_puts(state->buffer, ","); strbuf_json_hex(state->buffer, details->ply.author.binary, sizeof details->ply.author.binary); - strbuf_puts(state->buffer, ","); + strbuf_puts(state->buffer, details->blocked ? ",true," : ",false,"); strbuf_json_string(state->buffer, details->name); strbuf_puts(state->buffer, ","); strbuf_sprintf(state->buffer, "%d", details->timestamp); @@ -569,6 +558,7 @@ static int restful_meshmb_feedlist_json_content_chunk(struct http_request *hr, s const char *headers[] = { "id", "author", + "blocked", "name", "timestamp", "last_message" @@ -918,13 +908,21 @@ static int restful_meshmb_(httpd_request *r, const char *remainder) remainder = ""; } else if(str_startswith(remainder, "/follow/", &end) && strn_to_identity_t(&r->u.meshmb_feeds.bundle_id, end, &end) != -1) { - handler = restful_meshmb_follow; + handler = restful_meshmb_follow_ignore; verb = HTTP_VERB_POST; + r->ui64 = FLAG_FOLLOW; remainder = ""; } else if(str_startswith(remainder, "/ignore/", &end) && strn_to_identity_t(&r->u.meshmb_feeds.bundle_id, end, &end) != -1) { - handler = restful_meshmb_ignore; + handler = restful_meshmb_follow_ignore; verb = HTTP_VERB_POST; + r->ui64 = FLAG_IGNORE; + remainder = ""; + } else if(str_startswith(remainder, "/block/", &end) + && strn_to_identity_t(&r->u.meshmb_feeds.bundle_id, end, &end) != -1) { + handler = restful_meshmb_follow_ignore; + verb = HTTP_VERB_POST; + r->ui64 = FLAG_BLOCK; remainder = ""; } /* diff --git a/tests/meshmb b/tests/meshmb index 0acf91d3..7b91b72d 100755 --- a/tests/meshmb +++ b/tests/meshmb @@ -85,16 +85,16 @@ setup_meshmbFollow() { test_meshmbFollow() { executeOk_servald meshmb follow $IDA1 $IDA2 executeOk_servald meshmb list following $IDA1 - assertStdoutGrep --matches=1 ":$IDA2:$SIDA2:Feed B:[0-9]\+:Message 2\$" - assertStdoutGrep --matches=0 ":$IDA3:$SIDA3:Feed C:[0-9]\+:Message 3\$" + assertStdoutGrep --matches=1 ":$IDA2:$SIDA2:false:Feed B:[0-9]\+:Message 2\$" + assertStdoutGrep --matches=0 ":$IDA3:$SIDA3:false:Feed C:[0-9]\+:Message 3\$" executeOk_servald meshmb follow $IDA1 $IDA3 executeOk_servald meshmb list following $IDA1 - assertStdoutGrep --matches=1 ":$IDA2:$SIDA2:Feed B:[0-9]\+:Message 2\$" - assertStdoutGrep --matches=1 ":$IDA3:$SIDA3:Feed C:[0-9]\+:Message 3\$" + assertStdoutGrep --matches=1 ":$IDA2:$SIDA2:false:Feed B:[0-9]\+:Message 2\$" + assertStdoutGrep --matches=1 ":$IDA3:$SIDA3:false:Feed C:[0-9]\+:Message 3\$" executeOk_servald meshmb ignore $IDA1 $IDA2 executeOk_servald meshmb list following $IDA1 - assertStdoutGrep --matches=0 ":$IDA2:$SIDA2:Feed B:[0-9]\+:Message 2\$" - assertStdoutGrep --matches=1 ":$IDA3:$SIDA3:Feed C:[0-9]\+:Message 3\$" + assertStdoutGrep --matches=0 ":$IDA2:$SIDA2:false:Feed B:[0-9]\+:Message 2\$" + assertStdoutGrep --matches=1 ":$IDA3:$SIDA3:false:Feed C:[0-9]\+:Message 3\$" } doc_meshmbThreading="Thread incoming message feeds" @@ -143,4 +143,32 @@ test_meshmbThreading() { assertStdoutGrep --matches=1 "5:$IDA5:$SIDA5:Feed E:[0-9]\+:[0-9]\+:Message 6\$" } +doc_meshmbBlock="Record blocked feeds" +setup_meshmbBlock() { + setup_identities 4 + executeOk_servald keyring set did $SIDA1 "" "Feed A" + executeOk_servald keyring set did $SIDA2 "" "Feed B" + executeOk_servald keyring set did $SIDA3 "" "Feed C" + executeOk_servald keyring set did $SIDA4 "" "Feed D" + executeOk_servald meshmb send $IDA2 "Message 1" + executeOk_servald meshmb send $IDA3 "Message 2" + executeOk_servald meshmb send $IDA4 "Message 3" + executeOk_servald meshmb follow $IDA1 $IDA2 + executeOk_servald meshmb follow $IDA1 $IDA3 +} +test_meshmbBlock() { + executeOk_servald meshmb block $IDA1 $IDA3 + executeOk_servald meshmb block $IDA1 $IDA4 + executeOk_servald meshmb activity $IDA1 + tfw_cat --stdout + assertStdoutGrep --matches=1 "0:$IDA2:$SIDA2:Feed B:[0-9]\+:[0-9]\+:Message 1\$" + # what was followed, disappears + assertStdoutGrep --matches=0 ":$IDA3:$SIDA3:" + executeOk_servald meshmb list following $IDA1 + tfw_cat --stdout + assertStdoutGrep --matches=1 ":$IDA2:$SIDA2:false:Feed B:[0-9]\+:Message 1\$" + assertStdoutGrep --matches=1 ":$IDA3:$SIDA3:true::-1:\$" + assertStdoutGrep --matches=1 ":$IDA4:$SIDA4:true::-1:\$" +} + runTests "$@" diff --git a/tests/meshmbrestful b/tests/meshmbrestful index 517b8fa4..4dd90db7 100755 --- a/tests/meshmbrestful +++ b/tests/meshmbrestful @@ -110,8 +110,8 @@ test_MeshMBRestFollow() { --request POST \ "http://$addr_localhost:$PORTA/restful/meshmb/$IDA1/follow/$IDA2" executeOk_servald meshmb list following $IDA1 - assertStdoutGrep --matches=1 ":$IDA2:$SIDA2::[0-9]\+:Message 2\$" - assertStdoutGrep --matches=0 ":$IDA3:$SIDA3::[0-9]\+:Message 3\$" + assertStdoutGrep --matches=1 ":$IDA2:$SIDA2:false::[0-9]\+:Message 2\$" + assertStdoutGrep --matches=0 ":$IDA3:$SIDA3:false::[0-9]\+:Message 3\$" executeOk curl \ --silent --fail --show-error \ --output follow.json \ @@ -119,8 +119,8 @@ test_MeshMBRestFollow() { --request POST \ "http://$addr_localhost:$PORTA/restful/meshmb/$IDA1/follow/$IDA3" executeOk_servald meshmb list following $IDA1 - assertStdoutGrep --matches=1 ":$IDA2:$SIDA2::[0-9]\+:Message 2\$" - assertStdoutGrep --matches=1 ":$IDA3:$SIDA3::[0-9]\+:Message 3\$" + assertStdoutGrep --matches=1 ":$IDA2:$SIDA2:false::[0-9]\+:Message 2\$" + assertStdoutGrep --matches=1 ":$IDA3:$SIDA3:false::[0-9]\+:Message 3\$" executeOk curl \ --silent --fail --show-error \ --output follow.json \ @@ -128,8 +128,8 @@ test_MeshMBRestFollow() { --request POST \ "http://$addr_localhost:$PORTA/restful/meshmb/$IDA1/ignore/$IDA2" executeOk_servald meshmb list following $IDA1 - assertStdoutGrep --matches=0 ":$IDA2:$SIDA2::[0-9]\+:Message 2\$" - assertStdoutGrep --matches=1 ":$IDA3:$SIDA3::[0-9]\+:Message 3\$" + assertStdoutGrep --matches=0 ":$IDA2:$SIDA2:false::[0-9]\+:Message 2\$" + assertStdoutGrep --matches=1 ":$IDA3:$SIDA3:false::[0-9]\+:Message 3\$" } doc_MeshMBRestFeeds="Restful list subscribed feeds"