[2.0a1] python3-maas-client API 2.0 seems to no longer use op but MAASClient.post requires it and incorectly passes it along

Bug #1555393 reported by David Ames on 2016-03-10
6
This bug affects 1 person
Affects Status Importance Assigned to Milestone
MAAS
Critical
Unassigned

Bug Description

Testing bleeding edge python3-maas-client API 2.0 with Xenial and python3

The client from both ppa:maas/next and ppa:~maas-maintainers/experimental3 have the problem.

Note: Even to get to this point I needed to work around LP Bug#1555392

MAASClient post requires that op be set. However, every op option I tried led to HTTP Error 400: BAD REQUEST. It would seem the 2.0 API no longer uses an op however put incorrectly pushes op down to the request.

In my testing I am trying to create a new dnsresource using the 2.0 API.

Traceback (most recent call last):
  File "hooks/test.py", line 81, in <module>
    test_maas()
  File "hooks/test.py", line 65, in test_maas
    dns.create_dnsresource(fqdn, ip_address)
  File "hooks/test.py", line 49, in create_dnsresource
    address_ttl=address_ttl)
  File "/home/thedac/HADNS/device-registration/hooks/maasclient/__init__.py", line 361, in create_dnsresource
    resp = self.driver.create_dnsresource(fqdn, ip_address, address_ttl)
  File "/home/thedac/HADNS/device-registration/hooks/maasclient/apidriver.py", line 262, in create_dnsresource
    fqdn=fqdn, ip_address=ip_address)
  File "/home/thedac/HADNS/device-registration/hooks/maasclient/apidriver.py", line 141, in _post
    response = self.client.post(path, op, **kwargs)
  File "/usr/lib/python3/dist-packages/apiclient/maas_client.py", line 246, in post
    url, method="POST", headers=headers, data=body)
  File "/usr/lib/python3/dist-packages/apiclient/maas_client.py", line 109, in dispatch_query
    res = urllib.request.urlopen(req)
  File "/usr/lib/python3.5/urllib/request.py", line 162, in urlopen
    return opener.open(url, data, timeout)
  File "/usr/lib/python3.5/urllib/request.py", line 471, in open
    response = meth(req, response)
  File "/usr/lib/python3.5/urllib/request.py", line 581, in http_response
    'http', request, response, code, msg, hdrs)
  File "/usr/lib/python3.5/urllib/request.py", line 509, in error
    return self._call_chain(*args)
  File "/usr/lib/python3.5/urllib/request.py", line 443, in _call_chain
    result = func(*args)
  File "/usr/lib/python3.5/urllib/request.py", line 589, in http_error_default
    raise HTTPError(req.full_url, code, msg, hdrs, fp)
urllib.error.HTTPError: HTTP Error 400: BAD REQUEST

Quick and dirty fix (likely not the correct one:
--- /usr/lib/python3/dist-packages/apiclient/maas_client.py 2016-03-09 16:25:23.007185680 -0800
+++ maas_client.py 2016-03-09 16:35:25.922925474 -0800
@@ -231,14 +231,15 @@
         return self.dispatcher.dispatch_query(
             url, method="GET", headers=headers)

- def post(self, path, op, as_json=False, **kwargs):
+ def post(self, path, op=None, as_json=False, **kwargs):
         """Dispatch POST method `op` on `path`, with the given parameters.

         :param as_json: Instead of POSTing the content as multipart/form-data
             POST it as application/json
         :return: The result of the dispatch_query call on the dispatcher.
         """
- kwargs['op'] = op
+ if op:
+ kwargs['op'] = op
         url, headers, body = self._formulate_change(
             path, kwargs, as_json=as_json)
         return self.dispatcher.dispatch_query(

Related branches

Changed in maas:
importance: Undecided → Critical
milestone: none → 2.0.0
summary: - python3-maas-client API 2.0 seems to no longer use op but
+ [2.0a1] python3-maas-client API 2.0 seems to no longer use op but
MAASClient.post requires it and incorectly passes it along
Changed in maas:
status: New → Fix Committed
David Ames (thedac) wrote :
Download full text (3.7 KiB)

I am afraid this bug is still an issue using python3-maas-client 2.0.0~alpha3+bzr4809-0ubuntu1~xenial1.

Attempting to create a dnsresource with post:

With post request not specifying an op code:

Traceback (most recent call last):
  File "ocf/maas/maas_dns.py", line 149, in <module>
    telco_ha_dns()
  File "ocf/maas/maas_dns.py", line 131, in telco_ha_dns
    dns_obj.create_dnsresource()
  File "ocf/maas/maas_dns.py", line 44, in create_dnsresource
    self.ttl)
  File "/home/thedac/dev/hacluster/ocf/maas/maasclient/__init__.py", line 78,
in create_dnsresource
    resp = self.driver.create_dnsresource(fqdn, ip_address, address_ttl)
  File "/home/thedac/dev/hacluster/ocf/maas/maasclient/apidriver.py", line
166, in create_dnsresource
    address_ttl=address_ttl)
  File "/home/thedac/dev/hacluster/ocf/maas/maasclient/apidriver.py", line 89,
in _post
    response = self.client.post(path, op, **kwargs)
  File "/usr/lib/python3/dist-packages/apiclient/maas_client.py", line 242, in
post
    path, kwargs, as_json=as_json)
  File "/usr/lib/python3/dist-packages/apiclient/maas_client.py", line 212, in
_formulate_change
    url += '?' + urlencode([('op', op)])
  File "/usr/lib/python3/dist-packages/apiclient/utils.py", line 42, in
urlencode
    for name, value in data)
  File "/usr/lib/python3/dist-packages/apiclient/utils.py", line 42, in
<genexpr>
    for name, value in data)
  File "/usr/lib/python3.5/urllib/parse.py", line 728, in quote_plus
    string = quote(string, safe + space, encoding, errors)
  File "/usr/lib/python3.5/urllib/parse.py", line 712, in quote
    return quote_from_bytes(string, safe)
  File "/usr/lib/python3.5/urllib/parse.py", line 737, in quote_from_bytes
    raise TypeError("quote_from_bytes() expected bytes")
TypeError: quote_from_bytes() expected bytes

If I explicitly set the op code to op=bytes('update', encoding='utf-8') and
working around LP Bug#1555392 it returns 400 Bad Request:

Traceback (most recent call last):
  File "ocf/maas/maas_dns.py", line 149, in <module>
    telco_ha_dns()
  File "ocf/maas/maas_dns.py", line 131, in telco_ha_dns
    dns_obj.create_dnsresource()
  File "ocf/maas/maas_dns.py", line 44, in create_dnsresource
    self.ttl)
  File "/home/thedac/dev/hacluster/ocf/maas/maasclient/__init__.py", line 78,
in create_dnsresource
    resp = self.driver.create_dnsresource(fqdn, ip_address, address_ttl)
  File "/home/thedac/dev/hacluster/ocf/maas/maasclient/apidriver.py", line
166, in create_dnsresource
    address_ttl=address_ttl)
  File "/home/thedac/dev/hacluster/ocf/maas/maasclient/apidriver.py", line 89,
in _post
    response = self.client.post(path, op, **kwargs)
  File "/usr/lib/python3/dist-packages/apiclient/maas_client.py", line 245, in
post
    url, method="POST", headers=headers, data=body)
  File "/usr/lib/python3/dist-packages/apiclient/maas_client.py", line 109, in
dispatch_query
    res = urllib.request.urlopen(req)
  File "/usr/lib/python3.5/urllib/request.py", line 162, in urlopen
    return opener.open(url, data, timeout)
  File "/usr/lib/python3.5/urllib/request.py", line 471, in open
    response = meth(req, response)
  File "/usr/lib/python3.5/urllib/request.py", line 581, in ht...

Read more...

Changed in maas:
status: Fix Committed → Fix Released
To post a comment you must log in.
This report contains Public information  Edit
Everyone can see this information.

Other bug subscribers