Store items and icons into the db
This commit is contained in:
parent
f2b8abf82b
commit
6b9502ea3e
12 changed files with 219 additions and 9 deletions
|
@ -1 +1,2 @@
|
|||
option('base_url', type: 'string', value: 'https://api.originsro.org')
|
||||
option('database_file', type: 'string', value: 'originsro.db3')
|
||||
|
|
|
@ -3,5 +3,6 @@
|
|||
namespace duck {
|
||||
|
||||
constexpr const char g_base_url[] = "@BASE_URL@";
|
||||
constexpr const char g_database[] = "@DATABASE@";
|
||||
|
||||
} //namespace duck
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
#include "evloop.hpp"
|
||||
#include "timer_items.hpp"
|
||||
#include "timer_icons.hpp"
|
||||
#include "eventia/eventia.hpp"
|
||||
#include "eventia/timer.hpp"
|
||||
#include "roar11/ThreadPool.hpp"
|
||||
#include "oro/api.hpp"
|
||||
#include <iostream>
|
||||
|
@ -27,14 +27,15 @@ void join(roar11::ThreadPool& pool) {
|
|||
|
||||
} //unnamed namespace
|
||||
|
||||
void test(oro::Api* api) {
|
||||
void test(oro::Api* api, oro::OriginsDB* db) {
|
||||
const std::size_t thread_count = 2U; //std::min(std::max(3U, std::thread::hardware_concurrency()) - 1, 4U);
|
||||
std::cout << "Running with " << thread_count << " worker threads\n";
|
||||
roar11::ThreadPool pool(thread_count);
|
||||
eve::Eventia worker;
|
||||
pool.submit(worker.event_functor());
|
||||
|
||||
auto fetcher = worker.make_timer<TimerItems>(3.0, &pool, api);
|
||||
auto timer_items = worker.make_timer<TimerItems>(3.0, &pool, api, db);
|
||||
auto timer_icons = worker.make_timer<TimerIcons>(20.0, &pool, api, db);
|
||||
|
||||
join(pool);
|
||||
}
|
||||
|
|
|
@ -2,10 +2,11 @@
|
|||
|
||||
namespace oro {
|
||||
class Api;
|
||||
class OriginsDB;
|
||||
} //namespace oro
|
||||
|
||||
namespace duck {
|
||||
|
||||
void test(oro::Api* api);
|
||||
void test(oro::Api* api, oro::OriginsDB* db);
|
||||
|
||||
} //namespace duck
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
#include "oro/api.hpp"
|
||||
#include "oro/originsdb.hpp"
|
||||
#include "orotool_config.hpp"
|
||||
#include "SQLiteCpp/SQLiteCpp.h"
|
||||
#include "evloop.hpp"
|
||||
#include <iostream>
|
||||
|
||||
|
@ -24,7 +24,8 @@ int main(int argc, char* argv[]) {
|
|||
std::cout << "answer: " << ping.second.message << '\n';
|
||||
std::cout << "version: " << ping.second.version << '\n';
|
||||
|
||||
duck::test(&oro_api);
|
||||
oro::OriginsDB db;
|
||||
duck::test(&oro_api, &db);
|
||||
|
||||
/*
|
||||
{
|
||||
|
|
|
@ -20,6 +20,7 @@ endif
|
|||
|
||||
conf = configuration_data()
|
||||
conf.set('BASE_URL', base_url)
|
||||
conf.set('DATABASE', get_option('database_file'))
|
||||
project_config_file = configure_file(
|
||||
input: 'config.hpp.in',
|
||||
output: meson.project_name() + '_config.hpp',
|
||||
|
@ -44,6 +45,8 @@ executable(meson.project_name(),
|
|||
'eventia/eventia.cpp',
|
||||
'eventia/timer.cpp',
|
||||
'timer_items.cpp',
|
||||
'timer_icons.cpp',
|
||||
'oro/originsdb.cpp',
|
||||
project_config_file,
|
||||
install: true,
|
||||
dependencies: lib_deps,
|
||||
|
|
91
src/oro/originsdb.cpp
Normal file
91
src/oro/originsdb.cpp
Normal file
|
@ -0,0 +1,91 @@
|
|||
#include "originsdb.hpp"
|
||||
#include "SQLiteCpp/Database.h"
|
||||
#include "SQLiteCpp/Statement.h"
|
||||
#include "SQLiteCpp/Transaction.h"
|
||||
#include "orotool_config.hpp"
|
||||
#include "SQLiteCpp/SQLiteCpp.h"
|
||||
#include "oro/items.hpp"
|
||||
#include "oro/icons.hpp"
|
||||
#include "oro/base64.hpp"
|
||||
#include <mutex>
|
||||
|
||||
namespace oro {
|
||||
|
||||
namespace {
|
||||
class Database : private std::unique_lock<std::mutex>, public SQLite::Database {
|
||||
public:
|
||||
explicit Database(std::mutex& mtx) :
|
||||
std::unique_lock<std::mutex>(mtx),
|
||||
SQLite::Database(duck::g_database, SQLite::OPEN_READWRITE | SQLite::OPEN_CREATE)
|
||||
{
|
||||
}
|
||||
};
|
||||
} //unnamed namespace
|
||||
|
||||
OriginsDB::OriginsDB() = default;
|
||||
|
||||
OriginsDB::~OriginsDB() noexcept = default;
|
||||
|
||||
void OriginsDB::overwrite (const Items& items) {
|
||||
Database db(m_db_mutex);
|
||||
|
||||
db.exec("DROP TABLE IF EXISTS items");
|
||||
SQLite::Transaction transaction(db);
|
||||
|
||||
//example:
|
||||
//{
|
||||
// "item_id":501,
|
||||
// "unique_name":"Red_Potion",
|
||||
// "name":"Red Potion",
|
||||
// "type":"IT_HEALING",
|
||||
// "npc_price":50
|
||||
//}
|
||||
db.exec("CREATE TABLE items (item_id INTEGER PRIMARY KEY, unique_name TEXT, name TEXT, type INTEGER, subtype INTEGER, npc_price INTEGER, slots INTEGER, icon TEXT)");
|
||||
|
||||
SQLite::Statement query(db, "INSERT INTO items(item_id, unique_name, name, type, subtype, npc_price, slots) VALUES(?, ?, ?, ?, ?, ?, ?)");
|
||||
for (const auto& item : items.items) {
|
||||
query.bind(1, item.item_id);
|
||||
query.bind(2, item.unique_name);
|
||||
query.bind(3, item.name);
|
||||
query.bind(4, static_cast<int>(item.type.value));
|
||||
if (item.subtype)
|
||||
query.bind(5, static_cast<int>(item.subtype->value));
|
||||
else
|
||||
query.bind(5, nullptr);
|
||||
query.bind(6, item.npc_price);
|
||||
if (item.slots)
|
||||
query.bind(7, *item.slots);
|
||||
else
|
||||
query.bind(7, nullptr);
|
||||
|
||||
query.exec();
|
||||
query.reset();
|
||||
}
|
||||
|
||||
transaction.commit();
|
||||
}
|
||||
|
||||
void OriginsDB::update (const Icons& icons) {
|
||||
//example:
|
||||
//{
|
||||
// "item_id":501,
|
||||
// "icon":"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABgAAAAYCAMAAADXqc3KAAAABGdBTUEAALGPC/xhBQAAACBjSFJNAAB6JgAAgIQAAPoAAACA6AAAdTAAAOpgAAA6mAAAF3CculE8AAAAP1BMVEX/AP/XqpHDkHqudmL////ox6X/9LxJSUm3t7eSkpLb29tubm7Kt6//8+u+QzDTjG7tZEfyhVmPIhi4o5v/8OVQ35yOAAAAAXRSTlMAQObYZgAAAAFiS0dEBI9o2VEAAAAHdElNRQfkAg4MBBc1u27AAAAAmElEQVQoz7WP2w6DIBAFsSyedavLRf//W7uQVmk0afvQeSIzOQSc+wfDcPOXnigE/1MYxxBw0szTYAMwv2kikunuPcBEc+8XknkCVNXOfHhADOYYVYG9mE92V2y08iksQBbRp+/CDM3CSRulKNb9E5o4p/QK6/Fe0WyhpVI6bxORZK7SD+pELn0t7ZqTd25raT35mrZL/TUPifEKODGf6AcAAAAldEVYdGRhdGU6Y3JlYXRlADIwMjAtMDItMTRUMTI6MDQ6MjMrMDA6MDCsyg5gAAAAJXRFWHRkYXRlOm1vZGlmeQAyMDIwLTAyLTE0VDEyOjA0OjIzKzAwOjAw3Ze23AAAAABJRU5ErkJggg=="
|
||||
//}
|
||||
|
||||
Database db(m_db_mutex);
|
||||
SQLite::Transaction transaction(db);
|
||||
SQLite::Statement query(db, "UPDATE items SET icon = ? WHERE item_id = ?");
|
||||
|
||||
for (const auto& ico : icons.icons) {
|
||||
query.bind(1, ico.icon);
|
||||
query.bind(2, ico.item_id);
|
||||
query.exec();
|
||||
query.reset();
|
||||
|
||||
base64_decode(std::string_view(ico.icon).substr(std::string_view("data:image/png;base64,").size()));
|
||||
}
|
||||
|
||||
transaction.commit();
|
||||
}
|
||||
|
||||
} //namespace oro
|
24
src/oro/originsdb.hpp
Normal file
24
src/oro/originsdb.hpp
Normal file
|
@ -0,0 +1,24 @@
|
|||
#pragma once
|
||||
|
||||
#include <mutex>
|
||||
|
||||
namespace oro {
|
||||
|
||||
struct Items;
|
||||
struct Icons;
|
||||
struct Shops;
|
||||
struct Creators;
|
||||
|
||||
class OriginsDB {
|
||||
public:
|
||||
OriginsDB();
|
||||
~OriginsDB() noexcept;
|
||||
|
||||
void overwrite (const Items& items);
|
||||
void update (const Icons& icons);
|
||||
|
||||
private:
|
||||
std::mutex m_db_mutex;
|
||||
};
|
||||
|
||||
} //namespace oro
|
42
src/timer_icons.cpp
Normal file
42
src/timer_icons.cpp
Normal file
|
@ -0,0 +1,42 @@
|
|||
#include "timer_icons.hpp"
|
||||
#include "oro/originsdb.hpp"
|
||||
#include "oro/api.hpp"
|
||||
#include "eventia/private/context.hpp"
|
||||
#include "roar11/ThreadPool.hpp"
|
||||
#include <cassert>
|
||||
#include <iostream>
|
||||
|
||||
namespace duck {
|
||||
TimerIcons::TimerIcons (
|
||||
const eve::Context& ctx,
|
||||
double timeout,
|
||||
roar11::ThreadPool* pool,
|
||||
oro::Api* oro_api,
|
||||
oro::OriginsDB* db
|
||||
) :
|
||||
eve::Timer(timeout, ctx),
|
||||
m_pool(pool),
|
||||
m_oro_api(oro_api),
|
||||
m_db(db)
|
||||
{
|
||||
assert(m_pool);
|
||||
assert(m_oro_api);
|
||||
}
|
||||
|
||||
void TimerIcons::on_timer() {
|
||||
m_pool->submit(&TimerIcons::fetch_data, this);
|
||||
}
|
||||
|
||||
void TimerIcons::fetch_data() {
|
||||
auto icons = m_oro_api->items_icons();
|
||||
|
||||
{
|
||||
const int next_timer = icons.first.retry_after / icons.first.rate_limit;
|
||||
std::cout << "Next timer in " << next_timer << " secs\n";
|
||||
set_timer(static_cast<double>(next_timer));
|
||||
}
|
||||
|
||||
m_db->update(icons.second);
|
||||
}
|
||||
|
||||
} //namespace duck
|
37
src/timer_icons.hpp
Normal file
37
src/timer_icons.hpp
Normal file
|
@ -0,0 +1,37 @@
|
|||
#pragma once
|
||||
|
||||
#include "eventia/private/context.hpp"
|
||||
#include "eventia/timer.hpp"
|
||||
|
||||
namespace roar11 {
|
||||
class ThreadPool;
|
||||
} //namespace roar11
|
||||
|
||||
namespace oro {
|
||||
class Api;
|
||||
class OriginsDB;
|
||||
} //namespace oro
|
||||
|
||||
namespace duck {
|
||||
|
||||
class TimerIcons : eve::Timer {
|
||||
public:
|
||||
TimerIcons (
|
||||
const eve::Context& ctx,
|
||||
double timeout,
|
||||
roar11::ThreadPool* pool,
|
||||
oro::Api* oro_api,
|
||||
oro::OriginsDB* db
|
||||
);
|
||||
|
||||
virtual void on_timer() override;
|
||||
|
||||
private:
|
||||
void fetch_data();
|
||||
|
||||
roar11::ThreadPool* m_pool;
|
||||
oro::Api* m_oro_api;
|
||||
oro::OriginsDB* m_db;
|
||||
};
|
||||
|
||||
} //namespace duck
|
|
@ -1,4 +1,5 @@
|
|||
#include "timer_items.hpp"
|
||||
#include "oro/originsdb.hpp"
|
||||
#include "oro/api.hpp"
|
||||
#include "eventia/private/context.hpp"
|
||||
#include "roar11/ThreadPool.hpp"
|
||||
|
@ -10,11 +11,13 @@ namespace duck {
|
|||
const eve::Context& ctx,
|
||||
double timeout,
|
||||
roar11::ThreadPool* pool,
|
||||
oro::Api* oro_api
|
||||
oro::Api* oro_api,
|
||||
oro::OriginsDB* db
|
||||
) :
|
||||
eve::Timer(timeout, ctx),
|
||||
m_pool(pool),
|
||||
m_oro_api(oro_api)
|
||||
m_oro_api(oro_api),
|
||||
m_db(db)
|
||||
{
|
||||
assert(m_pool);
|
||||
assert(m_oro_api);
|
||||
|
@ -32,6 +35,8 @@ namespace duck {
|
|||
std::cout << "Next timer in " << next_timer << " secs\n";
|
||||
set_timer(static_cast<double>(next_timer));
|
||||
}
|
||||
|
||||
m_db->overwrite(items.second);
|
||||
}
|
||||
|
||||
} //namespace duck
|
||||
|
|
|
@ -9,6 +9,7 @@ namespace roar11 {
|
|||
|
||||
namespace oro {
|
||||
class Api;
|
||||
class OriginsDB;
|
||||
} //namespace oro
|
||||
|
||||
namespace duck {
|
||||
|
@ -19,7 +20,8 @@ public:
|
|||
const eve::Context& ctx,
|
||||
double timeout,
|
||||
roar11::ThreadPool* pool,
|
||||
oro::Api* oro_api
|
||||
oro::Api* oro_api,
|
||||
oro::OriginsDB* db
|
||||
);
|
||||
|
||||
virtual void on_timer() override;
|
||||
|
@ -29,6 +31,7 @@ private:
|
|||
|
||||
roar11::ThreadPool* m_pool;
|
||||
oro::Api* m_oro_api;
|
||||
oro::OriginsDB* m_db;
|
||||
};
|
||||
|
||||
} //namespace duck
|
||||
|
|
Loading…
Reference in a new issue