SEP='(?::|%3A)'
NUMBER='([0-9]+)'
NUMBER_IGNORE='(?:[0-9]+)'
-OPTIONAL_EXTENSION_FIELD = '(' + SEP + '[0-9' + SEP + ']+|)'
# "human-encoded" URIs are allowed to come with a leading
# 'http://127.0.0.1:(8123|3456)/uri/' that will be ignored.
def get_verify_cap(self):
return SSKVerifierURI(self.storage_index, self.fingerprint)
- def get_extension_params(self):
- return []
-
- def set_extension_params(self, params):
- pass
-
class ReadonlySSKFileURI(_BaseURI):
implements(IURI, IMutableFileURI)
def get_verify_cap(self):
return SSKVerifierURI(self.storage_index, self.fingerprint)
- def get_extension_params(self):
- return []
-
- def set_extension_params(self, params):
- pass
-
class SSKVerifierURI(_BaseURI):
implements(IVerifierURI)
def get_verify_cap(self):
return self
- def get_extension_params(self):
- return []
-
- def set_extension_params(self, params):
- pass
-
-class WritableMDMFFileURI(_BaseURI):
+class WriteableMDMFFileURI(_BaseURI):
implements(IURI, IMutableFileURI)
BASE_STRING='URI:MDMF:'
- STRING_RE=re.compile('^'+BASE_STRING+BASE32STR_128bits+':'+BASE32STR_256bits+OPTIONAL_EXTENSION_FIELD+'$')
- HUMAN_RE=re.compile('^'+OPTIONALHTTPLEAD+'URI'+SEP+'MDMF'+SEP+BASE32STR_128bits+SEP+BASE32STR_256bits+OPTIONAL_EXTENSION_FIELD+'$')
+ STRING_RE=re.compile('^'+BASE_STRING+BASE32STR_128bits+':'+BASE32STR_256bits+'(:|$)')
+ HUMAN_RE=re.compile('^'+OPTIONALHTTPLEAD+'URI'+SEP+'MDMF'+SEP+BASE32STR_128bits+SEP+BASE32STR_256bits+'(:|$)')
- def __init__(self, writekey, fingerprint, params=[]):
+ def __init__(self, writekey, fingerprint):
self.writekey = writekey
self.readkey = hashutil.ssk_readkey_hash(writekey)
self.storage_index = hashutil.ssk_storage_index_hash(self.readkey)
assert len(self.storage_index) == 16
self.fingerprint = fingerprint
- self.extension = params
@classmethod
def init_from_human_encoding(cls, uri):
mo = cls.HUMAN_RE.search(uri)
if not mo:
raise BadURIError("'%s' doesn't look like a %s cap" % (uri, cls))
- params = filter(lambda x: x != '', re.split(SEP, mo.group(3)))
- return cls(base32.a2b(mo.group(1)), base32.a2b(mo.group(2)), params)
+ return cls(base32.a2b(mo.group(1)), base32.a2b(mo.group(2)))
@classmethod
def init_from_string(cls, uri):
mo = cls.STRING_RE.search(uri)
if not mo:
raise BadURIError("'%s' doesn't look like a %s cap" % (uri, cls))
- params = mo.group(3)
- params = filter(lambda x: x != '', params.split(":"))
- return cls(base32.a2b(mo.group(1)), base32.a2b(mo.group(2)), params)
+ return cls(base32.a2b(mo.group(1)), base32.a2b(mo.group(2)))
def to_string(self):
assert isinstance(self.writekey, str)
assert isinstance(self.fingerprint, str)
ret = 'URI:MDMF:%s:%s' % (base32.b2a(self.writekey),
base32.b2a(self.fingerprint))
- if self.extension:
- ret += ":"
- ret += ":".join(self.extension)
-
return ret
def __repr__(self):
return True
def get_readonly(self):
- return ReadonlyMDMFFileURI(self.readkey, self.fingerprint, self.extension)
+ return ReadonlyMDMFFileURI(self.readkey, self.fingerprint)
def get_verify_cap(self):
- return MDMFVerifierURI(self.storage_index, self.fingerprint, self.extension)
-
- def get_extension_params(self):
- return self.extension
-
- def set_extension_params(self, params):
- params = map(str, params)
- self.extension = params
+ return MDMFVerifierURI(self.storage_index, self.fingerprint)
class ReadonlyMDMFFileURI(_BaseURI):
implements(IURI, IMutableFileURI)
BASE_STRING='URI:MDMF-RO:'
- STRING_RE=re.compile('^' +BASE_STRING+BASE32STR_128bits+':'+BASE32STR_256bits+OPTIONAL_EXTENSION_FIELD+'$')
- HUMAN_RE=re.compile('^'+OPTIONALHTTPLEAD+'URI'+SEP+'MDMF-RO'+SEP+BASE32STR_128bits+SEP+BASE32STR_256bits+OPTIONAL_EXTENSION_FIELD+'$')
+ STRING_RE=re.compile('^' +BASE_STRING+BASE32STR_128bits+':'+BASE32STR_256bits+'(:|$)')
+ HUMAN_RE=re.compile('^'+OPTIONALHTTPLEAD+'URI'+SEP+'MDMF-RO'+SEP+BASE32STR_128bits+SEP+BASE32STR_256bits+'(:|$)')
- def __init__(self, readkey, fingerprint, params=[]):
+ def __init__(self, readkey, fingerprint):
self.readkey = readkey
self.storage_index = hashutil.ssk_storage_index_hash(self.readkey)
assert len(self.storage_index) == 16
self.fingerprint = fingerprint
- self.extension = params
@classmethod
def init_from_human_encoding(cls, uri):
mo = cls.HUMAN_RE.search(uri)
if not mo:
raise BadURIError("'%s' doesn't look like a %s cap" % (uri, cls))
- params = mo.group(3)
- params = filter(lambda x: x!= '', re.split(SEP, params))
- return cls(base32.a2b(mo.group(1)), base32.a2b(mo.group(2)), params)
+ return cls(base32.a2b(mo.group(1)), base32.a2b(mo.group(2)))
@classmethod
def init_from_string(cls, uri):
if not mo:
raise BadURIError("'%s' doesn't look like a %s cap" % (uri, cls))
- params = mo.group(3)
- params = filter(lambda x: x != '', params.split(":"))
- return cls(base32.a2b(mo.group(1)), base32.a2b(mo.group(2)), params)
+ return cls(base32.a2b(mo.group(1)), base32.a2b(mo.group(2)))
def to_string(self):
assert isinstance(self.readkey, str)
assert isinstance(self.fingerprint, str)
ret = 'URI:MDMF-RO:%s:%s' % (base32.b2a(self.readkey),
base32.b2a(self.fingerprint))
- if self.extension:
- ret += ":"
- ret += ":".join(self.extension)
-
return ret
def __repr__(self):
return self
def get_verify_cap(self):
- return MDMFVerifierURI(self.storage_index, self.fingerprint, self.extension)
-
- def get_extension_params(self):
- return self.extension
-
- def set_extension_params(self, params):
- params = map(str, params)
- self.extension = params
+ return MDMFVerifierURI(self.storage_index, self.fingerprint)
class MDMFVerifierURI(_BaseURI):
implements(IVerifierURI)
BASE_STRING='URI:MDMF-Verifier:'
- STRING_RE=re.compile('^'+BASE_STRING+BASE32STR_128bits+':'+BASE32STR_256bits+OPTIONAL_EXTENSION_FIELD+'$')
- HUMAN_RE=re.compile('^'+OPTIONALHTTPLEAD+'URI'+SEP+'MDMF-Verifier'+SEP+BASE32STR_128bits+SEP+BASE32STR_256bits+OPTIONAL_EXTENSION_FIELD+'$')
+ STRING_RE=re.compile('^'+BASE_STRING+BASE32STR_128bits+':'+BASE32STR_256bits+'(:|$)')
+ HUMAN_RE=re.compile('^'+OPTIONALHTTPLEAD+'URI'+SEP+'MDMF-Verifier'+SEP+BASE32STR_128bits+SEP+BASE32STR_256bits+'(:|$)')
- def __init__(self, storage_index, fingerprint, params=[]):
+ def __init__(self, storage_index, fingerprint):
assert len(storage_index) == 16
self.storage_index = storage_index
self.fingerprint = fingerprint
- self.extension = params
@classmethod
def init_from_human_encoding(cls, uri):
mo = cls.HUMAN_RE.search(uri)
if not mo:
raise BadURIError("'%s' doesn't look like a %s cap" % (uri, cls))
- params = mo.group(3)
- params = filter(lambda x: x != '', re.split(SEP, params))
- return cls(si_a2b(mo.group(1)), base32.a2b(mo.group(2)), params)
+ return cls(si_a2b(mo.group(1)), base32.a2b(mo.group(2)))
@classmethod
def init_from_string(cls, uri):
mo = cls.STRING_RE.search(uri)
if not mo:
raise BadURIError("'%s' doesn't look like a %s cap" % (uri, cls))
- params = mo.group(3)
- params = filter(lambda x: x != '', params.split(":"))
- return cls(si_a2b(mo.group(1)), base32.a2b(mo.group(2)), params)
+ return cls(si_a2b(mo.group(1)), base32.a2b(mo.group(2)))
def to_string(self):
assert isinstance(self.storage_index, str)
assert isinstance(self.fingerprint, str)
ret = 'URI:MDMF-Verifier:%s:%s' % (si_b2a(self.storage_index),
base32.b2a(self.fingerprint))
- if self.extension:
- ret += ':'
- ret += ":".join(self.extension)
-
return ret
def is_readonly(self):
def get_verify_cap(self):
return self
- def get_extension_params(self):
- return self.extension
-
class _DirectoryBaseURI(_BaseURI):
implements(IURI, IDirnodeURI)
def __init__(self, filenode_uri=None):
BASE_STRING='URI:DIR2-MDMF:'
BASE_STRING_RE=re.compile('^'+BASE_STRING)
BASE_HUMAN_RE=re.compile('^'+OPTIONALHTTPLEAD+'URI'+SEP+'DIR2-MDMF'+SEP)
- INNER_URI_CLASS=WritableMDMFFileURI
+ INNER_URI_CLASS=WriteableMDMFFileURI
def __init__(self, filenode_uri=None):
if filenode_uri:
return ImmutableDirectoryURI(filecap)
if isinstance(filecap, LiteralFileURI):
return LiteralDirectoryURI(filecap)
- if isinstance(filecap, WritableMDMFFileURI):
+ if isinstance(filecap, WriteableMDMFFileURI):
return MDMFDirectoryURI(filecap)
if isinstance(filecap, ReadonlyMDMFFileURI):
return ReadonlyMDMFDirectoryURI(filecap)
def is_mutable(self):
return False
+ def is_readonly(self):
+ return True
+
+ def get_readonly(self):
+ return self
+
+
class DirectoryURIVerifier(_DirectoryBaseURI):
implements(IVerifierURI)
def is_mutable(self):
return False
+ def is_readonly(self):
+ return True
+
+ def get_readonly(self):
+ return self
+
class ImmutableDirectoryURIVerifier(DirectoryURIVerifier):
implements(IVerifierURI)
# on all URIs, even though we would only strictly need to do so for caps of
# new formats (post Tahoe-LAFS 1.6). URIs that are not consistent with their
# prefix are treated as unknown. This should be revisited when we add the
- # new cap formats. See <http://allmydata.org/trac/tahoe/ticket/833#comment:31>.
+ # new cap formats. See <http://allmydata.org/trac/tahoe-lafs/ticket/833#comment:31>.
s = u
can_be_mutable = can_be_writeable = not deep_immutable
if s.startswith(ALLEGED_IMMUTABLE_PREFIX):
elif s.startswith('URI:SSK-Verifier:'):
return SSKVerifierURI.init_from_string(s)
elif s.startswith('URI:MDMF:'):
- return WritableMDMFFileURI.init_from_string(s)
+ if can_be_writeable:
+ return WriteableMDMFFileURI.init_from_string(s)
+ kind = "URI:MDMF file writecap"
elif s.startswith('URI:MDMF-RO:'):
- return ReadonlyMDMFFileURI.init_from_string(s)
+ if can_be_mutable:
+ return ReadonlyMDMFFileURI.init_from_string(s)
+ kind = "URI:MDMF-RO readcap to a mutable file"
elif s.startswith('URI:MDMF-Verifier:'):
return MDMFVerifierURI.init_from_string(s)
elif s.startswith('URI:DIR2:'):
return DirectoryURIVerifier.init_from_string(s)
elif s.startswith('URI:DIR2-CHK:'):
return ImmutableDirectoryURI.init_from_string(s)
+ elif s.startswith('URI:DIR2-CHK-Verifier:'):
+ return ImmutableDirectoryURIVerifier.init_from_string(s)
elif s.startswith('URI:DIR2-LIT:'):
return LiteralDirectoryURI.init_from_string(s)
elif s.startswith('URI:DIR2-MDMF:'):
if can_be_mutable:
return ReadonlyMDMFDirectoryURI.init_from_string(s)
kind = "URI:DIR2-MDMF-RO readcap to a mutable directory"
+ elif s.startswith('URI:DIR2-MDMF-Verifier:'):
+ return MDMFDirectoryURIVerifier.init_from_string(s)
elif s.startswith('x-tahoe-future-test-writeable:') and not can_be_writeable:
# For testing how future writeable caps would behave in read-only contexts.
kind = "x-tahoe-future-test-writeable: testing cap"