linux-cli-community icon indicating copy to clipboard operation
linux-cli-community copied to clipboard

[BUG] "protonvpn s" doesn't work anymore

Open hertz0022 opened this issue 11 months ago • 8 comments

Hi, for one/two weeks now the status command doesn't work anymore. Latest v2.2.12-1, installed from AUR, Python v3.11.8. Here is its output:

ProtonVPN now offers an official Linux app which includes a graphical user interface. Visit https://protonvpn.com/support/official-linux-client to upgrade. Traceback (most recent call last): File "/sbin/protonvpn", line 33, in sys.exit(load_entry_point('protonvpn-cli==2.2.12', 'console_scripts', 'protonvpn')()) ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ File "/usr/lib/python3.11/site-packages/protonvpn_cli/cli.py", line 72, in main cli() File "/usr/lib/python3.11/site-packages/protonvpn_cli/cli.py", line 144, in cli connection.status() File "/usr/lib/python3.11/site-packages/protonvpn_cli/connection.py", line 444, in status + "Features: {0}\n".format(all_features[feature]) ~~~~~~~~~~~~^^^^^^^^^ KeyError: 12

The rest seems to work as usually. Maybe a python update that broke something? Don't remember when I last updated it. Thanks, great client btw, always used it!

hertz0022 avatar Mar 18 '24 08:03 hertz0022

Im experiencing the same thing. Also using the latest version from the AUR.

Expressive-Synapse avatar Mar 20 '24 19:03 Expressive-Synapse

A detail I didn't mention is that if it's disconnected the command runs as expected. Only happens under a vpn connection.

hertz0022 avatar Mar 20 '24 22:03 hertz0022

It seems that the feature key does not match the hardcoded all_features map anymore.

connection.py:

    # Collect Information
    all_features = {0: "Normal", 1: "Secure-Core", 2: "Tor", 4: "P2P"}

    logger.debug("Collecting status information")
    country_code = get_server_value(connected_server, "ExitCountry", servers)
    country = get_country_name(country_code)
    city = get_server_value(connected_server, "City", servers)
    load = get_server_value(connected_server, "Load", servers)
    feature = get_server_value(connected_server, "Features", servers)
    last_connection = get_config_value("metadata", "connected_time")
    connection_time = time.time() - int(last_connection)

    if os.path.isfile(os.path.join(CONFIG_DIR, "iptables.backup")):
        killswitch_on = True
    else:
        killswitch_on = False
    killswitch_status = "Enabled" if killswitch_on else "Disabled"
    # Turn time into human readable format and trim microseconds
    connection_time = str(datetime.timedelta(
        seconds=connection_time)).split(".")[0]

    tx_amount, rx_amount = get_transferred_data()

    # Print Status Output
    logger.debug("Printing status")
    print(
        "Status:       Connected\n"
        + "Time:         {0}\n".format(connection_time)
        + "IP:           {0}\n".format(ip)
        + "Server:       {0}\n".format(connected_server)
        + "Features:     {0}\n".format(all_features[feature])
        + "Protocol:     {0}\n".format(connected_protocol.upper())
        + "Kill Switch:  {0}\n".format(killswitch_status)
        + "Country:      {0}\n".format(country)
        + "City:         {0}\n".format(city)
        + "Load:         {0}%\n".format(load)
        + "Received:     {0}\n".format(rx_amount)
        + "Sent:         {0}".format(tx_amount)
    )

I'll look further into this, I might be able to submit a fix

marcel-engelke avatar Mar 24 '24 00:03 marcel-engelke

The VPN server features are stored as bitflags, but the CLI does not support decoding them, simply mapping every feature to a value instead. This causes the issue described above when a server supports multiple features.

After some digging, I found that the feature flags are defined in proton-vpn-session/servers/types.py

class ServerFeatureEnum(IntFlag):
    """
    A Class representing the Server features as encoded in the feature flags field of the API:
    """
    SECURE_CORE = 1 << 0  # 1
    TOR = 1 << 1  # 2
    P2P = 1 << 2  # 4
    STREAMING = 1 << 3  # 8
    IPV6 = 1 << 4  # 16

For example the 12 seen in KeyError: 12 would correspond to the server features P2P (4) + STREAMING (8).

I'm going to implement handling for this and submit a PR.

marcel-engelke avatar Mar 24 '24 01:03 marcel-engelke

This is upstream's fault for being a bad vendor. Tell them to package better and to document their dependencies.

nethershaw avatar Sep 20 '24 02:09 nethershaw

This is upstream's fault for being a bad vendor. Tell them to package better and to document their dependencies.

what do you mean by this?

I submitted a PR fixing this issue months ago: https://github.com/Rafficer/linux-cli-community/pull/368 Unfortunately, it seems that the maintainer of this repo is inactive. So feel free to use my fork until they come back.

marcel-engelke avatar Sep 21 '24 15:09 marcel-engelke

I submitted a PR fixing this issue months ago: #368 Unfortunately, it seems that the maintainer of this repo is inactive. So feel free to use my fork until they come back.

May I ask how? I've tried some ways by myself without success. Do I need to edit the AUR PKGBUILD?

hertz0022 avatar Sep 22 '24 14:09 hertz0022

May I ask how? I've tried some ways by myself without success. Do I need to edit the AUR PKGBUILD?

I simply put my fork into a directory (dependencies installed in a virtualenv) and aliased the protonvpn command to use its environment. It's not the prettiest solution, but since the repo is not really getting updated anymore, it seemed sufficient for me.

marcel-engelke avatar Oct 06 '24 19:10 marcel-engelke