A questão gira em torno mais da maneira como você obtém uma conexão a partir de algum identificador único do tenant do que da origem dessa informação (no caso, a requisição HTTP) propriamente dita. Trabalho hoje com um sistema multi tenant e dado o acoplamento do código legado (objeto request sendo um god object), tive que escrever uma nova base de código para os jobs, usando clean arch e padrões de projeto, nenhum framework. A ideia é construir uma lib desacoplada na nova base e incorporá-la à base antiga de maneira progressiva, o que é possível por serem bases TypeScript, de modo a extinguir o god object aos poucos. Ainda que isso nunca aconteça, a nova base já atende os novos executáveis da aplicação. Então, já há o benefício. No meu caso, o alto acoplamento justifica a reescrita. Tens que avaliar se é o mesmo caso com você.
De que maneira abortaria essa situação de cron jobs fora do contexto http?
No job, a resposta da pergunta "qual tenant?" entra como um argumento (de linha de comando, talvez, ou variável de ambiente, enfim). A questão é que para que isso funcione, a responsabilidade do seu middleware deve estar limitada a apenas responder a pergunta com base na requisição, não de fornecer acesso à infraestrutura correspondente. Uma vez que essa responsabilidade de acessar a infraestrutura (bancos de dados, armazenamento, etc.) esteja isolada, fora do middleware, pode ser utilizada tanto pelo contexto HTTP, quanto pelos jobs. Apenas a resposta de "qual tenant?" virá de fontes diferentes em cada caso, mas o acesso ao banco virá do mesmo código. O componente pode ser classe ou função (ou qualquer coisa) que execute "me forneça acesso ao banco do tenant X".