Browse Source

Support maxcjfee settings for tumble in Qt

Also refactor tumbler offer filter callback to tumble_support
Add default values for first page of tumbler wizard (Qt)
master
Adam Gibson 10 years ago
parent
commit
cdd072eb8c
No known key found for this signature in database
GPG Key ID: B3AE09F1E9A3197A
  1. 3
      jmclient/jmclient/__init__.py
  2. 16
      jmclient/jmclient/tumble_support.py
  3. 10
      scripts/joinmarket-qt.py
  4. 34
      scripts/qtsupport.py
  5. 17
      scripts/tumbler.py

3
jmclient/jmclient/__init__.py

@ -35,7 +35,8 @@ from .schedule import (get_schedule, get_tumble_schedule, schedule_to_text,
schedule_to_text)
from .commitment_utils import get_utxo_info, validate_utxo_data, quit
from .tumble_support import (tumbler_taker_finished_update, restart_waiter,
restart_wait, get_tumble_log)
restart_wait, get_tumble_log,
tumbler_filter_orders_callback)
# Set default logging handler to avoid "No handler found" warnings.
try:

16
jmclient/jmclient/tumble_support.py

@ -168,3 +168,19 @@ def tumbler_taker_finished_update(taker, schedulefile, tumble_log, options,
taker.schedule[taker.schedule_index][5] = 1
with open(schedulefile, "wb") as f:
f.write(schedule_to_text(taker.schedule))
def tumbler_filter_orders_callback(orders_fees, cjamount, taker, options):
"""Since the tumbler does not use interactive fee checking,
we use the -x values from the command line instead.
"""
orders, total_cj_fee = orders_fees
abs_cj_fee = 1.0 * total_cj_fee / taker.n_counterparties
rel_cj_fee = abs_cj_fee / cjamount
log.info('rel/abs average fee = ' + str(rel_cj_fee) + ' / ' + str(
abs_cj_fee))
if rel_cj_fee > options['maxcjfee'][
0] and abs_cj_fee > options['maxcjfee'][1]:
log.info("Rejected fees as too high according to options, will retry.")
return "retry"
return True

10
scripts/joinmarket-qt.py

@ -53,7 +53,7 @@ from jmclient import (load_program_config, get_network, Wallet,
get_blockchain_interface_instance, sync_wallet,
RegtestBitcoinCoreInterface, tweak_tumble_schedule,
human_readable_schedule_entry, tumbler_taker_finished_update,
get_tumble_log, restart_wait)
get_tumble_log, restart_wait, tumbler_filter_orders_callback)
from qtsupport import (ScheduleWizard, warnings, config_tips, config_types,
TaskThread, QtHandler, XStream, Buttons, CloseButton,
@ -614,7 +614,9 @@ class SpendTab(QWidget):
#sync_wallet(w.wallet, fast=True)
#Decide whether to interrupt processing to sanity check the fees
if jm_single().config.get("GUI", "checktx") == "true":
if self.tumbler_options:
check_offers_callback = self.checkOffersTumbler
elif jm_single().config.get("GUI", "checktx") == "true":
check_offers_callback = self.callback_checkOffers
else:
check_offers_callback = None
@ -699,6 +701,10 @@ class SpendTab(QWidget):
self.abortTransactions()
self.taker_info_response = True
def checkOffersTumbler(self, offers_fees, cjamount):
return tumbler_filter_orders_callback(offers_fees, cjamount,
self.taker, self.tumbler_options)
def checkOffers(self):
"""Parse offers and total fee from client protocol,
allow the user to agree or decide.

34
scripts/qtsupport.py

@ -508,24 +508,29 @@ class SchDynamicPage1(QWizardPage):
sN = ['Starting mixdepth', 'Average number of counterparties',
'How many mixdepths to tumble through',
'Average wait time between transactions, in minutes',
'Average number of transactions per mixdepth']
'Average number of transactions per mixdepth',
'Max relative fee per counterparty (e.g. 0.005)',
'Max fee per counterparty, satoshis (e.g. 10000)']
#Tooltips
sH = ["The starting mixdepth can be decided from the Wallet tab; it must "
"have coins in it, but it's OK if some coins are in other mixdepths.",
"How many other participants are in each coinjoin, on average; but "
"each individual coinjoin will have a number that's slightly varied "
"from this, randomly",
"each individual coinjoin will have a number that's varied according to "
"settings on the next page",
"For example, if you start at mixdepth 1 and enter 4 here, the tumble "
"will move coins from mixdepth 1 to mixdepth 5",
"This is the time waited *after* 1 confirmation has occurred, and is "
"varied randomly.",
"Will be varied randomly, with a minimum of 1 per mixdepth"]
"Will be varied randomly, see advanced settings next page",
"A decimal fraction (e.g. 0.001 = 0.1%) (this AND next must be violated to reject",
"Integer number of satoshis (this AND previous must be violated to reject)"]
#types
sT = [int, int, int, float, int]
sT = [int, int, int, float, int, float, int]
#constraints
sMM = [(0, jm_single().config.getint("GUI", "max_mix_depth") - 1), (3, 20),
(1, 5), (0.00000001, 100.0, 8), (2, 10)]
sD = ['', '', '', '', '']
(1, 5), (0.00000001, 100.0, 8), (2, 10), (0.000001, 0.25, 6),
(0, 10000000)]
sD = ['0', '4', '4', '0.25', '3', '0.005', '10000']
for x in zip(sN, sH, sT, sD, sMM):
ql = QLabel(x[0])
ql.setToolTip(x[1])
@ -541,11 +546,13 @@ class SchDynamicPage1(QWizardPage):
layout.addWidget(x[0], i + 1, 0)
layout.addWidget(x[1], i + 1, 1, 1, 2)
self.setLayout(layout)
self.registerField("mixdepthsrc*", results[0][1])
self.registerField("makercount*", results[1][1])
self.registerField("mixdepthcount*", results[2][1])
self.registerField("timelambda*", results[3][1])
self.registerField("txcountparams*", results[4][1])
self.registerField("mixdepthsrc", results[0][1])
self.registerField("makercount", results[1][1])
self.registerField("mixdepthcount", results[2][1])
self.registerField("timelambda", results[3][1])
self.registerField("txcountparams", results[4][1])
self.registerField("maxrelfee", results[5][1])
self.registerField("maxabsfee", results[6][1])
class SchDynamicPage2(QWizardPage):
@ -692,6 +699,9 @@ class ScheduleWizard(QWizard):
self.opts['timelambda'] = float(self.field("timelambda").toString())
self.opts['waittime'] = float(self.field("waittime").toString())
self.opts['mincjamount'] = int(self.field("mincjamount").toString())
relfeeval = float(self.field("maxrelfee").toString())
absfeeval = int(self.field("maxabsfee").toString())
self.opts['maxcjfee'] = (relfeeval, absfeeval)
#needed for Taker to check:
jm_single().mincjamount = self.opts['mincjamount']
return get_tumble_schedule(self.opts, self.destaddrs)

17
scripts/tumbler.py

@ -19,7 +19,7 @@ from jmclient import (Taker, load_program_config, get_schedule,
RegtestBitcoinCoreInterface, estimate_tx_fee,
tweak_tumble_schedule, human_readable_schedule_entry,
schedule_to_text, restart_waiter, get_tumble_log,
tumbler_taker_finished_update)
tumbler_taker_finished_update, tumbler_filter_orders_callback)
from jmbase.support import get_log, debug_dump_object, get_password
from cli_options import get_tumbler_parser
@ -101,20 +101,9 @@ def main():
print("Progress logging to logs/TUMBLE.log")
def filter_orders_callback(orders_fees, cjamount):
"""Since the tumbler does not use interactive fee checking,
we use the -x values from the command line instead.
"""Decide whether to accept fees
"""
orders, total_cj_fee = orders_fees
abs_cj_fee = 1.0 * total_cj_fee / taker.n_counterparties
rel_cj_fee = abs_cj_fee / cjamount
log.info('rel/abs average fee = ' + str(rel_cj_fee) + ' / ' + str(
abs_cj_fee))
if rel_cj_fee > options['maxcjfee'][
0] and abs_cj_fee > options['maxcjfee'][1]:
log.info("Rejected fees as too high according to options, will retry.")
return "retry"
return True
return tumbler_filter_orders_callback(orders_fees, cjamount, taker, options)
def taker_finished(res, fromtx=False, waittime=0.0, txdetails=None):
"""on_finished_callback for tumbler; processing is almost entirely

Loading…
Cancel
Save