Голос стал песочницей для множества начинающих разработчиков и просто любителей.
Блокчейн с открытым кодом + дружное сообщество - все это делает голос отличной площадкой для приобретения и прокачки разных навыков взаимодействия с трендовыми технологиями.
В этом посте я приведу пример, который поможет снять некоторые "мнимые" ограничения в API golos/steem
Надеюсь это поможет всем, кому нравится созидать что-то на блокчейне голоса.
Речь пойдет о steem-js она же golos-js и других форках.
Как минимум мы сможем выйти за рамки лимита в 100 постов в API для вызова getDiscussions
Мне это понадобилось в процессе разработки телеграм-бота и фан-карты для mapala.
На карту выводятся все существующие посты с MAPALA в которых есть географические координаты:
Посмотреть вживую можно тут https://chain.cf/mapala - это тестовый пример и весь скрипт выполняется в браузере,посты грузятся достаточно долго. Но при использовании рендера не сервере - это дело нескольких секунд. Я не зря назвал это фан-картой - так как акцентирую, что я не состою в команде разработчиков. То что делаю, это не коммерческие продукты, это скорее просто хобби.
В телеграм боте мне так же понадобилась возможность выводить все посты без ограничений в 100, при этом давая возможность прочесть контент и посмотреть фото прямо в боте.
Над этими и еще над с 10-к проектов идет работа, многое не получается успеть просто физически, а большая часть времени уходит на изучение API и ответы пользователям в тг, надеюсь и буду рад, если мои наработки и потраченное время сэкономят ресурсы таким же энтузиастам :)
Приступим!
Нам вместе с библиотеками golos-js/steem-js поставляется неполная инструкция к вызовам вида:
Get Discussions By Created
golos.api.getDiscussionsByCreated(query, function(err, result) {
console.log(err, result);
});
Здесь и далее будем рассматривать этот API вызов в качестве подопытного.
Вызов getDiscussionsByCreated
- возвращает нам список постов сортированных по дате создания, а query это конкретный запрос диктующий, что именно возвращать. Проблема в том, что на официальной странице либы нет описания того, что нужно вставлять в query
и начинающий разработчик-любитель полезет в документацию и увидит что в query
должен быть тег и лимит {"tag":"mapala","limit":100}
Скрин со страницы документации https://developers.golos.io/doc/client#discussions
Кроме официальной документации это так же указано в API explorer
Более того, если мы хотим вывести список постов в количестве большем чем 100, то мы получим ошибку.
Например если мой query будет {"select_tags":["mapala"],"limit":101}
, то я не получу 101 пост, а получу ошибку
Представьте, что нам нужно выводить подгружаемую ленту постов, эдакий infinity scroll на странице.
Для этого делаем запрос с пустым тегом (это выведет все посты,независимо от тегов):
get_discussions_by_created({"select_tags":["mapala"],"limit":100})
В качестве ответа мы получили максимум 100 постов и плюс ко всему, в этих 100 постах у нас 80 от bm, которые мы скроем, в остатке останется каких-то 20 постов с голоса без возможности подгрузить более ранние...
Долгое время я верил этому искусственному лимиту и он меня порядком раздражал.
Но как оказывается, проблема не в лимитах, а в неполной и недостаточной документации для вызовов.
Поражает, что есть полно не задокументированных возможностей!
картинку украл в комментах у Дена Ларимера :)
Вглянем еще раз на скрин ошибки
Сообщение о лимите api нам показывает файл database_api.hpp
. Так как мы работаем с открытом кодом (и это замечательно!) мы можем найти содержимое этого файла в исходниках голоса.
hpp
- это расширение для языка C++, идем в репозиторий голоса на github и находим там исходники на C++
Вышеупомянутый файл можно найти по пути /golos/libraries/app/database_api.cpp
Ищем запрос _created
и находим его на строке 1467
https://github.com/GolosChain/golos/blob/master/libraries/app/database_api.cpp#L1467
Я не стану приводить весь код, он достаточно объемный, нам нужно изучить строки с 1467 по 1520, что бы узнать, что лимит в js плагинах был искусственный.
Какое на самом деле доступно и может быть query для getDiscussionsByCreated
Кроме всюду упомянутых tag и лимит нам так же доступно вот что:
select_authors
Мы можем указать список авторов
select_tags
Мы можем указать сет тегов, а не только один!
filter_tags
Мы можем убрать из выдачи ненужные теги, например bm-open!
truncate_body
Мы можем сократить контент до короткого описания - например для вывода карточек постов с кратким описанием.
parent_author
Автор-родитель - будут выводится все ответы автору!
parent_permlink
Родительская ссылка - все ответы к определенному посту
start_author и start_permlink
А вот эти 2 параметра помогут сделать offset (отступ) для постов! Это именно то, что мне нужно было - возможность сделать отступ и загружать последовательно все посты на голосе забыв про лимит в 100 постов! Как именно это сделать я напишу ниже.
Бесконечный скролл всех постов голоса
Немного усложним задачу и выведем все посты с mapala в которых есть координаты местности (в клиенте мапала при размещении поста можно указать широту и долготу местности)
Создаем promise и загружаем в posts первые 100 постов с тегом mapala
const POSTCOUNT = 0
const item = []
const LATEST_POSTS = new Promise((resolve, reject) => {
golos.api.getDiscussionsByCreated({"select_tags":["mapala"],"limit":100},(err, posts) => {
if (err) {
reject(err)
}
else {
resolve(posts)
}
})
})
Передаем posts в следующую функцию, где задаем пустой массив nextset
const POSTS_FILTER = (posts) => {
let nextset = {
start_permlink:'',
start_author:''
}
Укажем количество постов которые получили в ответе
let len = posts.length
Создадим цикл для каждого полученного поста
for (let post of posts) {
В переменную meta будем сохранять json_metadata для каждого раунда цикла
let meta = JSON.parse(post.json_metadata)
Теперь создадим условие, с помощью которого будем обрабатывать только те посты, в которых указаны координаты местности
if(typeof meta.coordinates !=="undefined" && meta.coordinates.length > 10 ){
Внутри условия мы создадим массив в который будем толкать различные данные постов
item.push({
author:post.author,
parent:post.parent_permlink,
title:post.title,
body:post.body.replace(/<\/?[^>]+(>|$)/g, ""),
image:(typeof meta.image === 'undefined')?'/logo.png':meta.image[0],
payout:post.total_pending_payout_value,
url:'https://golos.io'+post.url,
meta:meta,
time:post.created,
geo:meta.coordinates
});
И после, когда мы будем на этапе обработки последнего поста в цикле мы заполним массив nextset автором и ссылкой на последний пост
if(i == len - 1){
nextset.start_permlink = post.permlink;
nextset.start_author = post.author;
NEXT_POSTS(nextset)
}
Это именно та уловка с помощью которой мы получаем возможность получить следующие 100 постов!
Сначала мы получили 100 первых постов, отфильтровали их по вкусу и данным, запомнили автора и ссылку на последний пост и теперь можем вызвать серию из 100 следующих постов задав полученные автора и ссылку как старт.
Вот так:
const NEXT_POSTS = (nextset) => {
golos.api.getDiscussionsByCreated({
"start_permlink":nextset.start_permlink,
"start_author":nextset.start_author,
"select_tags":["mapala"],"limit":100}
Полученные следующие 100 постов обрабатываем так же как и в предыдущем примере, затем снова сохраняем последнего автора и ссылку и с этим данными снова рекурсивно вызываем функцию NEXT_POSTS
nextset.start_permlink = post.permlink;
nextset.start_author = post.author;
if(len > 1){
NEXT_POSTS(nextset)
}
Условие if(len > 1)
помогает нам перестать вызывать функцию если мы уже получили абсолютно все посты.
Код полностью выглядит так
Вместо PS и вместо отчета делегата.
Народ требует отчетов, но мне просто иногда жаль засирать незыблемость блокчейна очередным отчетом, потому буду краток :)
Хочу напомнить, что вчера вместе с @ropox и @everythink мы запустили @dobrobot - бота который делает добро за ваш счет :) Вы пополняете добробота, а он раздает ваши монеты тем, за кого вы голосуете. Легкий способ почувствовать себя одаривающим китом :)
💱Подробнее
Так же напомню, что моя собственная инициатива @robot так же активно работает и делает добро, но уже за мой счет :) Не забывайте рекомендовать авторов, которым @robot будет оказывать финансовую поддержку.
🎁Подробнее
Кроме этого я принял участие в 10-ке разных ICO в т.ч. #mapala - ребята делают большую работу и скоро она будет показана публике, а сейчас есть возможность приобрести их токены по минимально возможной цене. Можно с уверенностью сказать, что у них все только начинается.
Про golos.io я так же не забыл, это можно видеть из финансовой статистики @arcange
Я в 10-ке пользователей больше всех инвестировавших в силу голоса. (Про голос я узнал только в январе, потому в ICO не участвовал)
К слову - из голоса я еще ни разу не выводил какие-либо средства :)
Из печального...
1. Это, как ни странно то, что я в вышеупомянутой 10-ке... Мне казалось что передо мной будет гораздо больше пользователей. Хотелось бы быть со своими копейками в хвосте.
2. Вторая печаль - это внезапный отказ достаточно дорогого сервера на котором была нода и десяток телеграм ботов которыми активно пользуется народ.
После чего я сразу поднял резервную ноду в другом датацентре - работа была восстановлена в кратчайшие сроки.
На связи
Я почти всегда доступен для обратной связи, признаться на это уходит очень много времени, так как стараюсь отвечать всем.
https://t.me/chain_cf - чат посвященный @robot и тг ботам для голоса
https://t.me/vikxx - личные сообщения
https://chat.golos.io/direct/vik - личные сообщения
https://discord.gg/k6TMZx6 - чат буржуйский.
забавно, я для Glasnost нашел такое же решение и тоже после долгого изучения исходников.
С документацией в Steem и по наследству в Голосе все совсем плохо.
@ontofractal, @t3ran13, какие изменения или улучшения документации вы можете предложить и хотите увидеть?
Команда Голоса.
Внимательно.
самое главное чб приходилось как можно меньше гуглить
но это ИМХНО, было бы немплохо всех местных "умельцев" поспрошать, чб впечатлениями поделились)
Спасибо. Мы постараемся как-то учесть все пожелания.
документация та, что есть, меня уже устраивает, но она не юзер френдли (нужно убивать море времени чб разобраться)
потом в нашей документации есть ошибки:
https://developers.golos.io/doc/client#discussions
это сейчас будет работать только для стима, у нас обновилось и тело изменилось, пофиксить нужно.
было бы не плохо чб кто-то сдедил и оперативно обновлял инфу, и была какая-то лента новостей с изменениями. я понимаю что в голосе постят, но во первых не все поститься с аккка голоса, очень много важного с личных, это плохо, так и еще это нужно все постоянно читать, не всегда есть время( потому лента с новостями для девелоперов решила бы вопрос. быть может отдельный акк golos-developer для тематических нововстей)
А по юзер-френдли какие предложения? Можно со структурой, примерами и картинками.
самое печатлдьно что теперь апихи отличаются, и это вносить свои неудобства(
@vik респект и уважуха тебе! Как, за то, что ты делаешь для Голоса, так и за то, что ты делаешь для Mapala. Очень рад, что есть такие люди, как ты!
поправь, если хотите конкретный тег а не все подряд
{"select_tags":["your_tag"], "limit":100}
{"tag":"your_tag", "limit":100}
если голосу отдать {"tag":"your_tag", "limit":100}, то получим все подряд посты, без фильтрации по тегам)
используй
https://developers.golos.io/doc/d4/dbd/classsteemit_1_1app_1_1database__api.html
@vik можно ссылку на полный код добавить?... И я так и не понял, как правильно вызов сделать, указав автора... Не работают никакие варианты (через curl).
чет я совсем пропала = (
нет времени и желания писать
ты как? как дела?
@vik, Поздравляю!
Ваш пост был упомянут в моем хит-параде в следующих категориях:
@vik Поздравляю! Вы добились некоторого прогресса на Голосе и были награждены следующими новыми бейджами:
Ваш пост получил высшую оплату за один день
Вы можете нажать на любой бейдж, чтобы увидеть свою страницу на Доске Почета.
Чтобы увидеть больше информации о Доске Почета, нажмите здесь
Если вы больше не хотите получать уведомления, ответьте на этот комментарий словом
стоп
Если вы хотите поддержать проект Доска Почета, вы можете проголосовать за это уведомление.
Мы рады создавать и поддерживать нужную атмосферу. Не без недостатков, конечно, но рады тёплым словам.
Команда Голоса.
было бы интересно узнавать от вас, как от человека разбирающейся во всей этой программной хренотени, о том что привлекает вас на рынке новых и перспективных разработок... короче если не трудно, кидайте небольшие посты о том куда и по каким причинам собираетесь инвестировать, это мне кажется интересно многим будет))