Skip to content
This repository has been archived by the owner on Jul 20, 2021. It is now read-only.

Commit

Permalink
hub: complete GetBalance implementation with test
Browse files Browse the repository at this point in the history
  • Loading branch information
th0br0 committed Apr 18, 2018
1 parent d03f803 commit c409a4e
Show file tree
Hide file tree
Showing 4 changed files with 152 additions and 45 deletions.
49 changes: 40 additions & 9 deletions hub/commands/get_balance.cc
Original file line number Diff line number Diff line change
@@ -1,33 +1,64 @@
#include "get_balance.h"

#include <cstdint>

#include <sqlpp11/connection.h>
#include <sqlpp11/select.h>
#include <sqlpp11/functions.h>

#include "proto/hub.pb.h"
#include "schema/schema.h"

#include "hub/db/db.h"
#include "hub/stats/session.h"

#include "helper.h"

using namespace sqlpp;

namespace {
SQLPP_ALIAS_PROVIDER(total);
}

namespace iota {
namespace cmd {

grpc::Status GetBalance::doProcess(const iota::rpc::GetBalanceRequest* request,
iota::rpc::GetBalanceReply* response) noexcept {
grpc::Status GetBalance::doProcess(
const iota::rpc::GetBalanceRequest* request,
iota::rpc::GetBalanceReply* response) noexcept {
db::sql::UserAccount acc;
db::sql::UserAddressBalance bal;
db::sql::UserAccountBalance bal;

uint64_t userId;

auto& connection = db::DBManager::get().connection();

// Get userId for identifier
{
const auto result = connection(
select(acc.id).from(acc).where(acc.identifier == request->userid()));

if (result.empty()) {
return grpc::Status(
grpc::StatusCode::FAILED_PRECONDITION, "",
errorToString(iota::rpc::ErrorCode::USER_DOES_NOT_EXIST));
}

userId = result.front().id;
}

auto& conn = db::DBManager::get().connection();
// Summarise all amounts for user_account_balance changes
{
const auto result = connection(select(sum(bal.amount).as(total))
.from(bal)
.where(bal.userAccount == userId));

auto userId = conn(select(acc.id).from(acc).where(acc.identifier == request->userid())).first();

LOG(ERROR) << userId;

if (result.empty()) {
return grpc::Status(grpc::StatusCode::FAILED_PRECONDITION, "",
errorToString(iota::rpc::ErrorCode::UNKNOWN));
}

response->set_available(result.front().total);
}

return grpc::Status::OK;
}
Expand Down
48 changes: 48 additions & 0 deletions hub/commands/tests/runner.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
#ifndef __HUB_COMMANDS_TESTS_RUNNER_H_
#define __HUB_COMMANDS_TESTS_RUNNER_H_

#include <gtest/gtest.h>

#include "hub/commands/create_user.h"
#include "hub/db/db.h"
#include "hub/stats/session.h"
#include "proto/hub.pb.h"

namespace iota {
class CommandTest : public ::testing::Test {
public:
virtual void SetUp() {
auto db = iota::db::DBManager::get();
db.resetConnection();
db.loadSchema(true);

_session = std::make_shared<ClientSession>();
}

virtual void TearDown() { _session = nullptr; }

std::shared_ptr<ClientSession> session() { return _session; }

grpc::Status createUser(std::shared_ptr<ClientSession> session,
std::string username) {
rpc::CreateUserRequest req;
rpc::CreateUserReply res;

req.set_userid(std::move(username));
cmd::CreateUser command(std::move(session));
return command.doProcess(&req, &res);
}

rpc::Error errorFromStatus(grpc::Status& status) {
rpc::Error err;
err.ParseFromString(status.error_details());

return err;
}

private:
std::shared_ptr<ClientSession> _session;
};

} // namespace iota
#endif /* __HUB_COMMANDS_TESTS_RUNNER_H_ */
47 changes: 11 additions & 36 deletions hub/commands/tests/test_create_user.cc
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
#include <gtest/gtest.h>

#include <sqlpp11/select.h>
#include <sqlpp11/functions.h>

Expand All @@ -7,36 +8,23 @@

#include "hub/commands/create_user.h"
#include "hub/db/db.h"
#include "hub/stats/session.h"

#include "runner.h"

using namespace iota;
using namespace sqlpp;

namespace {
class CommandTest : public ::testing::Test {
public:
virtual void SetUp() {
auto db = iota::db::DBManager::get();
db.resetConnection();
db.loadSchema(true);
}
};
class CreateUserTest : public CommandTest {};

TEST_F(CommandTest, ErrorOnDuplicate) {
rpc::CreateUserRequest req;
rpc::CreateUserReply res;
rpc::Error err;
TEST_F(CreateUserTest, ErrorOnDuplicate) {
db::sql::UserAccount tbl;

auto session = std::make_shared<ClientSession>();
auto& conn = iota::db::DBManager::get().connection();

req.set_identifier("User1");

cmd::CreateUser command(session);
command.doProcess(&req, &res);
auto status = command.doProcess(&req, &res);
err.ParseFromString(status.error_details());
createUser(session(), "User1");
auto status = createUser(session(), "User1");
auto err = errorFromStatus(status);

EXPECT_EQ(grpc::StatusCode::FAILED_PRECONDITION, status.error_code());
EXPECT_EQ(err.code(), rpc::ErrorCode::USER_EXISTS);
Expand All @@ -45,26 +33,13 @@ TEST_F(CommandTest, ErrorOnDuplicate) {
.count);
}

TEST_F(CommandTest, CreateUsers) {
rpc::CreateUserRequest req;
rpc::CreateUserReply res;
TEST_F(CreateUserTest, CreateUsers) {
db::sql::UserAccount tbl;

auto session = std::make_shared<ClientSession>();
auto& conn = iota::db::DBManager::get().connection();

req.set_identifier("User1");

{
cmd::CreateUser command(session);
command.doProcess(&req, &res);
}

req.set_identifier("User2");
{
cmd::CreateUser command(session);
command.doProcess(&req, &res);
}
EXPECT_TRUE(createUser(session(), "User1").ok());
EXPECT_TRUE(createUser(session(), "User2").ok());

EXPECT_EQ(2, conn(select(count(tbl.identifier)).from(tbl).unconditionally())
.front()
Expand Down
53 changes: 53 additions & 0 deletions hub/commands/tests/test_get_balance.cc
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
#include <gtest/gtest.h>
#include <sqlpp11/select.h>
#include <sqlpp11/functions.h>

#include "proto/hub.pb.h"
#include "schema/schema.h"

#include "hub/db/db.h"
#include "hub/stats/session.h"
#include "hub/commands/get_balance.h"

#include "runner.h"

using namespace iota;
using namespace sqlpp;

namespace {
class GetBalanceTest : public CommandTest {};

TEST_F(GetBalanceTest, UnknownUserShouldFail) {
rpc::GetBalanceRequest req;
rpc::GetBalanceReply res;

req.set_userid("User1");
cmd::GetBalance command(session());

auto status = command.doProcess(&req, &res);

EXPECT_FALSE(status.ok());

auto err = errorFromStatus(status);
EXPECT_EQ(err.code(), rpc::ErrorCode::USER_DOES_NOT_EXIST);
}

TEST_F(GetBalanceTest, NewUserHasZeroBalance) {
rpc::GetBalanceRequest req;
rpc::GetBalanceReply res;
rpc::Error err;

constexpr auto username = "User1";

createUser(session(), username);

req.set_userid("User1");

cmd::GetBalance command(session());

EXPECT_TRUE(command.doProcess(&req, &res).ok());

EXPECT_EQ(0, res.available());
}

}; // namespace

0 comments on commit c409a4e

Please sign in to comment.