The API does not verify termproxy tickets created by API token users

Balthild

New Member
Jul 1, 2021
2
0
1
27
This makes it impossible to connect to serial console of VMs through API with token.

Testing code (runs on a PVE host):

Python:
from proxmoxer import ProxmoxAPI

client = ProxmoxAPI(
    '11.22.33.44',
    user='root@pam',
    token_name='test-token',
    token_value='(the token secret)',
    verify_ssl=False,
)

print('getting serial console ticket')
ret = client.nodes('pve-eqhk2-60g').qemu('100000018').termproxy.post()
print(ret)
print()

# This is what `termproxy` does internally, according to
# https://git.proxmox.com/?p=pve-xtermjs.git;a=blob;f=src/main.rs;h=605a92ea1e9f2ebe82971888a1717aeaa3c61b90;hb=HEAD#l145

from urllib import request, parse

url = 'http://localhost:85/api2/json/access/ticket'
data = parse.urlencode({
    'username': ret['user'],
    'password': ret['ticket'],
    'path': '/vms/100000018',
    'privs': 'VM.Console',
}).encode()

print('verifying ticket')
req = request.Request(url, data=data)
authret = request.urlopen(req).read().decode()
print(authret)

The above code prints:

Code:
# python3 tt.py
getting serial console ticket
{'user': 'root@pam!test-token', 'port': '5900', 'upid': 'UPID:pve-eqhk2-60g:000047AC:11FE34C1:60DDCD7E:vncproxy:100000018:root@pam!test-token:', 'ticket': 'PVEVNC:60DDCD7E::HicOG0+hIY+lGA++2oBJlcirGrMnFegMs6+d3PdQNTW9gzD1rB9YYEP3+DB3VTMtEJH1/xa3UTEnIzb49Lo5/ACLGAvNOWWQhrF2XQolk1ajMobgKTdQfTuMDXZt3ApTy0YQkkQycDgohFdSbf+3NIl5oY/U7i5FGi6Txuxhsd77RROCcySQBgE5eJH8CkmCi625Uq8u1djUQh89A83JwF+kShikY0El3UA7Kabcw/LC6Wq54BkdE4jBwejRgyRhKHwCpB2pjETZWJyTHWQlgt/wGY+YXnar7a/+2TlAiROeDNGg8JjenRk1rsgao3OsdOhGp+22ttdBVvy09riQwQ=='}

verifying ticket
Traceback (most recent call last):
  File "tt.py", line 29, in <module>
    authret = request.urlopen(req)
  File "/usr/lib/python3.7/urllib/request.py", line 222, in urlopen
    return opener.open(url, data, timeout)
  File "/usr/lib/python3.7/urllib/request.py", line 531, in open
    response = meth(req, response)
  File "/usr/lib/python3.7/urllib/request.py", line 641, in http_response
    'http', request, response, code, msg, hdrs)
  File "/usr/lib/python3.7/urllib/request.py", line 569, in error
    return self._call_chain(*args)
  File "/usr/lib/python3.7/urllib/request.py", line 503, in _call_chain
    result = func(*args)
  File "/usr/lib/python3.7/urllib/request.py", line 649, in http_error_default
    raise HTTPError(req.full_url, code, msg, hdrs, fp)
urllib.error.HTTPError: HTTP Error 401: authentication failure

If I change the login credentials of API client to use password rather than API token, the verification will succeed instead:

Python:
client = ProxmoxAPI(
    '11.22.33.44',
    user='root@pam',
    password='(password here)',
    verify_ssl=False,
)

Code:
verifying ticket
{"data":{"username":"root@pam","cap":{"nodes":{"Sys.Syslog":1,"Sys.PowerMgmt":1,"Permissions.Modify":1,"Sys.Audit":1,"Sys.Console":1,"Sys.Modify":1},"sdn":{"SDN.Allocate":1,"Permissions.Modify":1,"SDN.Audit":1},"access":{"Group.Allocate":1,"Permissions.Modify":1,"User.Modify":1},"storage":{"Datastore.Allocate":1,"Datastore.AllocateSpace":1,"Permissions.Modify":1,"Datastore.AllocateTemplate":1,"Datastore.Audit":1},"vms":{"VM.Clone":1,"VM.Config.CPU":1,"VM.Config.CDROM":1,"VM.PowerMgmt":1,"VM.Config.Options":1,"VM.Console":1,"VM.Backup":1,"VM.Config.HWType":1,"VM.Config.Cloudinit":1,"VM.Snapshot.Rollback":1,"Permissions.Modify":1,"VM.Monitor":1,"VM.Allocate":1,"VM.Snapshot":1,"VM.Config.Disk":1,"VM.Config.Network":1,"VM.Config.Memory":1,"VM.Migrate":1,"VM.Audit":1},"dc":{"SDN.Allocate":1,"Sys.Audit":1,"SDN.Audit":1}}}}
 
Last edited:
Additionally, the tickets retrieved from /nodes/{node}/qumu/{vmid}/vncticket cannot be verified by /api2/json/access/ticket too. But I can connect to VNC with those tickets through /nodes/{node}/qumu/{vmid}/vncwebsocket. It seems that the vncterm does not verify tickets in the way like termproxy.
 
Last edited: