'Upload a file to flickr.
Be extra careful you spell the parameters correctly, or you will
get a rather cryptic "Invalid Signature" error on the upload!
Supported parameters:
One of filename or jpegData must be specified by name when
calling this method:
filename -- name of a file to upload
jpegData -- array of jpeg data to upload
api_key
auth_token
title
description
tags -- space-delimited list of tags, "tag1 tag2 tag3"
is_public -- "1" or "0"
is_friend -- "1" or "0"
is_family -- "1" or "0"'

def upload(self, filename=None, jpegData=None, **arg):

    if (((filename == None) and (jpegData == None)) or ((filename != None) and (jpegData != None))):
        raise UploadException('filename    OR    jpegData    must    be    specified')
    for a in arg.keys():
        if ((a != 'api_key') and (a != 'auth_token') and (a != 'title') and (a != 'description') and (a != 'tags') and (a != 'is_public') and (a != 'is_friend') and (a != 'is_family')):
            sys.stderr.write(('FlickrAPI:    warning:    unknown    parameter    "%s"    sent    to    FlickrAPI.upload\n' % a))
    arg['api_sig'] = self.__sign(arg)
    url = (('http://' + FlickrAPI.flickrHost) + FlickrAPI.flickrUploadForm)
    boundary = mimetools.choose_boundary()
    body = ''
    for a in ('api_key', 'auth_token', 'api_sig'):
        body += ('--%s\r\n' % boundary)
        body += (('Content-Disposition:    form-data;    name="' + a) + '"\r\n\r\n')
        body += ('%s\r\n' % arg[a])
    for a in ('title', 'description', 'tags', 'is_public', 'is_friend', 'is_family'):
        if arg.has_key(a):
            body += ('--%s\r\n' % boundary)
            body += (('Content-Disposition:    form-data;    name="' + a) + '"\r\n\r\n')
            body += ('%s\r\n' % arg[a])
    body += ('--%s\r\n' % boundary)
    body += 'Content-Disposition:    form-data;    name="photo";'
    body += ('    filename="%s"\r\n' % filename)
    body += 'Content-Type:    image/jpeg\r\n\r\n'
    if (filename != None):
        fp = file(filename, 'rb')
        data = fp.read()
        fp.close()
    else:
        data = jpegData
    postData = ((body.encode('utf_8') + data) + ('--%s--' % boundary).encode('utf_8'))
    request = urllib2.Request(url)
    request.add_data(postData)
    request.add_header('Content-Type', ('multipart/form-data;    boundary=%s' % boundary))
    response = urllib2.urlopen(request)
    rspXML = response.read()
    return XMLNode.parseXML(rspXML)
