Change Blog Paradigm to Short-Form

Removes teaser and makes body mandatory.

It also adds support for deleting blogs and
introduces a getAuthorStatus() method to the IdentityManager
that takes a running transaction.
This commit is contained in:
Torsten Grote
2016-06-20 16:00:05 -03:00
parent 5a9615265e
commit 30fe9f6e2a
13 changed files with 203 additions and 114 deletions

View File

@@ -16,9 +16,6 @@ public interface BlogConstants {
/** The length of a blog post's title in UTF-8 bytes. */
int MAX_BLOG_POST_TITLE_LENGTH = 100;
/** The length of a blog post's teaser in UTF-8 bytes. */
int MAX_BLOG_POST_TEASER_LENGTH = 240;
/** The maximum length of a blog post's body in bytes. */
int MAX_BLOG_POST_BODY_LENGTH = MAX_MESSAGE_BODY_LENGTH - 1024;
@@ -31,8 +28,6 @@ public interface BlogConstants {
// Metadata keys
String KEY_DESCRIPTION = "description";
String KEY_TITLE = "title";
String KEY_TEASER = "teaser";
String KEY_HAS_BODY = "hasBody";
String KEY_TIMESTAMP = "timestamp";
String KEY_PARENT = "parent";
String KEY_AUTHOR_ID = "id";

View File

@@ -1,6 +1,5 @@
package org.briarproject.api.blogs;
import org.briarproject.api.FormatException;
import org.briarproject.api.db.DbException;
import org.briarproject.api.db.Transaction;
import org.briarproject.api.identity.LocalAuthor;
@@ -20,6 +19,9 @@ public interface BlogManager {
Blog addBlog(LocalAuthor localAuthor, String name, String description)
throws DbException;
/** Removes and deletes a blog. */
void removeBlog(Blog b) throws DbException;
/** Stores a local blog post. */
void addLocalPost(BlogPost p) throws DbException;
@@ -45,4 +47,11 @@ public interface BlogManager {
/** Marks a blog post as read or unread. */
void setReadFlag(MessageId m, boolean read) throws DbException;
/** Registers a hook to be called whenever a blog is removed. */
void registerRemoveBlogHook(RemoveBlogHook hook);
interface RemoveBlogHook {
void removingBlog(Transaction txn, Blog b) throws DbException;
}
}

View File

@@ -1,43 +1,27 @@
package org.briarproject.api.blogs;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.briarproject.api.forum.ForumPost;
import org.briarproject.api.identity.Author;
import org.briarproject.api.sync.Message;
import org.briarproject.api.sync.MessageId;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
public class BlogPost extends ForumPost {
@Nullable
private final String title;
@NotNull
private final String teaser;
private final boolean hasBody;
public BlogPost(@Nullable String title, @NotNull String teaser,
boolean hasBody, @NotNull Message message,
@Nullable MessageId parent, @NotNull Author author,
public BlogPost(@Nullable String title, @NotNull Message message,
@Nullable MessageId parent, @NotNull Author author,
@NotNull String contentType) {
super(message, parent, author, contentType);
this.title = title;
this.teaser = teaser;
this.hasBody = hasBody;
}
@Nullable
public String getTitle() {
return title;
}
@NotNull
public String getTeaser() {
return teaser;
}
public boolean hasBody() {
return hasBody;
}
}

View File

@@ -12,8 +12,8 @@ import java.security.GeneralSecurityException;
public interface BlogPostFactory {
BlogPost createBlogPost(@NotNull GroupId groupId, @Nullable String title,
@NotNull String teaser, long timestamp, @Nullable MessageId parent,
long timestamp, @Nullable MessageId parent,
@NotNull LocalAuthor author, @NotNull String contentType,
@Nullable byte[] body)
@NotNull byte[] body)
throws FormatException, GeneralSecurityException;
}

View File

@@ -11,33 +11,18 @@ public class BlogPostHeader extends PostHeader {
@Nullable
private final String title;
@NotNull
private final String teaser;
private final boolean hasBody;
public BlogPostHeader(@Nullable String title, @NotNull String teaser,
boolean hasBody, @NotNull MessageId id,
public BlogPostHeader(@Nullable String title, @NotNull MessageId id,
@Nullable MessageId parentId, long timestamp,
@NotNull Author author, @NotNull Status authorStatus,
@NotNull String contentType, boolean read) {
super(id, parentId, timestamp, author, authorStatus, contentType, read);
this.title = title;
this.teaser = teaser;
this.hasBody = hasBody;
}
@Nullable
public String getTitle() {
return title;
}
@NotNull
public String getTeaser() {
return teaser;
}
public boolean hasBody() {
return hasBody;
}
}

View File

@@ -0,0 +1,32 @@
package org.briarproject.api.event;
import org.briarproject.api.blogs.BlogPostHeader;
import org.briarproject.api.sync.GroupId;
/** An event that is broadcast when a blog post was added to the database. */
public class BlogPostAddedEvent extends Event {
private final GroupId groupId;
private final BlogPostHeader header;
private final boolean local;
public BlogPostAddedEvent(GroupId groupId, BlogPostHeader header,
boolean local) {
this.groupId = groupId;
this.header = header;
this.local = local;
}
public GroupId getGroupId() {
return groupId;
}
public BlogPostHeader getHeader() {
return header;
}
public boolean isLocal() {
return local;
}
}

View File

@@ -29,6 +29,9 @@ public interface IdentityManager {
/** Returns the trust-level status of the author */
Status getAuthorStatus(AuthorId a) throws DbException;
/** Returns the trust-level status of the author */
Status getAuthorStatus(Transaction txn, AuthorId a) throws DbException;
interface AddIdentityHook {
void addingIdentity(Transaction txn, LocalAuthor a) throws DbException;
}

View File

@@ -10,9 +10,11 @@ import org.briarproject.api.clients.ClientHelper;
import org.briarproject.api.data.BdfDictionary;
import org.briarproject.api.data.BdfEntry;
import org.briarproject.api.data.BdfList;
import org.briarproject.api.data.MetadataParser;
import org.briarproject.api.db.DatabaseComponent;
import org.briarproject.api.db.DbException;
import org.briarproject.api.db.Transaction;
import org.briarproject.api.event.BlogPostAddedEvent;
import org.briarproject.api.identity.Author;
import org.briarproject.api.identity.Author.Status;
import org.briarproject.api.identity.AuthorId;
@@ -21,7 +23,9 @@ import org.briarproject.api.identity.LocalAuthor;
import org.briarproject.api.sync.ClientId;
import org.briarproject.api.sync.Group;
import org.briarproject.api.sync.GroupId;
import org.briarproject.api.sync.Message;
import org.briarproject.api.sync.MessageId;
import org.briarproject.clients.BdfIncomingMessageHook;
import org.briarproject.util.StringUtils;
import org.jetbrains.annotations.Nullable;
@@ -31,24 +35,24 @@ import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.concurrent.CopyOnWriteArrayList;
import java.util.logging.Logger;
import javax.inject.Inject;
import static java.util.logging.Level.WARNING;
import static org.briarproject.api.blogs.BlogConstants.KEY_AUTHOR;
import static org.briarproject.api.blogs.BlogConstants.KEY_AUTHOR_ID;
import static org.briarproject.api.blogs.BlogConstants.KEY_AUTHOR_NAME;
import static org.briarproject.api.blogs.BlogConstants.KEY_CONTENT_TYPE;
import static org.briarproject.api.blogs.BlogConstants.KEY_DESCRIPTION;
import static org.briarproject.api.blogs.BlogConstants.KEY_HAS_BODY;
import static org.briarproject.api.blogs.BlogConstants.KEY_PARENT;
import static org.briarproject.api.blogs.BlogConstants.KEY_PUBLIC_KEY;
import static org.briarproject.api.blogs.BlogConstants.KEY_READ;
import static org.briarproject.api.blogs.BlogConstants.KEY_TEASER;
import static org.briarproject.api.blogs.BlogConstants.KEY_TIMESTAMP;
import static org.briarproject.api.blogs.BlogConstants.KEY_TITLE;
class BlogManagerImpl implements BlogManager {
class BlogManagerImpl extends BdfIncomingMessageHook implements BlogManager {
private static final Logger LOG =
Logger.getLogger(BlogManagerImpl.class.getName());
@@ -59,17 +63,19 @@ class BlogManagerImpl implements BlogManager {
private final DatabaseComponent db;
private final IdentityManager identityManager;
private final ClientHelper clientHelper;
private final BlogFactory blogFactory;
private final List<RemoveBlogHook> removeHooks;
@Inject
BlogManagerImpl(DatabaseComponent db, IdentityManager identityManager,
ClientHelper clientHelper, BlogFactory blogFactory) {
ClientHelper clientHelper, MetadataParser metadataParser,
BlogFactory blogFactory) {
super(clientHelper, metadataParser);
this.db = db;
this.identityManager = identityManager;
this.clientHelper = clientHelper;
this.blogFactory = blogFactory;
removeHooks = new CopyOnWriteArrayList<RemoveBlogHook>();
}
@Override
@@ -77,6 +83,17 @@ class BlogManagerImpl implements BlogManager {
return CLIENT_ID;
}
@Override
protected void incomingMessage(Transaction txn, Message m, BdfList list,
BdfDictionary meta) throws DbException, FormatException {
GroupId groupId = m.getGroupId();
BlogPostHeader h = getPostHeaderFromMetadata(txn, m.getId(), meta);
BlogPostAddedEvent event =
new BlogPostAddedEvent(groupId, h, false);
txn.attach(event);
}
@Override
public Blog addBlog(LocalAuthor localAuthor, String name,
String description) throws DbException {
@@ -101,13 +118,25 @@ class BlogManagerImpl implements BlogManager {
}
@Override
public void addLocalPost(BlogPost p) throws DbException {
public void removeBlog(Blog b) throws DbException {
Transaction txn = db.startTransaction(false);
try {
BdfDictionary meta = new BdfDictionary();
for (RemoveBlogHook hook : removeHooks)
hook.removingBlog(txn, b);
db.removeGroup(txn, b.getGroup());
txn.setComplete();
} finally {
db.endTransaction(txn);
}
}
@Override
public void addLocalPost(BlogPost p) throws DbException {
BdfDictionary meta;
try {
meta = new BdfDictionary();
if (p.getTitle() != null) meta.put(KEY_TITLE, p.getTitle());
meta.put(KEY_TEASER, p.getTeaser());
meta.put(KEY_TIMESTAMP, p.getMessage().getTimestamp());
meta.put(KEY_HAS_BODY, p.hasBody());
if (p.getParent() != null) meta.put(KEY_PARENT, p.getParent());
Author a = p.getAuthor();
@@ -123,6 +152,22 @@ class BlogManagerImpl implements BlogManager {
} catch (FormatException e) {
throw new RuntimeException(e);
}
// broadcast event about new post
Transaction txn = db.startTransaction(true);
try {
GroupId groupId = p.getMessage().getGroupId();
MessageId postId = p.getMessage().getId();
BlogPostHeader h = getPostHeaderFromMetadata(txn, postId, meta);
BlogPostAddedEvent event =
new BlogPostAddedEvent(groupId, h, true);
txn.attach(event);
txn.setComplete();
} catch (FormatException e) {
if (LOG.isLoggable(WARNING)) LOG.log(WARNING, e.toString(), e);
} finally {
db.endTransaction(txn);
}
}
@Override
@@ -189,16 +234,20 @@ class BlogManagerImpl implements BlogManager {
@Nullable
public byte[] getPostBody(MessageId m) throws DbException {
try {
// content, signature
// content: parent, contentType, title, teaser, body, attachments
BdfList message = clientHelper.getMessageAsList(m);
BdfList content = message.getList(0);
return content.getRaw(4);
return getPostBody(message);
} catch (FormatException e) {
throw new DbException(e);
}
}
private byte[] getPostBody(BdfList message) throws FormatException {
// content, signature
// content: parent, contentType, title, body, attachments
BdfList content = message.getList(0);
return content.getRaw(3);
}
@Override
public Collection<BlogPostHeader> getPostHeaders(GroupId g)
throws DbException {
@@ -213,26 +262,9 @@ class BlogManagerImpl implements BlogManager {
for (Entry<MessageId, BdfDictionary> entry : metadata.entrySet()) {
try {
BdfDictionary meta = entry.getValue();
String title = meta.getOptionalString(KEY_TITLE);
String teaser = meta.getString(KEY_TEASER);
boolean hasBody = meta.getBoolean(KEY_HAS_BODY);
long timestamp = meta.getLong(KEY_TIMESTAMP);
MessageId parentId = null;
if (meta.containsKey(KEY_PARENT))
parentId = new MessageId(meta.getRaw(KEY_PARENT));
BdfDictionary d = meta.getDictionary(KEY_AUTHOR);
AuthorId authorId = new AuthorId(d.getRaw(KEY_AUTHOR_ID));
String name = d.getString(KEY_AUTHOR_NAME);
byte[] publicKey = d.getRaw(KEY_PUBLIC_KEY);
Author author = new Author(authorId, name, publicKey);
Status authorStatus = identityManager.getAuthorStatus(authorId);
String contentType = meta.getString(KEY_CONTENT_TYPE);
boolean read = meta.getBoolean(KEY_READ);
headers.add(new BlogPostHeader(title, teaser, hasBody,
entry.getKey(), parentId, timestamp, author,
authorStatus, contentType, read));
BlogPostHeader h =
getPostHeaderFromMetadata(null, entry.getKey(), meta);
headers.add(h);
} catch (FormatException e) {
throw new DbException(e);
}
@@ -251,10 +283,43 @@ class BlogManagerImpl implements BlogManager {
}
}
@Override
public void registerRemoveBlogHook(RemoveBlogHook hook) {
removeHooks.add(hook);
}
private String getBlogDescription(Transaction txn, GroupId g)
throws DbException, FormatException {
BdfDictionary d = clientHelper.getGroupMetadataAsDictionary(txn, g);
return d.getString(KEY_DESCRIPTION);
}
private BlogPostHeader getPostHeaderFromMetadata(@Nullable Transaction txn,
MessageId id, BdfDictionary meta)
throws DbException, FormatException {
String title = meta.getOptionalString(KEY_TITLE);
long timestamp = meta.getLong(KEY_TIMESTAMP);
MessageId parentId = null;
if (meta.containsKey(KEY_PARENT))
parentId = new MessageId(meta.getRaw(KEY_PARENT));
BdfDictionary d = meta.getDictionary(KEY_AUTHOR);
AuthorId authorId = new AuthorId(d.getRaw(KEY_AUTHOR_ID));
String name = d.getString(KEY_AUTHOR_NAME);
byte[] publicKey = d.getRaw(KEY_PUBLIC_KEY);
Author author = new Author(authorId, name, publicKey);
Status authorStatus;
if (txn == null)
authorStatus = identityManager.getAuthorStatus(authorId);
else {
authorStatus = identityManager.getAuthorStatus(txn, authorId);
}
String contentType = meta.getString(KEY_CONTENT_TYPE);
boolean read = meta.getBoolean(KEY_READ);
return new BlogPostHeader(title, id, parentId, timestamp, author,
authorStatus, contentType, read);
}
}

View File

@@ -22,7 +22,6 @@ import java.security.GeneralSecurityException;
import javax.inject.Inject;
import static org.briarproject.api.blogs.BlogConstants.MAX_BLOG_POST_BODY_LENGTH;
import static org.briarproject.api.blogs.BlogConstants.MAX_BLOG_POST_TEASER_LENGTH;
import static org.briarproject.api.blogs.BlogConstants.MAX_BLOG_POST_TITLE_LENGTH;
import static org.briarproject.api.blogs.BlogConstants.MAX_CONTENT_TYPE_LENGTH;
@@ -39,25 +38,22 @@ class BlogPostFactoryImpl implements BlogPostFactory {
@Override
public BlogPost createBlogPost(@NotNull GroupId groupId,
@Nullable String title, @NotNull String teaser, long timestamp,
@Nullable String title, long timestamp,
@Nullable MessageId parent, @NotNull LocalAuthor author,
@NotNull String contentType, @Nullable byte[] body)
@NotNull String contentType, @NotNull byte[] body)
throws FormatException, GeneralSecurityException {
// Validate the arguments
if (title != null &&
StringUtils.toUtf8(title).length > MAX_BLOG_POST_TITLE_LENGTH)
throw new IllegalArgumentException();
if (StringUtils.toUtf8(teaser).length > MAX_BLOG_POST_TEASER_LENGTH)
throw new IllegalArgumentException();
if (StringUtils.toUtf8(contentType).length > MAX_CONTENT_TYPE_LENGTH)
throw new IllegalArgumentException();
if (body != null && body.length > MAX_BLOG_POST_BODY_LENGTH)
if (body.length > MAX_BLOG_POST_BODY_LENGTH)
throw new IllegalArgumentException();
// Serialise the data to be signed
BdfList content =
BdfList.of(parent, contentType, title, teaser, body, null);
BdfList content = BdfList.of(parent, contentType, title, body, null);
BdfList signed = BdfList.of(groupId, timestamp, content);
// Generate the signature
@@ -72,7 +68,6 @@ class BlogPostFactoryImpl implements BlogPostFactory {
// Serialise the signed message
BdfList message = BdfList.of(content, sig);
Message m = clientHelper.createMessage(groupId, timestamp, message);
return new BlogPost(title, teaser, body != null, m, parent, author,
contentType);
return new BlogPost(title, m, parent, author, contentType);
}
}

View File

@@ -11,6 +11,7 @@ import org.briarproject.api.crypto.KeyParser;
import org.briarproject.api.crypto.PublicKey;
import org.briarproject.api.crypto.Signature;
import org.briarproject.api.data.BdfDictionary;
import org.briarproject.api.data.BdfEntry;
import org.briarproject.api.data.BdfList;
import org.briarproject.api.data.MetadataEncoder;
import org.briarproject.api.identity.Author;
@@ -25,15 +26,16 @@ import java.security.GeneralSecurityException;
import java.util.Collection;
import java.util.Collections;
import static org.briarproject.api.blogs.BlogConstants.KEY_AUTHOR;
import static org.briarproject.api.blogs.BlogConstants.KEY_AUTHOR_ID;
import static org.briarproject.api.blogs.BlogConstants.KEY_AUTHOR_NAME;
import static org.briarproject.api.blogs.BlogConstants.KEY_CONTENT_TYPE;
import static org.briarproject.api.blogs.BlogConstants.KEY_HAS_BODY;
import static org.briarproject.api.blogs.BlogConstants.KEY_PARENT;
import static org.briarproject.api.blogs.BlogConstants.KEY_PUBLIC_KEY;
import static org.briarproject.api.blogs.BlogConstants.KEY_READ;
import static org.briarproject.api.blogs.BlogConstants.KEY_TEASER;
import static org.briarproject.api.blogs.BlogConstants.KEY_TIMESTAMP;
import static org.briarproject.api.blogs.BlogConstants.KEY_TITLE;
import static org.briarproject.api.blogs.BlogConstants.MAX_BLOG_POST_BODY_LENGTH;
import static org.briarproject.api.blogs.BlogConstants.MAX_BLOG_POST_TEASER_LENGTH;
import static org.briarproject.api.blogs.BlogConstants.MAX_BLOG_POST_TITLE_LENGTH;
import static org.briarproject.api.blogs.BlogConstants.MAX_CONTENT_TYPE_LENGTH;
import static org.briarproject.api.identity.AuthorConstants.MAX_SIGNATURE_LENGTH;
@@ -60,37 +62,36 @@ class BlogPostValidator extends BdfMessageValidator {
checkSize(body, 2);
BdfList content = body.getList(0);
// Content: Parent ID, content type, title (optional), teaser,
// post body (optional), attachments (optional)
checkSize(body, 6);
// Content: Parent ID, content type, title (optional), post body,
// attachments (optional)
checkSize(content, 5);
// Parent ID is optional
byte[] parent = content.getOptionalRaw(0);
checkLength(parent, UniqueId.LENGTH);
// Content type
String contentType = content.getString(1);
checkLength(contentType, 0, MAX_CONTENT_TYPE_LENGTH);
if (!contentType.equals("text/plain"))
throw new InvalidMessageException("Invalid content type");
// Blog post title is optional
String title = content.getOptionalString(2);
checkLength(contentType, 0, MAX_BLOG_POST_TITLE_LENGTH);
// Blog teaser
String teaser = content.getString(3);
// TODO make sure that there is only text in the teaser
checkLength(contentType, 0, MAX_BLOG_POST_TEASER_LENGTH);
// Blog post body is optional
byte[] postBody = content.getOptionalRaw(4);
// Blog post body
byte[] postBody = content.getRaw(3);
checkLength(postBody, 0, MAX_BLOG_POST_BODY_LENGTH);
// Attachments
BdfDictionary attachments = content.getOptionalDictionary(5);
BdfDictionary attachments = content.getOptionalDictionary(4);
// TODO handle attachments somehow
// Signature
byte[] sig = body.getRaw(1);
checkLength(sig, 0, MAX_SIGNATURE_LENGTH);
// Verify the signature
Author a;
try {
// Get the blog author
Blog b = blogFactory.parseBlog(g, ""); // description doesn't matter
Author a = b.getAuthor();
a = b.getAuthor();
// Parse the public key
KeyParser keyParser = crypto.getSignatureKeyParser();
PublicKey key = keyParser.parsePublicKey(a.getPublicKey());
@@ -111,8 +112,12 @@ class BlogPostValidator extends BdfMessageValidator {
BdfDictionary meta = new BdfDictionary();
Collection<MessageId> dependencies = null;
if (title != null) meta.put(KEY_TITLE, title);
meta.put(KEY_TEASER, teaser);
meta.put(KEY_HAS_BODY, postBody != null);
BdfDictionary author = BdfDictionary.of(
new BdfEntry(KEY_AUTHOR_ID, a.getId()),
new BdfEntry(KEY_AUTHOR_NAME, a.getName()),
new BdfEntry(KEY_PUBLIC_KEY, a.getPublicKey())
);
meta.put(KEY_AUTHOR, author);
meta.put(KEY_TIMESTAMP, m.getTimestamp());
if (parent != null) {
meta.put(KEY_PARENT, parent);

View File

@@ -99,17 +99,24 @@ class IdentityManagerImpl implements IdentityManager {
public Status getAuthorStatus(AuthorId authorId) throws DbException {
Transaction txn = db.startTransaction(false);
try {
// Compare to the IDs of the user's identities
for (LocalAuthor a : db.getLocalAuthors(txn))
if (a.getId().equals(authorId)) return VERIFIED;
// Compare to the IDs of contacts' identities
for (Contact c : db.getContacts(txn))
if (c.getAuthor().getId().equals(authorId)) return VERIFIED;
// TODO also handle UNVERIFIED when #261 is implemented
return UNKNOWN;
return getAuthorStatus(txn, authorId);
} finally {
db.endTransaction(txn);
}
}
@Override
public Status getAuthorStatus(Transaction txn, AuthorId authorId)
throws DbException {
// Compare to the IDs of the user's identities
for (LocalAuthor a : db.getLocalAuthors(txn))
if (a.getId().equals(authorId)) return VERIFIED;
// Compare to the IDs of contacts' identities
for (Contact c : db.getContacts(txn))
if (c.getAuthor().getId().equals(authorId)) return VERIFIED;
// TODO also handle UNVERIFIED when #261 is implemented
return UNKNOWN;
}
}

View File

@@ -5,6 +5,7 @@ import org.briarproject.api.blogs.Blog;
import org.briarproject.api.blogs.BlogFactory;
import org.briarproject.api.blogs.BlogInvitationMessage;
import org.briarproject.api.blogs.BlogManager;
import org.briarproject.api.blogs.BlogManager.RemoveBlogHook;
import org.briarproject.api.blogs.BlogSharingManager;
import org.briarproject.api.blogs.BlogSharingMessage.BlogInvitation;
import org.briarproject.api.clients.ClientHelper;
@@ -40,7 +41,7 @@ import static org.briarproject.api.blogs.BlogConstants.BLOG_TITLE;
class BlogSharingManagerImpl extends
SharingManagerImpl<Blog, BlogInvitation, BlogInvitationMessage, BlogInviteeSessionState, BlogSharerSessionState, BlogInvitationReceivedEvent, BlogInvitationResponseReceivedEvent>
implements BlogSharingManager {
implements BlogSharingManager, RemoveBlogHook {
static final ClientId CLIENT_ID = new ClientId(StringUtils.fromHexString(
"bee438b5de0b3a685badc4e49d76e72d"
@@ -124,6 +125,11 @@ class BlogSharingManagerImpl extends
return irrFactory;
}
@Override
public void removingBlog(Transaction txn, Blog b) throws DbException {
removingShareable(txn, b);
}
static class SFactory implements
ShareableFactory<Blog, BlogInvitation, BlogInviteeSessionState, BlogSharerSessionState> {

View File

@@ -1,5 +1,6 @@
package org.briarproject.sharing;
import org.briarproject.api.blogs.BlogManager;
import org.briarproject.api.blogs.BlogSharingManager;
import org.briarproject.api.clients.ClientHelper;
import org.briarproject.api.clients.MessageQueueManager;
@@ -49,6 +50,7 @@ public class SharingModule {
LifecycleManager lifecycleManager,
ContactManager contactManager,
MessageQueueManager messageQueueManager,
BlogManager blogManager,
BlogSharingManagerImpl blogSharingManager) {
lifecycleManager.registerClient(blogSharingManager);
@@ -56,6 +58,7 @@ public class SharingModule {
contactManager.registerRemoveContactHook(blogSharingManager);
messageQueueManager.registerIncomingMessageHook(
BlogSharingManagerImpl.CLIENT_ID, blogSharingManager);
blogManager.registerRemoveBlogHook(blogSharingManager);
return blogSharingManager;
}