# 2013-07-03 johnpfeiffer
import sys
import os
import hashlib
import logging
import Queue # TODO: multithreading and batch
from lib import requests
from lib import o2lib
from collections import namedtuple
FileInfo = namedtuple( 'FileInfo' , 'fullPath, name, size, lastModified, hashValue' )
APPLICATION_NAME = 'APIUploader-0.3'
class AgentFactory( object ):
api_url = ''
api_key = ''
user = ''
password = ''
def __init__( self , caller_name , api_url , api_key , user , password ):
self.caller_name = caller_name
self.api_url = api_url
self.api_key = api_key
self.user = user
self.password = password
def create_valid_agent( self ):
agent = o2lib.OxygenAdapter( self.api_key , self.caller_name , self.api_url )
return self.login( agent )
def login( self , agent ):
user_login = agent.request_login_url()
agent.login_regular_user( user_login.tokenId , self.user , self.password ) # throws an Exception if there's a problem
agent.validate_login( user_login.tokenId ) # throws an Exception if there's a problem
return agent
class Uploader( object ):
@staticmethod
def get_files( directory ):
files = list()
for element in os.listdir( directory ):
full_path = os.path.join( directory , element )
if os.path.isfile( full_path ):
print element
if( element[0] != '.' ):
files.append( full_path )
return files
@staticmethod
def get_file_info( local_file_path ):
if not local_file_path:
raise ValueError( "ERROR could not find local file")
file_name = os.path.basename( local_file_path )
file_metadata = os.stat( local_file_path )
file_last_modified = file_metadata.st_mtime
file_size = file_metadata.st_size
sha1_instance = hashlib.sha1()
with open( local_file_path, 'rb' ) as file:
while True:
buffer = file.read( 1024 * 1024 ) # 1 MB buffer
if not buffer:
break
sha1_instance.update( buffer )
sha1_digest = sha1_instance.hexdigest()
file_sha1 = sha1_digest
return file_name , file_size , file_last_modified , file_sha1
@staticmethod
def upload( url, file_name, file_path ):
result = False
print 'using URL:', url
response = requests.post( url, files= { 'file': (file_name, open(file_path, 'rb')) } )
print response.status_code,
if response.status_code == 200:
print "Success! Confirming upload..."
result = True
else:
print "Fail!"
return result
if __name__ == '__main__':
CORRECTUSAGE = 'python uploader.py https://API.URL apikey user password local_path target_space'
if len( sys.argv ) < 7:
print 'ERROR: incorrect number of arguments (%s), correct usage: %s' % ( (len( sys.argv ) -1 ) , CORRECTUSAGE )
sys.exit( 1 )
api_url = sys.argv[1]
api_key = sys.argv[2]
user = sys.argv[3]
password = sys.argv[4]
local_path = sys.argv[5]
target_space_name = sys.argv[6]
try:
# login and find the target space
agent_factory = AgentFactory( APPLICATION_NAME, api_url , api_key , user , password )
agent = agent_factory.create_valid_agent()
spaces = agent.findAllSpacesInAccount( 0 )
print 'Spaces available:', repr( spaces )
target_oid = None
target_repository = None
for space in spaces:
if space.name == target_space_name:
print 'Found: ', space.name
target_oid = space.oid
target_repository = space.repositoryNodeId
if not target_oid:
print u"Could not find Space {}".format( target_space_name )
sys.exit( 1 )
# get the list of files and upload them
files = Uploader.get_files( local_path )
print "Found {} files: {}".format( len( files ) , files )
for file_path in files:
file_name , file_size , file_last_modified , file_sha1 = Uploader.get_file_info( file_path )
print u"Registering upload for: {} last modified: {} with size: {} bytes and hash: {}".format( file_name, file_last_modified, file_size, file_sha1 )
upload_url_wrapper = agent.create_upload_object( target_oid, target_repository, file_name, file_size , parent_folder_id = '' )
if Uploader.upload( upload_url_wrapper.uploadURL, file_name, file_path ):
file_id = agent.confirm_upload( target_oid, '', upload_url_wrapper.id, file_name, file_sha1, target_repository, file_last_modified)
if file_id:
print "{}/{} now has cloud oid: {}".format( target_space_name, file_name, file_id )
except o2lib.ApiInvalidInputException as error:
error_detail = o2lib.ApiInvalidInputErrorCode._VALUES_TO_NAMES[ error.errorCode ]
print '%s REASON: %s' % ( str( error ) , str( error_detail ) )
except o2lib.ApiRuleException as error:
error_detail = o2lib.ApiRuleErrorCode._VALUES_TO_NAMES[ error.errorCode ]
print '%s REASON: %s' % ( str( error ) , str( error_detail ) )
except o2lib.ApiSystemsException , error :
error_detail = o2lib.ApiSystemsErrorCode._VALUES_TO_NAMES[ error.errorCode ]
print '%s REASON: %s' % ( str( error ) , str( error_detail ) )
except o2lib.ApiSessionException , error :
error_detail = o2lib.ApiSessionErrorCode._VALUES_TO_NAMES[ error.errorCode ]
print '%s REASON: %s' % ( str( error ) , str( error_detail ) )
sys.exit( 1 )
except IOError as error:
print '%s ' % ( str( error ) )
except o2lib.ApiUnexpectedException , error :
print '%s REASON: %s' % ( str( error ) )
sys.exit( 1 )