loops/agent/transport/base.py
helmutm a689fb09bb work in progress: process upload of resources from loops.agent via HTTP PUT
git-svn-id: svn://svn.cy55.de/Zope3/src/loops/trunk@1954 fd906abe-77d9-0310-91a1-e0d9ade77398
2007-08-23 13:28:15 +00:00

119 lines
3.7 KiB
Python

#
# Copyright (c) 2007 Helmut Merz helmutm@cy55.de
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
#
"""
Transporter base classes.
$Id$
"""
from base64 import b64encode
from twisted.internet import reactor
from twisted.internet.defer import Deferred, DeferredList, fail
from twisted.web.client import getPage
from zope.interface import implements
from loops.agent.interfaces import ITransporter, ITransportJob
from loops.agent.schedule import Job
class TransportJob(Job):
implements(ITransportJob)
def __init__(self, transporter):
super(TransportJob, self).__init__()
self.transporter = transporter
def execute(self):
result = self.params.get('result')
if result is None:
return fail('No data available.')
transfers = []
for resource in result:
d = self.transporter.transfer(resource)
transfers.append(d)
d.addCallback(self.logTransfer)
d.addErrback(self.logError)
return DeferredList(transfers)
def logTransfer(self, result, err=None):
# TODO: logging
# self.transporter.agent.logger.log(...)
pass
def logError(self, error):
print '*** error on transfer', self.transporter.serverURL, error
class Transporter(object):
implements(ITransporter)
jobFactory = TransportJob
serverURL = 'http://localhost:8080'
method = 'PUT'
machineName = 'unknown'
userName = 'nobody'
password = 'secret'
def __init__(self, agent, **params):
self.agent = agent
for k, v in params.items():
setattr(self, k ,v)
def createJob(self):
return self.jobFactory(self)
def transfer(self, resource):
data = resource.data
if type(data) is file:
text = data.read()
data.close()
else:
text = data
# TODO: encode text (?)
# TODO: set headers: Content-Type, Authorization, User-Agent
path = resource.path
app = resource.application
deferreds = []
metadata = resource.metadata
auth = b64encode(':'.join((self.userName, self.password)))
headers = {'Authorization': 'Basic ' + auth}
if metadata is not None:
url = self.makePath('.meta', app, path, 'xml')
deferreds.append(getPage(url, method=self.method, headers=headers,
postdata=metadata.asXML()))
url = self.makePath('.data', app, path)
deferreds.append(getPage(url, method=self.method, headers=headers,
postdata=text))
return DeferredList(deferreds, fireOnOneErrback=True)
def makePath(self, infoType, app, path, extension=None):
if path.startswith('/'):
path = path[1:]
url = self.serverURL
if url.endswith('/'):
url = url[:-1]
fullPath = '/'.join((url, infoType,
self.machineName, self.userName, app, path))
if extension:
fullPath += '.' + extension
return fullPath