Нет, вы комментарии почитайте, они полезнее статьи. Там плохо написанный тест, производительность Явы показана в худшем свете (я не знаю, сделала бы она «ноду» в лучшем виде, но хотя бы отрыв был бы не такой большой), как если бы туда добавили Thread.Sleep, а потом развели бы руками.
Я предполагаю, что автор (оригинальной статьи) просто пиарится дешёвыми статьями, с примерами написанными на скорую руку. Погулил тут-там, и что-то состряпал.
Действительно выполняет запросы параллельно. Есть кое-какие запросы, которые сервер реджектит с 404. Плюс много ссылок ведут на разные домены типа «твитора», «фейсбука». Но если вы сомневаетесь с параллелизацией, то она есть.
Мне не понравились сами запросы, они, как бы вам сказать, немного подольше выполняются. Хотя и там, и там нормальный HTTP. А Ява даже обещает HTTP/2, присутствия которого я не особо заметил :)
Очень подозрительно много времени уходит на создание подключения (хоть в миллисекундах, но всё равно).
Потом я почитал, что есть разные библиотеки/API, где в сетевом подключении байты не копируются из нативных функций в приложение с помощью простого буфера в 8к (мы же выполняем тупую работу, послал запрос, получил ответ как строку), а действуют как-то иначе… Но как я сказал, я не стал эту тему слишком глубоко копать, может быть я бы переписал Ява код с некоторым пулом подключений и потоков.
И последнее, Ява да, создаёт много потоков, но в профайлинге я не видел того, что мы много времени на это тратим. Почти все потоки попросту простаивают, а трудятся 4-8 (у меня столько ядер) нативных тредов.
Я попытался ноду попрофилировать, но там JS кода не видно. Во всяком случае я его не нашёл :) всё упёрлось в нативный код с парсингом регулярки и кучи мелких вызовов имеющих отношение к Fetch.
Извините, если вышло сумбурно. Я много времени потратил, и не осилил fine tuning :)
Извините, я вас плюсанул, но попозже решил поподробнее поизучать код автора с помощью профайлинга кода на Яве и сетевых запросов как таковых. Попробую примазаться к вашей славе (хотя уже поздно).
Сравнение, к сожалению, двух реализаций очень плохое. Просто потому что, если посмотреть на запросы, которые делает, node-fetch и Ява, то мы увидим следующую разницу:
Java
Я приложил два скриншота, потому что соединения создаются разными способами, а значит заголовки разные.
Node
В ноде всё делается одной функцией, поэтому здесь никакой разницы нет.
Уже здесь видно, что сравнение нечестное. В случае с Явой мы скачиваем трафик неупакованный, а значит дольше. Вот разница между Явой и Нодой в этом случае (число запросов иногда разное, я не стал разбираться почему).
Разница в сетке
Вывод такой, что мы с помощью Явы скачиваем в 4 раза больше данных (40 мб).
Уже видите, что сравнение не честное.
К сожалению наскоком у меня не получилось сделать 100% правильный тест, просто из-за моей лени, поэтому я тупо добавил нужный мне заголовок и сравнил сетку ещё раз:
public CompletableFuture<List<UrlTxt>> requestManyUrls(List<String> urls) throws InterruptedException, ExecutionException {
...
.map(HttpRequest::newBuilder)
.map(r -> r.header("accept-encoding", "gzip,deflate,br")) // <-- сюда
.map(HttpRequest.Builder::build)
И оказалось, что запросы практически выровнялись. Приведу лишь для Явы. Я не уверен, что мы посчитаем ссылки правильно таким образом, но я лишь хотел сравнить сетевую составляющую:
Java (gzip)
Здесь получилось чуть больше, чем на «ноде», потому что я первый запрос не «упаковывал», так как при распаковке пришлось бы работать с бинарными данными. Говорю, мой тест лишь поверхностный.
Как вы видите, мы скачали не 40 мб, но 11 мб, что гораздо лучше. Но, здесь есть одно «но». Можете открыть две картинки и увидите, что Ява тратить чуть больше времени на установку соединения.
Эту часть я особо не смог проанализировать. Запутался и забил. У меня сложилось такое впечатление, что мы тратим время на SSL handshake. Такое ощущение, что на каждое соединение мы заново устанавливаем подключение.
Вот, что делает основной поток:
Main Thread
Я так понимаю, что мы завязаны на SSL и на то, что первый запрос у нас «несжатый», поэтому пока он не выполнится, ничего не произойдёт.
Плюс, как видно, мы построчно копируем ответ из сервера через буфер в «стринг билдер» и тратим там тоже какое-то время.
Я попробовал этот код немного изменить (погуглил про NIO), немного стало получше, но опять не идеально.
public class HttpUtils {
public static String get(String url) throws Exception {
HttpRequest request = HttpRequest.newBuilder()
.uri(new URI(url))
.build();
HttpResponse<String> response = HttpClient.newBuilder()
.followRedirects(HttpClient.Redirect.ALWAYS)
.build()
.send(request, HttpResponse.BodyHandlers.ofString());
return response.body();
}
Ладно, не буду никого утомлять, просто вспомню чью-то фразу, что написать плохой бенчмарк легко, а хороший — сложно. Вот и все дела.
Извините, если пофлудил за ваш счёт.
Мне кажется, что ваш метод немного дороговат для решаемой задачи. Во-первых, мне не понятно как часто каждый клиент будет опрашивать количество строк (каждую секунду, две и т.д.). Понятно, что посчитать записи тоже надо уметь. Давно была статья на Хабре, где читались системные вьюхи для этого. Возможно, вашу задачу можно было бы решить на триггерах (UPDATE/INSERT/DELETE), но лучше бы уведомить сервер приложений, а не каждого клиента в отдельности. А если есть сервер приложений, то проще сделать как слветуют на SO — некоторая шина данных, сообщения, подписка на изменение и т.д.
Согласен с вами. Видео приятнее иметь как дополнение. А грамотно оформленный туториал в разы полезнее.
Я ценю туториалы, которые помогают сделать первый hello world. Без всяких сбоев, гуглений, или какого-нибудь 15-минутного бормотания в Ютубе.
Бывает, что и туториалы пишут через одно место, но это либо по неопытности, либо просто наплевательское отношение к своему делу. Для меня хороший туториал — это лицо продукта. Жизнь коротка, чтобы ковыряться в чужих исходниках. Ну и хорошая документация облегчает суппорту жизнь.
Я не помню конкретную серию из Футурамы, но мне запомнился момент, когда они хотели назвать невиданное ранее существо. И робот ответил им, что все слова в мире уже кому-то принадлежат и осталось всего два, среди которых можно ещё выбрать.
Вот я думаю, что мы к такому идём, и это печально мне :(
Я, конечно, сочувствую всем (на всякий случай), но какая-то новость слабенькая. Кто-то заявил, что Эксмо теряет около 55е9 рублей. Да у них согласно другой новости (https://retailer.ru/vyruchka-jeksmo-ast-v-2020-godu-sostavila-60-mlrd-rublej/ ) вся выручка за 2020ый год составила 60е9 рублей!!! Выручка, а не прибыль.
Как в анекдоте, «… и вы говорите». Либо в новости надо хотя бы порядок суммы уменьшить, или наоборот увеличить, чтобы ещё больше сочувствия вызывать.
Тоже выглядит убого? А то реклама на Ютубе рассказывает обратное.
Я предполагаю, что автор (оригинальной статьи) просто пиарится дешёвыми статьями, с примерами написанными на скорую руку. Погулил тут-там, и что-то состряпал.
Мне не понравились сами запросы, они, как бы вам сказать, немного подольше выполняются. Хотя и там, и там нормальный HTTP. А Ява даже обещает HTTP/2, присутствия которого я не особо заметил :)
Очень подозрительно много времени уходит на создание подключения (хоть в миллисекундах, но всё равно).
Потом я почитал, что есть разные библиотеки/API, где в сетевом подключении байты не копируются из нативных функций в приложение с помощью простого буфера в 8к (мы же выполняем тупую работу, послал запрос, получил ответ как строку), а действуют как-то иначе… Но как я сказал, я не стал эту тему слишком глубоко копать, может быть я бы переписал Ява код с некоторым пулом подключений и потоков.
И последнее, Ява да, создаёт много потоков, но в профайлинге я не видел того, что мы много времени на это тратим. Почти все потоки попросту простаивают, а трудятся 4-8 (у меня столько ядер) нативных тредов.
Я попытался ноду попрофилировать, но там JS кода не видно. Во всяком случае я его не нашёл :) всё упёрлось в нативный код с парсингом регулярки и кучи мелких вызовов имеющих отношение к Fetch.
Извините, если вышло сумбурно. Я много времени потратил, и не осилил fine tuning :)
Сравнение, к сожалению, двух реализаций очень плохое. Просто потому что, если посмотреть на запросы, которые делает, node-fetch и Ява, то мы увидим следующую разницу:
Я приложил два скриншота, потому что соединения создаются разными способами, а значит заголовки разные.
В ноде всё делается одной функцией, поэтому здесь никакой разницы нет.
Уже здесь видно, что сравнение нечестное. В случае с Явой мы скачиваем трафик неупакованный, а значит дольше. Вот разница между Явой и Нодой в этом случае (число запросов иногда разное, я не стал разбираться почему).
Вывод такой, что мы с помощью Явы скачиваем в 4 раза больше данных (40 мб).
Уже видите, что сравнение не честное.
К сожалению наскоком у меня не получилось сделать 100% правильный тест, просто из-за моей лени, поэтому я тупо добавил нужный мне заголовок и сравнил сетку ещё раз:
И оказалось, что запросы практически выровнялись. Приведу лишь для Явы. Я не уверен, что мы посчитаем ссылки правильно таким образом, но я лишь хотел сравнить сетевую составляющую:
Здесь получилось чуть больше, чем на «ноде», потому что я первый запрос не «упаковывал», так как при распаковке пришлось бы работать с бинарными данными. Говорю, мой тест лишь поверхностный.
Как вы видите, мы скачали не 40 мб, но 11 мб, что гораздо лучше. Но, здесь есть одно «но». Можете открыть две картинки и увидите, что Ява тратить чуть больше времени на установку соединения.
Эту часть я особо не смог проанализировать. Запутался и забил. У меня сложилось такое впечатление, что мы тратим время на SSL handshake. Такое ощущение, что на каждое соединение мы заново устанавливаем подключение.
Вот, что делает основной поток:
Я так понимаю, что мы завязаны на SSL и на то, что первый запрос у нас «несжатый», поэтому пока он не выполнится, ничего не произойдёт.
Плюс, как видно, мы построчно копируем ответ из сервера через буфер в «стринг билдер» и тратим там тоже какое-то время.
Я попробовал этот код немного изменить (погуглил про NIO), немного стало получше, но опять не идеально.
Ладно, не буду никого утомлять, просто вспомню чью-то фразу, что написать плохой бенчмарк легко, а хороший — сложно. Вот и все дела.
Извините, если пофлудил за ваш счёт.
Мне кажется, что ваш метод немного дороговат для решаемой задачи. Во-первых, мне не понятно как часто каждый клиент будет опрашивать количество строк (каждую секунду, две и т.д.). Понятно, что посчитать записи тоже надо уметь. Давно была статья на Хабре, где читались системные вьюхи для этого. Возможно, вашу задачу можно было бы решить на триггерах (UPDATE/INSERT/DELETE), но лучше бы уведомить сервер приложений, а не каждого клиента в отдельности. А если есть сервер приложений, то проще сделать как слветуют на SO — некоторая шина данных, сообщения, подписка на изменение и т.д.
Но это моё мнение…
Согласен с вами. Видео приятнее иметь как дополнение. А грамотно оформленный туториал в разы полезнее.
Я ценю туториалы, которые помогают сделать первый hello world. Без всяких сбоев, гуглений, или какого-нибудь 15-минутного бормотания в Ютубе.
Бывает, что и туториалы пишут через одно место, но это либо по неопытности, либо просто наплевательское отношение к своему делу. Для меня хороший туториал — это лицо продукта. Жизнь коротка, чтобы ковыряться в чужих исходниках. Ну и хорошая документация облегчает суппорту жизнь.
Я понял. Я про то, что обычно очки продают, так как их воруют. Но я не вижу смысла в этом.
А зачем на IMAX очки продавать? Они же нигде не подходят, вроде бы.
До этого они какое-то время работали с Genius. Тоже было неплохо.
Я не помню конкретную серию из Футурамы, но мне запомнился момент, когда они хотели назвать невиданное ранее существо. И робот ответил им, что все слова в мире уже кому-то принадлежат и осталось всего два, среди которых можно ещё выбрать.
Вот я думаю, что мы к такому идём, и это печально мне :(
Жаль. Бедный Нетфликс. Оставит только пристойные фильмы в России.
Не так давно на Нетфликс ярлык повесили, теперь готовятся писать протокол и на них.
В ютубе можно легко shadow ban от владельца канала схватить.
Блин, ну почитайте, пожалуйста, git scm. Там книгу даже на русском выпустили.
Наступят новые выборы и, я думаю, к тому времени критическая масса уже наберется.
Я, конечно, сочувствую всем (на всякий случай), но какая-то новость слабенькая. Кто-то заявил, что Эксмо теряет около 55е9 рублей. Да у них согласно другой новости (https://retailer.ru/vyruchka-jeksmo-ast-v-2020-godu-sostavila-60-mlrd-rublej/ ) вся выручка за 2020ый год составила 60е9 рублей!!! Выручка, а не прибыль.
Как в анекдоте, «… и вы говорите». Либо в новости надо хотя бы порядок суммы уменьшить, или наоборот увеличить, чтобы ещё больше сочувствия вызывать.
Ох, вот так сенсация.
Спасибо вам, что вы ходили раньше как наблюдатель. И мне жаль, что сейчас это уже опасно делать :(
Не считайте чужих денег, может быть у них жизнь несчастная… может… (и заплакал)