Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 12 additions & 10 deletions ots-git-gpg-wrapper
Original file line number Diff line number Diff line change
Expand Up @@ -39,9 +39,13 @@ parser = otsclient.args.make_common_options_arg_parser()
parser.add_argument("-g", "--gpg-program", action="store", default="/usr/bin/gpg",
help="Path to the GnuPG binary (default %(default)s)")

parser.add_argument('-c','--calendar', metavar='URL', dest='calendar_urls', action='append', type=str,
default=["https://a.pool.opentimestamps.org", "https://b.pool.opentimestamps.org", "https://a.pool.eternitywall.com"],
help='Create timestamp with the aid of a remote calendar. May be specified multiple times. Default: %(default)r')
parser.add_argument('-a', '--aggregator', metavar='URL', dest='aggregators', action='append', type=str,
default=[],
help='Add an aggregator')
parser.add_argument('--no-default-aggregators', action='store_true', default=False,
help='Do not use the default list of aggregators; '
'use only aggregators manually added with --aggregator')

parser.add_argument('-b','--btc-wallet', dest='use_btc_wallet', action='store_true',
help='Create timestamp locally with the local Bitcoin wallet.')
parser.add_argument('--rehash-trees', action='store_true',
Expand All @@ -50,14 +54,12 @@ parser.add_argument("gpgargs", nargs=argparse.REMAINDER,
help='Arguments passed to GnuPG binary')

parser.add_argument("--timeout", type=int, default=5,
help="Timeout before giving up on a calendar. "
help="Timeout before giving up on an aggregator. "
"Default: %(default)d")

parser.add_argument("-m", type=int, default="2",
help="Commitments are sent to remote calendars,"
"in the event of timeout the timestamp is considered "
"done if at least M calendars replied. "
"Default: %(default)s")
parser.add_argument("-m", type=int, metavar='M', default=2,
help="Require at least M of the aggregators to respond for the "
"timestamp to be considered complete. Default: %(default)d")

args = otsclient.args.handle_common_options(parser.parse_args(), parser)

Expand Down Expand Up @@ -134,7 +136,7 @@ if gpgargs.bsau:
final_timestamp = signed_commit_timestamp.ops.add(OpAppend(tree_stamper.timestamp.msg)).ops.add(OpSHA256())
minor_version = 1

otsclient.cmds.create_timestamp(final_timestamp, args.calendar_urls, args)
otsclient.cmds.create_timestamp(final_timestamp, args)

if args.wait:
# Interpreted as override by the upgrade command
Expand Down
18 changes: 10 additions & 8 deletions otsclient/args.py
Original file line number Diff line number Diff line change
Expand Up @@ -160,9 +160,13 @@ def parse_ots_args(raw_args):
parser_stamp = subparsers.add_parser('stamp', aliases=['s'],
help='Timestamp files')

parser_stamp.add_argument('-c', '--calendar', metavar='URL', dest='calendar_urls', action='append', type=str,
parser_stamp.add_argument('-a', '--aggregator', metavar='URL', dest='aggregators', action='append', type=str,
default=[],
help='Create timestamp with the aid of a remote calendar. May be specified multiple times.')
help='Add an aggregator')

parser_stamp.add_argument('--no-default-aggregators', action='store_true', default=False,
help='Do not use the default list of aggregators; '
'use only aggregators manually added with --aggregator')

parser_stamp.add_argument('-b', '--btc-wallet', dest='use_btc_wallet', action='store_true',
help='Create timestamp locally with the local Bitcoin wallet.')
Expand All @@ -172,14 +176,12 @@ def parse_ots_args(raw_args):
help='Filename')

parser_stamp.add_argument("--timeout", type=int, default=5,
help="Timeout before giving up on a calendar. "
help="Timeout (in seconds) before giving up on an aggregator. "
"Default: %(default)d")

parser_stamp.add_argument("-m", type=int, default="2",
help="Commitments are sent to remote calendars,"
"in the event of timeout the timestamp is considered "
"done if at least M calendars replied. "
"Default: %(default)s")
parser_stamp.add_argument("-m", type=int, metavar='M', default=2,
help="Require at least M of the aggregators to respond for the "
"timestamp to be considered complete. Default: %(default)d")

# ----- upgrade -----
parser_upgrade = subparsers.add_parser('upgrade', aliases=['u'],
Expand Down
49 changes: 24 additions & 25 deletions otsclient/cmds.py
Original file line number Diff line number Diff line change
Expand Up @@ -45,13 +45,8 @@ def remote_calendar(calendar_uri):
user_agent="OpenTimestamps-Client/%s" % otsclient.__version__)


def create_timestamp(timestamp, calendar_urls, args):
"""Create a timestamp

calendar_urls - List of calendar's to use
setup_bitcoin - False if Bitcoin timestamp not desired; set to
args.setup_bitcoin() otherwise.
"""
def create_timestamp(timestamp, args):
"""Create a timestamp"""

setup_bitcoin = args.setup_bitcoin if args.use_btc_wallet else False
if setup_bitcoin:
Expand Down Expand Up @@ -92,17 +87,23 @@ def create_timestamp(timestamp, calendar_urls, args):
assert block_timestamp is not None
timestamp.merge(block_timestamp)

aggregator_urls = [] if args.no_default_aggregators else list(opentimestamps.calendar.DEFAULT_AGGREGATORS)
aggregator_urls.extend(args.aggregators)

m = args.m
n = len(calendar_urls)
if m > n or m <= 0:
logging.error("m (%d) cannot be greater than available calendar%s (%d) neither less or equal 0" % (m, "" if n == 1 else "s", n))
n = len(aggregator_urls)
if m > n:
logging.error("m (%d) cannot be greater than number of available aggregators", m)
sys.exit(1)
elif m <= 0:
logging.error("m must greater than zero")
sys.exit(1)

logging.debug("Doing %d-of-%d request, timeout is %d second%s" % (m, n, args.timeout, "" if n == 1 else "s"))

q = Queue()
for calendar_url in calendar_urls:
submit_async(calendar_url, timestamp.msg, q, args.timeout)
for aggregator_url in aggregator_urls:
submit_async(aggregator_url, timestamp.msg, q, args.timeout)

start = time.time()
merged = 0
Expand All @@ -123,23 +124,27 @@ def create_timestamp(timestamp, calendar_urls, args):
# Timeout
continue

# FIXME: we should change this to have a concept of trusted calendars, and
# actually check that the aggregators return pending attestations with
# enough redundancy

if merged < m:
logging.error("Failed to create timestamp: need at least %d attestation%s but received %s within timeout" % (m, "" if m == 1 else "s", merged))
logging.error("Failed to create timestamp: need at least %d attestation%s but received only %s within timeout" % (m, "" if m == 1 else "s", merged))
sys.exit(1)
logging.debug("%.2f seconds elapsed" % (time.time()-start))


def submit_async(calendar_url, msg, q, timeout):
def submit_async(aggregator_url, msg, q, timeout):

def submit_async_thread(remote, msg, q, timeout):
try:
calendar_timestamp = remote.submit(msg, timeout=timeout)
q.put(calendar_timestamp)
aggregator_timestamp = remote.submit(msg, timeout=timeout)
q.put(aggregator_timestamp)
except Exception as exc:
q.put(exc)

logging.info('Submitting to remote calendar %s' % calendar_url)
remote = remote_calendar(calendar_url)
logging.info('Submitting to aggregator %s' % aggregator_url)
remote = remote_calendar(aggregator_url)
t = threading.Thread(target=submit_async_thread, args=(remote, msg, q, timeout))
t.start()

Expand Down Expand Up @@ -181,13 +186,7 @@ def stamp_command(args):

merkle_tip = make_merkle_tree(merkle_roots)

if not args.calendar_urls:
# Neither calendar nor wallet specified; add defaults
args.calendar_urls.append('https://a.pool.opentimestamps.org')
args.calendar_urls.append('https://b.pool.opentimestamps.org')
args.calendar_urls.append('https://a.pool.eternitywall.com')

create_timestamp(merkle_tip, args.calendar_urls, args)
create_timestamp(merkle_tip, args)

if args.wait:
upgrade_timestamp(merkle_tip, args)
Expand Down
22 changes: 20 additions & 2 deletions release-notes.md
Original file line number Diff line number Diff line change
@@ -1,13 +1,31 @@
# OpenTimestamps Client Release Notes

## v0.5.0
## v0.5.0-PENDING

Breaking change: The remote calendar whitelist options have been reworked. The
### Breaking Change: Calendar Whitelists

The remote calendar whitelist options have been reworked. The
new behavior is that the `--whitelist` option adds additional remote calendars
to the default whitelist. If you don't want to use the default whitelist, it
can be disabled with the `--no-default-whitelist` option, replacing the prior
`--no-remote-calendars` option, which no longer exists.

Previously the default whitelist was only loaded if `--whitelist` wasn't used
at all, making it the client inconvenient to use if you wanted to be able to
verify timestamps using both standard and non-standard calendars at the same
time.


### Breaking Change: Aggregators

Previously commands that created timestamps incorrectly used the term
"calendar" when they should have used the term "aggregator" in both
documentation and command line options. This version fixes that oversight by
renaming the `--calendar` options of the `stamp` subcommand and
`ots-git-gpg-wrapper` to `--aggregator`. As with the new calendar whitelist
options, there's a default list of aggregators that can be disabled with the
`--no-default-aggregators` option.


## v0.4.0

Expand Down