forked from lthn/blockchain
Merge remote-tracking branch 'origin/frontend'
This commit is contained in:
commit
a609f6b974
69 changed files with 1568 additions and 587 deletions
|
|
@ -51,6 +51,7 @@ namespace math_helper
|
|||
average()
|
||||
{
|
||||
m_base = default_base;
|
||||
m_count = 0;
|
||||
}
|
||||
|
||||
bool set_base()
|
||||
|
|
@ -71,6 +72,7 @@ namespace math_helper
|
|||
CRITICAL_REGION_LOCAL(m_lock);
|
||||
|
||||
//#ifndef DEBUG_STUB
|
||||
m_count++;
|
||||
m_list.push_back(vl);
|
||||
if(m_list.size() > m_base )
|
||||
m_list.pop_front();
|
||||
|
|
@ -106,9 +108,20 @@ namespace math_helper
|
|||
|
||||
return 0;
|
||||
}
|
||||
uint64_t& get_count()
|
||||
{
|
||||
return m_count;
|
||||
}
|
||||
|
||||
void reset()
|
||||
{
|
||||
m_count = 0;
|
||||
m_list.clear();
|
||||
}
|
||||
|
||||
private:
|
||||
unsigned int m_base;
|
||||
unsigned int m_base;
|
||||
uint64_t m_count;
|
||||
std::list<value_type> m_list;
|
||||
mutable critical_section m_lock;
|
||||
};
|
||||
|
|
|
|||
|
|
@ -316,6 +316,7 @@ DISABLE_VS_WARNINGS(4355)
|
|||
send_guard.unlock();//manual unlock
|
||||
LOG_ERROR("send to [" << print_connection_context_short(context) << ", (" << (void*)this << ")] que size is more than ABSTRACT_SERVER_SEND_QUE_MAX_COUNT(" << ABSTRACT_SERVER_SEND_QUE_MAX_COUNT << "), shutting down connection");
|
||||
close();
|
||||
shutdown();
|
||||
return false;
|
||||
}
|
||||
|
||||
|
|
@ -351,6 +352,8 @@ DISABLE_VS_WARNINGS(4355)
|
|||
template<class t_protocol_handler>
|
||||
bool connection<t_protocol_handler>::shutdown()
|
||||
{
|
||||
if (m_was_shutdown)
|
||||
return true;
|
||||
// Initiate graceful connection closure.
|
||||
boost::system::error_code ignored_ec;
|
||||
socket_.shutdown(boost::asio::ip::tcp::socket::shutdown_both, ignored_ec);
|
||||
|
|
|
|||
|
|
@ -116,27 +116,27 @@ inline uint32_t random_math(uint32_t a, uint32_t b, uint32_t selector) noexcept
|
|||
switch (selector % 11)
|
||||
{
|
||||
default:
|
||||
case 0:
|
||||
return a * b;
|
||||
case 1:
|
||||
return a + b;
|
||||
case 2:
|
||||
return mul_hi32(a, b);
|
||||
return a + b;
|
||||
case 3:
|
||||
return std::min(a, b);
|
||||
return a * b;
|
||||
case 4:
|
||||
return rotl32(a, b);
|
||||
return mul_hi32(a, b);
|
||||
case 5:
|
||||
return rotr32(a, b);
|
||||
return std::min(a, b);
|
||||
case 6:
|
||||
return a & b;
|
||||
return rotl32(a, b);
|
||||
case 7:
|
||||
return a | b;
|
||||
return rotr32(a, b);
|
||||
case 8:
|
||||
return a ^ b;
|
||||
return a & b;
|
||||
case 9:
|
||||
return clz32(a) + clz32(b);
|
||||
return a | b;
|
||||
case 10:
|
||||
return a ^ b;
|
||||
case 0:
|
||||
return clz32(a) + clz32(b);
|
||||
case 1:
|
||||
return popcount32(a) + popcount32(b);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -75,15 +75,18 @@ namespace tools
|
|||
std::map<std::thread::id, std::vector<bool> > m_transactions_stack;
|
||||
std::atomic<bool> m_is_open;
|
||||
epee::shared_recursive_mutex& m_rwlock;
|
||||
|
||||
public:
|
||||
struct performance_data
|
||||
{
|
||||
epee::math_helper::average<uint64_t, 10> backend_set_pod_time;
|
||||
epee::math_helper::average<uint64_t, 10> backend_set_t_time;
|
||||
epee::math_helper::average<uint64_t, 10> set_serialize_t_time;
|
||||
epee::math_helper::average<uint64_t, 10> backend_get_pod_time;
|
||||
epee::math_helper::average<uint64_t, 10> backend_get_t_time;
|
||||
epee::math_helper::average<uint64_t, 10> get_serialize_t_time;
|
||||
};
|
||||
private:
|
||||
mutable performance_data m_gperformance_data;
|
||||
mutable std::unordered_map<container_handle, performance_data> m_performance_data_map;
|
||||
public:
|
||||
basic_db_accessor(std::shared_ptr<i_db_backend> backend, epee::shared_recursive_mutex& rwlock) :m_backend(backend), m_rwlock(rwlock), m_is_open(false)
|
||||
|
|
@ -93,7 +96,8 @@ namespace tools
|
|||
close();
|
||||
}
|
||||
|
||||
const performance_data& get_performance_data_for_handle(container_handle h) const { return m_performance_data_map[h]; }
|
||||
performance_data& get_performance_data_for_handle(container_handle h) const { return m_performance_data_map[h]; }
|
||||
performance_data& get_performance_data_global() const { return m_gperformance_data; }
|
||||
|
||||
|
||||
bool bind_parent_container(i_db_parent_to_container_callabck* pcontainer)
|
||||
|
|
@ -270,15 +274,23 @@ namespace tools
|
|||
template<class t_pod_key, class t_object>
|
||||
bool get_t_object(container_handle h, const t_pod_key& k, t_object& obj) const
|
||||
{
|
||||
performance_data& m_performance_data = m_gperformance_data;
|
||||
//TRY_ENTRY();
|
||||
std::string res_buff;
|
||||
size_t sk = 0;
|
||||
const char* pk = key_to_ptr(k, sk);
|
||||
|
||||
TIME_MEASURE_START_PD(backend_get_t_time);
|
||||
if (!m_backend->get(h, pk, sk, res_buff))
|
||||
return false;
|
||||
TIME_MEASURE_FINISH_PD(backend_get_t_time);
|
||||
|
||||
return t_unserializable_object_from_blob(obj, res_buff);
|
||||
|
||||
TIME_MEASURE_START_PD(get_serialize_t_time);
|
||||
bool res = t_unserializable_object_from_blob(obj, res_buff);
|
||||
TIME_MEASURE_FINISH_PD(get_serialize_t_time);
|
||||
|
||||
return res;
|
||||
//CATCH_ENTRY_L0("get_t_object_from_db", false);
|
||||
}
|
||||
|
||||
|
|
@ -310,15 +322,18 @@ namespace tools
|
|||
bool get_pod_object(container_handle h, const t_pod_key& k, t_pod_object& obj) const
|
||||
{
|
||||
static_assert(std::is_pod<t_pod_object>::value, "t_pod_object must be a POD type.");
|
||||
|
||||
performance_data& m_performance_data = m_gperformance_data;
|
||||
|
||||
//TRY_ENTRY();
|
||||
std::string res_buff;
|
||||
size_t sk = 0;
|
||||
const char* pk = key_to_ptr(k, sk);
|
||||
|
||||
TIME_MEASURE_START_PD(backend_get_pod_time);
|
||||
if (!m_backend->get(h, pk, sk, res_buff))
|
||||
return false;
|
||||
TIME_MEASURE_FINISH_PD(backend_get_pod_time);
|
||||
|
||||
|
||||
CHECK_AND_ASSERT_MES(sizeof(t_pod_object) == res_buff.size(), false, "sizes missmath at get_pod_object_from_db(). returned size = "
|
||||
<< res_buff.size() << "expected: " << sizeof(t_pod_object));
|
||||
|
|
@ -784,14 +799,19 @@ namespace tools
|
|||
m_cache.erase(k);
|
||||
}
|
||||
|
||||
const performance_data& get_performance_data() const
|
||||
performance_data& get_performance_data() const
|
||||
{
|
||||
return m_performance_data;
|
||||
}
|
||||
const typename basic_db_accessor::performance_data& get_performance_data_native() const
|
||||
typename basic_db_accessor::performance_data& get_performance_data_native() const
|
||||
{
|
||||
return base_class::bdb.get_performance_data_for_handle(base_class::m_h);
|
||||
}
|
||||
typename basic_db_accessor::performance_data& get_performance_data_global() const
|
||||
{
|
||||
return base_class::bdb.get_performance_data_global();
|
||||
}
|
||||
|
||||
private:
|
||||
mutable performance_data m_performance_data;
|
||||
};
|
||||
|
|
|
|||
|
|
@ -567,6 +567,8 @@ bool handle_get_daemon_info(po::variables_map& vm)
|
|||
<< "longhash_calculating_time_3: " << res.performance_data.longhash_calculating_time_3 << ENDL
|
||||
<< "raise_block_core_event: " << res.performance_data.raise_block_core_event << ENDL
|
||||
<< "target_calculating_time_2: " << res.performance_data.target_calculating_time_2 << ENDL
|
||||
<< "target_calculating_enum_blocks: " << res.performance_data.target_calculating_enum_blocks << ENDL
|
||||
<< "target_calculating_calc: " << res.performance_data.target_calculating_calc << ENDL
|
||||
<< "all_txs_insert_time_5: " << res.performance_data.all_txs_insert_time_5 << ENDL
|
||||
<< "tx_add_one_tx_time: " << res.performance_data.tx_add_one_tx_time << ENDL
|
||||
<< "tx_check_inputs_time: " << res.performance_data.tx_check_inputs_time << ENDL
|
||||
|
|
|
|||
|
|
@ -61,6 +61,7 @@ using namespace currency;
|
|||
#define BLOCKCHAIN_STORAGE_OPTIONS_ID_STORAGE_MAJOR_COMPATIBILITY_VERSION 3 //mismatch here means full resync
|
||||
#define BLOCKCHAIN_STORAGE_OPTIONS_ID_STORAGE_MINOR_COMPATIBILITY_VERSION 4 //mismatch here means some reinitializations
|
||||
|
||||
#define TARGETDATA_CACHE_SIZE DIFFICULTY_WINDOW + 10
|
||||
|
||||
|
||||
DISABLE_VS_WARNINGS(4267)
|
||||
|
|
@ -447,6 +448,8 @@ bool blockchain_storage::clear()
|
|||
m_db_aliases.clear();
|
||||
m_db_addr_to_alias.clear();
|
||||
m_db_per_block_gindex_incs.clear();
|
||||
m_pos_targetdata_cache.clear();
|
||||
m_pow_targetdata_cache.clear();
|
||||
|
||||
m_db.commit_transaction();
|
||||
|
||||
|
|
@ -889,25 +892,28 @@ wide_difficulty_type blockchain_storage::get_next_diff_conditional(bool pos) con
|
|||
CRITICAL_REGION_LOCAL(m_read_lock);
|
||||
std::vector<uint64_t> timestamps;
|
||||
std::vector<wide_difficulty_type> commulative_difficulties;
|
||||
size_t count = 0;
|
||||
if (!m_db_blocks.size())
|
||||
return DIFFICULTY_STARTER;
|
||||
//skip genesis timestamp
|
||||
uint64_t stop_ind = 0;
|
||||
uint64_t blocks_size = m_db_blocks.size();
|
||||
for (uint64_t cur_ind = blocks_size - 1; cur_ind != stop_ind && count < DIFFICULTY_WINDOW; cur_ind--)
|
||||
{
|
||||
auto beiptr = m_db_blocks[cur_ind];
|
||||
TIME_MEASURE_START_PD(target_calculating_enum_blocks);
|
||||
std::list<std::pair<wide_difficulty_type, uint64_t>>& targetdata_cache = pos ? m_pos_targetdata_cache : m_pow_targetdata_cache;
|
||||
if (targetdata_cache.empty())
|
||||
load_targetdata_cache(pos);
|
||||
|
||||
bool is_pos_bl = is_pos_block(beiptr->bl);
|
||||
if (pos != is_pos_bl)
|
||||
continue;
|
||||
timestamps.push_back(beiptr->bl.timestamp);
|
||||
commulative_difficulties.push_back(beiptr->cumulative_diff_precise);
|
||||
size_t count = 0;
|
||||
for (auto it = targetdata_cache.rbegin(); it != targetdata_cache.rend() && count < DIFFICULTY_WINDOW; it++)
|
||||
{
|
||||
timestamps.push_back(it->second);
|
||||
commulative_difficulties.push_back(it->first);
|
||||
++count;
|
||||
}
|
||||
|
||||
wide_difficulty_type& dif = pos ? m_cached_next_pos_difficulty : m_cached_next_pow_difficulty;
|
||||
return dif = next_difficulty(timestamps, commulative_difficulties, pos ? DIFFICULTY_POS_TARGET : DIFFICULTY_POW_TARGET);
|
||||
TIME_MEASURE_FINISH_PD(target_calculating_enum_blocks);
|
||||
TIME_MEASURE_START_PD(target_calculating_calc);
|
||||
dif = next_difficulty(timestamps, commulative_difficulties, pos ? DIFFICULTY_POS_TARGET : DIFFICULTY_POW_TARGET);
|
||||
TIME_MEASURE_FINISH_PD(target_calculating_calc);
|
||||
return dif;
|
||||
}
|
||||
//------------------------------------------------------------------
|
||||
wide_difficulty_type blockchain_storage::get_next_diff_conditional2(bool pos, const alt_chain_type& alt_chain, uint64_t split_height) const
|
||||
|
|
@ -4542,37 +4548,81 @@ bool blockchain_storage::handle_block_to_main_chain(const block& bl, const crypt
|
|||
<< ENDL << "HEIGHT " << bei.height << ", difficulty: " << current_diffic << ", cumul_diff_precise: " << bei.cumulative_diff_precise << ", cumul_diff_adj: " << bei.cumulative_diff_adjusted << " (+" << cumulative_diff_delta << ")"
|
||||
<< ENDL << "block reward: " << print_money_brief(base_reward + fee_summary) << " (" << print_money_brief(base_reward) << " + " << print_money_brief(fee_summary)
|
||||
<< ")" << ", coinbase_blob_size: " << coinbase_blob_size << ", cumulative size: " << cumulative_block_size << ", tx_count: " << bei.bl.tx_hashes.size()
|
||||
<< ", " << block_processing_time_0_ms
|
||||
<< "(" << block_processing_time_1
|
||||
<< "/" << target_calculating_time_2
|
||||
<< ", timing: " << block_processing_time_0_ms << "ms"
|
||||
<< "(micrsec:" << block_processing_time_1
|
||||
<< "(" << target_calculating_time_2 << "(" << m_performance_data.target_calculating_enum_blocks.get_last_val() << "/" << m_performance_data.target_calculating_calc.get_last_val() << ")"
|
||||
<< "/" << longhash_calculating_time_3
|
||||
<< "/" << insert_time_4
|
||||
<< "/" << all_txs_insert_time_5
|
||||
<< "/" << etc_stuff_6
|
||||
<< ")micrs");
|
||||
<< "))");
|
||||
|
||||
on_block_added(bei, id);
|
||||
|
||||
bvc.m_added_to_main_chain = true;
|
||||
return true;
|
||||
}
|
||||
//------------------------------------------------------------------
|
||||
void blockchain_storage::on_block_added(const block_extended_info& bei, const crypto::hash& id)
|
||||
{
|
||||
update_next_comulative_size_limit();
|
||||
m_timestamps_median_cache.clear();
|
||||
m_tx_pool.on_blockchain_inc(bei.height, id);
|
||||
|
||||
update_targetdata_cache_on_block_added(bei);
|
||||
|
||||
TIME_MEASURE_START_PD(raise_block_core_event);
|
||||
rise_core_event(CORE_EVENT_BLOCK_ADDED, void_struct());
|
||||
TIME_MEASURE_FINISH_PD(raise_block_core_event);
|
||||
|
||||
}
|
||||
//------------------------------------------------------------------
|
||||
void blockchain_storage::on_block_removed(const block_extended_info& bei)
|
||||
{
|
||||
m_tx_pool.on_blockchain_dec(m_db_blocks.size() - 1, get_top_block_id());
|
||||
m_timestamps_median_cache.clear();
|
||||
update_targetdata_cache_on_block_removed(bei);
|
||||
LOG_PRINT_L2("block at height " << bei.height << " was removed from the blockchain");
|
||||
}
|
||||
//------------------------------------------------------------------
|
||||
void blockchain_storage::update_targetdata_cache_on_block_added(const block_extended_info& bei)
|
||||
{
|
||||
if (bei.height == 0)
|
||||
return; //skip genesis
|
||||
std::list<std::pair<wide_difficulty_type, uint64_t>>& targetdata_cache = is_pos_block(bei.bl) ? m_pos_targetdata_cache : m_pow_targetdata_cache;
|
||||
targetdata_cache.push_back(std::pair<wide_difficulty_type, uint64_t>(bei.cumulative_diff_precise, bei.bl.timestamp));
|
||||
while (targetdata_cache.size() > TARGETDATA_CACHE_SIZE)
|
||||
targetdata_cache.pop_front();
|
||||
}
|
||||
//------------------------------------------------------------------
|
||||
void blockchain_storage::update_targetdata_cache_on_block_removed(const block_extended_info& bei)
|
||||
{
|
||||
std::list<std::pair<wide_difficulty_type, uint64_t>>& targetdata_cache = is_pos_block(bei.bl) ? m_pos_targetdata_cache : m_pow_targetdata_cache;
|
||||
if (targetdata_cache.size())
|
||||
targetdata_cache.pop_back();
|
||||
if (targetdata_cache.size() < DIFFICULTY_WINDOW)
|
||||
targetdata_cache.clear();
|
||||
}
|
||||
//------------------------------------------------------------------
|
||||
void blockchain_storage::load_targetdata_cache(bool is_pos)const
|
||||
{
|
||||
std::list<std::pair<wide_difficulty_type, uint64_t>>& targetdata_cache = is_pos? m_pos_targetdata_cache: m_pow_targetdata_cache;
|
||||
targetdata_cache.clear();
|
||||
uint64_t stop_ind = 0;
|
||||
uint64_t blocks_size = m_db_blocks.size();
|
||||
size_t count = 0;
|
||||
for (uint64_t cur_ind = blocks_size - 1; cur_ind != stop_ind && count < DIFFICULTY_WINDOW + 5; cur_ind--)
|
||||
{
|
||||
auto beiptr = m_db_blocks[cur_ind];
|
||||
|
||||
bool is_pos_bl = is_pos_block(beiptr->bl);
|
||||
if (is_pos != is_pos_bl)
|
||||
continue;
|
||||
targetdata_cache.push_front(std::pair<wide_difficulty_type, uint64_t>(beiptr->cumulative_diff_precise, beiptr->bl.timestamp));
|
||||
++count;
|
||||
}
|
||||
}
|
||||
//------------------------------------------------------------------
|
||||
void blockchain_storage::on_abort_transaction()
|
||||
{
|
||||
if (m_event_handler) m_event_handler->on_clear_events();
|
||||
|
|
|
|||
|
|
@ -68,6 +68,9 @@ namespace currency
|
|||
epee::math_helper::average<uint64_t, 5> etc_stuff_6;
|
||||
epee::math_helper::average<uint64_t, 5> insert_time_4;
|
||||
epee::math_helper::average<uint64_t, 5> raise_block_core_event;
|
||||
//target_calculating_time_2
|
||||
epee::math_helper::average<uint64_t, 5> target_calculating_enum_blocks;
|
||||
epee::math_helper::average<uint64_t, 5> target_calculating_calc;
|
||||
|
||||
//tx processing zone
|
||||
epee::math_helper::average<uint64_t, 5> tx_check_inputs_time;
|
||||
|
|
@ -498,7 +501,7 @@ namespace currency
|
|||
mutable core_runtime_config m_core_runtime_config;
|
||||
mutable i_core_event_handler* m_event_handler;
|
||||
mutable i_core_event_handler m_event_handler_stub;
|
||||
|
||||
|
||||
//tools::median_db_cache<uint64_t, uint64_t> m_tx_fee_median;
|
||||
mutable std::unordered_map<size_t, uint64_t> m_timestamps_median_cache;
|
||||
mutable performnce_data m_performance_data;
|
||||
|
|
@ -507,7 +510,10 @@ namespace currency
|
|||
//just informational
|
||||
mutable wide_difficulty_type m_cached_next_pow_difficulty;
|
||||
mutable wide_difficulty_type m_cached_next_pos_difficulty;
|
||||
//work like a cache to avoid
|
||||
|
||||
mutable std::list <std::pair<wide_difficulty_type, uint64_t>> m_pos_targetdata_cache;
|
||||
mutable std::list <std::pair<wide_difficulty_type, uint64_t>> m_pow_targetdata_cache;
|
||||
//work like a cache to avoid recalculation on read operations
|
||||
mutable uint64_t m_current_fee_median;
|
||||
mutable uint64_t m_current_fee_median_effective_index;
|
||||
bool m_is_reorganize_in_process;
|
||||
|
|
@ -557,9 +563,12 @@ namespace currency
|
|||
const std::vector<txin_etc_details_v>& get_txin_etc_options(const txin_v& in)const;
|
||||
void on_block_added(const block_extended_info& bei, const crypto::hash& id);
|
||||
void on_block_removed(const block_extended_info& bei);
|
||||
void update_targetdata_cache_on_block_added(const block_extended_info& bei);
|
||||
void update_targetdata_cache_on_block_removed(const block_extended_info& bei);
|
||||
uint64_t tx_fee_median_for_height(uint64_t h) const;
|
||||
uint64_t get_tx_fee_median_effective_index(uint64_t h) const;
|
||||
void on_abort_transaction();
|
||||
void load_targetdata_cache(bool is_pos) const;
|
||||
|
||||
|
||||
uint64_t get_adjusted_time()const;
|
||||
|
|
|
|||
|
|
@ -7,7 +7,7 @@
|
|||
#pragma once
|
||||
|
||||
|
||||
#define CURRENCY_FORMATION_VERSION 79
|
||||
#define CURRENCY_FORMATION_VERSION 81
|
||||
|
||||
|
||||
#define CURRENCY_MAX_BLOCK_NUMBER 500000000
|
||||
|
|
@ -53,7 +53,7 @@
|
|||
// #define CURRENCY_FIXED_REWARD_ZONE_REWARD_AMOUNT ((uint64_t)100000000) // should be TX_MINIMUM_FEE * CURRENCY_FIXED_REWARD_ZONE_FEE_MULTIPLIER
|
||||
// #define CURRENCY_FIXED_REWARD_ZONE_FEE_MULTIPLIER 1000 // reward in minimum fees for a block in the zone
|
||||
|
||||
#define CURRENCY_TESTNET_CONST_REWARD 100000000000000
|
||||
#define CURRENCY_BLOCK_REWARD 1000000000000 // 1.0 coin
|
||||
|
||||
|
||||
#define WALLET_MAX_ALLOWED_OUTPUT_AMOUNT ((uint64_t)0xffffffffffffffffLL)
|
||||
|
|
|
|||
|
|
@ -2377,7 +2377,7 @@ namespace currency
|
|||
if (!height)
|
||||
return PREMINE_AMOUNT;
|
||||
|
||||
return CURRENCY_TESTNET_CONST_REWARD;
|
||||
return CURRENCY_BLOCK_REWARD;
|
||||
}
|
||||
//-----------------------------------------------------------------------------------------------
|
||||
bool get_block_reward(bool is_pos, size_t median_size, size_t current_block_size, const boost::multiprecision::uint128_t& already_generated_coins, uint64_t &reward, uint64_t height)
|
||||
|
|
|
|||
|
|
@ -55,23 +55,7 @@ namespace currency {
|
|||
return a + b < a || (c && a + b == (uint64_t)-1);
|
||||
}
|
||||
|
||||
bool check_hash_old(const crypto::hash &hash, difficulty_type difficulty) {
|
||||
uint64_t low, high, top, cur;
|
||||
// First check the highest word, this will most likely fail for a random hash.
|
||||
mul(swap64le(((const uint64_t *)&hash)[3]), difficulty, top, high);
|
||||
if (high != 0) {
|
||||
return false;
|
||||
}
|
||||
mul(swap64le(((const uint64_t *)&hash)[0]), difficulty, low, cur);
|
||||
mul(swap64le(((const uint64_t *)&hash)[1]), difficulty, low, high);
|
||||
bool carry = cadd(cur, low);
|
||||
cur = high;
|
||||
mul(swap64le(((const uint64_t *)&hash)[2]), difficulty, low, high);
|
||||
carry = cadc(cur, low, carry);
|
||||
carry = cadc(high, top, carry);
|
||||
return !carry;
|
||||
}
|
||||
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
#ifdef max
|
||||
#undef max
|
||||
|
|
@ -143,48 +127,6 @@ namespace currency {
|
|||
}
|
||||
}
|
||||
|
||||
difficulty_type next_difficulty_old(vector<uint64_t> timestamps, vector<difficulty_type> cumulative_difficulties, size_t target_seconds) {
|
||||
//cutoff DIFFICULTY_LAG
|
||||
if (timestamps.size() > DIFFICULTY_WINDOW)
|
||||
{
|
||||
timestamps.resize(DIFFICULTY_WINDOW);
|
||||
cumulative_difficulties.resize(DIFFICULTY_WINDOW);
|
||||
}
|
||||
|
||||
|
||||
size_t length = timestamps.size();
|
||||
assert(length == cumulative_difficulties.size());
|
||||
if (length <= 1) {
|
||||
return DIFFICULTY_STARTER;
|
||||
}
|
||||
static_assert(DIFFICULTY_WINDOW >= 2, "Window is too small");
|
||||
assert(length <= DIFFICULTY_WINDOW);
|
||||
sort(timestamps.begin(), timestamps.end());
|
||||
size_t cut_begin, cut_end;
|
||||
static_assert(2 * DIFFICULTY_CUT <= DIFFICULTY_WINDOW - 2, "Cut length is too large");
|
||||
if (length <= DIFFICULTY_WINDOW - 2 * DIFFICULTY_CUT) {
|
||||
cut_begin = 0;
|
||||
cut_end = length;
|
||||
}
|
||||
else {
|
||||
cut_begin = (length - (DIFFICULTY_WINDOW - 2 * DIFFICULTY_CUT) + 1) / 2;
|
||||
cut_end = cut_begin + (DIFFICULTY_WINDOW - 2 * DIFFICULTY_CUT);
|
||||
}
|
||||
assert(/*cut_begin >= 0 &&*/ cut_begin + 2 <= cut_end && cut_end <= length);
|
||||
uint64_t time_span = timestamps[cut_end - 1] - timestamps[cut_begin];
|
||||
if (time_span == 0) {
|
||||
time_span = 1;
|
||||
}
|
||||
difficulty_type total_work = cumulative_difficulties[cut_end - 1] - cumulative_difficulties[cut_begin];
|
||||
assert(total_work > 0);
|
||||
uint64_t low, high;
|
||||
mul(total_work, target_seconds, low, high);
|
||||
if (high != 0 || low + time_span - 1 < low) {
|
||||
return 0;
|
||||
}
|
||||
return (low + time_span - 1) / time_span;
|
||||
}
|
||||
|
||||
void get_cut_location_from_len(size_t length, size_t& cut_begin, size_t& cut_end, size_t REDEF_DIFFICULTY_WINDOW, size_t REDEF_DIFFICULTY_CUT_OLD, size_t REDEF_DIFFICULTY_CUT_LAST)
|
||||
{
|
||||
if (length <= REDEF_DIFFICULTY_WINDOW)
|
||||
|
|
@ -239,6 +181,7 @@ namespace currency {
|
|||
|
||||
wide_difficulty_type next_difficulty(vector<uint64_t>& timestamps, vector<wide_difficulty_type>& cumulative_difficulties, size_t target_seconds)
|
||||
{
|
||||
TIME_MEASURE_START_PD(target_calculating_enum_blocks);
|
||||
// timestamps - first is latest, back - is oldest timestamps
|
||||
if (timestamps.size() > DIFFICULTY_WINDOW)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -15,13 +15,9 @@
|
|||
|
||||
namespace currency
|
||||
{
|
||||
typedef std::uint64_t difficulty_type;
|
||||
|
||||
typedef boost::multiprecision::uint128_t wide_difficulty_type;
|
||||
|
||||
bool check_hash_old(const crypto::hash &hash, difficulty_type difficulty);
|
||||
difficulty_type next_difficulty_old(std::vector<std::uint64_t> timestamps, std::vector<difficulty_type> cumulative_difficulties);
|
||||
difficulty_type next_difficulty_old(std::vector<std::uint64_t> timestamps, std::vector<difficulty_type> cumulative_difficulties, size_t target_seconds);
|
||||
|
||||
bool check_hash(const crypto::hash &hash, wide_difficulty_type difficulty);
|
||||
wide_difficulty_type next_difficulty(std::vector<std::uint64_t>& timestamps, std::vector<wide_difficulty_type>& cumulative_difficulties, size_t target_seconds);
|
||||
uint64_t difficulty_to_boundary(wide_difficulty_type difficulty);
|
||||
|
|
|
|||
|
|
@ -8,7 +8,7 @@
|
|||
namespace currency
|
||||
{
|
||||
const genesis_tx_raw_data ggenesis_tx_raw = { {
|
||||
0xa080800e00000101,0x800326b0b4a0f2fd,0x46f236cb0efcd16c,0x547fbb0ff9468d85,0x1da1229cbceeeddf,0x00509f1127de5f6d,0xb0b4a0f2fda08080,0x19fbc70d41860326,0xb0afa73cfe1209ca,0x0d299d4e62aa2f1f,0x7071d8e322c2ebfc,0xf2fda0808000ed15,0x9e5a660326b0b4a0,0x2928590bf14c0f33,0x3dfd3f48e046a8c2,0xfa969b2fa09ad0ed,0x808000acfcbb24be,0x0326b0b4a0f2fda0,0x682ecad7a79177d8,0xc9e501939827d6ec,0x7f55e8f25beacf76,0xc3a22fd82ddcb367,0xb4f89aecdce08000,0x6aeaf9b0de0326b0,0x631393eedf0fc04d,0x8ed9b961192f541a,0x5088f34df1470474,0x93dc80800011241e,0x30b80307d0ffc2e0,0xdcf3a14a0ac108e5,0xd508a0ec648f342d,0x0c1ac8310dcce994,0x8000346b43733822,0x05c6c5bc97b1a080,0x44663811c2802f03,0x5456a1cc803e5b0c,0x9a7c995f82c5bb18,0xe95939d19b769901,0xbc97b1a0808000e9,0xb0624da20305c6c5,0xe7921e8df615d26f,0x27abce5d4d975bc6,0xecb92e6224ce0952,0xa080800085eb1099,0xb10305c6c5bc97b1,0xea6de475ef2cdaaf,0xa47b3fe828343c89,0x8ec5057c0bf7dd44,0x000f2403abe0ade8,0xc6c5bc97b1a08080,0x60e1a72d445b0305,0x8bb2fc2bfd63e41b,0x7772ae843713073b,0xe1c2db8d00c414ff,0x97b1a0808000b5c2,0xd69ad60305c6c5bc,0x8b0b54a7a541d22c,0x312a3c33f20800c1,0xe401b39ce755f512,0x808000d176bfb84a,0x0305c6c5bc97b1a0,0x7711834fbded84b6,0x1d4dca20946a1b23,0x80bfed89b730469e,0x641a20bd14e5d7cf,0xc5bc97b1a0808000,0xca32ddfd2c0305c6,0xf662200d93c916ca,0x0ca700521b6ece14,0x1a14d2365bb10a8e,0xbd88808000fd386e,0xc6e40304dbfb86ad,0xaba7f00aede6da7a,0xc5a36eac7d327196,0x5237aa32dafc085e,0x11003545013f1ed3,0xbd65d3fbab8aa616,0xb8c69175919e298e,0xe4fe3762fd534801,0xba7de375298d061d,0xf917cbb4170015e4,0x1747ce171e061770,0x05d7177e6b170d69,0x69170e891774ff17,0x17882e17c3621765,0x000a0ec1de17d7e4 },
|
||||
{ 0x00 } };
|
||||
0xa080801700000101,0xf30326b0b4a0f2fd,0x46fe96860beb01ea,0x01323293f642c7c6,0x80e8a7730e20c142,0x00cb08b2016bbccc,0xb0b4a0f2fda08080,0xb67d52cae50e0326,0x71bb6e75bf256319,0x76dd703cec5e8f40,0xfca18c41540510b9,0xf2fda080800070f3,0xeea9320326b0b4a0,0xb5d90ea5fe49c4cb,0x3f1e5ca079fe6ebb,0x2f73ac1012e243d0,0x808000887086f29b,0x0326b0b4a0f2fda0,0x44f1a1dfe16379f9,0x50d93954cca94108,0x9ac47bb379e6f074,0xb44bdb69a986211e,0xb4f89aecdce08000,0x88b82d0dc60326b0,0x4e995861a27c03ae,0xdf48c9c97c449f1d,0xdd2ea49c4ecdcbdf,0x93dc80800046f5dc,0xedff0307d0ffc2e0,0x4a8442409d3719b1,0x2e385d03544c8122,0x0c592cfad6e8e900,0x8000ed0b32aa07c6,0x05c6c5bc97b1a080,0xa5d7620e38d8ef03,0x1c68e9cfd35cc1e5,0xbdba8ea5fb49f375,0x7fb77cff80f31c9e,0xbc97b1a080800040,0xd15b16b60305c6c5,0x7af40193ad86f123,0x5ba33fd12279af67,0x0db572d11ea1ad96,0xa080800024fc1fde,0x460305c6c5bc97b1,0x444d02aa28a539b9,0x9846386a58c71f35,0x27fd9af12bd3710a,0x0004b2acf589ce8d,0xc6c5bc97b1a08080,0x610c62c125e80305,0x44217ee86d4ed16f,0x5f27600912875c5f,0x51f2fbfd2b30ff54,0x97b1a08080002698,0x8180fc0305c6c5bc,0xaeb4bfd37d282432,0x10a11a1c799b6165,0x9c69b9b6aac75596,0x8080009c5a6d5e15,0x0305c6c5bc97b1a0,0xbf9f36e03f56393a,0x0a74acb0775f0e02,0x97665a42cb477844,0xff01a0c03c43df12,0xc5bc97b1a0808000,0xd5066341560305c6,0x5aa8c1962a148222,0xf83737ab96d43653,0x4b5007cf8fd4a1e2,0xd2dc808000565d84,0xa6a8030398c7f980,0x32c08d3989aa7f91,0xe4b5de74db34eb45,0xf2bd313bdefdfcba,0x80007e3bb1b21fd2,0x018e8df2b7f0a080,0xb2fe8efdeb17a903,0xe7f89d45d4b05be9,0x96f5300e672fd804,0xbd82737c2ce8c3cf,0xef93bf82808000c2,0x816c799a1f0308f0,0x98bd1487b0e05122,0x044d8ffd583693ba,0x1c954a13f5425015,0xfe848080007c6407,0xcde2510311e1dea6,0x3c62da3d50c8a8ee,0xa3acc1ed75d470b1,0xa479c78eecc2f96c,0x8080005f7388cbcb,0xbd0308f0ef93bf82,0xb5a5cca060105de4,0x92cf66a16d3b4d6b,0x5ca92a654f5a8400,0x00df465ad6e8d895,0x08f0ef93bf828080,0x2ce3338452319303,0xecc7b1c056651998,0xc3696cf2fb2fe9b9,0x69b4edf21f2bdaae,0xafeaa69a808000b8,0x1052e2e6de0301e3,0xa06855ba0d7eaab2,0x344998a33e968f15,0xa8a00006653f7005,0xa69a808000a95440,0x58e0580301e3afea,0xc0524c1a0a1d4b5f,0xad37550b686c838b,0x0eb1ef4a20771a79,0x80800080516862ab,0xa30301e3afeaa69a,0xda2b32dbac7f88cc,0x965536648651d1a2,0xbbe22f6bdc320069,0x00a8ea3fddccf16d,0x03c6dfd4ccb48080,0x9921a91a97490603,0x57ceadcb0611b6de,0xa53cee6b71e61ecb,0x0e56262c5e13302f,0x04ee9ff0161a000a,0xa43f85172baeb3d9,0x782309f5ee0a02f0,0x5d187fedafdfae4f,0x971700150f26e04b,0x17482917b0a717cb,0x1fe617c89e1725b4,0x4017c6e317a97217,0x17a7ca178e6117c1,0xd24717fd3917aa53,0xd217b83c178b9b17,0x17d92517d51c17d4,0xda9d17154f17f6fc },
|
||||
{ 0x17,0x41,0x0a,0x0e,0x0a,0x00,0x00 } };
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -8,11 +8,12 @@
|
|||
#include <string>
|
||||
namespace currency
|
||||
{
|
||||
#pragma pack(push, 1)
|
||||
#pragma pack(push, 1)
|
||||
struct genesis_tx_raw_data
|
||||
{
|
||||
uint64_t const v[86];
|
||||
uint8_t const r[1];
|
||||
uint64_t const v[136];
|
||||
uint8_t const r[7];
|
||||
};
|
||||
#pragma pack(pop)
|
||||
extern const genesis_tx_raw_data ggenesis_tx_raw;
|
||||
|
|
|
|||
|
|
@ -9,25 +9,34 @@
|
|||
|
||||
namespace currency
|
||||
{
|
||||
const std::string ggenesis_tx_pub_key_str = "a68aabfbd365bd8e299e917591c6b8014853fd6237fee41d068d2975e37dbae4";
|
||||
const std::string ggenesis_tx_pub_key_str = "f09fee04d9b3ae2b17853fa4f0020aeef50923784faedfafed7f185d4be0260f";
|
||||
const crypto::public_key ggenesis_tx_pub_key = epee::string_tools::parse_tpod_from_hex_string<crypto::public_key>(ggenesis_tx_pub_key_str);
|
||||
const genesis_tx_dictionary_entry ggenesis_dict[14] = {
|
||||
|
||||
const genesis_tx_dictionary_entry ggenesis_dict[23] = {
|
||||
{ 898363347618325980ULL,7 },
|
||||
{ 1234271292339965434ULL,1 },
|
||||
{ 2785329203593578547ULL,12 },
|
||||
{ 2912579291078040461ULL,18 },
|
||||
{ 3515932779881697835ULL,17 },
|
||||
{ 4955366495399988463ULL,11 },
|
||||
{ 5233257582118330150ULL,5 },
|
||||
{ 5511617689742669301ULL,22 },
|
||||
{ 6436517662239927298ULL,19 },
|
||||
{ 6604452700210763953ULL,13 },
|
||||
{ 7200550178847042641ULL,15 },
|
||||
{ 8712326356392296687ULL,9 },
|
||||
{ 8863158309745010598ULL,4 },
|
||||
{ 9048445805125559105ULL,16 },
|
||||
{ 9527474759752332295ULL,2 },
|
||||
{ 9647541513390373765ULL,20 },
|
||||
{ 9921730437908704447ULL,8 },
|
||||
{ 11109691972771859220ULL,0 },
|
||||
{ 14297297752337562678ULL,3 },
|
||||
{ 15636081871140663679ULL,21 },
|
||||
{ 15951161519112687845ULL,6 },
|
||||
{ 17146058209502212345ULL,14 },
|
||||
{ 17472133472787764818ULL,10 }
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -24,7 +24,7 @@ namespace currency
|
|||
}
|
||||
};
|
||||
#pragma pack(pop)
|
||||
extern const genesis_tx_dictionary_entry ggenesis_dict[14];
|
||||
extern const genesis_tx_dictionary_entry ggenesis_dict[23];
|
||||
|
||||
extern const crypto::public_key ggenesis_tx_pub_key;
|
||||
|
||||
|
|
|
|||
|
|
@ -4,6 +4,7 @@
|
|||
"SETUP_CONFIRM_PASS": "Confirm the password",
|
||||
"MASTER_PASS": "Master password",
|
||||
"BUTTON_NEXT": "Next",
|
||||
"BUTTON_SKIP": "Skip",
|
||||
"INCORRECT_PASSWORD": "Invalid password",
|
||||
"FORM_ERRORS": {
|
||||
"PASS_REQUIRED": "Password is required.",
|
||||
|
|
@ -83,6 +84,13 @@
|
|||
"NAME_REQUIRED": "Name is required.",
|
||||
"NAME_DUPLICATE": "Name is duplicate.",
|
||||
"MAX_LENGTH": "Maximum name length reached."
|
||||
},
|
||||
"MODAL": {
|
||||
"TITLE": "Type wallet password",
|
||||
"LABEL": "Password to this wallet",
|
||||
"OPEN": "Open wallet",
|
||||
"SKIP": "Skip",
|
||||
"NOT_FOUND": "Not found"
|
||||
}
|
||||
},
|
||||
"RESTORE_WALLET": {
|
||||
|
|
@ -440,11 +448,21 @@
|
|||
"TITLE_PENDING": "Pending",
|
||||
"TITLE_TOTAL": "Total",
|
||||
"TITLE_PERIOD": "Time period:",
|
||||
"DAY": "1 day",
|
||||
"WEEK": "1 week",
|
||||
"MONTH": "1 month",
|
||||
"YEAR": "1 year",
|
||||
"ALL": "All",
|
||||
"PERIOD": {
|
||||
"WEEK1": "1 week",
|
||||
"WEEK2": "2 week",
|
||||
"MONTH1": "1 month",
|
||||
"MONTH3": "3 month",
|
||||
"MONTH6": "6 month",
|
||||
"YEAR": "1 year",
|
||||
"ALL": "All"
|
||||
},
|
||||
"TITLE_GROUP": "Group:",
|
||||
"GROUP": {
|
||||
"DAY": "day",
|
||||
"WEEK": "week",
|
||||
"MONTH": "month"
|
||||
},
|
||||
"SWITCH": {
|
||||
"ON": "ON",
|
||||
"OFF": "OFF"
|
||||
|
|
|
|||
|
|
@ -33,6 +33,13 @@ button {
|
|||
background-color: themed(disabledButtonHoverColor);
|
||||
}
|
||||
}
|
||||
|
||||
&:focus {
|
||||
|
||||
@include themify($themes) {
|
||||
background-color: themed(disabledButtonFocusColor);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&.blue-button:not(:disabled) {
|
||||
|
|
@ -54,6 +61,13 @@ button {
|
|||
background-color: themed(blueButtonHoverColor);
|
||||
}
|
||||
}
|
||||
|
||||
&:focus {
|
||||
|
||||
@include themify($themes) {
|
||||
background-color: themed(blueButtonFocusColor);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&.green-button:not(:disabled) {
|
||||
|
|
@ -69,6 +83,13 @@ button {
|
|||
background-color: themed(greenButtonHoverColor);
|
||||
}
|
||||
}
|
||||
|
||||
&:focus {
|
||||
|
||||
@include themify($themes) {
|
||||
background-color: themed(greenButtonFocusColor);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&.turquoise-button:not(:disabled) {
|
||||
|
|
@ -84,6 +105,13 @@ button {
|
|||
background-color: themed(turquoiseButtonHoverColor);
|
||||
}
|
||||
}
|
||||
|
||||
&:focus {
|
||||
|
||||
@include themify($themes) {
|
||||
background-color: themed(turquoiseButtonFocusColor);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&.transparent-button {
|
||||
|
|
@ -597,6 +625,10 @@ input[type='checkbox'].style-checkbox {
|
|||
|
||||
.ng-value-container {
|
||||
padding: 0;
|
||||
|
||||
.ng-input {
|
||||
top: auto;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -752,3 +784,14 @@ app-progress-container {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
app-open-wallet-modal {
|
||||
|
||||
.modal {
|
||||
|
||||
@include themify($themes) {
|
||||
background: themed(modalBackground);
|
||||
color: themed(mainTextColor);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -13,26 +13,31 @@ $themes: (
|
|||
greenTextColor: #5cda9d,
|
||||
redTextColor: #fe5252,
|
||||
blueButtonBackgroundColor: #4db1ff,
|
||||
blueButtonHoverColor: #60b9ff,
|
||||
disabledButtonBackgroundColor: #90a4ae,
|
||||
disabledButtonHoverColor: #9bb0ba,
|
||||
blueButtonHoverColor: #82d7ff,
|
||||
blueButtonFocusColor: #59b5fd,
|
||||
disabledButtonBackgroundColor: #9cadb7,
|
||||
disabledButtonHoverColor: #b7d1e0,
|
||||
disabledButtonFocusColor: #a7b9c2,
|
||||
greenButtonBackgroundColor: #5cda9d,
|
||||
greenButtonHoverColor: #5ce2a1,
|
||||
greenButtonHoverColor: #8dfcc6,
|
||||
greenButtonFocusColor: #62e0b2,
|
||||
turquoiseButtonBackgroundColor: #4dd0e1,
|
||||
turquoiseButtonHoverColor: #52d9ea,
|
||||
turquoiseButtonHoverColor: #87f4f5,
|
||||
turquoiseButtonFocusColor: #42d5e8,
|
||||
transparentButtonBorderColor: #2b3644,
|
||||
inputBackgroundColor: #171e27,
|
||||
selectHoverColor: rgba(58, 72, 90, 0.5),
|
||||
selectHoverColor: rgba(58, 69, 85, 0.5),
|
||||
selectSelectedColor: rgba(43, 54, 68, 0.5),
|
||||
switchBackgroundColor: #000000,
|
||||
accountBackgroundColor: rgba(43, 54, 68, 0.5),
|
||||
accountHoverBackgroundColor: rgba(58, 72, 90, 0.5),
|
||||
accountHoverBackgroundColor: rgba(58, 69, 85, 0.5),
|
||||
accountMainTextColor: #e0e0e0,
|
||||
accountOptionalTextColor: #556576,
|
||||
accountIndicatorTextColor: #111921,
|
||||
accountSwitchBackgroundColor: #000000,
|
||||
accountIndicatorBackgroundColor: #4db1ff,
|
||||
tabInactiveBackgroundColor: rgba(23, 31, 39, 0.5),
|
||||
tabHoverBackgroundColor: rgba(58, 69, 85, 0.5),
|
||||
tableBackgroundColor: #18202a,
|
||||
messageMyBackgroundColor: #2a3544,
|
||||
messageBuddyBackgroundColor: #18202a,
|
||||
|
|
@ -47,7 +52,7 @@ $themes: (
|
|||
),
|
||||
gray: (
|
||||
bodyBackgroundColor: #101417,
|
||||
sidebarBackgroundColor: rgba(23, 25, 27, 0.5),
|
||||
sidebarBackgroundColor: rgba(28, 30, 33, 0.5),
|
||||
sidebarBorderColor: #2e3337,
|
||||
onlineColor: #47cf8d,
|
||||
offlineColor: #ff5252,
|
||||
|
|
@ -59,26 +64,31 @@ $themes: (
|
|||
greenTextColor: #47cf8d,
|
||||
redTextColor: #fe5252,
|
||||
blueButtonBackgroundColor: #42a5f5,
|
||||
blueButtonHoverColor: #4dafff,
|
||||
blueButtonHoverColor: #86d6ff,
|
||||
blueButtonFocusColor: #5fb6fc,
|
||||
disabledButtonBackgroundColor: #79848f,
|
||||
disabledButtonHoverColor: #85909b,
|
||||
disabledButtonHoverColor: #a1aebb,
|
||||
disabledButtonFocusColor: #8a959f,
|
||||
greenButtonBackgroundColor: #47cf8d,
|
||||
greenButtonHoverColor: #49d993,
|
||||
greenButtonHoverColor: #7bf6c6,
|
||||
greenButtonFocusColor: #5cdc9e,
|
||||
turquoiseButtonBackgroundColor: #3ec5d7,
|
||||
turquoiseButtonHoverColor: #43cee0,
|
||||
turquoiseButtonHoverColor: #72edfe,
|
||||
turquoiseButtonFocusColor: #50d0e1,
|
||||
transparentButtonBorderColor: #2f3438,
|
||||
inputBackgroundColor: #292d31,
|
||||
selectHoverColor: rgba(70, 76, 81, 0.5),
|
||||
selectHoverColor: rgba(58, 62, 66, 0.5),
|
||||
selectSelectedColor: rgba(37, 40, 43, 0.5),
|
||||
switchBackgroundColor: #000000,
|
||||
accountBackgroundColor: rgba(37, 40, 43, 0.5),
|
||||
accountHoverBackgroundColor: rgba(70, 76, 81, 0.5),
|
||||
accountHoverBackgroundColor: rgba(58, 62, 66, 0.5),
|
||||
accountMainTextColor: #e0e0e0,
|
||||
accountOptionalTextColor: #565c62,
|
||||
accountIndicatorTextColor: #1a1a1a,
|
||||
accountSwitchBackgroundColor: #000000,
|
||||
accountIndicatorBackgroundColor: #42a5f5,
|
||||
tabInactiveBackgroundColor: rgba(23, 25, 27, 0.5),
|
||||
tabInactiveBackgroundColor: rgba(28, 30, 33, 0.5),
|
||||
tabHoverBackgroundColor: rgba(58, 62, 66, 0.5),
|
||||
tableBackgroundColor: #25292d,
|
||||
messageMyBackgroundColor: #30363c,
|
||||
messageBuddyBackgroundColor: #25292d,
|
||||
|
|
@ -105,13 +115,17 @@ $themes: (
|
|||
greenTextColor: #46c172,
|
||||
redTextColor: #ff5252,
|
||||
blueButtonBackgroundColor: #2c95f1,
|
||||
blueButtonHoverColor: #379ffa,
|
||||
blueButtonHoverColor: #5cb3ff,
|
||||
blueButtonFocusColor: #379ffa,
|
||||
disabledButtonBackgroundColor: #90a4ae,
|
||||
disabledButtonHoverColor: #9baeb7,
|
||||
disabledButtonHoverColor: #aebec6,
|
||||
disabledButtonFocusColor: #a7b9c2,
|
||||
greenButtonBackgroundColor: #46c172,
|
||||
greenButtonHoverColor: #46ca75,
|
||||
greenButtonHoverColor: #5ad586,
|
||||
greenButtonFocusColor: #53c77c,
|
||||
turquoiseButtonBackgroundColor: #26b6c7,
|
||||
turquoiseButtonHoverColor: #2bbdcf,
|
||||
turquoiseButtonHoverColor: #52cbd9,
|
||||
turquoiseButtonFocusColor: #31becf,
|
||||
transparentButtonBorderColor: #ebebeb,
|
||||
inputBackgroundColor: #e6e6e6,
|
||||
selectHoverColor: rgba(240, 240, 240, 0.5),
|
||||
|
|
@ -125,6 +139,7 @@ $themes: (
|
|||
accountSwitchBackgroundColor: #ffffff,
|
||||
accountIndicatorBackgroundColor: #ffffff,
|
||||
tabInactiveBackgroundColor: rgba(224, 224, 224, 0.5),
|
||||
tabHoverBackgroundColor: #ffffff,
|
||||
tableBackgroundColor: #ffffff,
|
||||
messageMyBackgroundColor: #fff,
|
||||
messageBuddyBackgroundColor: #ededed,
|
||||
|
|
|
|||
|
|
@ -76,6 +76,13 @@ app-wallet {
|
|||
background-color: themed(contentBackgroundColor);
|
||||
}
|
||||
}
|
||||
|
||||
&:hover:not(.active) {
|
||||
|
||||
@include themify($themes) {
|
||||
background-color: themed(tabHoverBackgroundColor);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
|
|
@ -104,11 +104,11 @@ export class ContractStatusMessagesPipe implements PipeTransform {
|
|||
return state.part1 + (state.part2.length ? '. ' + state.part2 : '');
|
||||
}
|
||||
|
||||
transform(item: any, args?: any): any {
|
||||
if (item.is_a) {
|
||||
return this.getStateBuyer(item.state);
|
||||
transform(state: number, is_a?: boolean): any {
|
||||
if (is_a) {
|
||||
return this.getStateBuyer(state);
|
||||
} else {
|
||||
return this.getStateSeller(item.state);
|
||||
return this.getStateSeller(state);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -13,9 +13,27 @@ export class BackendService {
|
|||
backendObject: any;
|
||||
backendLoaded = false;
|
||||
|
||||
constructor(private translate: TranslateService, private variablesService: VariablesService, private modalService: ModalService, private moneyToIntPipe: MoneyToIntPipe) {}
|
||||
constructor(
|
||||
private translate: TranslateService,
|
||||
private variablesService: VariablesService,
|
||||
private modalService: ModalService,
|
||||
private moneyToIntPipe: MoneyToIntPipe
|
||||
) {
|
||||
}
|
||||
|
||||
private Debug(type, message) {
|
||||
static bigNumberParser(key, val) {
|
||||
if (val.constructor.name === 'BigNumber' && ['balance', 'unlocked_balance', 'amount', 'fee', 'b_fee', 'to_pay', 'a_pledge', 'b_pledge', 'coast', 'a'].indexOf(key) === -1) {
|
||||
return val.toNumber();
|
||||
}
|
||||
if (key === 'rcv' || key === 'spn') {
|
||||
for (let i = 0; i < val.length; i++) {
|
||||
val[i] = new BigNumber(val[i]);
|
||||
}
|
||||
}
|
||||
return val;
|
||||
}
|
||||
|
||||
static Debug(type, message) {
|
||||
switch (type) {
|
||||
case 0:
|
||||
console.error(message);
|
||||
|
|
@ -112,13 +130,14 @@ export class BackendService {
|
|||
}
|
||||
}
|
||||
break;
|
||||
case 'NOT_FOUND': if (command !== 'open_wallet' && command !== 'get_alias_info_by_name' && command !== 'get_alias_info_by_address') {
|
||||
error_translate = this.translate.instant('ERRORS.FILE_NOT_FOUND');
|
||||
params = JSON.parse(params);
|
||||
if (params.path) {
|
||||
error_translate += ': ' + params.path;
|
||||
case 'NOT_FOUND':
|
||||
if (command !== 'open_wallet' && command !== 'get_alias_info_by_name' && command !== 'get_alias_info_by_address') {
|
||||
error_translate = this.translate.instant('ERRORS.FILE_NOT_FOUND');
|
||||
params = JSON.parse(params);
|
||||
if (params.path) {
|
||||
error_translate += ': ' + params.path;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
case 'CANCELED':
|
||||
case '':
|
||||
|
|
@ -142,36 +161,21 @@ export class BackendService {
|
|||
}
|
||||
}
|
||||
|
||||
private bigNumberParser(key, val) {
|
||||
if (val.constructor.name === 'BigNumber' && ['balance', 'unlocked_balance', 'amount', 'fee', 'b_fee', 'to_pay', 'a_pledge', 'b_pledge', 'coast', 'a'].indexOf(key) === -1) {
|
||||
return val.toNumber();
|
||||
}
|
||||
if (key === 'rcv' || key === 'spn') {
|
||||
for (let i = 0; i < val.length; i++) {
|
||||
val[i] = new BigNumber(val[i]);
|
||||
}
|
||||
}
|
||||
return val;
|
||||
}
|
||||
|
||||
private commandDebug(command, params, result) {
|
||||
this.Debug(2, '----------------- ' + command + ' -----------------');
|
||||
BackendService.Debug(2, '----------------- ' + command + ' -----------------');
|
||||
const debug = {
|
||||
_send_params: params,
|
||||
_result: result
|
||||
};
|
||||
this.Debug(2, debug);
|
||||
BackendService.Debug(2, debug);
|
||||
try {
|
||||
this.Debug(2, JSONBigNumber.parse(result, this.bigNumberParser));
|
||||
BackendService.Debug(2, JSONBigNumber.parse(result, BackendService.bigNumberParser));
|
||||
} catch (e) {
|
||||
this.Debug(2, {response_data: result, error_code: 'OK'});
|
||||
BackendService.Debug(2, {response_data: result, error_code: 'OK'});
|
||||
}
|
||||
}
|
||||
|
||||
private asVal(data) {
|
||||
return {v: data};
|
||||
}
|
||||
|
||||
private backendCallback(resultStr, params, callback, command) {
|
||||
let Result = resultStr;
|
||||
if (command !== 'get_clipboard') {
|
||||
|
|
@ -179,7 +183,7 @@ export class BackendService {
|
|||
Result = {};
|
||||
} else {
|
||||
try {
|
||||
Result = JSONBigNumber.parse(resultStr, this.bigNumberParser);
|
||||
Result = JSONBigNumber.parse(resultStr, BackendService.bigNumberParser);
|
||||
} catch (e) {
|
||||
Result = {response_data: resultStr, error_code: 'OK'};
|
||||
}
|
||||
|
|
@ -194,7 +198,7 @@ export class BackendService {
|
|||
const Status = (Result.error_code === 'OK' || Result.error_code === 'TRUE');
|
||||
|
||||
if (!Status && Status !== undefined && Result.error_code !== undefined) {
|
||||
this.Debug(1, 'API error for command: "' + command + '". Error code: ' + Result.error_code);
|
||||
BackendService.Debug(1, 'API error for command: "' + command + '". Error code: ' + Result.error_code);
|
||||
}
|
||||
const data = ((typeof Result === 'object') && 'response_data' in Result) ? Result.response_data : Result;
|
||||
|
||||
|
|
@ -220,7 +224,7 @@ export class BackendService {
|
|||
if (this.backendObject) {
|
||||
const Action = this.backendObject[command];
|
||||
if (!Action) {
|
||||
this.Debug(0, 'Run Command Error! Command "' + command + '" don\'t found in backendObject');
|
||||
BackendService.Debug(0, 'Run Command Error! Command "' + command + '" don\'t found in backendObject');
|
||||
} else {
|
||||
const that = this;
|
||||
params = (typeof params === 'string') ? params : JSONBigNumber.stringify(params);
|
||||
|
|
@ -245,7 +249,7 @@ export class BackendService {
|
|||
this.backendObject[command].connect(callback);
|
||||
} else {
|
||||
this.backendObject[command].connect((str) => {
|
||||
callback(JSONBigNumber.parse(str, this.bigNumberParser));
|
||||
callback(JSONBigNumber.parse(str, BackendService.bigNumberParser));
|
||||
});
|
||||
}
|
||||
}
|
||||
|
|
@ -285,6 +289,12 @@ export class BackendService {
|
|||
}
|
||||
|
||||
storeAppData(callback?) {
|
||||
if (this.variablesService.wallets.length) {
|
||||
this.variablesService.settings.wallets = [];
|
||||
this.variablesService.wallets.forEach((wallet) => {
|
||||
this.variablesService.settings.wallets.push({name: wallet.name, path: wallet.path});
|
||||
});
|
||||
}
|
||||
this.runCommand('store_app_data', this.variablesService.settings, callback);
|
||||
}
|
||||
|
||||
|
|
@ -292,10 +302,7 @@ export class BackendService {
|
|||
this.runCommand('get_secure_app_data', pass, callback);
|
||||
}
|
||||
|
||||
storeSecureAppData(callback) {
|
||||
if (this.variablesService.appPass === '') {
|
||||
return callback(false);
|
||||
}
|
||||
storeSecureAppData(callback?) {
|
||||
const wallets = [];
|
||||
this.variablesService.wallets.forEach((wallet) => {
|
||||
wallets.push({name: wallet.name, pass: wallet.pass, path: wallet.path});
|
||||
|
|
@ -305,6 +312,12 @@ export class BackendService {
|
|||
});
|
||||
}
|
||||
|
||||
dropSecureAppData(callback?) {
|
||||
this.backendObject['drop_secure_app_data']((dataStore) => {
|
||||
this.backendCallback(dataStore, {}, callback, 'drop_secure_app_data');
|
||||
});
|
||||
}
|
||||
|
||||
haveSecureAppData(callback) {
|
||||
this.runCommand('have_secure_app_data', {}, callback);
|
||||
}
|
||||
|
|
@ -346,7 +359,7 @@ export class BackendService {
|
|||
this.runCommand('open_wallet', params, callback);
|
||||
}
|
||||
|
||||
closeWallet(wallet_id, callback) {
|
||||
closeWallet(wallet_id, callback?) {
|
||||
this.runCommand('close_wallet', {wallet_id: +wallet_id}, callback);
|
||||
}
|
||||
|
||||
|
|
@ -354,7 +367,7 @@ export class BackendService {
|
|||
this.runCommand('get_smart_wallet_info', {wallet_id: +wallet_id}, callback);
|
||||
}
|
||||
|
||||
runWallet(wallet_id, callback) {
|
||||
runWallet(wallet_id, callback?) {
|
||||
this.runCommand('run_wallet', {wallet_id: +wallet_id}, callback);
|
||||
}
|
||||
|
||||
|
|
@ -418,7 +431,7 @@ export class BackendService {
|
|||
fee: this.variablesService.default_fee_big,
|
||||
b_fee: this.variablesService.default_fee_big
|
||||
};
|
||||
this.Debug(1, params);
|
||||
BackendService.Debug(1, params);
|
||||
this.runCommand('create_proposal', params, callback);
|
||||
}
|
||||
|
||||
|
|
@ -426,7 +439,7 @@ export class BackendService {
|
|||
const params = {
|
||||
wallet_id: parseInt(wallet_id, 10)
|
||||
};
|
||||
this.Debug(1, params);
|
||||
BackendService.Debug(1, params);
|
||||
this.runCommand('get_contracts', params, callback);
|
||||
}
|
||||
|
||||
|
|
@ -435,7 +448,7 @@ export class BackendService {
|
|||
wallet_id: parseInt(wallet_id, 10),
|
||||
contract_id: contract_id
|
||||
};
|
||||
this.Debug(1, params);
|
||||
BackendService.Debug(1, params);
|
||||
this.runCommand('accept_proposal', params, callback);
|
||||
}
|
||||
|
||||
|
|
@ -445,7 +458,7 @@ export class BackendService {
|
|||
contract_id: contract_id,
|
||||
release_type: release_type // "normal" or "burn"
|
||||
};
|
||||
this.Debug(1, params);
|
||||
BackendService.Debug(1, params);
|
||||
this.runCommand('release_contract', params, callback);
|
||||
}
|
||||
|
||||
|
|
@ -456,7 +469,7 @@ export class BackendService {
|
|||
fee: this.variablesService.default_fee_big,
|
||||
expiration_period: parseInt(time, 10) * 60 * 60
|
||||
};
|
||||
this.Debug(1, params);
|
||||
BackendService.Debug(1, params);
|
||||
this.runCommand('request_cancel_contract', params, callback);
|
||||
}
|
||||
|
||||
|
|
@ -465,7 +478,7 @@ export class BackendService {
|
|||
wallet_id: parseInt(wallet_id, 10),
|
||||
contract_id: contract_id
|
||||
};
|
||||
this.Debug(1, params);
|
||||
BackendService.Debug(1, params);
|
||||
this.runCommand('accept_cancel_contract', params, callback);
|
||||
}
|
||||
|
||||
|
|
@ -506,7 +519,7 @@ export class BackendService {
|
|||
this.runCommand('set_localization_strings', params, callback);
|
||||
}
|
||||
|
||||
registerAlias (wallet_id, alias, address, fee, comment, reward, callback) {
|
||||
registerAlias(wallet_id, alias, address, fee, comment, reward, callback) {
|
||||
const params = {
|
||||
wallet_id: wallet_id,
|
||||
alias: {
|
||||
|
|
@ -521,7 +534,7 @@ export class BackendService {
|
|||
this.runCommand('request_alias_registration', params, callback);
|
||||
}
|
||||
|
||||
updateAlias (wallet_id, alias, fee, callback) {
|
||||
updateAlias(wallet_id, alias, fee, callback) {
|
||||
const params = {
|
||||
wallet_id: wallet_id,
|
||||
alias: {
|
||||
|
|
@ -535,24 +548,24 @@ export class BackendService {
|
|||
this.runCommand('request_alias_update', params, callback);
|
||||
}
|
||||
|
||||
getAllAliases (callback) {
|
||||
getAllAliases(callback) {
|
||||
this.runCommand('get_all_aliases', {}, callback);
|
||||
}
|
||||
|
||||
getAliasByName (value, callback) {
|
||||
getAliasByName(value, callback) {
|
||||
return this.runCommand('get_alias_info_by_name', value, callback);
|
||||
}
|
||||
|
||||
getAliasByAddress (value, callback) {
|
||||
getAliasByAddress(value, callback) {
|
||||
return this.runCommand('get_alias_info_by_address', value, callback);
|
||||
}
|
||||
|
||||
getAliasCoast (alias, callback) {
|
||||
getAliasCoast(alias, callback) {
|
||||
this.runCommand('get_alias_coast', {v: alias}, callback);
|
||||
}
|
||||
|
||||
getWalletAlias(address) {
|
||||
if (address != null && this.variablesService.daemon_state === 2) {
|
||||
if (address !== null && this.variablesService.daemon_state === 2) {
|
||||
if (this.variablesService.aliasesChecked[address] == null) {
|
||||
this.variablesService.aliasesChecked[address] = {};
|
||||
if (this.variablesService.aliases.length) {
|
||||
|
|
|
|||
|
|
@ -13,6 +13,7 @@ export class VariablesService {
|
|||
|
||||
public digits = 12;
|
||||
public appPass = '';
|
||||
public appLogin = false;
|
||||
public moneyEquivalent = 0;
|
||||
public defaultTheme = 'dark';
|
||||
public defaultCurrency = 'ZAN';
|
||||
|
|
@ -35,7 +36,8 @@ export class VariablesService {
|
|||
language: 'en',
|
||||
default_path: '/',
|
||||
viewedContracts: [],
|
||||
notViewedContracts: []
|
||||
notViewedContracts: [],
|
||||
wallets: []
|
||||
};
|
||||
|
||||
public wallets: Array<Wallet> = [];
|
||||
|
|
@ -46,6 +48,7 @@ export class VariablesService {
|
|||
public maxWalletNameLength = 25;
|
||||
public maxCommentLength = 255;
|
||||
|
||||
getExpMedTsEvent = new BehaviorSubject(null);
|
||||
getHeightAppEvent = new BehaviorSubject(null);
|
||||
getRefreshStackingEvent = new BehaviorSubject(null);
|
||||
getAliasChangedEvent = new BehaviorSubject(null);
|
||||
|
|
@ -56,6 +59,7 @@ export class VariablesService {
|
|||
this.ngZone.run(() => {
|
||||
this.idle.stop();
|
||||
this.appPass = '';
|
||||
this.appLogin = false;
|
||||
this.router.navigate(['/login'], {queryParams: {type: 'auth'}});
|
||||
});
|
||||
});
|
||||
|
|
@ -67,6 +71,13 @@ export class VariablesService {
|
|||
constructor(private router: Router, private ngZone: NgZone, private contextMenuService: ContextMenuService) {
|
||||
}
|
||||
|
||||
setExpMedTs(timestamp: number) {
|
||||
if (timestamp !== this.exp_med_ts) {
|
||||
this.exp_med_ts = timestamp;
|
||||
this.getExpMedTsEvent.next(timestamp);
|
||||
}
|
||||
}
|
||||
|
||||
setHeightApp(height: number) {
|
||||
if (height !== this.height_app) {
|
||||
this.height_app = height;
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
<app-sidebar *ngIf="variablesService.appPass"></app-sidebar>
|
||||
<app-sidebar *ngIf="variablesService.appLogin"></app-sidebar>
|
||||
|
||||
<div class="app-content scrolled-content">
|
||||
<router-outlet *ngIf="[0, 1, 2].indexOf(variablesService.daemon_state) !== -1"></router-outlet>
|
||||
|
|
@ -24,3 +24,6 @@
|
|||
<ng-template contextMenuItem (execute)="contextMenuPaste($event.item)">{{ 'CONTEXT_MENU.PASTE' | translate }}</ng-template>
|
||||
<ng-template contextMenuItem (execute)="contextMenuSelect($event.item)">{{ 'CONTEXT_MENU.SELECT' | translate }}</ng-template>
|
||||
</context-menu>
|
||||
|
||||
|
||||
<app-open-wallet-modal *ngIf="needOpenWallets.length" [wallets]="needOpenWallets"></app-open-wallet-modal>
|
||||
|
|
|
|||
|
|
@ -17,9 +17,12 @@ import {ModalService} from './_helpers/services/modal.service';
|
|||
export class AppComponent implements OnInit, OnDestroy {
|
||||
|
||||
intervalUpdateContractsState;
|
||||
expMedTsEvent;
|
||||
onQuitRequest = false;
|
||||
firstOnlineState = false;
|
||||
|
||||
needOpenWallets = [];
|
||||
|
||||
@ViewChild('allContextMenu') public allContextMenu: ContextMenuComponent;
|
||||
@ViewChild('onlyCopyContextMenu') public onlyCopyContextMenu: ContextMenuComponent;
|
||||
|
||||
|
|
@ -75,8 +78,9 @@ export class AppComponent implements OnInit, OnDestroy {
|
|||
this.ngZone.run(() => {
|
||||
this.router.navigate(['/']);
|
||||
});
|
||||
this.needOpenWallets = [];
|
||||
this.variablesService.daemon_state = 5;
|
||||
this.backend.storeSecureAppData(() => {
|
||||
const saveFunction = () => {
|
||||
this.backend.storeAppData(() => {
|
||||
const recursionCloseWallets = () => {
|
||||
if (this.variablesService.wallets.length) {
|
||||
|
|
@ -91,7 +95,14 @@ export class AppComponent implements OnInit, OnDestroy {
|
|||
};
|
||||
recursionCloseWallets();
|
||||
});
|
||||
});
|
||||
};
|
||||
if (this.variablesService.appPass) {
|
||||
this.backend.storeSecureAppData(() => {
|
||||
saveFunction();
|
||||
});
|
||||
} else {
|
||||
saveFunction();
|
||||
}
|
||||
}
|
||||
this.onQuitRequest = true;
|
||||
});
|
||||
|
|
@ -144,7 +155,8 @@ export class AppComponent implements OnInit, OnDestroy {
|
|||
console.log('----------------- update_daemon_state -----------------');
|
||||
console.log('DAEMON:' + data.daemon_network_state);
|
||||
console.log(data);
|
||||
this.variablesService.exp_med_ts = data['expiration_median_timestamp'] + 600 + 1;
|
||||
// this.variablesService.exp_med_ts = data['expiration_median_timestamp'] + 600 + 1;
|
||||
this.variablesService.setExpMedTs(data['expiration_median_timestamp'] + 600 + 1);
|
||||
this.variablesService.last_build_available = data.last_build_available;
|
||||
this.variablesService.setHeightApp(data.height);
|
||||
|
||||
|
|
@ -386,7 +398,8 @@ export class AppComponent implements OnInit, OnDestroy {
|
|||
for (let i = 0, length = data.events.length; i < length; i++) {
|
||||
|
||||
switch (data.events[i].method) {
|
||||
case 'CORE_EVENT_BLOCK_ADDED': break;
|
||||
case 'CORE_EVENT_BLOCK_ADDED':
|
||||
break;
|
||||
case 'CORE_EVENT_ADD_ALIAS':
|
||||
if (this.variablesService.aliasesChecked[data.events[i].details.address] != null) {
|
||||
this.variablesService.aliasesChecked[data.events[i].details.address]['name'] = '@' + data.events[i].details.alias;
|
||||
|
|
@ -439,7 +452,8 @@ export class AppComponent implements OnInit, OnDestroy {
|
|||
}
|
||||
this.variablesService.changeAliases();
|
||||
break;
|
||||
default: break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -460,6 +474,22 @@ export class AppComponent implements OnInit, OnDestroy {
|
|||
});
|
||||
}, 30000);
|
||||
|
||||
this.expMedTsEvent = this.variablesService.getExpMedTsEvent.subscribe((newTimestamp: number) => {
|
||||
this.variablesService.wallets.forEach((wallet) => {
|
||||
wallet.contracts.forEach((contract) => {
|
||||
if (contract.state === 1 && contract.expiration_time <= newTimestamp) {
|
||||
contract.state = 110;
|
||||
contract.is_new = true;
|
||||
wallet.recountNewContracts();
|
||||
} else if (contract.state === 5 && contract.cancel_expiration_time <= newTimestamp) {
|
||||
contract.state = 130;
|
||||
contract.is_new = true;
|
||||
wallet.recountNewContracts();
|
||||
}
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
this.backend.getAppData((status, data) => {
|
||||
if (data && Object.keys(data).length > 0) {
|
||||
|
|
@ -490,9 +520,17 @@ export class AppComponent implements OnInit, OnDestroy {
|
|||
this.router.navigate(['/login'], {queryParams: {type: 'auth'}});
|
||||
});
|
||||
} else {
|
||||
this.ngZone.run(() => {
|
||||
this.router.navigate(['/login'], {queryParams: {type: 'reg'}});
|
||||
});
|
||||
if (Object.keys(data).length !== 0) {
|
||||
this.needOpenWallets = JSON.parse(JSON.stringify(this.variablesService.settings.wallets));
|
||||
this.ngZone.run(() => {
|
||||
this.variablesService.appLogin = true;
|
||||
this.router.navigate(['/']);
|
||||
});
|
||||
} else {
|
||||
this.ngZone.run(() => {
|
||||
this.router.navigate(['/login'], {queryParams: {type: 'reg'}});
|
||||
});
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
|
@ -521,6 +559,9 @@ export class AppComponent implements OnInit, OnDestroy {
|
|||
|
||||
getAliases() {
|
||||
this.backend.getAllAliases((status, data, error) => {
|
||||
|
||||
console.warn(error);
|
||||
|
||||
if (error === 'CORE_BUSY') {
|
||||
window.setTimeout(() => {
|
||||
this.getAliases();
|
||||
|
|
@ -528,6 +569,9 @@ export class AppComponent implements OnInit, OnDestroy {
|
|||
} else if (error === 'OVERFLOW') {
|
||||
this.variablesService.aliases = [];
|
||||
this.variablesService.enableAliasSearch = false;
|
||||
this.variablesService.wallets.forEach(wallet => {
|
||||
wallet.alias = this.backend.getWalletAlias(wallet.address);
|
||||
});
|
||||
} else {
|
||||
this.variablesService.enableAliasSearch = true;
|
||||
if (data.aliases && data.aliases.length) {
|
||||
|
|
@ -544,10 +588,18 @@ export class AppComponent implements OnInit, OnDestroy {
|
|||
wallet.alias = this.backend.getWalletAlias(wallet.address);
|
||||
});
|
||||
this.variablesService.aliases = this.variablesService.aliases.sort((a, b) => {
|
||||
if (a.name.length > b.name.length) return 1;
|
||||
if (a.name.length < b.name.length) return -1;
|
||||
if (a.name > b.name) return 1;
|
||||
if (a.name < b.name) return -1;
|
||||
if (a.name.length > b.name.length) {
|
||||
return 1;
|
||||
}
|
||||
if (a.name.length < b.name.length) {
|
||||
return -1;
|
||||
}
|
||||
if (a.name > b.name) {
|
||||
return 1;
|
||||
}
|
||||
if (a.name < b.name) {
|
||||
return -1;
|
||||
}
|
||||
return 0;
|
||||
});
|
||||
this.variablesService.changeAliases();
|
||||
|
|
@ -608,6 +660,7 @@ export class AppComponent implements OnInit, OnDestroy {
|
|||
if (this.intervalUpdateContractsState) {
|
||||
clearInterval(this.intervalUpdateContractsState);
|
||||
}
|
||||
this.expMedTsEvent.unsubscribe();
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
|||
|
|
@ -10,6 +10,7 @@ import { SidebarComponent } from './sidebar/sidebar.component';
|
|||
import { MainComponent } from './main/main.component';
|
||||
import { CreateWalletComponent } from './create-wallet/create-wallet.component';
|
||||
import { OpenWalletComponent } from './open-wallet/open-wallet.component';
|
||||
import { OpenWalletModalComponent } from './open-wallet-modal/open-wallet-modal.component';
|
||||
import { RestoreWalletComponent } from './restore-wallet/restore-wallet.component';
|
||||
import { SeedPhraseComponent } from './seed-phrase/seed-phrase.component';
|
||||
import { WalletDetailsComponent } from './wallet-details/wallet-details.component';
|
||||
|
|
@ -73,6 +74,7 @@ Highcharts.setOptions({
|
|||
MainComponent,
|
||||
CreateWalletComponent,
|
||||
OpenWalletComponent,
|
||||
OpenWalletModalComponent,
|
||||
RestoreWalletComponent,
|
||||
SeedPhraseComponent,
|
||||
WalletDetailsComponent,
|
||||
|
|
|
|||
|
|
@ -31,8 +31,8 @@
|
|||
<div>{{item.private_detailes.to_pay | intToMoney}} {{variablesService.defaultCurrency}}</div>
|
||||
</td>
|
||||
<td>
|
||||
<div class="status" [class.error-text]="item.state === 4" tooltip="{{ item | contractStatusMessages }}" placement="top" tooltipClass="table-tooltip" [delay]="500">
|
||||
{{item | contractStatusMessages}}
|
||||
<div class="status" [class.error-text]="item.state === 4" tooltip="{{item.state | contractStatusMessages : item.is_a}}" placement="top" tooltipClass="table-tooltip" [delay]="500">
|
||||
{{item.state | contractStatusMessages : item.is_a}}
|
||||
</div>
|
||||
</td>
|
||||
<td>
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
import {Component, OnInit, OnDestroy} from '@angular/core';
|
||||
import {ActivatedRoute, Router} from '@angular/router';
|
||||
import {ActivatedRoute} from '@angular/router';
|
||||
import {VariablesService} from '../_helpers/services/variables.service';
|
||||
|
||||
@Component({
|
||||
|
|
@ -14,8 +14,7 @@ export class ContractsComponent implements OnInit, OnDestroy {
|
|||
|
||||
constructor(
|
||||
private route: ActivatedRoute,
|
||||
private router: Router,
|
||||
private variablesService: VariablesService
|
||||
public variablesService: VariablesService
|
||||
) {
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -77,6 +77,7 @@ export class CreateWalletComponent implements OnInit {
|
|||
generate_data['wi'].mined_total,
|
||||
generate_data['wi'].tracking_hey
|
||||
);
|
||||
this.variablesService.opening_wallet.alias = this.backend.getWalletAlias(generate_data['wi'].address);
|
||||
this.ngZone.run(() => {
|
||||
this.walletSaved = true;
|
||||
this.progressWidth = '50%';
|
||||
|
|
|
|||
|
|
@ -9,21 +9,11 @@
|
|||
<div class="input-block">
|
||||
<label for="master-pass">{{ 'LOGIN.SETUP_MASTER_PASS' | translate }}</label>
|
||||
<input type="password" id="master-pass" formControlName="password" (contextmenu)="variablesService.onContextMenuPasteSelect($event)">
|
||||
<div class="error-block" *ngIf="regForm.controls['password'].invalid && (regForm.controls['password'].dirty || regForm.controls['password'].touched)">
|
||||
<div *ngIf="regForm.controls['password'].errors['required']">
|
||||
{{ 'LOGIN.FORM_ERRORS.PASS_REQUIRED' | translate }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="input-block">
|
||||
<label for="confirm-pass">{{ 'LOGIN.SETUP_CONFIRM_PASS' | translate }}</label>
|
||||
<input type="password" id="confirm-pass" formControlName="confirmation" (contextmenu)="variablesService.onContextMenuPasteSelect($event)">
|
||||
<div class="error-block" *ngIf="regForm.controls['confirmation'].invalid && (regForm.controls['confirmation'].dirty || regForm.controls['confirmation'].touched)">
|
||||
<div *ngIf="regForm.controls['confirmation'].errors['required']">
|
||||
{{ 'LOGIN.FORM_ERRORS.CONFIRM_REQUIRED' | translate }}
|
||||
</div>
|
||||
</div>
|
||||
<div class="error-block" *ngIf="regForm.controls['password'].dirty && regForm.controls['confirmation'].dirty && regForm.errors">
|
||||
<div *ngIf="regForm.errors['mismatch']">
|
||||
{{ 'LOGIN.FORM_ERRORS.MISMATCH' | translate }}
|
||||
|
|
@ -31,7 +21,10 @@
|
|||
</div>
|
||||
</div>
|
||||
|
||||
<button type="submit" class="blue-button">{{ 'LOGIN.BUTTON_NEXT' | translate }}</button>
|
||||
<div class="wrap-button">
|
||||
<button type="submit" class="blue-button" [disabled]="!regForm.controls['password'].value.length || !regForm.controls['confirmation'].value.length || (regForm.errors && regForm.errors['mismatch'])">{{ 'LOGIN.BUTTON_NEXT' | translate }}</button>
|
||||
<button type="button" class="blue-button" (click)="onSkipCreatePass()" [disabled]="regForm.controls['password'].value.length || regForm.controls['confirmation'].value.length">{{ 'LOGIN.BUTTON_SKIP' | translate }}</button>
|
||||
</div>
|
||||
|
||||
</form>
|
||||
|
||||
|
|
@ -40,11 +33,6 @@
|
|||
<div class="input-block">
|
||||
<label for="master-pass-login">{{ 'LOGIN.MASTER_PASS' | translate }}</label>
|
||||
<input type="password" id="master-pass-login" formControlName="password" autofocus (contextmenu)="variablesService.onContextMenuPasteSelect($event)">
|
||||
<div class="error-block" *ngIf="authForm.controls['password'].invalid && (authForm.controls['password'].dirty || authForm.controls['password'].touched)">
|
||||
<div *ngIf="authForm.controls['password'].errors['required']">
|
||||
{{ 'LOGIN.FORM_ERRORS.PASS_REQUIRED' | translate }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<button type="submit" class="blue-button">{{ 'LOGIN.BUTTON_NEXT' | translate }}</button>
|
||||
|
|
|
|||
|
|
@ -16,13 +16,23 @@
|
|||
.logo {
|
||||
background: url(../../assets/icons/logo.svg) no-repeat center;
|
||||
width: 100%;
|
||||
height: 20rem;
|
||||
height: 15rem;
|
||||
}
|
||||
|
||||
.form-login {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
|
||||
.wrap-button {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: space-between;
|
||||
|
||||
button {
|
||||
margin: 2.5rem 0;
|
||||
}
|
||||
}
|
||||
|
||||
button {
|
||||
margin: 2.5rem auto;
|
||||
width: 100%;
|
||||
|
|
|
|||
|
|
@ -16,14 +16,14 @@ export class LoginComponent implements OnInit, OnDestroy {
|
|||
queryRouting;
|
||||
|
||||
regForm = new FormGroup({
|
||||
password: new FormControl('', Validators.required),
|
||||
confirmation: new FormControl('', Validators.required)
|
||||
password: new FormControl(''),
|
||||
confirmation: new FormControl('')
|
||||
}, function (g: FormGroup) {
|
||||
return g.get('password').value === g.get('confirmation').value ? null : {'mismatch': true};
|
||||
});
|
||||
|
||||
authForm = new FormGroup({
|
||||
password: new FormControl('', Validators.required)
|
||||
password: new FormControl('')
|
||||
});
|
||||
|
||||
type = 'reg';
|
||||
|
|
@ -32,7 +32,7 @@ export class LoginComponent implements OnInit, OnDestroy {
|
|||
private route: ActivatedRoute,
|
||||
private router: Router,
|
||||
private backend: BackendService,
|
||||
private variablesService: VariablesService,
|
||||
public variablesService: VariablesService,
|
||||
private modalService: ModalService,
|
||||
private ngZone: NgZone
|
||||
) {
|
||||
|
|
@ -51,6 +51,8 @@ export class LoginComponent implements OnInit, OnDestroy {
|
|||
this.variablesService.appPass = this.regForm.get('password').value;
|
||||
this.backend.storeSecureAppData((status, data) => {
|
||||
if (status) {
|
||||
this.variablesService.appLogin = true;
|
||||
this.variablesService.startCountdown();
|
||||
this.ngZone.run(() => {
|
||||
this.router.navigate(['/']);
|
||||
});
|
||||
|
|
@ -61,11 +63,20 @@ export class LoginComponent implements OnInit, OnDestroy {
|
|||
}
|
||||
}
|
||||
|
||||
onSkipCreatePass(): void {
|
||||
this.variablesService.appPass = '';
|
||||
this.ngZone.run(() => {
|
||||
this.variablesService.appLogin = true;
|
||||
this.router.navigate(['/']);
|
||||
});
|
||||
}
|
||||
|
||||
onSubmitAuthPass(): void {
|
||||
if (this.authForm.valid) {
|
||||
const appPass = this.authForm.get('password').value;
|
||||
this.backend.getSecureAppData({pass: appPass}, (status, data) => {
|
||||
if (!data.error_code) {
|
||||
this.variablesService.appLogin = true;
|
||||
this.variablesService.startCountdown();
|
||||
this.variablesService.appPass = appPass;
|
||||
if (this.variablesService.wallets.length) {
|
||||
|
|
|
|||
|
|
@ -0,0 +1,18 @@
|
|||
<div class="modal">
|
||||
<h3 class="title">{{ 'OPEN_WALLET.MODAL.TITLE' | translate }}</h3>
|
||||
<form class="open-form" (ngSubmit)="openWallet()">
|
||||
<div class="wallet-path">{{ wallet.name }}</div>
|
||||
<div class="wallet-path">{{ wallet.path }}</div>
|
||||
<div class="input-block" *ngIf="!wallet.notFound && !wallet.emptyPass">
|
||||
<label for="password">{{ 'OPEN_WALLET.MODAL.LABEL' | translate }}</label>
|
||||
<input type="password" id="password" name="password" [(ngModel)]="wallet.pass" (contextmenu)="variablesService.onContextMenuPasteSelect($event)"/>
|
||||
</div>
|
||||
<div class="error-block" *ngIf="wallet.notFound">
|
||||
{{ 'OPEN_WALLET.MODAL.NOT_FOUND' | translate }}
|
||||
</div>
|
||||
<div class="wrap-button">
|
||||
<button type="submit" class="blue-button" [disabled]="wallet.notFound">{{ 'OPEN_WALLET.MODAL.OPEN' | translate }}</button>
|
||||
<button type="button" class="blue-button" (click)="skipWallet()">{{ 'OPEN_WALLET.MODAL.SKIP' | translate }}</button>
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
|
|
@ -0,0 +1,45 @@
|
|||
:host {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
background: rgba(255, 255, 255, 0.25);
|
||||
}
|
||||
|
||||
.modal {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
background-position: center;
|
||||
background-size: 200%;
|
||||
padding: 2rem;
|
||||
width: 34rem;
|
||||
|
||||
.title {
|
||||
font-size: 1.8rem;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.open-form {
|
||||
|
||||
.wallet-path {
|
||||
font-size: 1.3rem;
|
||||
margin: 5rem 0 2rem;
|
||||
}
|
||||
|
||||
.wrap-button {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: space-between;
|
||||
margin: 2rem -2rem 0;
|
||||
|
||||
button {
|
||||
flex: 1 0 0;
|
||||
margin: 0 2rem ;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,25 @@
|
|||
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
|
||||
|
||||
import { OpenWalletModalComponent } from './open-wallet-modal.component';
|
||||
|
||||
describe('OpenWalletModalComponent', () => {
|
||||
let component: OpenWalletModalComponent;
|
||||
let fixture: ComponentFixture<OpenWalletModalComponent>;
|
||||
|
||||
beforeEach(async(() => {
|
||||
TestBed.configureTestingModule({
|
||||
declarations: [ OpenWalletModalComponent ]
|
||||
})
|
||||
.compileComponents();
|
||||
}));
|
||||
|
||||
beforeEach(() => {
|
||||
fixture = TestBed.createComponent(OpenWalletModalComponent);
|
||||
component = fixture.componentInstance;
|
||||
fixture.detectChanges();
|
||||
});
|
||||
|
||||
it('should create', () => {
|
||||
expect(component).toBeTruthy();
|
||||
});
|
||||
});
|
||||
|
|
@ -0,0 +1,121 @@
|
|||
import {Component, OnInit, Input, NgZone} from '@angular/core';
|
||||
import {VariablesService} from '../_helpers/services/variables.service';
|
||||
import {Wallet} from '../_helpers/models/wallet.model';
|
||||
import {BackendService} from '../_helpers/services/backend.service';
|
||||
import {TranslateService} from '@ngx-translate/core';
|
||||
import {ModalService} from '../_helpers/services/modal.service';
|
||||
|
||||
@Component({
|
||||
selector: 'app-open-wallet-modal',
|
||||
templateUrl: './open-wallet-modal.component.html',
|
||||
styleUrls: ['./open-wallet-modal.component.scss']
|
||||
})
|
||||
export class OpenWalletModalComponent implements OnInit {
|
||||
|
||||
@Input() wallets;
|
||||
|
||||
wallet = {
|
||||
name: '',
|
||||
path: '',
|
||||
pass: '',
|
||||
notFound: false,
|
||||
emptyPass: false
|
||||
};
|
||||
|
||||
constructor(
|
||||
public variablesService: VariablesService,
|
||||
private backend: BackendService,
|
||||
private translate: TranslateService,
|
||||
private modalService: ModalService,
|
||||
private ngZone: NgZone,
|
||||
) {
|
||||
}
|
||||
|
||||
ngOnInit() {
|
||||
if (this.wallets.length) {
|
||||
this.wallet = this.wallets[0];
|
||||
this.wallet.pass = '';
|
||||
|
||||
this.backend.openWallet(this.wallet.path, '', true, (status, data, error) => {
|
||||
if (error === 'FILE_NOT_FOUND') {
|
||||
this.wallet.notFound = true;
|
||||
}
|
||||
if (status) {
|
||||
this.wallet.pass = '';
|
||||
this.wallet.emptyPass = true;
|
||||
this.backend.closeWallet(data.wallet_id);
|
||||
this.openWallet();
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
openWallet() {
|
||||
if (this.wallets.length === 0) {
|
||||
return;
|
||||
}
|
||||
this.backend.openWallet(this.wallet.path, this.wallet.pass, false, (open_status, open_data, open_error) => {
|
||||
if (open_error && open_error === 'FILE_NOT_FOUND') {
|
||||
let error_translate = this.translate.instant('OPEN_WALLET.FILE_NOT_FOUND1');
|
||||
error_translate += ':<br>' + this.wallet.path;
|
||||
error_translate += this.translate.instant('OPEN_WALLET.FILE_NOT_FOUND2');
|
||||
this.modalService.prepareModal('error', error_translate);
|
||||
} else {
|
||||
if (open_status || open_error === 'FILE_RESTORED') {
|
||||
|
||||
let exists = false;
|
||||
this.variablesService.wallets.forEach((wallet) => {
|
||||
if (wallet.address === open_data['wi'].address) {
|
||||
exists = true;
|
||||
}
|
||||
});
|
||||
|
||||
if (exists) {
|
||||
this.modalService.prepareModal('error', 'OPEN_WALLET.WITH_ADDRESS_ALREADY_OPEN');
|
||||
this.backend.closeWallet(open_data.wallet_id);
|
||||
} else {
|
||||
const new_wallet = new Wallet(
|
||||
open_data.wallet_id,
|
||||
this.wallet.name,
|
||||
this.wallet.pass,
|
||||
open_data['wi'].path,
|
||||
open_data['wi'].address,
|
||||
open_data['wi'].balance,
|
||||
open_data['wi'].unlocked_balance,
|
||||
open_data['wi'].mined_total,
|
||||
open_data['wi'].tracking_hey
|
||||
);
|
||||
new_wallet.alias = this.backend.getWalletAlias(new_wallet.address);
|
||||
if (open_data.recent_history && open_data.recent_history.history) {
|
||||
new_wallet.prepareHistory(open_data.recent_history.history);
|
||||
}
|
||||
this.backend.getContracts(open_data.wallet_id, (contracts_status, contracts_data) => {
|
||||
if (contracts_status && contracts_data.hasOwnProperty('contracts')) {
|
||||
this.ngZone.run(() => {
|
||||
new_wallet.prepareContractsAfterOpen(
|
||||
contracts_data.contracts,
|
||||
this.variablesService.exp_med_ts,
|
||||
this.variablesService.height_app,
|
||||
this.variablesService.settings.viewedContracts,
|
||||
this.variablesService.settings.notViewedContracts
|
||||
);
|
||||
});
|
||||
}
|
||||
});
|
||||
this.variablesService.wallets.push(new_wallet);
|
||||
this.backend.runWallet(open_data.wallet_id);
|
||||
this.skipWallet();
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
skipWallet() {
|
||||
if (this.wallets.length) {
|
||||
this.wallets.splice(0, 1);
|
||||
this.ngOnInit();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -110,9 +110,9 @@ export class OpenWalletComponent implements OnInit, OnDestroy {
|
|||
this.variablesService.wallets.push(new_wallet);
|
||||
this.backend.runWallet(open_data.wallet_id, (run_status, run_data) => {
|
||||
if (run_status) {
|
||||
this.backend.storeSecureAppData((status, data) => {
|
||||
console.log('Store App Data', status, data);
|
||||
});
|
||||
if (this.variablesService.appPass) {
|
||||
this.backend.storeSecureAppData();
|
||||
}
|
||||
this.ngZone.run(() => {
|
||||
this.router.navigate(['/wallet/' + open_data.wallet_id]);
|
||||
});
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
import {Component, NgZone, OnDestroy, OnInit} from '@angular/core';
|
||||
import {Location} from "@angular/common";
|
||||
import {Location} from '@angular/common';
|
||||
import {BackendService} from '../_helpers/services/backend.service';
|
||||
import {ActivatedRoute, Router} from '@angular/router';
|
||||
import {VariablesService} from '../_helpers/services/variables.service';
|
||||
|
|
@ -52,9 +52,9 @@ export class SeedPhraseComponent implements OnInit, OnDestroy {
|
|||
this.backend.runWallet(this.wallet_id, (run_status, run_data) => {
|
||||
if (run_status) {
|
||||
this.variablesService.wallets.push(this.variablesService.opening_wallet);
|
||||
this.backend.storeSecureAppData((status, data) => {
|
||||
console.log('Store App Data', status, data);
|
||||
});
|
||||
if (this.variablesService.appPass) {
|
||||
this.backend.storeSecureAppData();
|
||||
}
|
||||
this.ngZone.run(() => {
|
||||
this.router.navigate(['/wallet/' + this.wallet_id]);
|
||||
});
|
||||
|
|
|
|||
|
|
@ -54,14 +54,9 @@
|
|||
|
||||
<span class="master-password-title">{{ 'SETTINGS.MASTER_PASSWORD.TITLE' | translate }}</span>
|
||||
|
||||
<div class="input-block">
|
||||
<div class="input-block" *ngIf="variablesService.appPass">
|
||||
<label for="old-password">{{ 'SETTINGS.MASTER_PASSWORD.OLD' | translate }}</label>
|
||||
<input type="password" id="old-password" formControlName="password" (contextmenu)="variablesService.onContextMenuPasteSelect($event)"/>
|
||||
<div class="error-block" *ngIf="changeForm.controls['password'].invalid && (changeForm.controls['password'].dirty || changeForm.controls['password'].touched)">
|
||||
<div *ngIf="changeForm.controls['password'].errors['required']">
|
||||
{{ 'SETTINGS.FORM_ERRORS.PASS_REQUIRED' | translate }}
|
||||
</div>
|
||||
</div>
|
||||
<div class="error-block" *ngIf="changeForm.invalid && changeForm.controls['password'].valid && (changeForm.controls['password'].dirty || changeForm.controls['password'].touched) && changeForm.errors && changeForm.errors.pass_mismatch">
|
||||
{{ 'SETTINGS.FORM_ERRORS.PASS_NOT_MATCH' | translate }}
|
||||
</div>
|
||||
|
|
@ -70,21 +65,11 @@
|
|||
<div class="input-block">
|
||||
<label for="new-password">{{ 'SETTINGS.MASTER_PASSWORD.NEW' | translate }}</label>
|
||||
<input type="password" id="new-password" formControlName="new_password" (contextmenu)="variablesService.onContextMenuPasteSelect($event)"/>
|
||||
<div class="error-block" *ngIf="changeForm.controls['new_password'].invalid && (changeForm.controls['new_password'].dirty || changeForm.controls['new_password'].touched)">
|
||||
<div *ngIf="changeForm.controls['new_password'].errors['required']">
|
||||
{{ 'SETTINGS.FORM_ERRORS.PASS_REQUIRED' | translate }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="input-block">
|
||||
<label for="confirm-password">{{ 'SETTINGS.MASTER_PASSWORD.CONFIRM' | translate }}</label>
|
||||
<input type="password" id="confirm-password" formControlName="new_confirmation" (contextmenu)="variablesService.onContextMenuPasteSelect($event)"/>
|
||||
<div class="error-block" *ngIf="changeForm.controls['new_confirmation'].invalid && (changeForm.controls['new_confirmation'].dirty || changeForm.controls['new_confirmation'].touched)">
|
||||
<div *ngIf="changeForm.controls['new_confirmation'].errors['required']">
|
||||
{{ 'SETTINGS.FORM_ERRORS.PASS_REQUIRED' | translate }}
|
||||
</div>
|
||||
</div>
|
||||
<div class="error-block" *ngIf="changeForm.invalid && (changeForm.controls['new_confirmation'].dirty || changeForm.controls['new_confirmation'].touched) && changeForm.errors && changeForm.errors.confirm_mismatch">
|
||||
{{ 'SETTINGS.FORM_ERRORS.CONFIRM_NOT_MATCH' | translate }}
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
import {Component, NgZone, OnInit, Renderer2} from '@angular/core';
|
||||
import {VariablesService} from '../_helpers/services/variables.service';
|
||||
import {BackendService} from '../_helpers/services/backend.service';
|
||||
import {FormControl, FormGroup, Validators} from '@angular/forms';
|
||||
import {FormControl, FormGroup} from '@angular/forms';
|
||||
import {Location} from '@angular/common';
|
||||
|
||||
@Component({
|
||||
|
|
@ -63,13 +63,16 @@ export class SettingsComponent implements OnInit {
|
|||
this.theme = this.variablesService.settings.theme;
|
||||
this.scale = this.variablesService.settings.scale;
|
||||
this.changeForm = new FormGroup({
|
||||
password: new FormControl('', Validators.required),
|
||||
new_password: new FormControl('', Validators.required),
|
||||
new_confirmation: new FormControl('', Validators.required)
|
||||
password: new FormControl(''),
|
||||
new_password: new FormControl(''),
|
||||
new_confirmation: new FormControl('')
|
||||
}, [(g: FormGroup) => {
|
||||
return g.get('new_password').value === g.get('new_confirmation').value ? null : {'confirm_mismatch': true};
|
||||
}, (g: FormGroup) => {
|
||||
return g.get('password').value === this.variablesService.appPass ? null : {'pass_mismatch': true};
|
||||
if (this.variablesService.appPass) {
|
||||
return g.get('password').value === this.variablesService.appPass ? null : {'pass_mismatch': true};
|
||||
}
|
||||
return null;
|
||||
}]);
|
||||
}
|
||||
|
||||
|
|
@ -99,18 +102,19 @@ export class SettingsComponent implements OnInit {
|
|||
onSubmitChangePass() {
|
||||
if (this.changeForm.valid) {
|
||||
this.variablesService.appPass = this.changeForm.get('new_password').value;
|
||||
this.backend.storeSecureAppData((status, data) => {
|
||||
if (status) {
|
||||
this.changeForm.reset();
|
||||
} else {
|
||||
console.log(data);
|
||||
}
|
||||
});
|
||||
if (this.variablesService.appPass) {
|
||||
this.backend.storeSecureAppData();
|
||||
} else {
|
||||
this.backend.dropSecureAppData();
|
||||
}
|
||||
this.changeForm.reset();
|
||||
}
|
||||
}
|
||||
|
||||
onLockChange() {
|
||||
this.variablesService.restartCountdown();
|
||||
if (this.variablesService.appLogin) {
|
||||
this.variablesService.restartCountdown();
|
||||
}
|
||||
this.backend.storeAppData();
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -9,13 +9,13 @@
|
|||
<span class="balance">{{wallet.balance | intToMoney : '3' }} {{variablesService.defaultCurrency}}</span>
|
||||
</div>
|
||||
<div class="sidebar-account-row account-alias">
|
||||
<div style="display: flex; align-items: center;">
|
||||
<span>{{wallet.alias['name']}}</span>
|
||||
<div class="name">
|
||||
<span tooltip="{{wallet.alias['name']}}" placement="top-left" tooltipClass="table-tooltip account-tooltip" [delay]="500" [showWhenNoOverflow]="false">{{wallet.alias['name']}}</span>
|
||||
<ng-container *ngIf="wallet.alias['comment'] && wallet.alias['comment'].length">
|
||||
<i class="icon comment" tooltip="{{wallet.alias['comment']}}" placement="top" tooltipClass="table-tooltip account-tooltip" [delay]="500"></i>
|
||||
</ng-container>
|
||||
</div>
|
||||
<span>$ {{wallet.getMoneyEquivalent(variablesService.moneyEquivalent) | intToMoney | number : '1.2-2'}}</span>
|
||||
<span class="price">$ {{wallet.getMoneyEquivalent(variablesService.moneyEquivalent) | intToMoney | number : '1.2-2'}}</span>
|
||||
</div>
|
||||
<div class="sidebar-account-row account-staking" *ngIf="!(!wallet.loaded && variablesService.daemon_state === 2)">
|
||||
<span class="text">{{ 'SIDEBAR.ACCOUNT.STAKING' | translate }}</span>
|
||||
|
|
|
|||
|
|
@ -72,6 +72,25 @@
|
|||
line-height: 3.4rem;
|
||||
margin-bottom: 0.7rem;
|
||||
|
||||
.name {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
flex-shrink: 1;
|
||||
line-height: 1.6rem;
|
||||
padding-right: 1rem;
|
||||
overflow: hidden;
|
||||
|
||||
span {
|
||||
text-overflow: ellipsis;
|
||||
overflow: hidden;
|
||||
white-space: nowrap;
|
||||
}
|
||||
}
|
||||
|
||||
.price {
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.icon {
|
||||
margin-left: 0.5rem;
|
||||
width: 1.2rem;
|
||||
|
|
|
|||
|
|
@ -49,6 +49,7 @@ export class SidebarComponent implements OnInit, OnDestroy {
|
|||
|
||||
logOut() {
|
||||
this.variablesService.stopCountdown();
|
||||
this.variablesService.appLogin = false;
|
||||
this.variablesService.appPass = '';
|
||||
this.ngZone.run(() => {
|
||||
this.router.navigate(['/login'], {queryParams: {type: 'auth'}});
|
||||
|
|
|
|||
|
|
@ -16,9 +16,7 @@
|
|||
</div>
|
||||
</div>
|
||||
<div class="selected" *ngIf="selectedDate && selectedDate.date">
|
||||
<span *ngIf="currentPeriod === '1 day'">{{selectedDate.date | date : 'HH:00 - HH:59, MMM. EEEE, dd, yyyy'}}</span>
|
||||
<span *ngIf="currentPeriod === 'All'">{{selectedDate.date | date : 'HH:mm, MMM. EEEE, dd, yyyy'}}</span>
|
||||
<span *ngIf="!(currentPeriod === '1 day' || currentPeriod === 'All')">{{selectedDate.date | date : 'MMM. EEEE, dd, yyyy'}}</span>
|
||||
<span>{{selectedDate.date | date : 'MMM. EEEE, dd, yyyy'}}</span>
|
||||
<span>{{selectedDate.amount}} {{variablesService.defaultCurrency}}</span>
|
||||
</div>
|
||||
</div>
|
||||
|
|
@ -36,4 +34,13 @@
|
|||
<button type="button" [class.active]="period.active" (click)="changePeriod(period)">{{period.title}}</button>
|
||||
</ng-container>
|
||||
</div>
|
||||
|
||||
<div class="title">
|
||||
{{ 'STAKING.TITLE_GROUP' | translate }}
|
||||
</div>
|
||||
<div class="options">
|
||||
<ng-container *ngFor="let group of groups">
|
||||
<button type="button" [class.active]="group.active" (click)="changeGroup(group)">{{group.title}}</button>
|
||||
</ng-container>
|
||||
</div>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -64,7 +64,11 @@
|
|||
|
||||
.title {
|
||||
font-size: 1.3rem;
|
||||
width: 9rem;
|
||||
padding: 0 1rem;
|
||||
|
||||
&:first-child{
|
||||
padding-left: 0;
|
||||
}
|
||||
}
|
||||
|
||||
.options {
|
||||
|
|
|
|||
|
|
@ -20,32 +20,60 @@ export class StakingComponent implements OnInit, OnDestroy {
|
|||
|
||||
periods = [
|
||||
{
|
||||
title: this.translate.instant('STAKING.DAY'),
|
||||
key: '1 day',
|
||||
active: false
|
||||
},
|
||||
{
|
||||
title: this.translate.instant('STAKING.WEEK'),
|
||||
title: this.translate.instant('STAKING.PERIOD.WEEK1'),
|
||||
key: '1 week',
|
||||
active: false
|
||||
},
|
||||
{
|
||||
title: this.translate.instant('STAKING.MONTH'),
|
||||
title: this.translate.instant('STAKING.PERIOD.WEEK2'),
|
||||
key: '2 week',
|
||||
active: false
|
||||
},
|
||||
{
|
||||
title: this.translate.instant('STAKING.PERIOD.MONTH1'),
|
||||
key: '1 month',
|
||||
active: false
|
||||
},
|
||||
{
|
||||
title: this.translate.instant('STAKING.YEAR'),
|
||||
title: this.translate.instant('STAKING.PERIOD.MONTH3'),
|
||||
key: '3 month',
|
||||
active: false
|
||||
},
|
||||
{
|
||||
title: this.translate.instant('STAKING.PERIOD.MONTH6'),
|
||||
key: '6 month',
|
||||
active: false
|
||||
},
|
||||
{
|
||||
title: this.translate.instant('STAKING.PERIOD.YEAR'),
|
||||
key: '1 year',
|
||||
active: false
|
||||
},
|
||||
{
|
||||
title: this.translate.instant('STAKING.ALL'),
|
||||
title: this.translate.instant('STAKING.PERIOD.ALL'),
|
||||
key: 'All',
|
||||
active: true
|
||||
}
|
||||
];
|
||||
|
||||
groups = [
|
||||
{
|
||||
title: this.translate.instant('STAKING.GROUP.DAY'),
|
||||
key: 'day',
|
||||
active: true
|
||||
},
|
||||
{
|
||||
title: this.translate.instant('STAKING.GROUP.WEEK'),
|
||||
key: 'week',
|
||||
active: false
|
||||
},
|
||||
{
|
||||
title: this.translate.instant('STAKING.GROUP.MONTH'),
|
||||
key: 'month',
|
||||
active: false
|
||||
}
|
||||
];
|
||||
|
||||
selectedDate = {
|
||||
date: null,
|
||||
amount: null
|
||||
|
|
@ -61,8 +89,6 @@ export class StakingComponent implements OnInit, OnDestroy {
|
|||
total: new BigNumber(0)
|
||||
};
|
||||
|
||||
currentPeriod = 'All';
|
||||
|
||||
constructor(
|
||||
private route: ActivatedRoute,
|
||||
private variablesService: VariablesService,
|
||||
|
|
@ -73,6 +99,15 @@ export class StakingComponent implements OnInit, OnDestroy {
|
|||
) {
|
||||
}
|
||||
|
||||
static makeGroupTime(key, date) {
|
||||
if (key === 'day') {
|
||||
return date.setHours(0, 0, 0, 0);
|
||||
} else if (key === 'week') {
|
||||
return new Date(date.setDate(date.getDate() - date.getDay())).setHours(0, 0, 0, 0);
|
||||
} else {
|
||||
return new Date(date.setDate(1)).setHours(0, 0, 0, 0);
|
||||
}
|
||||
}
|
||||
|
||||
ngOnInit() {
|
||||
this.parentRouting = this.route.parent.params.subscribe(() => {
|
||||
|
|
@ -112,7 +147,12 @@ export class StakingComponent implements OnInit, OnDestroy {
|
|||
type: 'line',
|
||||
backgroundColor: 'transparent',
|
||||
height: null,
|
||||
zoomType: null
|
||||
zoomType: null,
|
||||
events: {
|
||||
load: () => {
|
||||
this.changePeriod();
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
yAxis: {
|
||||
|
|
@ -241,39 +281,31 @@ export class StakingComponent implements OnInit, OnDestroy {
|
|||
});
|
||||
}
|
||||
this.ngZone.run(() => {
|
||||
this.drawChart(JSON.parse(JSON.stringify(this.originalData)));
|
||||
this.drawChart([]);
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
changePeriod(period) {
|
||||
this.periods.forEach((p) => {
|
||||
p.active = false;
|
||||
});
|
||||
period.active = true;
|
||||
this.currentPeriod = period.key;
|
||||
changePeriod(period?) {
|
||||
if (period) {
|
||||
this.periods.forEach((p) => {
|
||||
p.active = false;
|
||||
});
|
||||
period.active = true;
|
||||
} else {
|
||||
period = this.periods.find((p) => p.active);
|
||||
}
|
||||
|
||||
const d = new Date();
|
||||
let min = null;
|
||||
const newData = [];
|
||||
|
||||
if (period.key === '1 day') {
|
||||
const group = this.groups.find((g) => g.active);
|
||||
|
||||
if (period.key === '1 week') {
|
||||
this.originalData.forEach((item) => {
|
||||
const time = (new Date(item[0])).setUTCMinutes(0, 0, 0);
|
||||
const find = newData.find(itemNew => itemNew[0] === time);
|
||||
if (find) {
|
||||
find[1] = new BigNumber(find[1]).plus(item[1]).toNumber();
|
||||
} else {
|
||||
newData.push([time, item[1]]);
|
||||
}
|
||||
});
|
||||
this.chart.ref.series[0].setData(newData, true);
|
||||
min = Date.UTC(d.getFullYear(), d.getMonth(), d.getDate() - 1, 0, 0, 0, 0);
|
||||
} else if (period.key === '1 week') {
|
||||
this.originalData.forEach((item) => {
|
||||
const time = (new Date(item[0])).setUTCHours(0, 0, 0, 0);
|
||||
const time = StakingComponent.makeGroupTime(group.key, new Date(item[0]));
|
||||
const find = newData.find(itemNew => itemNew[0] === time);
|
||||
if (find) {
|
||||
find[1] = new BigNumber(find[1]).plus(item[1]).toNumber();
|
||||
|
|
@ -283,9 +315,21 @@ export class StakingComponent implements OnInit, OnDestroy {
|
|||
});
|
||||
this.chart.ref.series[0].setData(newData, true);
|
||||
min = Date.UTC(d.getFullYear(), d.getMonth(), d.getDate() - 7, 0, 0, 0, 0);
|
||||
} else if (period.key === '2 week') {
|
||||
this.originalData.forEach((item) => {
|
||||
const time = StakingComponent.makeGroupTime(group.key, new Date(item[0]));
|
||||
const find = newData.find(itemNew => itemNew[0] === time);
|
||||
if (find) {
|
||||
find[1] = new BigNumber(find[1]).plus(item[1]).toNumber();
|
||||
} else {
|
||||
newData.push([time, item[1]]);
|
||||
}
|
||||
});
|
||||
this.chart.ref.series[0].setData(newData, true);
|
||||
min = Date.UTC(d.getFullYear(), d.getMonth(), d.getDate() - 14, 0, 0, 0, 0);
|
||||
} else if (period.key === '1 month') {
|
||||
this.originalData.forEach((item) => {
|
||||
const time = (new Date(item[0])).setUTCHours(0, 0, 0, 0);
|
||||
const time = StakingComponent.makeGroupTime(group.key, new Date(item[0]));
|
||||
const find = newData.find(itemNew => itemNew[0] === time);
|
||||
if (find) {
|
||||
find[1] = new BigNumber(find[1]).plus(item[1]).toNumber();
|
||||
|
|
@ -295,9 +339,33 @@ export class StakingComponent implements OnInit, OnDestroy {
|
|||
});
|
||||
this.chart.ref.series[0].setData(newData, true);
|
||||
min = Date.UTC(d.getFullYear(), d.getMonth() - 1, d.getDate(), 0, 0, 0, 0);
|
||||
} else if (period.key === '3 month') {
|
||||
this.originalData.forEach((item) => {
|
||||
const time = StakingComponent.makeGroupTime(group.key, new Date(item[0]));
|
||||
const find = newData.find(itemNew => itemNew[0] === time);
|
||||
if (find) {
|
||||
find[1] = new BigNumber(find[1]).plus(item[1]).toNumber();
|
||||
} else {
|
||||
newData.push([time, item[1]]);
|
||||
}
|
||||
});
|
||||
this.chart.ref.series[0].setData(newData, true);
|
||||
min = Date.UTC(d.getFullYear(), d.getMonth() - 3, d.getDate(), 0, 0, 0, 0);
|
||||
} else if (period.key === '6 month') {
|
||||
this.originalData.forEach((item) => {
|
||||
const time = StakingComponent.makeGroupTime(group.key, new Date(item[0]));
|
||||
const find = newData.find(itemNew => itemNew[0] === time);
|
||||
if (find) {
|
||||
find[1] = new BigNumber(find[1]).plus(item[1]).toNumber();
|
||||
} else {
|
||||
newData.push([time, item[1]]);
|
||||
}
|
||||
});
|
||||
this.chart.ref.series[0].setData(newData, true);
|
||||
min = Date.UTC(d.getFullYear(), d.getMonth() - 6, d.getDate(), 0, 0, 0, 0);
|
||||
} else if (period.key === '1 year') {
|
||||
this.originalData.forEach((item) => {
|
||||
const time = (new Date(item[0])).setUTCHours(0, 0, 0, 0);
|
||||
const time = StakingComponent.makeGroupTime(group.key, new Date(item[0]));
|
||||
const find = newData.find(itemNew => itemNew[0] === time);
|
||||
if (find) {
|
||||
find[1] = new BigNumber(find[1]).plus(item[1]).toNumber();
|
||||
|
|
@ -308,12 +376,28 @@ export class StakingComponent implements OnInit, OnDestroy {
|
|||
this.chart.ref.series[0].setData(newData, true);
|
||||
min = Date.UTC(d.getFullYear() - 1, d.getMonth(), d.getDate(), 0, 0, 0, 0);
|
||||
} else {
|
||||
this.chart.ref.series[0].setData(this.originalData, true);
|
||||
this.originalData.forEach((item) => {
|
||||
const time = StakingComponent.makeGroupTime(group.key, new Date(item[0]));
|
||||
const find = newData.find(itemNew => itemNew[0] === time);
|
||||
if (find) {
|
||||
find[1] = new BigNumber(find[1]).plus(item[1]).toNumber();
|
||||
} else {
|
||||
newData.push([time, item[1]]);
|
||||
}
|
||||
});
|
||||
this.chart.ref.series[0].setData(newData, true);
|
||||
}
|
||||
|
||||
this.chart.ref.xAxis[0].setExtremes(min, null);
|
||||
}
|
||||
|
||||
changeGroup(group) {
|
||||
this.groups.forEach((g) => {
|
||||
g.active = false;
|
||||
});
|
||||
group.active = true;
|
||||
this.changePeriod();
|
||||
}
|
||||
|
||||
ngOnDestroy() {
|
||||
this.parentRouting.unsubscribe();
|
||||
|
|
|
|||
|
|
@ -72,16 +72,17 @@ export class WalletDetailsComponent implements OnInit, OnDestroy {
|
|||
this.variablesService.wallets.splice(i, 1);
|
||||
}
|
||||
}
|
||||
this.backend.storeSecureAppData(() => {
|
||||
this.ngZone.run(() => {
|
||||
if (this.variablesService.wallets.length) {
|
||||
this.variablesService.currentWallet = this.variablesService.wallets[0];
|
||||
this.router.navigate(['/wallet/' + this.variablesService.currentWallet.wallet_id]);
|
||||
} else {
|
||||
this.router.navigate(['/']);
|
||||
}
|
||||
});
|
||||
this.ngZone.run(() => {
|
||||
if (this.variablesService.wallets.length) {
|
||||
this.variablesService.currentWallet = this.variablesService.wallets[0];
|
||||
this.router.navigate(['/wallet/' + this.variablesService.currentWallet.wallet_id]);
|
||||
} else {
|
||||
this.router.navigate(['/']);
|
||||
}
|
||||
});
|
||||
if (this.variablesService.appPass) {
|
||||
this.backend.storeSecureAppData();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -4,6 +4,7 @@
|
|||
"SETUP_CONFIRM_PASS": "Confirm the password",
|
||||
"MASTER_PASS": "Master password",
|
||||
"BUTTON_NEXT": "Next",
|
||||
"BUTTON_SKIP": "Skip",
|
||||
"INCORRECT_PASSWORD": "Invalid password",
|
||||
"FORM_ERRORS": {
|
||||
"PASS_REQUIRED": "Password is required.",
|
||||
|
|
@ -83,6 +84,13 @@
|
|||
"NAME_REQUIRED": "Name is required.",
|
||||
"NAME_DUPLICATE": "Name is duplicate.",
|
||||
"MAX_LENGTH": "Maximum name length reached."
|
||||
},
|
||||
"MODAL": {
|
||||
"TITLE": "Type wallet password",
|
||||
"LABEL": "Password to this wallet",
|
||||
"OPEN": "Open wallet",
|
||||
"SKIP": "Skip",
|
||||
"NOT_FOUND": "Not found"
|
||||
}
|
||||
},
|
||||
"RESTORE_WALLET": {
|
||||
|
|
@ -440,11 +448,21 @@
|
|||
"TITLE_PENDING": "Pending",
|
||||
"TITLE_TOTAL": "Total",
|
||||
"TITLE_PERIOD": "Time period:",
|
||||
"DAY": "1 day",
|
||||
"WEEK": "1 week",
|
||||
"MONTH": "1 month",
|
||||
"YEAR": "1 year",
|
||||
"ALL": "All",
|
||||
"PERIOD": {
|
||||
"WEEK1": "1 week",
|
||||
"WEEK2": "2 week",
|
||||
"MONTH1": "1 month",
|
||||
"MONTH3": "3 month",
|
||||
"MONTH6": "6 month",
|
||||
"YEAR": "1 year",
|
||||
"ALL": "All"
|
||||
},
|
||||
"TITLE_GROUP": "Group:",
|
||||
"GROUP": {
|
||||
"DAY": "day",
|
||||
"WEEK": "week",
|
||||
"MONTH": "month"
|
||||
},
|
||||
"SWITCH": {
|
||||
"ON": "ON",
|
||||
"OFF": "OFF"
|
||||
|
|
|
|||
|
|
@ -33,6 +33,13 @@ button {
|
|||
background-color: themed(disabledButtonHoverColor);
|
||||
}
|
||||
}
|
||||
|
||||
&:focus {
|
||||
|
||||
@include themify($themes) {
|
||||
background-color: themed(disabledButtonFocusColor);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&.blue-button:not(:disabled) {
|
||||
|
|
@ -54,6 +61,13 @@ button {
|
|||
background-color: themed(blueButtonHoverColor);
|
||||
}
|
||||
}
|
||||
|
||||
&:focus {
|
||||
|
||||
@include themify($themes) {
|
||||
background-color: themed(blueButtonFocusColor);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&.green-button:not(:disabled) {
|
||||
|
|
@ -69,6 +83,13 @@ button {
|
|||
background-color: themed(greenButtonHoverColor);
|
||||
}
|
||||
}
|
||||
|
||||
&:focus {
|
||||
|
||||
@include themify($themes) {
|
||||
background-color: themed(greenButtonFocusColor);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&.turquoise-button:not(:disabled) {
|
||||
|
|
@ -84,6 +105,13 @@ button {
|
|||
background-color: themed(turquoiseButtonHoverColor);
|
||||
}
|
||||
}
|
||||
|
||||
&:focus {
|
||||
|
||||
@include themify($themes) {
|
||||
background-color: themed(turquoiseButtonFocusColor);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&.transparent-button {
|
||||
|
|
@ -597,6 +625,10 @@ input[type='checkbox'].style-checkbox {
|
|||
|
||||
.ng-value-container {
|
||||
padding: 0;
|
||||
|
||||
.ng-input {
|
||||
top: auto;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -752,3 +784,14 @@ app-progress-container {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
app-open-wallet-modal {
|
||||
|
||||
.modal {
|
||||
|
||||
@include themify($themes) {
|
||||
background: themed(modalBackground);
|
||||
color: themed(mainTextColor);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -13,26 +13,31 @@ $themes: (
|
|||
greenTextColor: #5cda9d,
|
||||
redTextColor: #fe5252,
|
||||
blueButtonBackgroundColor: #4db1ff,
|
||||
blueButtonHoverColor: #60b9ff,
|
||||
disabledButtonBackgroundColor: #90a4ae,
|
||||
disabledButtonHoverColor: #9bb0ba,
|
||||
blueButtonHoverColor: #82d7ff,
|
||||
blueButtonFocusColor: #59b5fd,
|
||||
disabledButtonBackgroundColor: #9cadb7,
|
||||
disabledButtonHoverColor: #b7d1e0,
|
||||
disabledButtonFocusColor: #a7b9c2,
|
||||
greenButtonBackgroundColor: #5cda9d,
|
||||
greenButtonHoverColor: #5ce2a1,
|
||||
greenButtonHoverColor: #8dfcc6,
|
||||
greenButtonFocusColor: #62e0b2,
|
||||
turquoiseButtonBackgroundColor: #4dd0e1,
|
||||
turquoiseButtonHoverColor: #52d9ea,
|
||||
turquoiseButtonHoverColor: #87f4f5,
|
||||
turquoiseButtonFocusColor: #42d5e8,
|
||||
transparentButtonBorderColor: #2b3644,
|
||||
inputBackgroundColor: #171e27,
|
||||
selectHoverColor: rgba(58, 72, 90, 0.5),
|
||||
selectHoverColor: rgba(58, 69, 85, 0.5),
|
||||
selectSelectedColor: rgba(43, 54, 68, 0.5),
|
||||
switchBackgroundColor: #000000,
|
||||
accountBackgroundColor: rgba(43, 54, 68, 0.5),
|
||||
accountHoverBackgroundColor: rgba(58, 72, 90, 0.5),
|
||||
accountHoverBackgroundColor: rgba(58, 69, 85, 0.5),
|
||||
accountMainTextColor: #e0e0e0,
|
||||
accountOptionalTextColor: #556576,
|
||||
accountIndicatorTextColor: #111921,
|
||||
accountSwitchBackgroundColor: #000000,
|
||||
accountIndicatorBackgroundColor: #4db1ff,
|
||||
tabInactiveBackgroundColor: rgba(23, 31, 39, 0.5),
|
||||
tabHoverBackgroundColor: rgba(58, 69, 85, 0.5),
|
||||
tableBackgroundColor: #18202a,
|
||||
messageMyBackgroundColor: #2a3544,
|
||||
messageBuddyBackgroundColor: #18202a,
|
||||
|
|
@ -47,7 +52,7 @@ $themes: (
|
|||
),
|
||||
gray: (
|
||||
bodyBackgroundColor: #101417,
|
||||
sidebarBackgroundColor: rgba(23, 25, 27, 0.5),
|
||||
sidebarBackgroundColor: rgba(28, 30, 33, 0.5),
|
||||
sidebarBorderColor: #2e3337,
|
||||
onlineColor: #47cf8d,
|
||||
offlineColor: #ff5252,
|
||||
|
|
@ -59,26 +64,31 @@ $themes: (
|
|||
greenTextColor: #47cf8d,
|
||||
redTextColor: #fe5252,
|
||||
blueButtonBackgroundColor: #42a5f5,
|
||||
blueButtonHoverColor: #4dafff,
|
||||
blueButtonHoverColor: #86d6ff,
|
||||
blueButtonFocusColor: #5fb6fc,
|
||||
disabledButtonBackgroundColor: #79848f,
|
||||
disabledButtonHoverColor: #85909b,
|
||||
disabledButtonHoverColor: #a1aebb,
|
||||
disabledButtonFocusColor: #8a959f,
|
||||
greenButtonBackgroundColor: #47cf8d,
|
||||
greenButtonHoverColor: #49d993,
|
||||
greenButtonHoverColor: #7bf6c6,
|
||||
greenButtonFocusColor: #5cdc9e,
|
||||
turquoiseButtonBackgroundColor: #3ec5d7,
|
||||
turquoiseButtonHoverColor: #43cee0,
|
||||
turquoiseButtonHoverColor: #72edfe,
|
||||
turquoiseButtonFocusColor: #50d0e1,
|
||||
transparentButtonBorderColor: #2f3438,
|
||||
inputBackgroundColor: #292d31,
|
||||
selectHoverColor: rgba(70, 76, 81, 0.5),
|
||||
selectHoverColor: rgba(58, 62, 66, 0.5),
|
||||
selectSelectedColor: rgba(37, 40, 43, 0.5),
|
||||
switchBackgroundColor: #000000,
|
||||
accountBackgroundColor: rgba(37, 40, 43, 0.5),
|
||||
accountHoverBackgroundColor: rgba(70, 76, 81, 0.5),
|
||||
accountHoverBackgroundColor: rgba(58, 62, 66, 0.5),
|
||||
accountMainTextColor: #e0e0e0,
|
||||
accountOptionalTextColor: #565c62,
|
||||
accountIndicatorTextColor: #1a1a1a,
|
||||
accountSwitchBackgroundColor: #000000,
|
||||
accountIndicatorBackgroundColor: #42a5f5,
|
||||
tabInactiveBackgroundColor: rgba(23, 25, 27, 0.5),
|
||||
tabInactiveBackgroundColor: rgba(28, 30, 33, 0.5),
|
||||
tabHoverBackgroundColor: rgba(58, 62, 66, 0.5),
|
||||
tableBackgroundColor: #25292d,
|
||||
messageMyBackgroundColor: #30363c,
|
||||
messageBuddyBackgroundColor: #25292d,
|
||||
|
|
@ -105,13 +115,17 @@ $themes: (
|
|||
greenTextColor: #46c172,
|
||||
redTextColor: #ff5252,
|
||||
blueButtonBackgroundColor: #2c95f1,
|
||||
blueButtonHoverColor: #379ffa,
|
||||
blueButtonHoverColor: #5cb3ff,
|
||||
blueButtonFocusColor: #379ffa,
|
||||
disabledButtonBackgroundColor: #90a4ae,
|
||||
disabledButtonHoverColor: #9baeb7,
|
||||
disabledButtonHoverColor: #aebec6,
|
||||
disabledButtonFocusColor: #a7b9c2,
|
||||
greenButtonBackgroundColor: #46c172,
|
||||
greenButtonHoverColor: #46ca75,
|
||||
greenButtonHoverColor: #5ad586,
|
||||
greenButtonFocusColor: #53c77c,
|
||||
turquoiseButtonBackgroundColor: #26b6c7,
|
||||
turquoiseButtonHoverColor: #2bbdcf,
|
||||
turquoiseButtonHoverColor: #52cbd9,
|
||||
turquoiseButtonFocusColor: #31becf,
|
||||
transparentButtonBorderColor: #ebebeb,
|
||||
inputBackgroundColor: #e6e6e6,
|
||||
selectHoverColor: rgba(240, 240, 240, 0.5),
|
||||
|
|
@ -125,6 +139,7 @@ $themes: (
|
|||
accountSwitchBackgroundColor: #ffffff,
|
||||
accountIndicatorBackgroundColor: #ffffff,
|
||||
tabInactiveBackgroundColor: rgba(224, 224, 224, 0.5),
|
||||
tabHoverBackgroundColor: #ffffff,
|
||||
tableBackgroundColor: #ffffff,
|
||||
messageMyBackgroundColor: #fff,
|
||||
messageBuddyBackgroundColor: #ededed,
|
||||
|
|
|
|||
|
|
@ -76,6 +76,13 @@ app-wallet {
|
|||
background-color: themed(contentBackgroundColor);
|
||||
}
|
||||
}
|
||||
|
||||
&:hover:not(.active) {
|
||||
|
||||
@include themify($themes) {
|
||||
background-color: themed(tabHoverBackgroundColor);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -193,6 +193,8 @@ namespace currency
|
|||
res.performance_data.etc_stuff_6 = pd.etc_stuff_6.get_avg();
|
||||
res.performance_data.insert_time_4 = pd.insert_time_4.get_avg();
|
||||
res.performance_data.raise_block_core_event = pd.raise_block_core_event.get_avg();
|
||||
res.performance_data.target_calculating_enum_blocks = pd.target_calculating_enum_blocks.get_avg();
|
||||
res.performance_data.target_calculating_calc = pd.target_calculating_calc.get_avg();
|
||||
//tx processing zone
|
||||
res.performance_data.tx_check_inputs_time = pd.tx_check_inputs_time.get_avg();
|
||||
res.performance_data.tx_add_one_tx_time = pd.tx_add_one_tx_time.get_avg();
|
||||
|
|
@ -802,7 +804,7 @@ namespace currency
|
|||
LOG_ERROR("Failed to create block template");
|
||||
return false;
|
||||
}
|
||||
res.difficulty = dt.convert_to<uint64_t>();
|
||||
res.difficulty = dt.convert_to<std::string>();
|
||||
blobdata block_blob = t_serializable_object_to_blob(b);
|
||||
|
||||
res.blocktemplate_blob = string_tools::buff_to_hex_nodelimer(block_blob);
|
||||
|
|
@ -891,7 +893,7 @@ namespace currency
|
|||
response.height = get_block_height(blk);
|
||||
response.depth = m_core.get_current_blockchain_size() - response.height - 1;
|
||||
response.hash = string_tools::pod_to_hex(get_block_hash(blk));
|
||||
response.difficulty = m_core.get_blockchain_storage().block_difficulty(response.height).convert_to<uint64_t>();
|
||||
response.difficulty = m_core.get_blockchain_storage().block_difficulty(response.height).convert_to<std::string>();
|
||||
response.reward = get_block_reward(blk);
|
||||
return true;
|
||||
}
|
||||
|
|
@ -1110,7 +1112,7 @@ namespace currency
|
|||
set_session_blob(job_id, b);
|
||||
job.blob = string_tools::buff_to_hex_nodelimer(currency::get_block_hashing_blob(b));
|
||||
//TODO: set up share difficulty here!
|
||||
job.difficulty = std::to_string(bt_res.difficulty); //difficulty leaved as string field since it will be refactored into 128 bit format
|
||||
job.difficulty = bt_res.difficulty; //difficulty leaved as string field since it will be refactored into 128 bit format
|
||||
job.job_id = "SOME_JOB_ID";
|
||||
get_current_hi(job.prev_hi);
|
||||
return true;
|
||||
|
|
|
|||
|
|
@ -459,6 +459,8 @@ namespace currency
|
|||
uint64_t etc_stuff_6;
|
||||
uint64_t insert_time_4;
|
||||
uint64_t raise_block_core_event;
|
||||
uint64_t target_calculating_enum_blocks;
|
||||
uint64_t target_calculating_calc;
|
||||
|
||||
//tx processing zone
|
||||
uint64_t tx_check_inputs_time;
|
||||
|
|
@ -505,7 +507,8 @@ namespace currency
|
|||
KV_SERIALIZE(etc_stuff_6)
|
||||
KV_SERIALIZE(insert_time_4)
|
||||
KV_SERIALIZE(raise_block_core_event)
|
||||
|
||||
KV_SERIALIZE(target_calculating_enum_blocks)
|
||||
KV_SERIALIZE(target_calculating_calc)
|
||||
//tx processing zone
|
||||
KV_SERIALIZE(tx_check_inputs_time)
|
||||
KV_SERIALIZE(tx_add_one_tx_time)
|
||||
|
|
@ -788,7 +791,7 @@ namespace currency
|
|||
|
||||
struct response
|
||||
{
|
||||
uint64_t difficulty;
|
||||
std::string difficulty;
|
||||
uint64_t height;
|
||||
crypto::hash seed;
|
||||
blobdata blocktemplate_blob;
|
||||
|
|
@ -831,7 +834,7 @@ namespace currency
|
|||
uint64_t height;
|
||||
uint64_t depth;
|
||||
std::string hash;
|
||||
difficulty_type difficulty;
|
||||
std::string difficulty;
|
||||
uint64_t reward;
|
||||
|
||||
BEGIN_KV_SERIALIZE_MAP()
|
||||
|
|
|
|||
|
|
@ -2,6 +2,6 @@
|
|||
|
||||
#define BUILD_COMMIT_ID "@VERSION@"
|
||||
#define PROJECT_VERSION "1.0"
|
||||
#define PROJECT_VERSION_BUILD_NO 14
|
||||
#define PROJECT_VERSION_BUILD_NO 16
|
||||
#define PROJECT_VERSION_BUILD_NO_STR STRINGIFY_EXPAND(PROJECT_VERSION_BUILD_NO)
|
||||
#define PROJECT_VERSION_LONG PROJECT_VERSION "." PROJECT_VERSION_BUILD_NO_STR "[" BUILD_COMMIT_ID "]"
|
||||
|
|
|
|||
|
|
@ -34,8 +34,8 @@ target_link_libraries(difficulty-tests currency_core ${CMAKE_THREAD_LIBS_INIT} e
|
|||
target_link_libraries(functional_tests wallet currency_core crypto common rpc zlibstatic ethash upnpc-static ${CMAKE_THREAD_LIBS_INIT} ${Boost_LIBRARIES})
|
||||
target_link_libraries(hash-tests crypto ethash)
|
||||
target_link_libraries(hash-target-tests crypto currency_core ethash ${CMAKE_THREAD_LIBS_INIT} ${Boost_LIBRARIES})
|
||||
target_link_libraries(performance_tests currency_core common crypto zlibstatic ethash${CMAKE_THREAD_LIBS_INIT} ${Boost_LIBRARIES})
|
||||
target_link_libraries(unit_tests wallet currency_core crypto common gtest_main zlibstatic ethash${CMAKE_THREAD_LIBS_INIT} ${Boost_LIBRARIES})
|
||||
target_link_libraries(performance_tests currency_core common crypto zlibstatic ethash ${CMAKE_THREAD_LIBS_INIT} ${Boost_LIBRARIES})
|
||||
target_link_libraries(unit_tests wallet currency_core crypto common gtest_main zlibstatic ethash ${CMAKE_THREAD_LIBS_INIT} ${Boost_LIBRARIES})
|
||||
target_link_libraries(net_load_tests_clt currency_core common crypto gtest_main ${CMAKE_THREAD_LIBS_INIT} ${Boost_LIBRARIES})
|
||||
target_link_libraries(net_load_tests_srv currency_core common crypto gtest_main ${CMAKE_THREAD_LIBS_INIT} ${Boost_LIBRARIES})
|
||||
|
||||
|
|
|
|||
|
|
@ -52,7 +52,7 @@ bool gen_chain_switch_pow_pos::generate(std::vector<test_event_entry>& events) c
|
|||
for(size_t i = 0; i < CURRENCY_MINED_MONEY_UNLOCK_WINDOW; ++i)
|
||||
{
|
||||
block blk = AUTO_VAL_INIT(blk);
|
||||
uint64_t ts = blk_0r.timestamp + DIFFICULTY_BLOCKS_ESTIMATE_TIMESPAN / 3; // to increase main chain difficulty
|
||||
uint64_t ts = blk_0r.timestamp + DIFFICULTY_BLOCKS_ESTIMATE_TIMESPAN / 2; // to increase main chain difficulty
|
||||
bool r = generator.construct_block_manually(blk, blk_0r, miner_acc,test_generator::bf_timestamp, 0, 0, ts);
|
||||
CHECK_AND_ASSERT_MES(r, false, "construct_block_manually failed");
|
||||
events.push_back(blk);
|
||||
|
|
|
|||
|
|
@ -628,7 +628,7 @@ bool gen_no_attchments_in_coinbase::init_config_set_cp(currency::core& c, size_t
|
|||
crc.pos_minimum_heigh = 1;
|
||||
c.get_blockchain_storage().set_core_runtime_config(crc);
|
||||
|
||||
m_checkpoints.add_checkpoint(12, "446b25ca3816e36df92745ea91c3c54a8745db565bafd4d2aa7df9da49220a19");
|
||||
m_checkpoints.add_checkpoint(12, "ea03a5c99aeedc2050ca5dae011a6c411b31f8b7fb9d0b82735c403b5c608b7b");
|
||||
c.set_checkpoints(currency::checkpoints(m_checkpoints));
|
||||
|
||||
return true;
|
||||
|
|
|
|||
|
|
@ -1625,7 +1625,7 @@ multisig_and_checkpoints::multisig_and_checkpoints()
|
|||
bool multisig_and_checkpoints::set_cp(currency::core& c, size_t ev_index, const std::vector<test_event_entry>& events)
|
||||
{
|
||||
currency::checkpoints checkpoints;
|
||||
checkpoints.add_checkpoint(15, "37da2a30fd8cf1daa05ba11cb2ac5f7a3cc998bce56e4b575fbbea58f0592f5b");
|
||||
checkpoints.add_checkpoint(15, "46f45b849160be33937c60fa564e820792b0aaa6cf4a080e6002b6f25d84d688");
|
||||
c.set_checkpoints(std::move(checkpoints));
|
||||
|
||||
return true;
|
||||
|
|
|
|||
|
|
@ -28,7 +28,7 @@ std::atomic<int64_t> test_core_time::m_time_shift;
|
|||
|
||||
#define TESTS_DEFAULT_FEE TX_DEFAULT_FEE
|
||||
|
||||
static std::atomic<uint64_t> s_generated_money_total(0);
|
||||
static std::atomic<uint64_t> s_generated_money_total(0); // TODO: consiger changing to boost::multiprecision::uint128_t
|
||||
static size_t s_wallets_total_count = 10; // total number of wallet that will be randomly used to generate transactions
|
||||
//static size_t s_althchains_minimum_height = 150; // height at which althchaining is started
|
||||
static size_t s_tx_generation_minimum_height = 100; // height at which tx generation is started
|
||||
|
|
@ -43,7 +43,7 @@ typedef std::vector<std::shared_ptr<tools::wallet2>> cct_wallets_t;
|
|||
static const std::vector<currency::extra_v> empty_extra;
|
||||
static const std::vector<currency::attachment_v> empty_attachment;
|
||||
|
||||
bool create_block_template_manually(const currency::block& prev_block, uint64_t already_generated_coins, const std::vector<const currency::transaction*>& txs, const currency::account_public_address& miner_addr, currency::block& result)
|
||||
bool create_block_template_manually(const currency::block& prev_block, boost::multiprecision::uint128_t already_generated_coins, const std::vector<const currency::transaction*>& txs, const currency::account_public_address& miner_addr, currency::block& result)
|
||||
{
|
||||
result.flags = 0;
|
||||
result.major_version = CURRENT_BLOCK_MAJOR_VERSION;
|
||||
|
|
@ -572,7 +572,7 @@ bool core_concurrency_test(boost::program_options::variables_map& vm, size_t wth
|
|||
<< replay_time_ms / (events.empty() ? 1 : events.size()) << " ms per event, " << events.size() << " events total", LOG_LEVEL_0);
|
||||
|
||||
core_state_after_playback.fill(c);
|
||||
uint64_t already_generated_coins = 0;
|
||||
boost::multiprecision::uint128_t already_generated_coins = 0;
|
||||
{
|
||||
block_extended_info bei = AUTO_VAL_INIT(bei);
|
||||
c.get_blockchain_storage().get_block_extended_info_by_hash(c.get_blockchain_storage().get_top_block_id(), bei);
|
||||
|
|
@ -583,7 +583,7 @@ bool core_concurrency_test(boost::program_options::variables_map& vm, size_t wth
|
|||
if (rthreads > 0)
|
||||
{
|
||||
s_generated_money_total = s_generated_money_total / rthreads;
|
||||
LOG_PRINT("Generated coins: " << print_money(already_generated_coins) << ", counted by readers (with fee): " << print_money(s_generated_money_total), LOG_LEVEL_0);
|
||||
LOG_PRINT("Generated coins: " << print_money(already_generated_coins) << ", counted by readers (with fee): " << print_money(s_generated_money_total.load()), LOG_LEVEL_0);
|
||||
}
|
||||
|
||||
LOG_PRINT("Writers' stats:", LOG_LEVEL_0);
|
||||
|
|
|
|||
|
|
@ -12,6 +12,7 @@
|
|||
using namespace epee;
|
||||
#include "wallet/wallet2.h"
|
||||
#include "currency_core/blockchain_storage.h"
|
||||
#include "currency_core/basic_pow_helpers.h"
|
||||
|
||||
|
||||
using std::size_t;
|
||||
|
|
@ -318,11 +319,29 @@ void run_emulation(const std::string& path)
|
|||
LOG_PRINT_L0("Done");
|
||||
}
|
||||
|
||||
void hash_rate_analysis(const std::string& path);
|
||||
|
||||
void run_difficulty_analysis(const std::string& path)
|
||||
{
|
||||
//hash_rate_analysis(path);
|
||||
run_emulation(path);
|
||||
// currency::block b = AUTO_VAL_INIT(b);
|
||||
// std::string s("sdsccasc");
|
||||
// b.miner_tx.extra.push_back(s);
|
||||
//
|
||||
// crypto::hash mining_hash = currency::null_hash;
|
||||
// bool r = string_tools::parse_tpod_from_hex_string("7759031ee0f014fe45476724df268f61c890b4a4637df1489a6c94c0135efbd8", mining_hash);
|
||||
// uint64_t nonce = 13704307308123612296;
|
||||
// crypto::hash pow_hash = currency::get_block_longhash(6, mining_hash, nonce);
|
||||
//
|
||||
// std::cout << mining_hash << ENDL;
|
||||
// std::cout << pow_hash << ENDL;
|
||||
|
||||
//crypto::hash mining_hash = currency::get_block_header_mining_hash(b);
|
||||
//crypto::hash id_hash = currency::get_block_hash(b);
|
||||
|
||||
|
||||
|
||||
hash_rate_analysis(path);
|
||||
//run_emulation(path);
|
||||
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -589,7 +589,7 @@ bool transactions_flow_test(
|
|||
if (action == TRANSACTIONS_FLOW_TESTACTION_MIXED)
|
||||
{
|
||||
current_action++;
|
||||
if (current_action > TRANSACTIONS_FLOW_TESTACTION_OFFERS)
|
||||
if (current_action >= TRANSACTIONS_FLOW_TESTACTION_OFFERS)
|
||||
current_action = TRANSACTIONS_FLOW_TESTACTION_DEFAULT;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -264,7 +264,7 @@ TEST_F(positive_test_connection_to_levin_protocol_handler_calls, handler_initial
|
|||
TEST_F(positive_test_connection_to_levin_protocol_handler_calls, concurent_handler_initialization_and_destruction_is_correct)
|
||||
{
|
||||
const size_t connection_count = 10000;
|
||||
auto create_and_destroy_connections = [this]()
|
||||
auto create_and_destroy_connections = [&]()
|
||||
{
|
||||
std::vector<test_connection_ptr> connections(connection_count);
|
||||
for (size_t i = 0; i < connection_count; ++i)
|
||||
|
|
|
|||
|
|
@ -128,11 +128,11 @@ TEST(validate_parse_amount_case, validate_parse_amount)
|
|||
uint64_t res = 0;
|
||||
bool r = currency::parse_amount(res, "0.0001");
|
||||
ASSERT_TRUE(r);
|
||||
ASSERT_EQ(res, 10000);
|
||||
ASSERT_EQ(res, 100000000);
|
||||
|
||||
r = currency::parse_amount(res, "100.0001");
|
||||
ASSERT_TRUE(r);
|
||||
ASSERT_EQ(res, 10000010000);
|
||||
ASSERT_EQ(res, 100000100000000);
|
||||
|
||||
r = currency::parse_amount(res, "000.0000");
|
||||
ASSERT_TRUE(r);
|
||||
|
|
@ -145,11 +145,11 @@ TEST(validate_parse_amount_case, validate_parse_amount)
|
|||
|
||||
r = currency::parse_amount(res, " 100.0001 ");
|
||||
ASSERT_TRUE(r);
|
||||
ASSERT_EQ(res, 10000010000);
|
||||
ASSERT_EQ(res, 100000100000000);
|
||||
|
||||
r = currency::parse_amount(res, " 100.0000 ");
|
||||
ASSERT_TRUE(r);
|
||||
ASSERT_EQ(res, 10000000000);
|
||||
ASSERT_EQ(res, 100000000000000);
|
||||
|
||||
r = currency::parse_amount(res, " 100. 0000 ");
|
||||
ASSERT_FALSE(r);
|
||||
|
|
|
|||
|
|
@ -3,7 +3,7 @@ curr_path=${BASH_SOURCE%/*}
|
|||
version_file_path=../src/version.h.in
|
||||
|
||||
pushd $curr_path
|
||||
git pull
|
||||
git pull --ff-only
|
||||
if [ $? -ne 0 ]; then
|
||||
echo "Failed to pull"
|
||||
popd
|
||||
|
|
|
|||
|
|
@ -12,4 +12,4 @@ EOM
|
|||
esac
|
||||
|
||||
printf "tx_daily_count.value "
|
||||
connectivity_tool --ip=127.0.0.1 --rpc-port=$ZANO_RPC_PORT --timeout=1000 --rpc-get-daemon-info --getinfo-flags-hex="0x0000000000000080" | grep transactions_cnt_per_day | cut -d ' ' -f2
|
||||
connectivity_tool --ip=127.0.0.1 --rpc-port=$ZANO_RPC_PORT --timeout=10000 --rpc-get-daemon-info --getinfo-flags-hex="0x0000000000000080" | grep transactions_cnt_per_day | cut -d ' ' -f2
|
||||
|
|
|
|||
|
|
@ -12,4 +12,4 @@ EOM
|
|||
esac
|
||||
|
||||
printf "tx_daily_volume.value "
|
||||
connectivity_tool --ip=127.0.0.1 --rpc-port=$ZANO_RPC_PORT --timeout=1000 --rpc-get-daemon-info --getinfo-flags-hex="0x0000000000000080" | grep transactions_volume_per_day | cut -d ' ' -f2
|
||||
connectivity_tool --ip=127.0.0.1 --rpc-port=$ZANO_RPC_PORT --timeout=10000 --rpc-get-daemon-info --getinfo-flags-hex="0x0000000000000080" | grep transactions_volume_per_day | cut -d ' ' -f2
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue