xmlrpc newPaste - expected an object with the buffer interface - python

in py2 there was
rv = xmlrpc.pastes.newPaste(language, code, None, filename, mimetype, private)
I'm getting error : expected an object with the buffer interface
Can't find any docs about xmlrpc and py3. I found only this snippet :
p1 = subprocess.Popen(['gpg','--clearsign'], stdin = subprocess.PIPE, stdout=subprocess.PIPE)
p1.stdin.write(bytes(input, 'UTF8'))
output = p1.communicate()[0]
s = ServerProxy('http://paste.pocoo.org/xmlrpc/')
pasteid = s.pastes.newPaste('text',output.decode())
print ("http://paste.pocoo.org/raw/",pasteid,"/", sep="")
but I'm still being confused about it... my version used many arguments, where can I find full description of it / fix for it ?
Thank you.

That error message usually means it's looking for str (which is Unicode in Python 3), not bytes . Like in the example, you'll need to decode the argument which is in bytes. Maybe:
rv = xmlrpc.pastes.newPaste(language, code.decode(), None, filename, mimetype, private)
But it's hard to tell what the problem is without seeing your code.

In Python 3. xmlrpclib has been split into two modules, xmlrpc.client and xmlrpc.server.
The docs for 3.2.1 can be found at:
http://docs.python.org/release/3.2.1/library/xmlrpc.client.html
http://docs.python.org/release/3.2.1/library/xmlrpc.server.html

Related

TypeError: expected string or bytes-like object and works on server but not on PC

Introduction
I have problem with python program written in python 3.4.2. At the beginning i want to say, that it's not my program.
When i connect with server by SSH and compile it, it works just fine.
Server and PC specification
:
...and from my PC:
I have different Python version, but i can't compile it at 3.4.2, because there is no typing module for this specific version, which i need. I don't know if GCC version could cause this problem, but i've tried different versions.
I've downloaded it, and tried to compile it by myself. I run it in the exactly same way.
The real problem
Traceback (most recent call last):
File "gads.py", line 28, in <module>
lists = list_working.ListWorking(files_data)
File "/home/grzesiek/googleads/lib/list_working.py", line 43, in __init__
self._acc = self._split_str_list(list_data['accepted']['content'])
File "/home/grzesiek/googleads/lib/common.py", line 69, in _split_str_list
splited = re.split(separator, content)
File "/usr/local/lib/python3.5/re.py", line 203, in split
return _compile(pattern, flags).split(string, maxsplit)
TypeError: expected string or bytes-like object
So far i know that ListWorking(files_data) passes some files which are dictionaries, and at the end when i want to use regex it throws an error. But i can't change these dictionaries to strings or lists, because then it compiles, but erase data that i provide to ListWorking()
Here is fragment of code which i've tried to change:
def __init__(self, list_data: dict) -> None:
self._acc = self._split_str_list(list_data['accepted']['content'])
self._acc = self._del_dup(self._acc)
self._ign = self._split_str_list(list_data['ignored']['content'])
self._ign = self._del_dup(self._ign)
self._pro = self._split_str_list(list_data['protected']['content'])
self._pro = self._del_dup(self._pro)
self._fign = self._split_str_list(list_data['full_ignored']['content'])
self._fign = self._del_dup(self._fign)
self._key = self._split_str_list(list_data['keywords']['content'])
self._key = self._del_dup(self._key)
self._unk = self._split_str_list(list_data['unknown']['content'])
self._unk = self._del_dup(self._unk)
self._sw = self._split_str_list(list_data['stopwords']['content'])
And where the last error occurs:
def _split_str_list(content: str, separator: str = '\n') -> list:
"""Split string to list"""
splited = re.split(separator, content)
splited = list(x.strip() for x in splited)
splited = list(filter(None, splited))
return splited
Also, in Python 3.4.2 it comes to import typing and throws an error, because there is no typing lib in this version of Python.
So - how is it possible to work fine on Linux server but it doesn't on my PC?
Well, the answer was much simpler than i thought it would be...
I just had to install correct version of enca, code author didn't wrote the specific informations if something is missing, so it was very hard to find, because whole project has about ~5000 lines of code, and enca was used only by one function.
It had nothing to do with Linux or GCC.

Python 3.6 Googleads TypeError: cannot use a string pattern on a bytes-like object

I try to make connection with the Google Adwords API using Python 3.6. I managed to install the libraries, got a developer token, client_customer_id, user_agent, client_id, client_secret and requested succesfully a refresh_token.
My googleads.yaml file looks like this:
adwords:
developer_token: hta...
client_customer_id: 235-...-....
user_agent: mycompany
client_id: 25785...apps.googleusercontent.com
client_secret: J9Da...
refresh_token: 1/ckhGH6...
When running the first python script get_campaigns.py, I get the very generic response TypeError: cannot use a string pattern on a bytes-like object in ...\Anaconda3\lib\site-packages\googleads-10.0.0-py3.6.egg\googleads\util.py", line 302, in filter
Other functions like traffic_estimator_service.get(selector) produce the same error. Furthermore, when starting the Python script get_campaigns.py, I get the following warning, which might explains something:
WARNING:googleads.common:Your default encoding, cp1252, is not UTF-8. Please run this script with UTF-8 encoding to avoid errors.
INFO:oauth2client.client:Refreshing access_token
INFO:googleads.common:Request summary - {'methodName': get, 'clientCustomerId': xxx-xxx-xxxx}
I tried many things, but still can't find what causes my error. My settings seem to be right, and I use the examples as provided here. Help is highly appreciated!
There are two solutions for now:
One:
Use Python2.7, solved this error for me.
Two:
For python 3
def method_waraper(self, record):
def filter(self, record):
if record.args:
arg = record.args[0]
if isinstance(arg, suds.transport.Request):
new_arg = suds.transport.Request(arg.url)
sanitized_headers = arg.headers.copy()
if self._AUTHORIZATION_HEADER in sanitized_headers:
sanitized_headers[self._AUTHORIZATION_HEADER] = self._REDACTED
new_arg.headers = sanitized_headers
msg = arg.message
if sys.version_info.major < 3:
msg = msg.decode('utf-8')
new_arg.message = self._DEVELOPER_TOKEN_SUB.sub(
self._REDACTED, str(msg, encoding='utf-8'))
record.args = (new_arg,)
return filter(self, record)
googleads.util._SudsTransportFilter.filter = method_waraper
This solution changes code provided by google and add utf encoding for the binary string, which solves our problem.

PyQt5: cannot write cookie to file using QFile

I have a file named cookies.txt.
fd = QFile(":/cookies.txt")
available_cookies = QtNetwork.QNetworkCookieJar().allCookies()
for cookie in available_cookies:
print(cookie.toRawForm(1))
QTextStream(cookie.toRawForm(1), fd.open(QIODevice.WriteOnly))
fd.close()
Here is my full traceback:
QTextStream(cookie.toRawForm(1), fd.open(QIODevice.WriteOnly))
TypeError: arguments did not match any overloaded call:
QTextStream(): too many arguments
QTextStream(QIODevice): argument 1 has unexpected type 'QByteArray'
QTextStream(QByteArray, mode: Union[QIODevice.OpenMode, QIODevice.OpenModeFlag] = QIODevice.ReadWrite): argument 2 has unexpected type 'bool'
I am following the C++ documentation, and I am having trouble writing the corresponding python syntax.
In QTextStream(cookie.toRawForm(1), fd.open(QIODevice.WriteOnly)), you pass 2 arguments, a QByteArray, and a bool (QIODevice::open returns a boolean), but QTextStream cannot take a QByteArray with a bool.
Are you really trying to write to a resource path? Resources are read-only, so that is not going to work.
To write to a non-resource path:
fd = QFile('/tmp/cookies.txt')
if fd.open(QIODevice.WriteOnly):
available_cookies = QtNetwork.QNetworkCookieJar().allCookies()
stream = QTextStream(fd)
for cookie in available_cookies:
data = cookie.toRawForm(QtNetwork.QNetworkCookie.Full)
stream << data
fd.close()

Pycurl and io.StringIO - pycurl.error: (23, 'Failed writing body)

I'm porting ebay sdk to python3 and I've stumbled upon the following issue.
I'm using pycurl to send some HTTP requests.
Here is how I configure it:
self._curl = pycurl.Curl()
self._curl.setopt(pycurl.FOLLOWLOCATION, 1)
self._curl.setopt(pycurl.URL, str(request_url))
self._curl.setopt(pycurl.SSL_VERIFYPEER, 0)
self._response_header = io.StringIO()
self._response_body = io.StringIO()
self._curl.setopt(pycurl.CONNECTTIMEOUT, self.timeout)
self._curl.setopt(pycurl.TIMEOUT, self.timeout)
self._curl.setopt(pycurl.HEADERFUNCTION, self._response_header.write)
self._curl.setopt(pycurl.WRITEFUNCTION, self._response_body.write)
When I call self._curl.perform() I get the following error:
pycurl.error: (23, 'Failed writing body (1457 != 1460)')
As far as I know this means that there is an issue with the write function, but I can't figure out what it is exactly. Could be related to migration from StringIO module to io, but I'm not sure.
UPD:
I've tried the following:
def body(buf):
self._response_body.write(buf)
def header(buf):
self._response_header.write(buf)
self._curl.setopt(pycurl.HEADERFUNCTION, header)
self._curl.setopt(pycurl.WRITEFUNCTION, body)
and it works. I've tried to do the same trick with lambdas (instead of defining those awkward function, but it didn't work.
I believe the problem is that pycurl no longer functions with StringIO like desired. A solution is to use io.BytesIO instead. You can then get information written into the buffer and decode it into a string.
Using BytesIO with pycurl instead of StringIO:
e = io.BytesIO()
c.setopt(pycurl.WRITEFUNCTION, e.write)
Decoding byte information from the BytesIO object:
htmlString = e.getvalue().decode('UTF-8')
You can use any type of decoding you want, but this should give you a string object you can parse.
Hope this helps people using Python 3.

Error running basic python-gearman example

I am trying to run a basic example of gearman using python-gearman library available here. I am running python 2.7.3
Worker:
import gearman
gm_worker = gearman.GearmanWorker(['localhost:4730'])
def task_listener_reverse(gearman_worker, gearman_job):
print 'reporting status'
return reversed(gearman_job.data)
gm_worker.set_client_id('testclient')
gm_worker.register_task('reverse', task_listener_reverse)
gm_worker.work()
Client:
import gearman
gm_client = gearman.GearmanClient(['localhost:4730'])
print 'Sending job...'
request = gm_client.submit_job('reverse', 'Hello World!')
print "Result: " + request.result
I am getting the following error (full trace available here)
File "/Users/developer/gearman/connection_manager.py", line 27, in _enforce_byte_string
raise TypeError("Expecting byte string, got %r" % type(given_object))
TypeError: Expecting byte string, got <type 'reversed'>
Any help would be appreciated!
Thanks.
reversed() returns an iterator, not a bytestring. Use the negative stride slicing trick instead:
return gearman_job.data[::-1]
This returns a reversed string instead.
Compare:
>>> reversed('somedata')
<reversed object at 0x100480e50>
>>> 'somedata'[::-1]
'atademos'
For the sake of other people facing similar errors, you need to return a string from worker. If you do not return explicitly or return data of any other type, scrapy throws an error. Reason is simple that Gearman's protocol is text based.

Categories