Add button to join/leave communities

This commit is contained in:
Rogerio Chaves 2020-04-26 18:45:45 +02:00
parent bf7f2e7aeb
commit 5282ba0648
No known key found for this signature in database
GPG Key ID: E6AF5440509B1D94
6 changed files with 108 additions and 14 deletions

View File

@ -501,9 +501,13 @@ router.get(
const communityData = (req) => {
const name = req.params.name;
return queries.getCommunityMembers(name).then((members) => ({
return Promise.all([
queries.getCommunityMembers(name),
queries.isMember(req.context.profile.id, name),
]).then(([members, isMember]) => ({
name,
members,
isMember,
}));
};
@ -558,6 +562,38 @@ router.post("/communities/:name/new", async (req, res) => {
res.redirect(`/communities/${name}/${topic.key.replace("%", "")}`);
});
router.post("/communities/:name/join", async (req, res) => {
const name = req.params.name;
await ssb.client().identities.publishAs({
id: req.context.profile.id,
private: false,
content: {
type: "channel",
channel: name,
subscribed: true,
},
});
res.redirect(`/communities/${name}`);
});
router.post("/communities/:name/leave", async (req, res) => {
const name = req.params.name;
await ssb.client().identities.publishAs({
id: req.context.profile.id,
private: false,
content: {
type: "channel",
channel: name,
subscribed: false,
},
});
res.redirect(`/communities/${name}`);
});
router.post("/communities/:name/:key(*)/publish", async (req, res) => {
const name = req.params.name;
const key = req.params.key;

View File

@ -94,13 +94,14 @@ module.exports.setupRoutes = (router) => {
async (req, res) => {
const name = req.params.name;
const [posts, members] = await Promise.all([
const [posts, members, isMember] = await Promise.all([
queries.getCommunityPosts(name),
queries.getCommunityMembers(name),
queries.isMember(req.context.profile.id, name),
]);
res.render("mobile/communities/community", {
community: { name, members },
community: { name, members, isMember },
posts,
layout: "mobile/_layout",
});

View File

@ -8,7 +8,8 @@ const debugPosts = require("debug")("queries:posts"),
debugProfile = require("debug")("queries:profile"),
debugCommunities = require("debug")("queries:communities"),
debugCommunityMembers = require("debug")("queries:communityMembers"),
debugCommunityPosts = require("debug")("queries:communityPosts");
debugCommunityPosts = require("debug")("queries:communityPosts"),
debugCommunityIsMember = require("debug")("queries:communityIsMember");
const paramap = require("pull-paramap");
const { promisePull, mapValues } = require("./utils");
const ssb = require("./ssb-client");
@ -450,6 +451,32 @@ const getCommunities = async () => {
return communities;
};
const isMember = async (id, channel) => {
debugCommunityIsMember("Fetching");
const [lastSubscription] = await promisePull(
ssb.client().query.read({
reverse: true,
limit: 1,
query: [
{
$filter: {
value: {
author: id,
content: {
type: "channel",
channel: channel,
},
},
},
},
],
})
);
debugCommunityIsMember("Done");
return lastSubscription && lastSubscription.value.content.subscribed;
};
const getCommunityMembers = async (name) => {
debugCommunityMembers("Fetching");
@ -472,10 +499,22 @@ const getCommunityMembers = async (name) => {
}),
paramap(mapProfiles)
);
const dedupMembers = {};
for (const member of communityMembers) {
const author = member.value.author;
if (dedupMembers[author]) continue;
dedupMembers[author] = member;
}
const onlySubscribedMembers = Object.values(dedupMembers).filter(
(x) => x.value.content.subscribed
);
const memberProfiles = onlySubscribedMembers.map(
(x) => x.value.authorProfile
);
debugCommunityMembers("Done");
return communityMembers.map((x) => x.value.authorProfile);
return memberProfiles;
};
const getPostWithReplies = async (channel, key) => {
@ -611,4 +650,5 @@ module.exports = {
getPostWithReplies,
progress,
autofollow,
isMember,
};

View File

@ -6,8 +6,8 @@
}
</style>
<div style="background: #9b5f5f; padding: 50px; border-radius: 5px 5px 0 0">
<div style="max-width: 1200px; margin: 0 auto">
<div style="background: #9b5f5f; padding: 14px; border-radius: 5px 5px 0 0">
<div style="max-width: 1200px; margin: 0 auto; padding: 36px;">
<h1 style="font-size: 60px">
<a href="/communities/<%= community.name %>" style="color: #FFF; text-decoration: none;">
#<%= community.name %>
@ -19,7 +19,12 @@
<div style="max-width: 1200px; margin: 0 auto; border-radius: 0 0 5px 5px">
<div class="columns">
<div class="friends-communities" style="border-radius: 0">
<h2>Members</h2>
<div style="display: flex; justify-content: space-between; align-items: center; margin-bottom: 10px;">
<h2 style="margin: 0;">Members</h2>
<div>
<%- include('../shared/_join_button') %>
</div>
</div>
<%- include('../_friends', { friends: community.members }) %>
</div>
<div class="wall">

View File

@ -1,9 +1,12 @@
<div class="pink-background" style="flex-grow: 0;">
<h1>
<a href="/communities/<%= community.name %>" style="color: #600; text-decoration: none;">
#<%= community.name %>
</a>
</h1>
<div style="display: flex; justify-content: space-between;">
<h1>
<a href="/communities/<%= community.name %>" style="color: #600; text-decoration: none;">
#<%= community.name %>
</a>
</h1>
<%- include('../../shared/_join_button') %>
</div>
<a href="/mobile/communities/<%= community.name %>/new" class="compose-new-button" style="background: #fbb">
<div style="font-size: 40px; color: #FFF">+</div>
</a>
@ -19,7 +22,7 @@
<div class="tab-content">
<div class="tab-item js-tab-item">
<% posts.map(post => { %>
<a href="/communities/<%= community.name %>/<%= post.key.replace("%", "") %>" class="columns community-topic-link">
<a href="/mobile/communities/<%= community.name %>/<%= post.key.replace("%", "") %>" class="columns community-topic-link">
<div class="community-topic-name">
<%- topicTitle(post.value) %>
</div>

View File

@ -0,0 +1,9 @@
<% if (community.isMember) { %>
<form action="/communities/<%= community.name %>/leave" method="POST">
<input type="submit" value="Leave" />
</form>
<% } else { %>
<form action="/communities/<%= community.name %>/join" method="POST">
<input type="submit" value="Join" />
</form>
<% } %>