17
16
# You should have received a copy of the GNU General Public License
18
17
# along with this program. If not, see <http://www.gnu.org/licenses/>.
21
gettext.bindtextdomain('sendToImageshack', '.')
22
gettext.textdomain('sendToImageshack')
27
from threading import Thread
20
from AbstractPycurlPlugin import AbstractPycurlPlugin
21
from pycurl import FORM_FILE
29
22
#from helpers.gnomeHelper import getMimeTypes
30
23
from StringIO import StringIO
31
from threading import BoundedSemaphore
32
24
from xml.dom import minidom
33
25
from libs.uploadHelper import createLinks
34
26
from libs.cliHelper import printLink, printProgressToCLI
37
from plugins.libs.pycurlHelper import getPycurlProxyAuthenticationType
38
from Settings import Settings
42
acceptedFiletypes = ["jpg", "bmp", "gif", "png", "tif"]
43
acceptImageExtensions = acceptedFiletypes #depracated, use acceptedFiletypes instead
44
hosting_name="Imageshack"
45
def getAcceptedImageTypes(): #depracated, use acceptedFiletypes instead
46
return acceptImageExtensions
48
def correctExtension(file): #depracated
49
"""checks if given string have a allowed extension"""
50
#TODO: switch to checking mime types
51
return file.split('.')[-1].lower() in acceptImageExtensions
56
class SendToImageshack():
28
class Imageshack_us(AbstractPycurlPlugin):
30
acceptedFiletypes = ["jpg", "bmp", "gif", "png", "tif"]
58
33
def __init__(self, fileNumber, progressCallbackFunction):
59
34
self.fileNumber = fileNumber
60
35
self.progressCallbackFunction = progressCallbackFunction
62
def parseXML(self, xml):
37
def parseResponse(self, xml, fileName = None):
64
39
returns dictionary with keys: IM, Forum, Alt Forum, HTML, Direct, Forum Thumb, Alt Forum Thumb, HTML Thumb, Twitter Link"""
65
40
xmldoc = minidom.parse(StringIO(xml))
71
46
if thumbExists == "no":
72
47
thumbLink = imageLink # thumb was not generated, use image as a thumb
73
48
links = createLinks(adLink, None, imageLink,thumbLink)
74
return links, [imageLink, thumbLink, adLink]
49
return links#, [imageLink, thumbLink, adLink]
76
51
def progress(self, download_t, download_d, upload_t, upload_d):
77
52
"""passes self.fileNumber and arguments to self.progressCallbackFunction"""
78
53
self.progressCallbackFunction(self.fileNumber, download_t, download_d, upload_t, upload_d)
80
def upload(self, file, semaphore, callbackFunction):
81
"""can throw errors"""
82
if not correctExtension(file): # usually this check is not needed, but it can help later in other script
83
raise Exception(_("Invalid file extension\nYou can upload only ") + str(acceptImageExtensions), _("Invalid file extension"))
55
def __changePngExtensionIfNeeded(self, file):
85
56
#workaround for imageshack failing to accept png https://bugs.launchpad.net/pyshare/+bug/587255
86
57
#copies png files to temporary file with jpg extension
87
58
#imports are embed to make it easier to delete workaround when no longer needed
91
62
from shutil import copyfile
92
63
copyfile(file, tempName)
97
curl.setopt(pycurl.URL, "http://www.imageshack.us/index.php")
98
#curl.setopt(pycurl.HTTPHEADER, ["Except:"])
99
if(set.getUseProxy()):
100
curl.setopt(pycurl.PROXY,set.getProxyName())
101
curl.setopt(pycurl.PROXYPORT, set.getProxyPort())
102
credentials = set.getProxyCredentials()
104
userNameAndPassword = credentials[0] + ":" + credentials[1]
105
curl.setopt(pycurl.PROXYUSERPWD,userNameAndPassword)
106
del userNameAndPassword
108
curl.setopt(pycurl.PROXYAUTH,getPycurlProxyAuthenticationType())
109
curl.setopt(pycurl.POST, 1)
110
curl.setopt(pycurl.HTTPPOST, [('fileupload', (pycurl.FORM_FILE, file)), ('xml', 'yes')])
113
curl.setopt(pycurl.WRITEFUNCTION, buf.write)
114
curl.setopt(curl.NOPROGRESS, 0)
115
curl.setopt(curl.PROGRESSFUNCTION, self.progress)
119
result = curl.perform()
122
raise Exception(file)
124
response = buf.getvalue().strip()
126
links, basicLinks = self.parseXML(response) # sometimes there are leading witespace in stream and minidom don't like them
128
raise Exception("error uploading file: " + str(file) + "\n" + response)
129
# db.addImage("Imageshack",basicLinks[0], basicLinks[1], os.path.basename(file), os.path.getsize(file),file.split('.')[-1].lower(), getMimeTypes(file))
130
callbackFunction(links,self.fileNumber,file)
67
def upload(self, file, callbackFunction, username, password):
68
"""Uploads file, and passed links to callbackFunction.
69
Optionaly this method may call self.progress to inform about upload status"""
71
file = self.__changePngExtensionIfNeeded(file)
72
post = [('fileupload', (FORM_FILE, file)), ('xml', 'yes')]
74
post.append(('a_username', username))
75
post.append(('a_password', password))
76
self.uploadUsingPycurlPost(file, callbackFunction,
77
"http://www.imageshack.us/index.php",
78
#"http://www.imageshack.us/upload_api.php", #returns more info, that we don't need
83
#used only if __name__ == "__main__"
84
from threading import Thread
85
from threading import BoundedSemaphore
133
86
def uploadFile(file, resultCallbackFunction=printLink, progressCallbackFunction=printProgressToCLI, fileNumber = 0, semaphore = BoundedSemaphore(2), username="", password=""):
134
sti = SendToImageshack(fileNumber, progressCallbackFunction)
87
sti = Imageshack_us(fileNumber, progressCallbackFunction)
135
88
sti.upload(file, semaphore, resultCallbackFunction)
90
#used only if __name__ == "__main__"
137
91
def uploadFiles(files, resultCallbackFunction=printLink, progressCallbackFunction=printProgressToCLI, fileNumber = 0, semaphore = BoundedSemaphore(2)):
138
92
"""uploads given files in threads
139
93
This function is non blocking, you should give a callback function as parameter if you want to know when it ended or what is the progress
140
94
Error will be thrown if upload was unsuccessful"""
142
96
for file in files:
143
sti = SendToImageshack(fileNumber, progressCallbackFunction)
97
sti = Imageshack_us(fileNumber, progressCallbackFunction)
145
99
t = Thread(None, sti.upload, None,(file, semaphore, resultCallbackFunction))