Разделение задачи pg-promise между частями http-запроса

Я использую pg-обещание в приложении GraphQL, и из-за вложенного/итеративного характера распознавателей каждый HTTP-запрос делает много запросов к базе данных.

Итак, мне интересно, есть ли более эффективный способ поделиться соединением из пула соединений, когда распознаватели собирают данные?

Я понимаю, что задача pg-promise актуальна только для обратного вызова функции, и я не вижу другого способа связать запросы (как задокументировано здесь).

Пример

Запрос GraphQL:

{
  users {
    files {
      name
      date
    }
  }
}

Пример распознавателей при использовании Сервер Аполлона

Query: {
    users: (obj, args, context, info) => {
      return context.db.manyOrNone('select id from users')
    }
 }

и

Users: {
  files: (obj, args, context, info) => {
    const userId = obj.id;
    return context.db.manyOrNone('select * from files where user_id = $1', userId);
  }
}

Это создаст множество SQL-запросов, если, например, много пользователей.

ПРИМЕЧАНИЕ

Я знаю о таких методах, как dataloader, для решения таких проблем, как выбор N+1, но я не могу позволить себе изменить архитектуру этого приложения в данный момент, и просто более эффективное подключение к базе данных было бы огромным выигрышем в производительности.

Спасибо.

Стоит ли изучать PHP в 2026-2027 годах?
Стоит ли изучать PHP в 2026-2027 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
0
0
171
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

Каждая конечная точка HTTP и каждое соединение с базой данных из пула должны быть асинхронными.

Если вы попытаетесь повторно использовать одно и то же соединение с базой данных на нескольких конечных точках HTTP, они будут блокировать друг друга всякий раз, когда им потребуется доступ к базе данных, что нехорошо.

И если количество подключений в пуле меньше, чем количество конечных точек HTTP, которые обращаются к базе данных, вы получаете плохо масштабируемый HTTP-сервис. Вам нужно количество подключений, по крайней мере, чтобы соответствовать количеству конечных точек HTTP.

Итак, что вы ищете - совместное использование соединения с базой данных несколькими конечными точками HTTP - плохая идея для начала.

А если вы хотите сгруппировать несколько распознавателей данных в рамках одного HTTP-запроса, вы можете унифицировать логику обработки в рамках одной задачи (см. Задания).

Существует также ручное подключение с помощью метода соединять, но я бы не рекомендовал его для общего повторного использования подключения, так как он существует для конкретных случаев, в противном случае может быть подвержен ошибкам и сводит на нет идею автоматических подключений.

Спасибо @vitaly-t, мой вопрос больше относится к совместному использованию соединения для множества вызовов БД в пределах одним запросом, не обязательно между конечными точками (думал, что это запутывается с graphql). По сути, я спрашиваю, есть ли способ использовать метод Task, но это не ограничивается обратным вызовом, с которым он вызывается. Я не могу поместить эту часть кода в этот обратный вызов. Имеет ли это смысл?

Dan Fairaizl 14.02.2019 16:21

Я считаю, что проблема, скорее всего, в том, что вы неправильно подходите к задаче. Лучше всего выяснить, как это сделать, поскольку это, по сути, тот же контекст. В этом случае использование метода connect было бы обходом недостатка реализации.

vitaly-t 14.02.2019 16:25

Да, это то, что я понял. Круто, спасибо за проверку на вменяемость. Сначала я попробую использовать connect и посмотрю, какова производительность, пока ищу долгосрочное решение с использованием задач.

Dan Fairaizl 14.02.2019 16:42

Другие вопросы по теме