Skip to content

Instantly share code, notes, and snippets.

@2-click
Last active February 27, 2025 10:42
Show Gist options
  • Save 2-click/d3267354648bd6175db78ef171472e1d to your computer and use it in GitHub Desktop.
Save 2-click/d3267354648bd6175db78ef171472e1d to your computer and use it in GitHub Desktop.
Getting NordVPN Wireguard Keys from API with powershell
  1. Go to https://my.nordaccount.com/dashboard/nordvpn/manual-configuration/ and create an access token
  2. Copy token
  3. Use powershell to get Wireguard key
$username = "token"
$password = "<token goes here>"
$pair = "$($username):$($Password)"
$bytes = [System.Text.Encoding]::ASCII.GetBytes($pair)
$encodedCredentials = [Convert]::ToBase64String($bytes)
$url = "https://api.nordvpn.com/v1/users/services/credentials"

$headers = @{
    Authorization = "Basic $encodedCredentials"
}

Invoke-RestMethod -Uri $url -Headers $headers -Method Get

id                   : xxxx
created_at           : xxxx
updated_at           : xxxx
username             : xxxxx
password             : xxxxx
nordlynx_private_key : xxxx
  1. Use powershell to get recommended server:
$server = Invoke-RestMethod -Uri "https://api.nordvpn.com/v1/servers/recommendations?&filters[servers_technologies][identifier]=wireguard_udp&limit=1"

$server | ForEach-Object {
    $wireguardTech = $_.technologies | Where-Object { $_.identifier -eq 'wireguard_udp' }
    if ($wireguardTech) {
        # Extract metadata values
        $publicKey = $wireguardTech.metadata | Where-Object { $_.name -eq 'public_key' } | Select-Object -ExpandProperty value
        
        # Output with additional metadata columns
        [pscustomobject]@{
            Name           = $_.name
            Load           = $_.load
            Station        = $_.Station
            TechnologyID   = $wireguardTech.id
            TechnologyName = $wireguardTech.name
            Identifier     = $wireguardTech.identifier
            CreatedAt      = $wireguardTech.created_at
            UpdatedAt      = $wireguardTech.updated_at
            PublicKey      = $publicKey
        }
    }
}

Name           : Germany xxx
Load           : 13
Station        : xx.xxx.xx.xxx
TechnologyID   : 35
TechnologyName : Wireguard
Identifier     : wireguard_udp
CreatedAt      : 2019-02-14 14:08:43
UpdatedAt      : 2019-02-14 14:08:43
PublicKey      : xxxxxx
@ehinkle27
Copy link

Great info the powershell stuff worked for me thanks.

@Kapusten
Copy link

Kapusten commented Nov 22, 2024

thx man, it works!!

@Kapusten
Copy link

for GLiNet owners:

[Interface]
Address = 123.some.address/32
DNS = 103.666.some.address,103.different.address
PrivateKey = write-it-here
[Peer]
publickey=write-it-here
AllowedIPs = 0.0.0.0/0, ::/0
Endpoint = 193.some.address:51somePort

@SadieFord1
Copy link

Thank you so much for the solution.

@3dflea
Copy link

3dflea commented Dec 7, 2024

Nice. Thanks

@hkpD
Copy link

hkpD commented Dec 25, 2024

Much thanks, OP.

@N1c074
Copy link

N1c074 commented Jan 29, 2025

Hello, sorry I'm a neophyte and I don't understand much . Can this command of yours be used with Powershell under windows operating system? Because I tried and it doesn't work to me, thank you very much.

@C4J3
Copy link

C4J3 commented Jan 29, 2025

Hello, sorry I'm a neophyte and I don't understand much . Can this command of yours be used with Powershell under windows operating system? Because I tried and it doesn't work to me, thank you very much.

I just used it so it should work,

make sure you are only copying the commands:

$username = "token"
$password = "<token goes here>"
$pair = "$($username):$($Password)"
$bytes = [System.Text.Encoding]::ASCII.GetBytes($pair)
$encodedCredentials = [Convert]::ToBase64String($bytes)
$url = "https://api.nordvpn.com/v1/users/services/credentials"

$headers = @{
    Authorization = "Basic $encodedCredentials"
}

Invoke-RestMethod -Uri $url -Headers $headers -Method Get
and
$server = Invoke-RestMethod -Uri "https://api.nordvpn.com/v1/servers/recommendations?&filters[servers_technologies][identifier]=wireguard_udp&limit=1"

$server | ForEach-Object {
    $wireguardTech = $_.technologies | Where-Object { $_.identifier -eq 'wireguard_udp' }
    if ($wireguardTech) {
        # Extract metadata values
        $publicKey = $wireguardTech.metadata | Where-Object { $_.name -eq 'public_key' } | Select-Object -ExpandProperty value
        
        # Output with additional metadata columns
        [pscustomobject]@{
            Name           = $_.name
            Load           = $_.load
            Station        = $_.Station
            TechnologyID   = $wireguardTech.id
            TechnologyName = $wireguardTech.name
            Identifier     = $wireguardTech.identifier
            CreatedAt      = $wireguardTech.created_at
            UpdatedAt      = $wireguardTech.updated_at
            PublicKey      = $publicKey
        }
    }
}

The other bits are previews of what the outputs should look like if done correctly, not part of the commands themselves.
(Note: I did this with powershell 7 with the windows terminal program but it should work with 'normal' powershell (5.1 for me) and with any program that runs it.)

@N1c074
Copy link

N1c074 commented Jan 29, 2025

Thank you for the answer. Being a beginner I don't understand much, and not speaking English being Italian I didn't understand your explanation well. please help me
[](url)

@C4J3
Copy link

C4J3 commented Jan 29, 2025

Thank you for the answer. Being a beginner I don't understand much, and not speaking English being Italian I didn't understand your explanation well. please help me [](url)

It looks like you've got the angle bracket "<" at the start and possibly the end. Your token line should look like
$password = "aslkjakjbge;jlkn4h5y0-9q3wpiub34p8h" (I put random characters here for my example) Then, after the lines:

...
    Authorization = "Basic $encodedCredentials"
}

lines you should paste the Invoke-RestMethod -Uri $url -Headers $headers -Method Get command and press run it by pressing enter.

Copy pasted commands:
powershell_xJJn1fzAhK

After running:
powershell_YqMmcApHmj

Let me know if this helps!

Edit: On second look it seems you're sending commands one at a time which might be causing powershell to get confused. If you open a text editor like notepad or notepad++ and paste everything here:

$username = "token"
$password = "<token goes here>"
$pair = "$($username):$($Password)"
$bytes = [System.Text.Encoding]::ASCII.GetBytes($pair)
$encodedCredentials = [Convert]::ToBase64String($bytes)
$url = "https://api.nordvpn.com/v1/users/services/credentials"

$headers = @{
    Authorization = "Basic $encodedCredentials"
}

Invoke-RestMethod -Uri $url -Headers $headers -Method Get

then replace the "<token goes here>" part as I said. Then select all the text, copy it (might need to right-click copy - I've had issues with ctrl+c working for this) go back to powershell, press escape (makes sure it's not got anything weird selected) then right-click or press ctrl+v and it should appear the same as in my screenshot. Then you can just copy paste the second set of commands directly (without using notepad) if you need that as well.

@N1c074
Copy link

N1c074 commented Jan 30, 2025

It worked, thank you so much, you were amazing. Now I'll try to follow a guide in English, to put everything on a Linksys WRT3200ACM "Firmware versionDD-WRT v3.0-r59302 std (01/22/25)". If I have problems can I always write here? Thank you very much

@madamson747
Copy link

The scripts worked great for me. Thanks. :)

@MLSci
Copy link

MLSci commented Feb 25, 2025

This is much easier to use than the Linux method

@psycho-realm
Copy link

First of all, thank you for sharing this information! Your work is really helpful.

I have a quick question: Do you experience any issues when a server reaches a high “load”? For example, does it affect performance, or are there mechanisms in place to balance the load?

Also, do you happen to know which country in Europe is the best in terms of VPN security and speed? I assume Switzerland might be a good choice, but I’d love to hear your thoughts.

Looking forward to your insights!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment