Existe alguma maneira de desativar temporariamente o RateLimiter para criação em massa por administrador?

So here is my issue. I have a requirement to essentially seed a Discourse production instance with around 200 posts at a time from a plugin admin action. These posts will be ‘created by’ 1 of 10 different regular users. The reason it’s a plugin action is because the users of this particular instance have a team of moderators they want to train up, and wanted some test posts to train them on, and the ability to seed more when they need them.

I got this working fine by passing skip_validations: true to PostCreator.new, however now there’s a requirement that some of the created posts are also flagged.

I’m using PostActionCreator.create to flag some of these posts, but now I’m getting hit by the rate limiter here: https://github.com/discourse/discourse/blob/ad7a13921f2af8c792530c84386b64911c8e7ea2/lib/post_action_creator.rb#L69

I first attempted to disable the RateLimiter but that was causing my action to crash the server process eventually, possibly when I was trying to turn it back on, and then I realised it probably wasn’t a good idea anyway.

So my question is, is there a better way to bypass the rate limiter when running some arbitrary code i.e. something like:

RateLimiter.bypass do
# run some code not affected by the rate limiter
end

Or do I need to basically just need to copy most of what the PostActionCreator is doing but leave out the troublesome line?

Any help would be greatly appreciated! I’m still absorbing a lot of the Discourse code so I’m aware I’ve probably missed something that makes this a lot easier!

1 curtida

What I’d likely do is run a script in the Rails console. Have you checked out: Global rate limits and throttling in Discourse? It looks like you can change those rate limits.

2 curtidas

This isn’t really a path I want to go down as I want it to initiated by users rather than them relying on me to run a script in the console.

3 curtidas

Did you look at the link about changing the rate limits?

Você descobriu isso? Modificar o arquivo yaml não é ideal, pois requer uma reconstrução. Eu não sou familiar o suficiente com rails/discourse para descobrir como desativá-lo temporariamente no console.

Qual é o seu caso de uso? Que problema você está tentando resolver que os limites de taxa estão impedindo?

Tentando importar 60 mil usuários via API o mais rápido possível sem fazer um rebuild. Eu também tentei em uma instalação de teste aumentar o limite da API ADMIN via YAML, mas não pareceu funcionar, mas talvez eu tenha feito algo errado. (Estou executando as importações no container, então o throttling HTTP não deveria se aplicar).

Isso não é muito útil, mas o que eu faria seria criar os usuários no Rails em vez de via API. discourse/script/import_scripts/csv_importer.rb at main · discourse/discourse · GitHub poderia ser um começo.

Mas você pode entrar no contêiner e editar /var/www/discourse/config/discourse.conf e definir essas variáveis lá e depois fazer um sv restart unicorn (ou talvez sv reload unicorn). Provavelmente você vai querer fazer algo como apt-get update; apt-get install -y vim para ter um editor.

2 curtidas

Estranho. Quando visualizo o arquivo de configuração, o novo limite já está definido. Então a atualização do YAML funcionou:

max_admin_api_reqs_per_key_per_minute = '6000'

Mas parece não funcionar. Ainda há uma limitação de 60 por minuto. Quando limito as requisições para 60 por minuto, a maioria passa, mas devido a oscilações, algumas ainda acionam o limitador de taxa:

{'success': True, 'active': True, 'message': 'Sua conta está ativada e pronta para uso.', 'user_id': 3596}
{'success': False, 'message': 'Novos registros não são permitidos do seu endereço IP (limite máximo atingido). Entre em contato com um membro da equipe.', 'errors': {'ip_address': ['Novos registros não são permitidos do seu endereço IP (limite máximo atingido). Entre em contato com um membro da equipe.']}, 'values': {'name': None, 'username': 'asdfd', 'email': 'user@domain.com'}, 'is_developer': False}
{'success': True, 'active': True, 'message': 'Sua conta está ativada e pronta para uso.', 'user_id': 3597}

Será que é um problema com as aspas?

Você pode verificar SiteSettings.max_admin_api_reqs_per_key_per_minute e ver se é um inteiro.

1 curtida

em default_current_user_provider.rb (o único arquivo que encontrei que parecia referenciar esse valor, ele tem:

limit = GlobalSetting.max_admin_api_reqs_per_minute.to_i

então parece que ele o converte. Eu até tentei substituí-lo por um número no código.

1 curtida

Droga. Eu temia isso.

1 curtida

Eu acho que está relacionado a outro limite: acho que é o limite máximo de registros de um IP que está sendo atingido, mas não entendo por que, depois de atingir esse limite, ele não bloqueia permanentemente. Possivelmente um bug neste limite de spam?

Se todos esses usuários tiverem o mesmo IP, então aposto que você está certo. Acho que a solução é alterar essa configuração ou dar às pessoas endereços IP falsos como 127.0.0.x (ou talvez usar IPv6 para facilitar?)

1 curtida

Eu acho que ele está detectando de onde a solicitação está sendo feita (computador host), mas posso contornar isso adicionando um usuário TL2 no mesmo endereço IP (ou ajustar o limite de IP).

A API do usuário é muito lenta, no entanto.

É por isso que recomendo fazer isso em rails. Provavelmente fará cerca de 500/minuto.

1 curtida

Sim, vou tentar isso. Mas não está claro como devo executar o script, onde devo copiá-lo e como devo executá-lo (depois de colocar o CSV nos lugares certos)?

Você pode consultar outros tópicos de como fazer para os outros. Eles funcionam quase todos da mesma maneira.

1 curtida

Apenas como acompanhamento, dado o esforço para entender os scripts e Ruby, etc., e o desempenho provável, segui outro caminho e contornei todos os limites escrevendo diretamente no banco de dados usando SQL. Desta forma, consegui várias milhares de inserções por segundo.

Houve um tópico perguntando quais tabelas eram necessárias, ele está fechado agora, então respondo aqui que alterei as seguintes tabelas para inserir os usuários:

user_avatars
user_emails
user_profiles
user_search_data
user_stats
users
1 curtida