SF.net SVN: fclient: [216] trunk/sandbox/fcp/fcp2_0_requests.py
Status: Pre-Alpha
Brought to you by:
jurner
|
From: <ju...@us...> - 2008-02-16 10:07:49
|
Revision: 216
http://fclient.svn.sourceforge.net/fclient/?rev=216&view=rev
Author: jurner
Date: 2008-02-16 02:07:55 -0800 (Sat, 16 Feb 2008)
Log Message:
-----------
worked a bit on uploads. Still a sketch
Modified Paths:
--------------
trunk/sandbox/fcp/fcp2_0_requests.py
Modified: trunk/sandbox/fcp/fcp2_0_requests.py
===================================================================
--- trunk/sandbox/fcp/fcp2_0_requests.py 2008-02-16 10:07:11 UTC (rev 215)
+++ trunk/sandbox/fcp/fcp2_0_requests.py 2008-02-16 10:07:55 UTC (rev 216)
@@ -4,28 +4,29 @@
#******************************************************************************************************************
#
#******************************************************************************************************************
+#TODO: if only one item is added its name is ignored so far. How to handle self.targetName vs. item['Name']
+#TODO: Metadata.ContentType vs. ContentType is pretty inconsistent
class Upload(object):
- """Wrapper class to represent a freenet upload
+ """Wrapper class to manage a freenet uploads
+ @ivar defaultItem: (int) for directories or multiple uploads the name of this item is used as
+ default item when a page is displayed
@ivar directoryAdded: (bool) True if the upload contains a directory, False otherwise
@ivar items: (list) of dicts containing paramaters for each upload
@ivar keyType: L{consts.KeyType} the type of key to upload
@ivar params: (dict) request parameters
@ivar privateKey: (str) private keey (required for SSK or USK uploads)
+ @ivar targetName: (str) for CHKs the name to be appended to the CHK. For SSKs and USKs the
+ (target-name/version) part of the key
@ivar targetNames: (list) of names already in use (for multi-uploads)
@note: you can upload one or more items of any kind (data, files, redirects), except from directories
wich have to be the only item to upload
"""
+ PrivateParamNames = ('Data', 'RequestType', 'Name')
- ReservedParamPrefix = 'Fc' # params prefixed with this are skipped when generating the message
- ItemTypeData = 0
- ItemTypeDirectory = 1
- ItemTypeFile = 2
- ItemTypeRedirect = 3
-
def __init__(self,
keyType,
dontCompress=None,
@@ -35,6 +36,7 @@
priorityClass=consts.Priority.Medium,
privateKey=None,
+ targetName=None,
):
"""
@param keyType: (L{consts.KeyType}) the desired key type to upload
@@ -45,14 +47,19 @@
@param priorityClass:
@param privateKey: (str) privateKey if keyType is SSK or USK
+ @param targetName:
"""
if keyType not in consts.KeyType.TypesAll:
raise ValueError('Invalid key type: %r' % keyType)
- if keyType in (consts.KeyType.SSK, consts.KeyType.USK) and privateKey is None:
- raise ValueError('For %s a public key is required' % keyType)
+ if keyType in (consts.KeyType.SSK, consts.KeyType.USK) :
+ if privateKey is None:
+ raise ValueError('For %s a public key is required' % keyType)
+ if not targetName:
+ raise ValueError('For %s a target name is required' % keyType)
elif keyType in (consts.KeyType.CHK, consts.KeyType.KSK) and privateKey is not None:
raise ValueError('For %s no public key is required' % keyType)
+ self.defaultItem = 0
self.directoryAdded = False
self.items = []
self.keyType = keyType
@@ -64,15 +71,16 @@
'PriorityClass': priorityClass,
}
self.privateKey = privateKey
+ self.targetName = targetName
self.targetNames = [] # record to check if names are unique (assert order is arbitrary)
- def _addItem(self, **params):
+ def _addItem(self, isDefault=False, **params):
"""Private method to add an upload item"""
if self.directoryAdded:
raise ValueError('A directory has already been added, no other items allowed')
- if params['FcItemType'] == self.ItemTypeDirectory:
+ if params['RequestType'] == self.RequestTypeDirectory:
if self.directoryAdded:
raise ValueError('An item has already been added, no additional directory allowed')
else:
@@ -85,16 +93,22 @@
self.targetNames.append(name)
self.items.append(params)
+ if isDefault:
+ self.defaultItem =len(self.items) -1
+
- def addData(self, name, data, contentType=None):
+ def addData(self, name, data, contentType=None, isDefault=False):
"""Adds data to be uploaded
@param name: target name
@param data: (str) data to upload
@param contentType: (str) content type of the data (if desired)
+ @param isDefault: (bool) if True, the item is the default item
"""
return self._addItem(
- FcItemType=self.ItemTypeData,
- FcData=data,
+ isDefault=isDefault,
+
+ RequestType=consts.RequestType.PutData,
+ Data=data,
ContentType=contentType,
DataLength=len(data),
Name=name,
@@ -111,7 +125,7 @@
@note: if you add a directory, every attempt to add anything else will fail
"""
return self._addItem(
- FcItemType=self.ItemTypeDirectory,
+ RequestType=consts.RequestType.PutDir,
AllowUnreadableFiles=allowUnreadableFiles,
Filename=directory,
Name=name,
@@ -119,28 +133,34 @@
)
- def addFile(self, name, filename, contentType=None):
+ def addFile(self, name, filename, contentType=None, isDefault=False):
"""Adds a file to be uploaded
@param name: target name
@param filename: (abspath) of the file to be uploaded
@param contentType: (str) content type of the file (if desired)
+ @param isDefault: (bool) if True, the item is the default item
"""
return self._addItem(
- FcItemType=self.ItemTypeFile,
+ isDefault=isDefault,
+
+ RequestType=sconsts.RequestType.PutFile,
ContentType=contentType,
Filename=filename,
Name=name,
UploadFrom=consts.UploadFrom.Disk,
)
-
- def addRedirect(self, name, redirect):
+ #TODO: isDefault for redirects???
+ def addRedirect(self, name, redirect, isDefault=False):
"""Adds a redirect to be uploaded
@param name: target name
@param redirect: (freenet-key) to redirect to
+ @param isDefault: (bool) if True, the item is the default item
"""
return self._addItem(
- FcItemType=self.ItemTypeRedirect,
+ isDefault=isDefault,
+
+ RequestType=consts.RequestType.PutRedirect,
ContentType=contentType,
DataLength=len(data),
Name=name,
@@ -152,81 +172,80 @@
def getMessage(self, messageClass):
"""Returns the message for the request, ready to send the request to the node
@param messageClass: (L{fcp2_0_message.Message}) class to fill in
- @return: (L{fcp2_0_message.Message}) instance
+ @return: (tuple) (L{consts.RequestType}, L{fcp2_0_message.Message}) or (None, None)
+ if ther is nothing to upload
"""
n = len(self.items)
if n == 0:
- return None
+ return None, None
- elif n == 1 and self.items[0]['FcItemType'] == self.ItemTypeDirectory:
- msg = messageClass(consts.Message.ClientPutDiskDir)
- params = self.items[0]
- targetName = params.pop('Name')
- for param, value in params.items():
- if value is None:
- continue
- if param.startswith(self.ReservedParamPrefix):
- continue
- msg[param] = value
+ elif n == 1:
+ requestType = self.items[0]['RequestType']
- elif n == 1:
- msg = messageClass(consts.Message.ClientPut)
- params = self.items[0]
- targetFilename = params.pop('Name')
- for param, value in params.items():
- if value is None:
- continue
- if param.startswith(self.ReservedParamPrefix):
- continue
+ if requestType == consts.RequestType.PutDir:
+ msg = messageClass(consts.Message.ClientPutDiskDir)
+ params = self.items[0]
+ for param, value in params.items():
+ if value is None or param in PrivateParamNames:
+ continue
+ msg[param] = value
+
+ item = self.items[self.defaultItem]
+ msg['DefaultName'] = item['Name']
+
+ else:
+ msg = messageClass(consts.Message.ClientPut)
+ for param, value in params.items():
+ if value is None or param in PrivateParamNames:
+ continue
+ if param == 'ContentType':
+ param = 'Metadata.ContentType'
+ msg[param] = value
+
+ if params['RequestType'] == self.RequestTypeData:
+ msg.data = params['Data']
- if param == 'ContentType':
- param = 'Metadata.ContentType'
- msg[param] = value
-
- if params['FcItemType'] == self.ItemTypeData:
- msg.data = params['FcData']
- if self.keyType == consts.KeyType.CHK:
- msg['TargetFilename'] = targetFilename
-
-
- #TODO: USK@s allowed for complex dirs?
else:
-
- #NOTE: for simplicity we take the first item as default item and its name
- # as TargetName if that causes any problems, pass it twice
+ requestType = consts.PutMultipole
msg = messageClass(consts.Message.ClientPutComplexDir)
- msg.data = ''
- header = self.items.pop(0)
- targetFilename = header['Name']
- msg['DefaultName'] = self.items[0]['Name']
- k = 0
- for itemParams in self.items:
+ data = None
+ for n, itemParams in enumerate(self.items):
for param, value in itemParams.items():
- if value is None:
+ if param == 'Data':
+ if data is None:
+ data = ''
+ data += value
continue
- if param.startswith(self.ReservedParamPrefix):
- if param == 'FcData':
- msg.data += value
+
+ if param == 'Name':
+ param = 'Files.%s.%s' % (n, param)
+ msg[param] = value
continue
-
+
+ if value is None or param in PrivateParamNames:
+ continue
+
if param == 'ContentType':
param = 'Metadata.ContentType'
- param = 'Files.%s.%s' % (k, param)
+ param = 'Files.%s.%s' % (n, param)
msg[param] = value
- k += 1
+
+ item = self.items[self.defaultItem]
+ msg['DefaultName'] = item['Name']
+ if data is not None:
+ msg.data = data
- if not msg.data:
- msg.data = None
-
# determine Uri
if self.keyType == consts.KeyType.CHK:
msg['URI'] = consts.KeyType.CHK
+ if self.targetName:
+ msg['TargetFilename'] = self.targetName
elif self.keyType == consts.KeyType.KSK:
- msg['URI'] = consts.KeyType.KSK + targetFilename
+ msg['URI'] = consts.KeyType.KSK + self.targetName
elif self.keyType == consts.KeyType.SSK:
- msg['URI'] = self.privateKey + targetFilename
+ msg['URI'] = self.privateKey + self.targetName
elif self.keyType == consts.KeyType.USK:
- msg['URI'] = self.privateKey + targetFilename
+ msg['URI'] = self.privateKey + self.targetName
# set params and some defaults
msg['Global'] = False
@@ -236,5 +255,5 @@
continue
msg[param] = value
- return msg
+ return requestType, msg
This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
|