RocketChat / Rocket.Chat.js.SDK

Utility for apps and bots to interact with Rocket.Chat via DDP and/or API
MIT License
136 stars 95 forks source link

Logs flooding by canAccessRoom method #112

Open emikolajczak opened 4 years ago

emikolajczak commented 4 years ago

Hello, We are trying to do performance tests in our Rocket.Chat installation. To do that, we created bots using Rocket.Chat.js.SDK to simulate message senders and receivers. Bots are in pairs which means one bot always sends message exactly to the same receiver: 1) Sender_A sends message to Receiver_A 2) Sender_B sends message to Receiver_B 3) Sender_C sends message to Receiver_C ... n) Sender_XXX sends message to Receiver_XXX

Sender bots sends messages in loop by using following code (I simply paste key parts/methods from SDK we use):

    await driver.connect({
        host: 'xxx',
        useSsl: true
    });

    await driver.login({
        username: 'bot_sender_X',
        password: 'pass_X'
    });

    await sendMessage = async(msg, receiver) => {

        await driver.sendDirectToUser(msg, receiver)
    };

    //some loop here...

    await sendMessage('Message number ' + i, receiver);
    console.log('Message number ' + i + ' sent');

    // wait for a few seconds before sending next message

    // end loop...

Receivers are listening for incoming messages using following:

    await driver.connect({
        host: 'xxx',
        useSsl: true
    });

    await driver.login({
        username: 'bot_receiver_X',
        password: 'pass_X'
    });

    const subscription = await driver.subscribeToMessages();
    const handler = await driver.reactToMessages(async(err, message, opts) => {
        if (err) {
            throw err;
        }

        if (message.u._id === driver.userId) {
            return;
        };

        // we received a message from our target
        if (message.u.username === sender) {
            //do smth
            console.log('Received message from ...');
        }
    });

Everything works fine when bots number is like 10, 20, 30 etc. Senders sends messages, receivers are receiving everything and it is OK. Problems start when we run simulation for ~100 users or more. Meteor starts logging a big amount of canAccessRoom method calling:

Meteor ➔ method canAccessRoom -> userId: null, arguments: ["sender_X_receiver_X_DM_channel_Name","receiver_A"]
Meteor ➔ method canAccessRoom -> userId: null, arguments: ["sender_D_receiver_D_DM_channel_Name","receiver_A"]
Meteor ➔ method canAccessRoom -> userId: null, arguments: ["sender_E_receiver_E_DM_channel_Name","receiver_A"]
Meteor ➔ method canAccessRoom -> userId: null, arguments: ["sender_F_receiver_F_DM_channel_Name","receiver_A"]
Meteor ➔ method canAccessRoom -> userId: null, arguments: ["sender_G_receiver_G_DM_channel_Name","receiver_A"]

The case is receiver_A of course does not have access to DM channel which belongs to sender_X and receiver_X. But Meteor is continuously checking access to rooms to which user does not belong. Why? We suppose this may cause performance problems that causes rocket to crash when there are ~1000 bots connected (independently from number of Rocket instances - ~10 instances [not] work same as ~20 instances). It looks like driver.reactToMessages would catch all incoming messages and after that filter it whether user has access to read it. But this case does not appear for small number of bots (10, 20, 30...). Bots are executed from one machine in separate processes.