• Home
  • Categories
  • Recent
  • Popular
  • Top
  • Tags
  • Users
  • Groups
  • Documentation
    • Home
    • Read API
    • Write API
    • Plugin Development
Skins
  • Light
  • Cerulean
  • Cosmo
  • Flatly
  • Journal
  • Litera
  • Lumen
  • Lux
  • Materia
  • Minty
  • Morph
  • Pulse
  • Sandstone
  • Simplex
  • Sketchy
  • Spacelab
  • United
  • Yeti
  • Zephyr
  • Dark
  • Cyborg
  • Darkly
  • Quartz
  • Slate
  • Solar
  • Superhero
  • Vapor

  • Default (No Skin)
  • No Skin
Collapse
v3.5.2 Latest
Buy Hosting

Display Group Badge On Topic List?

Scheduled Pinned Locked Moved Plugin Development
13 Posts 3 Posters 752 Views
    • Oldest to Newest
    • Newest to Oldest
    • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • T Offline
    T Offline
    Teemberland
    wrote on last edited by Teemberland
    #2

    EDIT:

    I'm trying to create a plugin that shows the group badge next to or below the topic name. The idea is to notify the readers that a 'dev' or 'admin' has posted/responded to the topic.

    Are there any plugins available that can do this? Is it possible to create?

    Thank you in advance!

    1 Reply Last reply
    0
  • barisB Offline
    barisB Offline
    <baris> NodeBB
    wrote on last edited by
    #3

    This shouldn't be hard to do, listen for filter:topics.get and then load the users groups into the user object. Once that is done you can display them on partials/topics_list.tpl

    myPlugin.filterTopicsGet = async function (hookData) {
      const uids = hookData.topics.map(t => t.uid);
      const userGroups = await Groups.getUserGroups(uids);
      hookData.topics.forEach((t, i) => {
          t.user.groups = userGroups[i];
      });
      return hookData;
    };
    

    This would create a groups variable on every user object which you can access in the template.

    T 1 Reply Last reply
    1
  • T Offline
    T Offline
    Teemberland
    replied to <baris> on last edited by
    #4

    @baris Thank you for this. I can now see the groups variable for users listed on the topics page. I do have a follow up question. Is there a way for us to access all posts (including users) in a topic from the topics page? Our goal is to dynamically place a badge under the topic title to indicate that a dev had posted/replied in the topic.

    barisB 1 Reply Last reply
    0
  • barisB Offline
    barisB Offline
    <baris> NodeBB
    replied to Teemberland on last edited by
    #5

    @Teemberland For this you can use the sorted set tid:<tid>:posters it contains all uids who have posted in the topic (including the OP) and the score is the number of posts they have in that topic. So you need to grab the uids from this sorted set and check if any of the uids are in a dev group.

    T 2 Replies Last reply
    1
  • T Offline
    T Offline
    Teemberland
    replied to <baris> on last edited by
    #6

    @baris great! I'll give this one a shot!

    1 Reply Last reply
    0
  • T Offline
    T Offline
    Teemberland
    replied to <baris> on last edited by Teemberland
    #7

    @baris thank you for your suggestion. I can get the posters now, but I'm not able to get their groups. Here's my code. Can you tell me what I'm missing here?

    var db = require.main.require('./src/database');
    
    theme.filterTopicsGetDevActivity = async function(hookData) {
      hookData.topics.forEach((t, i) => {
        db.getSortedSetRange('tid:' + t.tid + ':posters', 0, -1, function (err, uids) {
          t.foobar = uids;
        });
      });
      return hookData;
    }
    

    Here's my hook:

    {
      "hook": "filter:topics.get",
      "method": "filterTopicsGetDevActivity"
     }
    

    My template:

    <!-- IF topics.foobar.length -->
      <!-- BEGIN topics.foobar -->
        {topics.foobar}
      <!-- END topics.foobar -->
    <!-- ENDIF topics.foobar.length -->
    

    I tried using {topics.foobar.groups.slug} to display the group name, but the object becomes empty.

    0C69C8F1-2645-4727-9FAF-1FB311D185AF.png

    1 Reply Last reply
    0
  • barisB Offline
    barisB Offline
    <baris> NodeBB
    wrote on last edited by
    #8

    Your code is only getting the uids who have posted in the topic it is not loading any group data. It is also loading the uids in a foreach which won't work as you expect it. You need to use promises and assign the data once the call is complete.

    You want something like below, adjust as necessary.

    myPlugin.filterTopicsGet = async function (hookData) {
      const groupData = hookData.topics.map(async (t) => {
           const uids = await db.getSortedSetMembers('tid:' + t.tid + ':posters'));
           const userGroups = await Groups.getUserGroupMembership('groups:createtime', uids);       
           return userGroups.flat().includes('My developer group');
      });
    
      hookData.topics.forEach((t, i) => {
          t.postedInByDeveloper = groupData[i];
      });
      return hookData;
    };
    
    T 1 Reply Last reply
    0
  • T Offline
    T Offline
    Teemberland
    replied to <baris> on last edited by
    #9

    @baris thank you! I think we're very close. When I call postedInByDeveloper in my template {topics.postedInByDeveloper} I get an [object Promise] in view.

    I also tried making an api call in the console to check the object and found that postedInByDeveloper is empty. See screenshot below.

    Screen Shot 2020-07-07 at 14.27.20 PM.png

    1 Reply Last reply
    0
  • barisB Offline
    barisB Offline
    <baris> NodeBB
    wrote on last edited by baris
    #10

    I was writing the code of the top of my head so it had errors, this should work I think.

    myPlugin.filterTopicsGet = async function (hookData) {
      const groupData = await Promise.all(hookData.topics.map(async (t) => {
           const uids = await db.getSortedSetMembers('tid:' + t.tid + ':posters');
           const userGroups = await Groups.getUserGroupMembership('groups:createtime', uids);       
           return userGroups.flat().includes('My developer group');
      }));
    
      hookData.topics.forEach((t, i) => {
          t.postedInByDeveloper = groupData[i];
      });
      return hookData;
    };
    
    T 1 Reply Last reply
    0
  • T Offline
    T Offline
    Teemberland
    replied to <baris> on last edited by
    #11

    @baris I had to update to 1.14.x to get access to getSortedSetMember. I didn't know that this method was new. Also, I had to use a different method for flat() since I'm on the older version of node locally.

    Thank you once again for all your help!

    1 Reply Last reply
    0
  • patsanchP patsanch referenced this topic on
  • barisB Offline
    barisB Offline
    <baris> NodeBB
    wrote on last edited by
    #12

    @Teemberland @patsanch I've rewritten the above filter to use less database calls. You can give it a try as well if you don't want to add new hooks from the referenced topic.

    myPlugin.filterTopicsGet = async function (hookData) {
    	const tids = hookData.topics.map(t => t && t.tid);
    	const posterUids = await db.getSortedSetsMembers(tids.map(tid => `tid:${tid}:posters`));
    	const uids = _.uniq(_.flatten(posterUids));
    	const isMembers = await Groups.isMembers(uids, 'My developer group');
    	const membershipMap = _.zipObject(uids, isMembers);
    	hookData.topics.forEach((t, i) => {
    		t.postedInByDeveloper = posterUids[i].some(uid => membershipMap[uid]);
    	});
    	return hookData;
    };
    

    This runs a lot faster since it's only making 2 database calls.

    before 
    took 975.6332 milliseconds
    took 922.0847 milliseconds
    took 819.809 milliseconds
    
    after
    took 3.9381 milliseconds
    took 3.8666 milliseconds
    took 3.1888 milliseconds
    
    1 Reply Last reply
    2
  • patsanchP Offline
    patsanchP Offline
    patsanch
    wrote on last edited by
    #13

    Thanks baris! We'll keep this for reference 🙂

    1 Reply Last reply
    0

Copyright © 2023 NodeBB | Contributors
  • Login

  • Don't have an account? Register

  • Login or register to search.
Powered by NodeBB Contributors
  • First post
    Last post
0
  • Home
  • Categories
  • Recent
  • Popular
  • Top
  • Tags
  • Users
  • Groups
  • Documentation
    • Home
    • Read API
    • Write API
    • Plugin Development