How to download LXC version of OpenWRT and run it on Proxmox

I tried turning off the dhcp server in the openwrt LXC

Code:
uci set dhcp.lan.ignore='1'
uci commit dhcp
/etc/init.d/dnsmasq restart

I tried changing the virtual mac address to something else

It shows up in my router's dhcp server leases

Active DHCP Leases​

HostnameIPv4 addressMAC addressLease time remainingStatic Lease
openwrt (openwrt.lan)192.168.1.136DE:AD:BE:EF:01:9911h 59m 51s
-192.168.1.237DE:AD:BE:EF:00:9911h 45m 59s

I ran nmap scan from proxmox host, shows all ports are closed

Code:
root@proxmox:~/test2# nmap 192.168.1.136
Starting Nmap 7.93 ( https://nmap.org ) at 2024-09-25 07:05 EST
Nmap scan report for 192.168.1.136
Host is up (0.000088s latency).
All 1000 scanned ports on 192.168.1.136 are in ignored states.
Not shown: 1000 closed tcp ports (reset)
MAC Address: DE:AD:BE:EF:01:99 (Unknown)

Nmap done: 1 IP address (1 host up) scanned in 38.64 seconds

Seems like something very basic is not working !
 
Ok, I have figured it out

By default this LXC container has only one network interace and it is configured as "WAN" which is locked down,

The following, can be pasted entire as is into the console or into a .sh script file

It will download the file, create the container and issue a series of command to turn the WAN interface into LAN

Proxmox openwrt LXC LAN only

Code:
CT_ID="999"  # Adjust the container ID
CT_template_download="https://jenkins.linuxcontainers.org/job/image-openwrt/architecture=amd64,release=23.05,variant=default/lastSuccessfulBuild/artifact/rootfs.tar.xz"
CT_template_filename="openwrt-amd64,23.05,default.tar.xz"
CT_template_file="local:vztmpl/$CT_template_filename"
CT_net_mac="DE:AD:BE:EF:01:99"
CT_hostname="myopenwrt"
CT_memory="1024"
CT_cores="4"
CT_rootfs_size="2"
CT_key_file="/ssh_key.pub"
CT_key="ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQCIWFBY0G/lbORqeMXI2PfIcVBuDO66KeCzFr4IqXOFC1ehuC573tXRW6TQTAAR6nlYTXrzw4Mw+1y2lgwP3rkibH/RpkCIu96hPygad2ZrxObNoM44Hpzxq6Jq/S8sXNjpsb7Q0yN7yqjAwQIKA9eDvRaC/03yPz9pLcZ3gjk3YUVPZuZ3zUrjJV+n4XeCmw1HvMTkGRJ3SVCHw1tyB1K8rCxu6sGw55HK3P70moPj8JiAvxe2y+V84DGU9n4vWuwVMWcpISrubaQIeUo2WQebRB5C3qCkNyGzwTdTR6v6gBy+aiL1VvL2qUiNGQ3LE1FgnLnvwQZk5IubPMjfoyvT rsa-key-20240925"

[ ! -f /var/lib/vz/template/cache/$CT_template_filename ] && wget "$CT_template_download" -O /var/lib/vz/template/cache/$CT_template_filename

#Obtain the next CT_ID if not already set
: ${CT_ID:=$(pct list | awk 'NR>1 {print $1}' | sort -n | awk 'NR==1{prev=$1} NR>1 && $1>prev+1{print prev+1; exit} {prev=$1} END{if (prev+1 > $1) print prev+1}')}

echo "$CT_key" > $CT_key_file

# Create the container
pct create $CT_ID $CT_template_file --arch amd64 --cores $CT_cores --memory $CT_memory --hostname $CT_hostname --net0 name=eth0,bridge=vmbr0,firewall=1,hwaddr=$CT_net_mac,ip=dhcp,type=veth --rootfs local-lvm:$CT_rootfs_size --features nesting=1 --unprivileged 1 --ostype unmanaged

rm $CT_key_file

# Start the container
pct start $CT_ID

#Wait until container is finished booting
: ${CT_ID:=101}; while [[ $(pct status $CT_ID) != *"running"* ]]; do echo "Waiting for container $CT_ID to start..."; sleep 2; done; echo "Container $CT_ID is running."

sleep 5

# Step 1: Remove WAN and WAN6 interfaces
pct exec $CT_ID -- uci delete network.wan
pct exec $CT_ID -- uci delete network.wan6

# Step 2: Set LAN interface to use DHCP (so eth0 will act as a DHCP client)
pct exec $CT_ID -- uci set network.lan=interface
pct exec $CT_ID -- uci set network.lan.ifname='eth0'
pct exec $CT_ID -- uci set network.lan.proto='dhcp'

# Step 3: Commit the network configuration changes
pct exec $CT_ID -- uci commit network

# Step 4: Remove the WAN zone from the firewall (this includes removing WAN and WAN6)
pct exec $CT_ID -- uci delete firewall.@zone[1]

# Step 5: Update LAN zone in the firewall (associate it with the LAN network)
pct exec $CT_ID -- uci set firewall.@zone[0].network='lan'

# Step 6: Remove LAN-to-WAN forwarding rule (since there's no WAN now)
pct exec $CT_ID -- uci delete firewall.@forwarding[0]

# Step 7: Remove firewall rules specific to the WAN zone
pct exec $CT_ID -- uci delete firewall.@rule[8]  # Allow-ISAKMP
pct exec $CT_ID -- uci delete firewall.@rule[7]  # Allow-IPSec-ESP
pct exec $CT_ID -- uci delete firewall.@rule[6]  # Allow-ICMPv6-Forward
pct exec $CT_ID -- uci delete firewall.@rule[5]  # Allow-ICMPv6-Input
pct exec $CT_ID -- uci delete firewall.@rule[4]  # Allow-MLD
pct exec $CT_ID -- uci delete firewall.@rule[3]  # Allow-DHCPv6
pct exec $CT_ID -- uci delete firewall.@rule[2]  # Allow-IGMP
pct exec $CT_ID -- uci delete firewall.@rule[1]  # Allow-Ping
pct exec $CT_ID -- uci delete firewall.@rule[0]  # Allow-DHCP-Renew

# Step 8: Commit the firewall configuration changes
pct exec $CT_ID -- uci commit firewall

# Step 9: Restart the network and firewall services to apply the changes
pct exec $CT_ID -- /etc/init.d/network restart
pct exec $CT_ID -- /etc/init.d/firewall restart
 
Here is what you should see when running the above script

Code:
--2024-09-25 08:16:45--  https://jenkins.linuxcontainers.org/job/image-openwrt/architecture=amd64,release=23.05,variant=default/lastSuccessfulBuild/artifact/rootfs.tar.xz
Resolving jenkins.linuxcontainers.org (jenkins.linuxcontainers.org)... 45.45.148.7, 2602:fc62:a:1::7
Connecting to jenkins.linuxcontainers.org (jenkins.linuxcontainers.org)|45.45.148.7|:443... connected.
HTTP request sent, awaiting response... 200 OK
Length: 3758948 (3.6M) [application/x-xz]
Saving to: ‘/var/lib/vz/template/cache/openwrt-amd64,23.05,default.tar.xz’

/var/lib/vz/template/cache/openwrt-amd64,23.05,default.tar.xz      100%[=============================================================================================================================================================>]   3.58M  --.-KB/s    in 0.1s

2024-09-25 08:16:46 (32.4 MB/s) - ‘/var/lib/vz/template/cache/openwrt-amd64,23.05,default.tar.xz’ saved [3758948/3758948]

  WARNING: You have not turned on protection against thin pools running out of space.
  WARNING: Set activation/thin_pool_autoextend_threshold below 100 to trigger automatic extension of thin pools before they get full.
  Logical volume "vm-999-disk-0" created.
  WARNING: Sum of all thin volume sizes (1.92 TiB) exceeds the size of thin pool pve/data and the size of whole volume group (<446.13 GiB).
Creating filesystem with 524288 4k blocks and 131072 inodes
Filesystem UUID: 119175af-d979-4bac-8a73-d8f6f8d4199b
Superblock backups stored on blocks:
        32768, 98304, 163840, 229376, 294912
extracting archive '/var/lib/vz/template/cache/openwrt-amd64,23.05,default.tar.xz'
Total bytes read: 14315520 (14MiB, 70MiB/s)
Container 999 is running.

Then in your browser at myopenwrt.lan

There will be an empty password set as the web interface does not allow login in with a private key file, it will tell you to change the password immediately

1727270285286.png

When you go to Network -> Interface
you will have the following message
I don't know why, it does not appear to change anything in the configuration
You can ignore this message and it will only say that once

1727270387312.png
 
Here is another version of the Openwrt LXC container install script

This version will have two network interfaces setup

Note that the WAN interface will receive the myopenwrt2.lan hostname while the LAN interface will not receive a hostname

So http://myopenwrt2.lan will not work in your browser
But you can run
pct exec 1001 -- ifconfig
to get the ip address of your LAN interface (eth1)


Proxmox openwrt LXC WAN+LAN

Code:
CT_ID="1001"  # Adjust the container ID
CT_template_download="https://jenkins.linuxcontainers.org/job/image-openwrt/architecture=amd64,release=23.05,variant=default/lastSuccessfulBuild/artifact/rootfs.tar.xz"
CT_template_filename="openwrt-amd64,23.05,default.tar.xz"
CT_template_file="local:vztmpl/$CT_template_filename"
CT_net_mac="DE:AD:BE:EF:01:98"
CT_net_mac2="DE:AD:BE:EF:02:98"
CT_hostname="myopenwrt2"
CT_memory="1024"
CT_cores="4"
CT_rootfs_size="2"
CT_key_file="/ssh_key.pub"
CT_key="ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQCIWFBY0G/lbORqeMXI2PfIcVBuDO66KeCzFr4IqXOFC1ehuC573tXRW6TQTAAR6nlYTXrzw4Mw+1y2lgwP3rkibH/RpkCIu96hPygad2ZrxObNoM44Hpzxq6Jq/S8sXNjpsb7Q0yN7yqjAwQIKA9eDvRaC/03yPz9pLcZ3gjk3YUVPZuZ3zUrjJV+n4XeCmw1HvMTkGRJ3SVCHw1tyB1K8rCxu6sGw55HK3P70moPj8JiAvxe2y+V84DGU9n4vWuwVMWcpISrubaQIeUo2WQebRB5C3qCkNyGzwTdTR6v6gBy+aiL1VvL2qUiNGQ3LE1FgnLnvwQZk5IubPMjfoyvT rsa-key-20240925"

[ ! -f /var/lib/vz/template/cache/$CT_template_filename ] && wget "$CT_template_download" -O /var/lib/vz/template/cache/$CT_template_filename

#Obtain the next CT_ID if not already set
: ${CT_ID:=$(pct list | awk 'NR>1 {print $1}' | sort -n | awk 'NR==1{prev=$1} NR>1 && $1>prev+1{print prev+1; exit} {prev=$1} END{if (prev+1 > $1) print prev+1}')}

echo "$CT_key" > $CT_key_file

# Create the container
pct create $CT_ID $CT_template_file --arch amd64 --cores $CT_cores --memory $CT_memory --hostname $CT_hostname --net0 name=eth0,bridge=vmbr0,firewall=1,hwaddr=$CT_net_mac,ip=dhcp,type=veth --net1 name=eth1,bridge=vmbr0,firewall=1,hwaddr=$CT_net_mac2,ip=dhcp,type=veth --rootfs local-lvm:$CT_rootfs_size --features nesting=1 --unprivileged 1 --ostype unmanaged

rm $CT_key_file

# Start the container
pct start $CT_ID

#Wait until container is finished booting
: ${CT_ID:=101}; while [[ $(pct status $CT_ID) != *"running"* ]]; do echo "Waiting for container $CT_ID to start..."; sleep 2; done; echo "Container $CT_ID is running."

sleep 5

# Step 1: Set LAN interface to use DHCP (so eth1 will act as a DHCP client)
pct exec $CT_ID -- uci set network.lan=interface
pct exec $CT_ID -- uci set network.lan.ifname='eth1'
pct exec $CT_ID -- uci set network.lan.proto='dhcp'
pct exec $CT_ID -- uci commit network
pct exec $CT_ID -- /etc/init.d/network restart
pct exec $CT_ID -- /etc/init.d/firewall restart
 
Shodan, thank you so much for the script. I have been going crazy trying to build my arr stack in lxc while moving away from Docker where I can. I need a VPN on a few containers via openvpn. The process has been very frustrating I have tried the helper script for the Openwrt with the plan to add OpenVPN after the build, but there is no support for access after the VM is created. I got the idea from Novaspirit Tech's video about building openwrt as an LXC https://www.youtube.com/watch?v=3mPbrunpjpk&t=329s but it's full of missing info and as soon as I try to boot the container as seen at 6:04 in the video I get Error: Startup for container xxx failed. The video is 9 months old so there isn't much of a discussion going on in the comments. I also tried BigBear Techworld's video https://www.youtube.com/watch?v=8RoYUsNe4gE&t=4s I get this one to boot and can access the management IP but all the network interfaces are totally different than Naova's tutorial for next steps and BigBear really doesn't explain the OpenVPN part. I found this thread, and people were having similar issues with the forced WAN and with everyone's help and your script, I am up and running and have OpenVPN configured with Express VPN. I still need help with understanding the network interfaces and how to force my lxcs through the interface (eth1 and eth0). Would anyone have any ideas based on Novatech's video above? Thanks
 
Thanks @shodan. Used as well. a couple optional changes I made was to set a static IP for the lan ipaddr and if you stick with DHCP I added the ifconfig command as the last step to show the IP at the end of the script.

added the 2 variables below to the top section for those wanting a known/static LAN IP:
Code:
CT_lan_ipaddr='172.20.10.1' # Adjust the Lan static IP address
CT_lan_netmask='255.255.255.0' # Adjust Lan netmask

Code:
# Step 1: Set LAN interface to use static address (so eth1 will be reachable)
pct exec $CT_ID -- uci set network.lan=interface
pct exec $CT_ID -- uci set network.lan.ifname='eth1'
pct exec $CT_ID -- uci set network.lan.proto='static'
pct exec $CT_ID -- uci set network.lan.ipaddr=$CT_lan_ipaddr
pct exec $CT_ID -- uci set network.lan.netmask=$CT_lan_netmask
pct exec $CT_ID -- uci commit network
pct exec $CT_ID -- /etc/init.d/network restart
pct exec $CT_ID -- /etc/init.d/firewall restart
pct exec $CT_ID -- ifconfig
 
  • Like
Reactions: enigmacarpc
Thank you both. I was wondering about how to build the container with a static IP, and that would help. Would either of you have any idea how to set up the VPN on eth1 or eth0 so that I can make that the interface of my lxc container to force the traffic through it? Thanks
 

Attachments

  • Container network.png
    Container network.png
    17.4 KB · Views: 3
  • Promox network.png
    Promox network.png
    21.7 KB · Views: 3
  • OpenVPN 1.png
    OpenVPN 1.png
    223.8 KB · Views: 1
  • OpenVPN 2.png
    OpenVPN 2.png
    117.7 KB · Views: 3
Hi,

Getting VPN to work was the reason why I was setting openwrt inside my proxmox server

I've worked all night on this and I've got it working but I still need to make it into a script

But basically, for openvpn layer 3 tunnel, it is something like

opkg install openvpn-openssl luci-app-openvpn
(uci set) openvpn.routedmulti=openvpn
openvpn.routedmulti.verb='3'
openvpn.routedmulti.compress='lz4'
openvpn.routedmulti.port='53'
openvpn.routedmulti.proto='udp'
openvpn.routedmulti.dev_type='tun'
openvpn.routedmulti.nobind='1'
openvpn.routedmulti.client='1'
openvpn.routedmulti.remote='us-fl-mia.321inter.net'
openvpn.routedmulti.auth_user_pass='/etc/openvpn/beetvpn.auth'
openvpn.routedmulti.auth_nocache='1'
openvpn.routedmulti.auth='SHA256'
openvpn.routedmulti.cipher='AES-256-GCM'
openvpn.routedmulti.tls_client='1'
openvpn.routedmulti.persist_key='1'
openvpn.routedmulti.persist_tun='1'
openvpn.routedmulti.tls_crypt='/etc/openvpn/beetvpn.tlscrypt'
openvpn.routedmulti.ca='/etc/openvpn/beetvpn.ca'
openvpn.routedmulti.tls_cipher='TLS-ECDHE-ECDSA-WITH-AES-256-GCM-SHA384'
openvpn.routedmulti.enabled='1'
openvpn.routedmulti.dev='tun0'

and then creating the

/etc/openvpn/beetvpn.auth (login and password)
/etc/openvpn/beetvpn.tlscrypt (tls key, I believe this is the client side private key certificate )
/etc/openvpn/beetvpn.ca (certificate authority public key)


And beyond that there would be need to support

PKCS#12 (which is a single file that contains all the X.509 certificated inside of one file)

"Pre-shared key" support (PSK is like the wifi password, a more basic form of authentification)

L2TP and IPSec support (layer 2 VPN, this would be with the packages softethervpn-base / softethervpn-client / luci-app-softether )

IKEv2 on IPSec supprt (layer 3 VPN, said to be more efficient than openvpn and have "mobility" options for maintaining connectivity through difficult network conditions, like your IP address changing, this is supported via strongswan / strongswan-ipsec / package , no luci support)

and wireguard (which might not be all that amazing ??? wireguard-tools luci-proto-wireguard wg-installer-client , no luci support )

some resources

https://openwrt.org/docs/guide-user/services/vpn/openvpn/client
https://openwrt.org/docs/guide-user/services/vpn/openvpn/extras
https://openwrt.org/docs/guide-user/services/vpn/softethervpn/client?s[]=softether
https://openwrt.org/docs/guide-user/services/vpn/strongswan/roadwarrior
https://openwrt.org/docs/guide-user/services/vpn/strongswan/configuration
https://openwrt.org/docs/guide-user/services/vpn/libreswan/openswanxl2tpvpn

BTW if you want LAN to LAN, L2TP with IPSec is probably what you want, this is equivalent to Hamachi and maybe Zerotier-ish ?

Ah, also I need to check out Zerotier itself on openwrt, the STUN/TURN coordinators and so much other stufff ...
 
  • Like
Reactions: enigmacarpc
Hi,

Getting VPN to work was the reason why I was setting openwrt inside my proxmox server

I've worked all night on this and I've got it working but I still need to make it into a script

But basically, for openvpn layer 3 tunnel, it is something like

opkg install openvpn-openssl luci-app-openvpn
(uci set) openvpn.routedmulti=openvpn
openvpn.routedmulti.verb='3'
openvpn.routedmulti.compress='lz4'
openvpn.routedmulti.port='53'
openvpn.routedmulti.proto='udp'
openvpn.routedmulti.dev_type='tun'
openvpn.routedmulti.nobind='1'
openvpn.routedmulti.client='1'
openvpn.routedmulti.remote='us-fl-mia.321inter.net'
openvpn.routedmulti.auth_user_pass='/etc/openvpn/beetvpn.auth'
openvpn.routedmulti.auth_nocache='1'
openvpn.routedmulti.auth='SHA256'
openvpn.routedmulti.cipher='AES-256-GCM'
openvpn.routedmulti.tls_client='1'
openvpn.routedmulti.persist_key='1'
openvpn.routedmulti.persist_tun='1'
openvpn.routedmulti.tls_crypt='/etc/openvpn/beetvpn.tlscrypt'
openvpn.routedmulti.ca='/etc/openvpn/beetvpn.ca'
openvpn.routedmulti.tls_cipher='TLS-ECDHE-ECDSA-WITH-AES-256-GCM-SHA384'
openvpn.routedmulti.enabled='1'
openvpn.routedmulti.dev='tun0'

and then creating the

/etc/openvpn/beetvpn.auth (login and password)
/etc/openvpn/beetvpn.tlscrypt (tls key, I believe this is the client side private key certificate )
/etc/openvpn/beetvpn.ca (certificate authority public key)


And beyond that there would be need to support

PKCS#12 (which is a single file that contains all the X.509 certificated inside of one file)

"Pre-shared key" support (PSK is like the wifi password, a more basic form of authentification)

L2TP and IPSec support (layer 2 VPN, this would be with the packages softethervpn-base / softethervpn-client / luci-app-softether )

IKEv2 on IPSec supprt (layer 3 VPN, said to be more efficient than openvpn and have "mobility" options for maintaining connectivity through difficult network conditions, like your IP address changing, this is supported via strongswan / strongswan-ipsec / package , no luci support)

and wireguard (which might not be all that amazing ??? wireguard-tools luci-proto-wireguard wg-installer-client , no luci support )

some resources

https://openwrt.org/docs/guide-user/services/vpn/openvpn/client
https://openwrt.org/docs/guide-user/services/vpn/openvpn/extras
https://openwrt.org/docs/guide-user/services/vpn/softethervpn/client?s[]=softether
https://openwrt.org/docs/guide-user/services/vpn/strongswan/roadwarrior
https://openwrt.org/docs/guide-user/services/vpn/strongswan/configuration
https://openwrt.org/docs/guide-user/services/vpn/libreswan/openswanxl2tpvpn

BTW if you want LAN to LAN, L2TP with IPSec is probably what you want, this is equivalent to Hamachi and maybe Zerotier-ish ?

Ah, also I need to check out Zerotier itself on openwrt, the STUN/TURN coordinators and so much other stufff ...
Wow all night, I know how that feels and thanks for all the work. I use Tailscale for remote access. I only need the VPN to pass the lcxs through to mask Torrents, trackers and file-sharing services. When using Docker I do the same thing with Gluetun. I think we will start seeing the lxc with VPN become huge as there is a large gap in this space currently. Please let me know when you finish the script, I hope what you build will be similar to Nocahspirits video I linked, that ultimately the best option for passing the containers. Thanks
 
Teaser, this almost works

This should create openwrt setup with many different network configuration and multiple vpn connections

I need to create new firewall zones and test ipv6 stuff


Code:
CT_ID="1001"  # Adjust the container ID
CT_hostname="myopenwrt2"
CT_root_password="qwerty"

CT_memory="1024"
CT_cores="4"
CT_rootfs_size="2"

#Setup networking
network.lan.ifname=eth0
network.wan.ifname=eth1
CT_net_ubound=1 #how many interfaces to include

#LAN interface
CT_net_fw_0=0 ; CT_net_dev_0=eth0
CT_net_mac_0="DE:AD:BE:EF:01:95"
CT_net_ip_0=dhcp
CT_net_ip6_0=dhcp
#CT_net_ip_0=manual
#CT_net_ip6_0=manual
#CT_net_ip_0="192.168.1.90/24" ; CT_net_gw_0=192.168.1.1
#CT_net_ip6_0="fd69:DEAD:BEEF:::10/64" ; CT_net_gw6_0=fd69:DEAD:BEEF:::1
CT_net_type_0=veth ; CT_net_bridge_0=vmbr0

#WAN interface
CT_net_fw_1=0 ; CT_net_dev_1=eth1
CT_net_mac_1="DE:AD:BE:EF:01:96"
CT_net_ip_1=dhcp
CT_net_ip6_1=dhcp
#CT_net_ip_1=manual
#CT_net_ip6_1=manual
#CT_net_ip_1="192.168.1.91/24" ; CT_net_gw_1=192.168.1.1
#CT_net_ip6_1="fd69:DEAD:BEEF:::11/64" ; CT_net_gw6_1=fd69:DEAD:BEEF:::1

#Extra network interface 1
CT_net_fw_2=0 ; CT_net_dev_2=eth2
CT_net_mac_2="DE:AD:BE:EF:01:97"
CT_net_ip_2=dhcp
CT_net_ip6_2=dhcp
#CT_net_ip_2=manual
#CT_net_ip6_2=manual
#CT_net_ip_2="192.168.1.92/24" ; CT_net_gw_2=192.168.1.1
#CT_net_ip6_2="fd69:DEAD:BEEF:::12/64" ; CT_net_gw6_2=fd69:DEAD:BEEF:::1

#Extra network interface 2
CT_net_fw_3=0 ; CT_net_dev_3=eth3
CT_net_mac_3="DE:AD:BE:EF:01:99"
CT_net_ip_3=dhcp
CT_net_ip6_3=dhcp
#CT_net_ip_3=manual
#CT_net_ip6_3=manual
#CT_net_ip_3="192.168.1.93/24" ; CT_net_gw_3=192.168.1.1
#CT_net_ip6_3="fd69:DEAD:BEEF:::13/64" ; CT_net_gw6_3=fd69:DEAD:BEEF:::1

vpn_ubound=0
# vpn_ubound=-1 #uncomment to disable vpn support
vpn_name_0=BeetVPN
vpn_verb_0=3 #verbosity level of logs
vpn_remove_0=us-fl-mia.321inter.net
vpn_port_0=53
vpn_proto_0=udp
vpn_dev_type_0=tun  #tun means layer 3, tap means layer2
vpn_dev_0=tun0
vpn_nobind_0=1
vpn_client_0=client
vpn_tls_client_0=1
vpn_persist_key_0=1
vpn_persist_tun_0=1
vpn_auth_nocache_0=1
vpn_enabled_0=1
vpn_compress_0='lz4'
vpn_auth_0=SHA256
vpn_cipher_0=AES-256-GCM
vpn_tls_cipher_0=TLS-ECDHE-ECDSA-WITH-AES-256-GCM-SHA384
vpn_auth_user_pass_0='/etc/openvpn/beetvpn.auth'
vpn_ca_0=/etc/openvpn/beetvpn.ca
vpn_tls_crypt_0=/etc/openvpn/beetvpn.tlscrypt

file_ubound=-1
file_ubound=$((file_ubound + 1))
file_line_ubound=-1
# Set file metadata (using declare for dynamic variable names)
declare file_name_${file_ubound}="/etc/openvpn/beetvpn.ca"
declare filepermission_${file_ubound}=600
declare fileowner_${file_ubound}="root:root"
# Set file lines (using declare for dynamic variable names)
file_line_ubound=$((file_line_ubound + 1)); declare file_line_${file_line_ubound}_${file_ubound}="<ca>"
file_line_ubound=$((file_line_ubound + 1)); declare file_line_${file_line_ubound}_${file_ubound}="-----BEGIN CERTIFICATE-----"
file_line_ubound=$((file_line_ubound + 1)); declare file_line_${file_line_ubound}_${file_ubound}="MIIBFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFVBAMM"
file_line_ubound=$((file_line_ubound + 1)); declare file_line_${file_line_ubound}_${file_ubound}="DDMyFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFaMBcx"
file_line_ubound=$((file_line_ubound + 1)); declare file_line_${file_line_ubound}_${file_ubound}="FTATFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFABGja"
file_line_ubound=$((file_line_ubound + 1)); declare file_line_${file_line_ubound}_${file_ubound}="TAidFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFo+SGx"
file_line_ubound=$((file_line_ubound + 1)); declare file_line_${file_line_ubound}_${file_ubound}="zR8oFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFvHaOB"
file_line_ubound=$((file_line_ubound + 1)); declare file_line_${file_line_ubound}_${file_ubound}="hjCBFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFwPoAU"
file_line_ubound=$((file_line_ubound + 1)); declare file_line_${file_line_ubound}_${file_ubound}="ThoKFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFyLm5l"
file_line_ubound=$((file_line_ubound + 1)); declare file_line_${file_line_ubound}_${file_ubound}="dIIJFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFGSM49"
file_line_ubound=$((file_line_ubound + 1)); declare file_line_${file_line_ubound}_${file_ubound}="BAMCFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFzV5/T"
file_line_ubound=$((file_line_ubound + 1)); declare file_line_${file_line_ubound}_${file_ubound}="4c53FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFyRQHn"
file_line_ubound=$((file_line_ubound + 1)); declare file_line_${file_line_ubound}_${file_ubound}="Nqxoy1tXLIfKApc8CQ=="
file_line_ubound=$((file_line_ubound + 1)); declare file_line_${file_line_ubound}_${file_ubound}="-----END CERTIFICATE-----"
file_line_ubound=$((file_line_ubound + 1)); declare file_line_${file_line_ubound}_${file_ubound}="</ca>"
declare file_line_count_${file_ubound}=$file_line_ubound



CT_template_download="https://jenkins.linuxcontainers.org/job/image-openwrt/architecture=amd64,release=23.05,variant=default/lastSuccessfulBuild/artifact/rootfs.tar.xz"
CT_template_filename="openwrt-amd64,23.05,default.tar.xz"
CT_template_file="local:vztmpl/$CT_template_filename"
CT_key="ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQCIWFBY0G/lbORqeMXI2PfIcVBuDO66KeCzFr4IqXOFC1ehuC573tXRW6TQTAAR6nlYTXrzw4Mw+1y2lgwP3rkibH/RpkCIu96hPygad2ZrxObNoM44Hpzxq6Jq/S8sXNjpsb7Q0yN7yqjAwQIKA9eDvRaC/03yPz9pLcZ3gjk3YUVPZuZ3zUrjJV+n4XeCmw1HvMTkGRJ3SVCHw1tyB1K8rCxu6sGw55HK3P70moPj8JiAvxe2y+V84DGU9n4vWuwVMWcpISrubaQIeUo2WQebRB5C3qCkNyGzwTdTR6v6gBy+aiL1VvL2qUiNGQ3LE1FgnLnvwQZk5IubPMjfoyvT rsa-key-20240925"
CT_key_file="/ssh_key.openwrt.pub"

#Only download template file if it is not already present
[ ! -f /var/lib/vz/template/cache/$CT_template_filename ] && wget "$CT_template_download" -O /var/lib/vz/template/cache/$CT_template_filename

#Obtain the next CT_ID if not already set
: ${CT_ID:=$(pct list | awk 'NR>1 {print $1}' | sort -n | awk 'NR==1{prev=$1} NR>1 && $1>prev+1{print prev+1; exit} {prev=$1} END{if (prev+1 > $1) print prev+1}')}

echo "$CT_key" > $CT_key_file

# Create the container
pct create $CT_ID $CT_template_file --arch amd64 --cores $CT_cores --memory $CT_memory --hostname $CT_hostname --net0 name=eth0,bridge=vmbr0,firewall=1,hwaddr=$CT_net0_mac,ip=dhcp,type=veth --net1 name=eth1,bridge=vmbr0,firewall=1,hwaddr=$CT_net1_mac,ip=dhcp,type=veth --rootfs local-lvm:$CT_rootfs_size --features nesting=1 --unprivileged 1 --ostype unmanaged

rm $CT_key_file

# If vpn enabled, then add tun

lxc.cgroup2.devices.allow: c 10:200 rwm
lxc.mount.entry: /dev/net/tun dev/net/tun none bind,create=file


# Start the container
pct start $CT_ID

#Wait until container is finished booting
: ${CT_ID:=101}; while [[ $(pct status $CT_ID) != *"running"* ]]; do echo "Waiting for container $CT_ID to start..."; sleep 2; done; echo "Container $CT_ID is running."

#Wait a bit more to make sure it is done booting (it might still not be)
sleep 5

# Disable DHCP server on LAN
pct exec $CT_ID -- uci set dhcp.lan.ignore='1'

# Set LAN interface to use DHCP (so eth1 will act as a DHCP client)
pct exec $CT_ID -- uci set network.lan=interface
pct exec $CT_ID -- uci set network.lan.proto='dhcp'
# Making LAN on eth0 so that it received the hostname on the LAN first
pct exec $CT_ID -- uci set network.lan.ifname='eth0'
pct exec $CT_ID -- uci set network.wan.ifname='eth1'
pct exec $CT_ID -- uci commit network
pct exec $CT_ID -- /etc/init.d/network restart
pct exec $CT_ID -- /etc/init.d/firewall restart
pct exec $CT_ID --

#write all the files into the container
for i in $(seq 0 $file_line_ubound); do pct exec $CT_ID -- /bin/sh -c "echo \"$(eval echo \${file_line_${i}_${file_ubound}})\" >> \"$(eval echo \${file_name_${file_ubound}})\""; done && pct exec $CT_ID -- chmod $(eval echo \${filepermission_${file_ubound}}) $(eval echo \${file_name_${file_ubound}}) && pct exec $CT_ID -- chown $(eval echo \${fileowner_${file_ubound}}) $(eval echo \${file_name_${file_ubound}})

#create all vpn settings
for i in $(seq 0 $vpn_ubound); do eval vpn_name=\${vpn_name_${i}}; eval vpn_verb=\${vpn_verb_${i}}; eval vpn_remote=\${vpn_remote_${i}}; eval vpn_port=\${vpn_port_${i}}; eval vpn_proto=\${vpn_proto_${i}}; eval vpn_dev_type=\${vpn_dev_type_${i}}; eval vpn_dev=\${vpn_dev_${i}}; eval vpn_nobind=\${vpn_nobind_${i}}; eval vpn_client=\${vpn_client_${i}}; eval vpn_tls_client=\${vpn_tls_client_${i}}; eval vpn_persist_key=\${vpn_persist_key_${i}}; eval vpn_persist_tun=\${vpn_persist_tun_${i}}; eval vpn_auth_nocache=\${vpn_auth_nocache_${i}}; eval vpn_enabled=\${vpn_enabled_${i}}; eval vpn_compress=\${vpn_compress_${i}}; eval vpn_auth=\${vpn_auth_${i}}; eval vpn_cipher=\${vpn_cipher_${i}}; eval vpn_tls_cipher=\${vpn_tls_cipher_${i}}; eval vpn_auth_user_pass=\${vpn_auth_user_pass_${i}}; eval vpn_ca=\${vpn_ca_${i}}; eval vpn_tls_crypt=\${vpn_tls_crypt_${i}}; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.verb=$vpn_verb"; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.remote=$vpn_remote"; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.port=$vpn_port"; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.proto=$vpn_proto"; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.dev_type=$vpn_dev_type"; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.dev=$vpn_dev"; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.nobind=$vpn_nobind"; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.client=$vpn_client"; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.tls_client=$vpn_tls_client"; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.persist_key=$vpn_persist_key"; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.persist_tun=$vpn_persist_tun"; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.auth_nocache=$vpn_auth_nocache"; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.compress=$vpn_compress"; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.auth=$vpn_auth"; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.cipher=$vpn_cipher"; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.tls_cipher=$vpn_tls_cipher"; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.auth_user_pass=$vpn_auth_user_pass"; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.ca=$vpn_ca"; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.tls_crypt=$vpn_tls_crypt"; echo "pct exec \$CT_ID -- uci set vpn.$vpn_name.enabled=$vpn_enabled"; echo "pct exec \$CT_ID -- uci commit vpn.$vpn_name"; echo "VPN $vpn_name configuration commands displayed."; done
 
Here is my latest version
with multi-vpn support

The first section is several shell functions to make the settings cleaner

They help with adding net interfaces, vpn config and insert files into the container

For instance if you were a beetvpn subscriber, you could use this by

1. writing your tls-crypt openvpn shared key
2. writing in your login and password in the auth file
3. pasting all of this into your proxmox console

then head to vpn.lan and you should see the following at

https://vpn.lan/cgi-bin/luci/admin/vpn/openvpn

1728991981085.png

Code:
#----------------------------------------
# shell function to create --net variable
addnet() { CT_net_count=${CT_net_count:-0}; local net_name=$1; shift; local _CT_new_config="--net$CT_net_count name=$net_name"; local valid_params=("bridge" "firewall" "gw" "gw6" "hwaddr" "ip" "ip6" "link_down" "mtu" "rate" "tag" "trunks" "type"); while [ $# -gt 0 ]; do key=$1; value=$2; if [[ " ${valid_params[*]} " =~ " $key " ]]; then _CT_new_config="$_CT_new_config,$key=$value"; shift 2; else shift 1; fi; done; _CT_net_config="$_CT_net_config $_CT_new_config"; echo "Interface added: $_CT_new_config"; CT_net_count=$((CT_net_count + 1)); }
# shell function for create each file line variables
addline() { file_line_ubound=$((file_line_ubound + 1)); eval "file_line_${file_line_ubound}_${file_ubound}=\"$1\""; eval "file_line_count_${file_ubound}=$file_line_ubound"; }
addfile() { file_ubound=$((file_ubound + 1)); eval "file_name_${file_ubound}=\"$1\""; [ -n "$2" ] && [[ "$2" =~ ^[0-9]+$ ]] && eval "filepermission_${file_ubound}=\"$2\""; [ -n "$3" ] && eval "fileowner_${file_ubound}=\"$3\""; unset file_line_ubound; }
pct_append_text() { local file=$1; local text_or_var=$2; if [ -n "${!text_or_var}" ]; then local text=${!text_or_var}; elif [[ "$text_or_var" == file_line* ]]; then local text=$(eval echo \${$text_or_var}); else local text="$text_or_var"; fi; local command="echo \"$text\" >> \"$file\""; [ "$VERBOSE" -gt 0 ] && echo "pct exec $CT_ID -- /bin/sh -c \"$command\""; pct exec $CT_ID -- /bin/sh -c "$command"; }
writefile() { local file_index=$1; local file_name=$(eval echo \${file_name_${file_index}}); local file_permission=$(eval echo \${filepermission_${file_index}}); local file_owner=$(eval echo \${fileowner_${file_index}}); local file_line_count=$(eval echo \${file_line_count_${file_index}}); for i in $(seq 1 $file_line_count); do local file_line_var="file_line_${i}_${file_index}"; pct_append_text "$file_name" "$file_line_var"; done; [ -n "$file_permission" ] && pct_exec "chmod $file_permission $file_name"; [ -n "$file_owner" ] && pct_exec "chown $file_owner $file_name"; }
# shell function to add a VPN and define its parameters
addvpn() { vpn_ubound=$((vpn_ubound + 1)); }
vpn() { eval vpn_${1}_${vpn_ubound}=\"$2\"; }
apply_vpn_config() { local vpn_index=$1 vpn_name vpn_type var_name var_value sanitized_vpn_name; vpn_name=$(eval echo \${vpn_name_${vpn_index}}); vpn_type=$(eval echo \${vpn_type_${vpn_index}}); sanitized_vpn_name=$(echo "$vpn_name" | sed 's/-/_/g'); pct_exec "uci set $vpn_type.$sanitized_vpn_name=$vpn_type"; for var in $(compgen -A variable | grep "vpn_.*_${vpn_index}$"); do var_name=$(echo $var | sed -r 's/vpn_(.*)_'${vpn_index}'/\1/'); if [ "$var_name" = "name" ] || [ "$var_name" = "type" ]; then continue; fi; var_value=$(eval echo \${$var}); pct_exec "uci set $vpn_type.$sanitized_vpn_name.$var_name=$var_value"; done; pct_exec "uci commit $vpn_type.$sanitized_vpn_name"; echo "VPN $vpn_name configuration applied."; }
copyvpn() { local source_name=$1; local source_index=""; for i in $(seq 1 $vpn_ubound); do if [ "$(eval echo \${vpn_name_${i}})" = "$source_name" ]; then source_index=$i; break; fi; done; [ -z "$source_index" ] && { echo "Error: VPN with name '$source_name' not found."; return 1; }; vpn_ubound=$((vpn_ubound + 1)); for var in $(compgen -A variable | grep "vpn_.*_${source_index}$"); do var_name=$(echo $var | sed -r "s/vpn_(.*)_${source_index}/\1/"); var_value=$(eval echo \${$var}); eval vpn_${var_name}_${vpn_ubound}=\"$var_value\"; done; echo "VPN '$source_name' copied to new VPN index $vpn_ubound."; }
# shell function to type pct exec commands
pct_exec() { [ "$VERBOSE" -gt 0 ] && echo "pct exec $CT_ID -- /bin/sh -c \"$*\""; pct exec $CT_ID -- /bin/sh -c "$*"; }

VERBOSE=1  # Enable verbose mode

echo "------------------------------ Creation of openwrt LXC container ------------------------------"

CT_ID="1002"  # Adjust the container ID
CT_hostname="vpn"
CT_root_password="qwerty"
CT_memory="1024"
CT_cores="4"
CT_rootfs_size="2"

#Setup networking
#network.lan.ifname=eth0
#network.wan.ifname=eth1

addnet eth0 hwaddr "DE:AD:BE:EF:01:95" ip dhcp ip6 manual firewall 0 bridge vmbr0 # LAN interface (eth0)
addnet eth1 hwaddr "DE:AD:BE:EF:01:96" ip dhcp ip6 manual firewall 0 bridge vmbr0 # WAN interface (eth1)
#addnet eth2 hwaddr "DE:AD:BE:EF:01:97" ip dhcp ip6 dhcp bridge vmbr1 firewall 0 # Extra network interface 2 (eth2)
#addnet eth3 hwaddr "DE:AD:BE:EF:01:99" ip dhcp ip6 dhcp bridge vmbr1 firewall 0 # Extra network interface 3 (eth3)


# Add VPN configuration for OpenVPN
addvpn
vpn name "beetvpn-asia-jakarta-5"
vpn type "openvpn"
vpn verb 3
vpn remote "asia-id5.321inter.net"
vpn port 53
vpn proto "udp"
vpn dev_type "tun"
vpn dev "tun0"
vpn nobind 1
vpn client 1
vpn tls_client 1
vpn persist_key 1
vpn persist_tun 1
vpn auth_nocache 1
vpn enabled 1
vpn compress "stub-v2"
#vpn compress "lz4-v2"
#vpn allow-compression "1"  # might be wrong syntax
vpn auth "SHA256"
vpn cipher "AES-256-GCM"
vpn tls_cipher "TLS-ECDHE-ECDSA-WITH-AES-256-GCM-SHA384"
#vpn remote_cert_tls='server'
vpn auth_user_pass "/etc/openvpn/beetvpn.auth"
vpn ca "/etc/openvpn/beetvpn.ca"
vpn tls_crypt "/etc/openvpn/beetvpn.tlscrypt"
#vpn remote_cert_eku "\"TLS Web Server Authentication\"" # might be wrong syntax

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-asia-jakarta-6"
vpn remote "asia-id6.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-aus-sydney"
vpn remote "oc-syd.321inter.net"
vpn port 1194
vpn enabled 0

copyvpn "beetvpn-aus-sydney"
vpn name "beetvpn-aus-sydney-2"
vpn remote "oc-syd2.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-ca-montreal"
vpn remote "us-ca-mon.321inter.net"
vpn enabled 0

copyvpn "beetvpn-aus-sydney"
vpn name "beetvpn-ca-toronto"
vpn remote "us-ca-tor.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-ca-vancouver"
vpn remote "ca-van.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-eu-amsterdam"
vpn remote "eu-nl.321inter.net"
vpn enabled 0

copyvpn "beetvpn-aus-sydney"
vpn name "beetvpn-eu-barcelona"
vpn remote "eu-es.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-eu-brussels"
vpn remote "eu-be.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-eu-dublin"
vpn remote "eu-ie-dub.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-eu-dusseldorf"
vpn remote "eu-de.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-eu-frankfurt"
vpn remote "eu-de-fra.321inter.net"
vpn enabled 0

copyvpn "beetvpn-aus-sydney"
vpn name "beetvpn-eu-helsinki"
vpn remote "eu-fi.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-eu-kiev"
vpn remote "eu-ua.321inter.net"
vpn enabled 0

copyvpn "beetvpn-aus-sydney"
vpn name "beetvpn-eu-ljubljana"
vpn remote "eu-si-lju.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-eu-palermo"
vpn remote "eu-it-syc.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-eu-paris"
vpn remote "eu-fr.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-eu-prague"
vpn remote "eu-cz-pra.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-eu-rotterdam"
vpn remote "eu-nl-rtm.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-eu-seville"
vpn remote "eu-es-sev.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-eu-sophia"
vpn remote "eu-bg-sof.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-eu-stockholm"
vpn remote "eu-se.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-eu-thessaloniki"
vpn remote "eu-gr-the.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-eu-warsaw"
vpn remote "eu-pl3.321inter.net"
vpn enabled 0

copyvpn "beetvpn-aus-sydney"
vpn name "beetvpn-eu-zurich"
vpn remote "eu-ch.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-mena-bursa"
vpn remote "asia-tr-bur.321inter.net"
vpn enabled 0

copyvpn "beetvpn-aus-sydney"
vpn name "beetvpn-mena-mumbai"
vpn remote "asia-in.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-mena-tel-aviv"
vpn remote "asia-il-tel.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-ru-moscow"
vpn remote "asia-ru.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-ru-st-petersburg"
vpn remote "asia-ru-spe.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-sa-sao-paulo"
vpn remote "sa-br.321inter.net"
vpn enabled 0

copyvpn "beetvpn-aus-sydney"
vpn name "beetvpn-sea-bangkok"
vpn remote "asia-th.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-sea-hong-kong"
vpn remote "asia-hk2.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-sea-manila"
vpn remote "ph-man.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-sea-singapore"
vpn remote "asia-sg.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-sea-singapore-2"
vpn remote "sg2.ipcover.net"
vpn port 1194
vpn compress "stub-v2"
vpn data_ciphers "AES-256-GCM"
vpn enabled 0

copyvpn "beetvpn-aus-sydney"
vpn name "beetvpn-sea-tokyo"
vpn remote "asia-jp4.321inter.net"
vpn enabled 0

copyvpn "beetvpn-aus-sydney"
vpn name "beetvpn-sea-tokyo-2"
vpn remote "asia-jp5.321inter.net"
vpn enabled 0

copyvpn "beetvpn-aus-sydney"
vpn name "beetvpn-sea-tokyo-6"
vpn remote "asia-jp6.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-uk-london"
vpn remote "uk-lon.321inter.net"
vpn enabled 0

copyvpn "beetvpn-sea-singapore-2"
vpn name "beetvpn-uk-london-2"
vpn remote "uk2.ipcover.net"
vpn enabled 0
 
Cut here, due to forum character limit of 16384 characters maximum

Code:
copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-us-los-angeles"
vpn remote "us-fl-la.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-us-miami"
vpn remote "us-fl-mia.321inter.net"
vpn enabled 0

copyvpn "beetvpn-sea-singapore-2"
vpn name "beetvpn-us-miami-2"
vpn remote "us2.ipcover.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-us-new-york"
vpn remote "us-nyc.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-za-johannesburg"
vpn remote "za-joh.321inter.net"
vpn enabled 0

copyvpn "beetvpn-aus-sydney"
vpn name "beetvpn-za-johannesburg-2"
vpn remote "za-joh2.321inter.net"
vpn enabled 0



# Create the file and set its metadata
addfile "/etc/openvpn/beetvpn.ca" "600" "root:root"
addline "<ca>"
addline "-----BEGIN CERTIFICATE-----"
addline "MIIB6TCCAW+gAwIBAgIJAO7HEvJxfUUCMAoGCCqGSM49BAMCMBcxFTATBgNVBAMM"
addline "DDMyMWludGVyLm5ldDAeFw0xOTA1MjExMzI3NDlaFw0yOTA1MTgxMzI3NDlaMBcx"
addline "FTATBgNVBAMMDDMyMWludGVyLm5ldDB2MBAGByqGSM49AgEGBSuBBAAiA2IABGja"
addline "TAidcTxY9ud7w3Jr1y6BSS7trkeu3kZqDg/TDCxE4k0Ay6AXVkooORyidfco+SGx"
addline "zR8oxcit7JGjCf5+JCufjKjl3s/yULt7gYfQnfBYN4ULcr1gpKCZQMIlORnvHaOB"
addline "hjCBgzAdBgNVHQ4EFgQUThoKRpgMcQwcQwlfjfzf5vE2mOUwRwYDVR0jBEAwPoAU"
addline "ThoKRpgMcQwcQwlfjfzf5vE2mOWhG6QZMBcxFTATBgNVBAMMDDMyMWludGVyLm5l"
addline "dIIJAO7HEvJxfUUCMAwGA1UdEwQFMAMBAf8wCwYDVR0PBAQDAgEGMAoGCCqGSM49"
addline "BAMCA2gAMGUCMCL6jOfO1j5lC6q0DN5Z8Aw0GQ5SAFlmlvyAkk1/dGSgA1gzV5/T"
addline "4c53qemB1vz4SQIxAN7onHBiSvGwnCePjDSoonHA9CUlWUX9hurwIdFFqLWyRQHn"
addline "Nqxoy1tXLIfKApc8CQ=="
addline "-----END CERTIFICATE-----"
addline "</ca>"

addfile "/etc/openvpn/beetvpn.auth" "600" "root:root"
addline "beet_my_username"
addline "mypassword"

addfile "/etc/openvpn/beetvpn.tlscrypt" "600" "root:root"
addline "<tls-crypt>"
addline "#"
addline "# 2048 bit OpenVPN static key"
addline "#"
addline "-----BEGIN OpenVPN Static key V1-----"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "-----END OpenVPN Static key V1-----"
addline "</tls-crypt>"

CT_template_download="https://jenkins.linuxcontainers.org/job/image-openwrt/architecture=amd64,release=23.05,variant=default/lastSuccessfulBuild/artifact/rootfs.tar.xz"
CT_template_filename="openwrt-amd64,23.05,default.tar.xz"
CT_template_file="local:vztmpl/$CT_template_filename"
CT_key="ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQCIWFBY0G/lbORqeMXI2PfIcVBuDO66KeCzFr4IqXOFC1ehuC573tXRW6TQTAAR6nlYTXrzw4Mw+1y2lgwP3rkibH/RpkCIu96hPygad2ZrxObNoM44Hpzxq6Jq/S8sXNjpsb7Q0yN7yqjAwQIKA9eDvRaC/03yPz9pLcZ3gjk3YUVPZuZ3zUrjJV+n4XeCmw1HvMTkGRJ3SVCHw1tyB1K8rCxu6sGw55HK3P70moPj8JiAvxe2y+V84DGU9n4vWuwVMWcpISrubaQIeUo2WQebRB5C3qCkNyGzwTdTR6v6gBy+aiL1VvL2qUiNGQ3LE1FgnLnvwQZk5IubPMjfoyvT rsa-key-20240925"
CT_key_file="/ssh_key.openwrt.pub"

#Only download template file if it is not already present
[ ! -f /var/lib/vz/template/cache/$CT_template_filename ] && wget "$CT_template_download" -O /var/lib/vz/template/cache/$CT_template_filename

#Obtain the next CT_ID if not already set
: ${CT_ID:=$(pct list | awk 'NR>1 {print $1}' | sort -n | awk 'NR==1{prev=$1} NR>1 && $1>prev+1{print prev+1; exit} {prev=$1} END{if (prev+1 > $1) print prev+1}')}

echo "$CT_key" > $CT_key_file

# Create the container
echo ""; echo Creating LXC Container for $CT_template_filename
[ "$VERBOSE" -gt 0 ] && echo "pct create $CT_ID $CT_template_file --arch amd64 --cores $CT_cores --memory $CT_memory --hostname $CT_hostname $_CT_net_config --rootfs local-lvm:$CT_rootfs_size --features nesting=1 --unprivileged 1 --ostype unmanaged"
pct create $CT_ID $CT_template_file --arch amd64 --cores $CT_cores --memory $CT_memory --hostname $CT_hostname $_CT_net_config --rootfs local-lvm:$CT_rootfs_size --features nesting=1 --unprivileged 1 --ostype unmanaged

rm $CT_key_file

# If vpn enabled, then add tun
# Define the LXC configuration file path
LXC_CONF_FILE="/etc/pve/nodes/proxmox/lxc/$CT_ID.conf"

# Add permissions mapping for tun/tap devices
[ "$vpn_ubound" -gt 0 ] && echo "lxc.cgroup2.devices.allow: c 10:200 rwm" >> "$LXC_CONF_FILE"
[ "$vpn_ubound" -gt 0 ] && echo "lxc.mount.entry: /dev/net/tun dev/net/tun none bind,create=file" >> "$LXC_CONF_FILE"


# Start the container
pct start $CT_ID

#Wait until container is finished booting
: ${CT_ID:=101}; while [[ $(pct status $CT_ID) != *"running"* ]]; do echo "Waiting for container $CT_ID to start..."; sleep 2; done; echo "Container $CT_ID is running."

#Wait a bit more to make sure it is done booting (it might still not be)
sleep 5

# Disable DHCP server on LAN
pct_exec uci set dhcp.lan.ignore='1'

# Set LAN interface to use DHCP (so eth1 will act as a DHCP client)
pct_exec uci set network.lan=interface
pct_exec uci set network.lan.proto='dhcp'
# Making LAN on eth0 so that it received the hostname on the LAN first
pct_exec uci set network.lan.ifname='eth0'
pct_exec uci set network.wan.ifname='eth1'
pct_exec uci commit network
pct_exec /etc/init.d/network restart
pct_exec /etc/init.d/firewall restart

pct_exec mkdir /etc/openvpn

#write all the files into the container
for i in $(seq 1 $file_ubound); do writefile ${i} ; done

pct_exec opkg update -q
pct_exec opkg install openvpn-openssl luci-app-openvpn
pct_exec uci del openvpn.custom_config
pct_exec uci del openvpn.sample_server
pct_exec uci del openvpn.sample_client


#create all vpn settings (only if there is a vpn)
for i in $(seq 1 $vpn_ubound); do apply_vpn_config ${i} ; done

pct_exec uci changes
pct_exec uci commit

pct_exec /etc/init.d/openvpn start
pct_exec passwd root -d '$CT_root_password'


password setting doesn't seem to work
it should not swap LAN and WAN if there is not at least 2 net interfaces (CT_net_count)

TO DO next

for each VPN interface activated,
Create a LAN interface alias macvlan virtual
with a dhcp open 61 client ID with the name of the vpn example "beetvpn-mena-mumbai.vpn.lan"
setup NAT forwarding from that new virtual interface to the right tunX interface


And then, get port forwarding to work properly on each (that's going to be a big one)

And then explore Multi-WAN to combine multiple VPN connection into a single one so I can download at 3GBPS from a single HTTP server, as the goal

opkg update ceases to work when connected to vpn

Code:
root@vpn:~# ping google.com
PING google.com (172.217.13.206): 56 data bytes
64 bytes from 172.217.13.206: seq=0 ttl=111 time=80.358 ms
64 bytes from 172.217.13.206: seq=1 ttl=111 time=80.494 ms
64 bytes from 172.217.13.206: seq=2 ttl=111 time=82.447 ms
^C
--- google.com ping statistics ---
3 packets transmitted, 3 packets received, 0% packet loss
round-trip min/avg/max = 80.358/81.099/82.447 ms
root@vpn:~# opkg update
Downloading https://downloads.openwrt.org/releases/23.05.5/targets/x86/64/packages/Packages.gz
*** Failed to download the package list from https://downloads.openwrt.org/releases/23.05.5/targets/x86/64/packages/Packages.gz

Downloading https://downloads.openwrt.org/releases/23.05.5/packages/x86_64/base/Packages.gz
*** Failed to download the package list from https://downloads.openwrt.org/releases/23.05.5/packages/x86_64/base/Packages.gz

Downloading https://downloads.openwrt.org/releases/23.05.5/packages/x86_64/luci/Packages.gz
*** Failed to download the package list from https://downloads.openwrt.org/releases/23.05.5/packages/x86_64/luci/Packages.gz
 
Last edited:
  • Like
Reactions: enigmacarpc
Cut here, due to forum character limit of 16384 characters maximum

Code:
copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-us-los-angeles"
vpn remote "us-fl-la.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-us-miami"
vpn remote "us-fl-mia.321inter.net"
vpn enabled 0

copyvpn "beetvpn-sea-singapore-2"
vpn name "beetvpn-us-miami-2"
vpn remote "us2.ipcover.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-us-new-york"
vpn remote "us-nyc.321inter.net"
vpn enabled 0

copyvpn "beetvpn-asia-jakarta-5"
vpn name "beetvpn-za-johannesburg"
vpn remote "za-joh.321inter.net"
vpn enabled 0

copyvpn "beetvpn-aus-sydney"
vpn name "beetvpn-za-johannesburg-2"
vpn remote "za-joh2.321inter.net"
vpn enabled 0



# Create the file and set its metadata
addfile "/etc/openvpn/beetvpn.ca" "600" "root:root"
addline "<ca>"
addline "-----BEGIN CERTIFICATE-----"
addline "MIIB6TCCAW+gAwIBAgIJAO7HEvJxfUUCMAoGCCqGSM49BAMCMBcxFTATBgNVBAMM"
addline "DDMyMWludGVyLm5ldDAeFw0xOTA1MjExMzI3NDlaFw0yOTA1MTgxMzI3NDlaMBcx"
addline "FTATBgNVBAMMDDMyMWludGVyLm5ldDB2MBAGByqGSM49AgEGBSuBBAAiA2IABGja"
addline "TAidcTxY9ud7w3Jr1y6BSS7trkeu3kZqDg/TDCxE4k0Ay6AXVkooORyidfco+SGx"
addline "zR8oxcit7JGjCf5+JCufjKjl3s/yULt7gYfQnfBYN4ULcr1gpKCZQMIlORnvHaOB"
addline "hjCBgzAdBgNVHQ4EFgQUThoKRpgMcQwcQwlfjfzf5vE2mOUwRwYDVR0jBEAwPoAU"
addline "ThoKRpgMcQwcQwlfjfzf5vE2mOWhG6QZMBcxFTATBgNVBAMMDDMyMWludGVyLm5l"
addline "dIIJAO7HEvJxfUUCMAwGA1UdEwQFMAMBAf8wCwYDVR0PBAQDAgEGMAoGCCqGSM49"
addline "BAMCA2gAMGUCMCL6jOfO1j5lC6q0DN5Z8Aw0GQ5SAFlmlvyAkk1/dGSgA1gzV5/T"
addline "4c53qemB1vz4SQIxAN7onHBiSvGwnCePjDSoonHA9CUlWUX9hurwIdFFqLWyRQHn"
addline "Nqxoy1tXLIfKApc8CQ=="
addline "-----END CERTIFICATE-----"
addline "</ca>"

addfile "/etc/openvpn/beetvpn.auth" "600" "root:root"
addline "beet_my_username"
addline "mypassword"

addfile "/etc/openvpn/beetvpn.tlscrypt" "600" "root:root"
addline "<tls-crypt>"
addline "#"
addline "# 2048 bit OpenVPN static key"
addline "#"
addline "-----BEGIN OpenVPN Static key V1-----"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF"
addline "-----END OpenVPN Static key V1-----"
addline "</tls-crypt>"

CT_template_download="https://jenkins.linuxcontainers.org/job/image-openwrt/architecture=amd64,release=23.05,variant=default/lastSuccessfulBuild/artifact/rootfs.tar.xz"
CT_template_filename="openwrt-amd64,23.05,default.tar.xz"
CT_template_file="local:vztmpl/$CT_template_filename"
CT_key="ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQCIWFBY0G/lbORqeMXI2PfIcVBuDO66KeCzFr4IqXOFC1ehuC573tXRW6TQTAAR6nlYTXrzw4Mw+1y2lgwP3rkibH/RpkCIu96hPygad2ZrxObNoM44Hpzxq6Jq/S8sXNjpsb7Q0yN7yqjAwQIKA9eDvRaC/03yPz9pLcZ3gjk3YUVPZuZ3zUrjJV+n4XeCmw1HvMTkGRJ3SVCHw1tyB1K8rCxu6sGw55HK3P70moPj8JiAvxe2y+V84DGU9n4vWuwVMWcpISrubaQIeUo2WQebRB5C3qCkNyGzwTdTR6v6gBy+aiL1VvL2qUiNGQ3LE1FgnLnvwQZk5IubPMjfoyvT rsa-key-20240925"
CT_key_file="/ssh_key.openwrt.pub"

#Only download template file if it is not already present
[ ! -f /var/lib/vz/template/cache/$CT_template_filename ] && wget "$CT_template_download" -O /var/lib/vz/template/cache/$CT_template_filename

#Obtain the next CT_ID if not already set
: ${CT_ID:=$(pct list | awk 'NR>1 {print $1}' | sort -n | awk 'NR==1{prev=$1} NR>1 && $1>prev+1{print prev+1; exit} {prev=$1} END{if (prev+1 > $1) print prev+1}')}

echo "$CT_key" > $CT_key_file

# Create the container
echo ""; echo Creating LXC Container for $CT_template_filename
[ "$VERBOSE" -gt 0 ] && echo "pct create $CT_ID $CT_template_file --arch amd64 --cores $CT_cores --memory $CT_memory --hostname $CT_hostname $_CT_net_config --rootfs local-lvm:$CT_rootfs_size --features nesting=1 --unprivileged 1 --ostype unmanaged"
pct create $CT_ID $CT_template_file --arch amd64 --cores $CT_cores --memory $CT_memory --hostname $CT_hostname $_CT_net_config --rootfs local-lvm:$CT_rootfs_size --features nesting=1 --unprivileged 1 --ostype unmanaged

rm $CT_key_file

# If vpn enabled, then add tun
# Define the LXC configuration file path
LXC_CONF_FILE="/etc/pve/nodes/proxmox/lxc/$CT_ID.conf"

# Add permissions mapping for tun/tap devices
[ "$vpn_ubound" -gt 0 ] && echo "lxc.cgroup2.devices.allow: c 10:200 rwm" >> "$LXC_CONF_FILE"
[ "$vpn_ubound" -gt 0 ] && echo "lxc.mount.entry: /dev/net/tun dev/net/tun none bind,create=file" >> "$LXC_CONF_FILE"


# Start the container
pct start $CT_ID

#Wait until container is finished booting
: ${CT_ID:=101}; while [[ $(pct status $CT_ID) != *"running"* ]]; do echo "Waiting for container $CT_ID to start..."; sleep 2; done; echo "Container $CT_ID is running."

#Wait a bit more to make sure it is done booting (it might still not be)
sleep 5

# Disable DHCP server on LAN
pct_exec uci set dhcp.lan.ignore='1'

# Set LAN interface to use DHCP (so eth1 will act as a DHCP client)
pct_exec uci set network.lan=interface
pct_exec uci set network.lan.proto='dhcp'
# Making LAN on eth0 so that it received the hostname on the LAN first
pct_exec uci set network.lan.ifname='eth0'
pct_exec uci set network.wan.ifname='eth1'
pct_exec uci commit network
pct_exec /etc/init.d/network restart
pct_exec /etc/init.d/firewall restart

pct_exec mkdir /etc/openvpn

#write all the files into the container
for i in $(seq 1 $file_ubound); do writefile ${i} ; done

pct_exec opkg update -q
pct_exec opkg install openvpn-openssl luci-app-openvpn
pct_exec uci del openvpn.custom_config
pct_exec uci del openvpn.sample_server
pct_exec uci del openvpn.sample_client


#create all vpn settings (only if there is a vpn)
for i in $(seq 1 $vpn_ubound); do apply_vpn_config ${i} ; done

pct_exec uci changes
pct_exec uci commit

pct_exec /etc/init.d/openvpn start
pct_exec passwd root -d '$CT_root_password'


password setting doesn't seem to work
it should not swap LAN and WAN if there is not at least 2 net interfaces (CT_net_count)

TO DO next

for each VPN interface activated,
Create a LAN interface alias macvlan virtual
with a dhcp open 61 client ID with the name of the vpn example "beetvpn-mena-mumbai.vpn.lan"
setup NAT forwarding from that new virtual interface to the right tunX interface


And then, get port forwarding to work properly on each (that's going to be a big one)

And then explore Multi-WAN to combine multiple VPN connection into a single one so I can download at 3GBPS from a single HTTP server, as the goal

opkg update ceases to work when connected to vpn

Code:
root@vpn:~# ping google.com
PING google.com (172.217.13.206): 56 data bytes
64 bytes from 172.217.13.206: seq=0 ttl=111 time=80.358 ms
64 bytes from 172.217.13.206: seq=1 ttl=111 time=80.494 ms
64 bytes from 172.217.13.206: seq=2 ttl=111 time=82.447 ms
^C
--- google.com ping statistics ---
3 packets transmitted, 3 packets received, 0% packet loss
round-trip min/avg/max = 80.358/81.099/82.447 ms
root@vpn:~# opkg update
Downloading https://downloads.openwrt.org/releases/23.05.5/targets/x86/64/packages/Packages.gz
*** Failed to download the package list from https://downloads.openwrt.org/releases/23.05.5/targets/x86/64/packages/Packages.gz

Downloading https://downloads.openwrt.org/releases/23.05.5/packages/x86_64/base/Packages.gz
*** Failed to download the package list from https://downloads.openwrt.org/releases/23.05.5/packages/x86_64/base/Packages.gz

Downloading https://downloads.openwrt.org/releases/23.05.5/packages/x86_64/luci/Packages.gz
*** Failed to download the package list from https://downloads.openwrt.org/releases/23.05.5/packages/x86_64/luci/Packages.gz
Wow this is insane! Thank you for all the work. I will test soon and see what I get.
 
Ok just tested it.

First question, why can't I add a static IP to the login IP on eth0? If I change it later via the network tab on the container or openwrt interfaces lan eoth0 I can't login to the static IP address anymore.
Second question In Novaspirit Tech's video he has eth0 and eth1 eth0 points to vmbr0 and eth1 to vmbr1 if I change this I can't access openwrt anymore. Any ideas?

Also, I don't see a tun interface created but you added it to the conf file to pass through.

Last the VPN settings are not worth adding since you can just upload your VPN.ovpn file to save a lot of work plus this removes a lot of lines of code.

Thanks
 
In my latest version, I swap the zone of eth0 and eth1 so that eth0 become LAN instead of the default which is WAN
This is because eth0 gets the dhcp answer first and gets the domain name like vpn.lan from the dhcp server first

For now, go to your router and check the dhcp address

You'd only create and use vmbr1 if you want your WAN on a different physical interface, as in, you are using this container as an actual router between two networks. I have not been using it this way so far.

I have not figured how to make the second interface get a different hostname than the container hostname, I think it will involve adding dhcp option 61 for a customer client ID but I have not investigated this further.


Another bug I found, all the vpn clients are using tun0

It seems that the dev name for openvpn can be things other than tunX, even arbitrary names

So I am trying to use the vpn name as the device name but it doesn't work so far

Example

Code:
openvpn.beetvpn_asia_jakarta_5=openvpn
openvpn.beetvpn_asia_jakarta_5.auth='SHA256'
openvpn.beetvpn_asia_jakarta_5.auth_nocache='1'
openvpn.beetvpn_asia_jakarta_5.auth_user_pass='/etc/openvpn/beetvpn.auth'
openvpn.beetvpn_asia_jakarta_5.ca='/etc/openvpn/beetvpn.ca'
openvpn.beetvpn_asia_jakarta_5.cipher='AES-256-GCM'
openvpn.beetvpn_asia_jakarta_5.client='1'
openvpn.beetvpn_asia_jakarta_5.compress='stub-v2'
openvpn.beetvpn_asia_jakarta_5.dev='beetvpn_asia_jakarta_5'
openvpn.beetvpn_asia_jakarta_5.dev_type='tun'
openvpn.beetvpn_asia_jakarta_5.enabled='1'
openvpn.beetvpn_asia_jakarta_5.nobind='1'
openvpn.beetvpn_asia_jakarta_5.persist_key='1'
openvpn.beetvpn_asia_jakarta_5.persist_tun='1'
openvpn.beetvpn_asia_jakarta_5.port='53'
openvpn.beetvpn_asia_jakarta_5.proto='udp'
openvpn.beetvpn_asia_jakarta_5.remote='asia-id5.321inter.net'
openvpn.beetvpn_asia_jakarta_5.tls_cipher='TLS-ECDHE-ECDSA-WITH-AES-256-GCM-SHA384'
openvpn.beetvpn_asia_jakarta_5.tls_client='1'
openvpn.beetvpn_asia_jakarta_5.tls_crypt='/etc/openvpn/beetvpn.tlscrypt'
openvpn.beetvpn_asia_jakarta_5.verb='3'

This appears to connect, but then the TLS handshake fails with these error

Code:
Thu Oct 17 06:29:57 2024 daemon.err openvpn(beetvpn_asia_jakarta_5)[4860]: TLS Error: TLS key negotiation failed to occur within 60 seconds (check your network connectivity)
Thu Oct 17 06:29:57 2024 daemon.err openvpn(beetvpn_asia_jakarta_5)[4860]: TLS Error: TLS handshake failed


There might be the "tun" name hardcoded in a script somewhere I am searching for this.



After that I want to make each vpn connection spawn a "macvlan" virtual LAN zoned interface with its own dhcp client (and the name of the vpn as the hostname.vpn.lan that way it won't even need to use dhcp option 61 client id)
 
In my latest version, I swap the zone of eth0 and eth1 so that eth0 become LAN instead of the default which is WAN
This is because eth0 gets the dhcp answer first and gets the domain name like vpn.lan from the dhcp server first

For now, go to your router and check the dhcp address

You'd only create and use vmbr1 if you want your WAN on a different physical interface, as in, you are using this container as an actual router between two networks. I have not been using it this way so far.

I have not figured how to make the second interface get a different hostname than the container hostname, I think it will involve adding dhcp option 61 for a customer client ID but I have not investigated this further.


Another bug I found, all the vpn clients are using tun0

It seems that the dev name for openvpn can be things other than tunX, even arbitrary names

So I am trying to use the vpn name as the device name but it doesn't work so far

Example

Code:
openvpn.beetvpn_asia_jakarta_5=openvpn
openvpn.beetvpn_asia_jakarta_5.auth='SHA256'
openvpn.beetvpn_asia_jakarta_5.auth_nocache='1'
openvpn.beetvpn_asia_jakarta_5.auth_user_pass='/etc/openvpn/beetvpn.auth'
openvpn.beetvpn_asia_jakarta_5.ca='/etc/openvpn/beetvpn.ca'
openvpn.beetvpn_asia_jakarta_5.cipher='AES-256-GCM'
openvpn.beetvpn_asia_jakarta_5.client='1'
openvpn.beetvpn_asia_jakarta_5.compress='stub-v2'
openvpn.beetvpn_asia_jakarta_5.dev='beetvpn_asia_jakarta_5'
openvpn.beetvpn_asia_jakarta_5.dev_type='tun'
openvpn.beetvpn_asia_jakarta_5.enabled='1'
openvpn.beetvpn_asia_jakarta_5.nobind='1'
openvpn.beetvpn_asia_jakarta_5.persist_key='1'
openvpn.beetvpn_asia_jakarta_5.persist_tun='1'
openvpn.beetvpn_asia_jakarta_5.port='53'
openvpn.beetvpn_asia_jakarta_5.proto='udp'
openvpn.beetvpn_asia_jakarta_5.remote='asia-id5.321inter.net'
openvpn.beetvpn_asia_jakarta_5.tls_cipher='TLS-ECDHE-ECDSA-WITH-AES-256-GCM-SHA384'
openvpn.beetvpn_asia_jakarta_5.tls_client='1'
openvpn.beetvpn_asia_jakarta_5.tls_crypt='/etc/openvpn/beetvpn.tlscrypt'
openvpn.beetvpn_asia_jakarta_5.verb='3'

This appears to connect, but then the TLS handshake fails with these error

Code:
Thu Oct 17 06:29:57 2024 daemon.err openvpn(beetvpn_asia_jakarta_5)[4860]: TLS Error: TLS key negotiation failed to occur within 60 seconds (check your network connectivity)
Thu Oct 17 06:29:57 2024 daemon.err openvpn(beetvpn_asia_jakarta_5)[4860]: TLS Error: TLS handshake failed


There might be the "tun" name hardcoded in a script somewhere I am searching for this.



After that I want to make each vpn connection spawn a "macvlan" virtual LAN zoned interface with its own dhcp client (and the name of the vpn as the hostname.vpn.lan that way it won't even need to use dhcp option 61 client id)
I get the eth0 (LAN) and eth1(WAN) but how do I change from DHCP to static without losing connectivity to the interface? I always knew what my IPs on both interfaces where via DHCP but they cant be changed. There must be a config hardcoding the IP to the interface.

Secondly, how do I force an lxc to pass traffic via the OpenWRT VPN?

Thanks
 
You really have to have access to your dhcp server logs if you're going to do this.
It will make this much easier.

When you say "static" did you use manual ?


if so try this syntax instead

addnet eth0 hwaddr "DE:AD:BE:EF:01:95" ip 192.168.1.99/24 gw 192.168.1.1 ip6 manual firewall 0 bridge vmbr0 # LAN interface (eth0)
 
Here is the latest version of the script

This new version makes adding many VPN very easy, only openvpn vpn however.

each VPN gets it's own tun device name, named after the vpn name

what needs to be done

the option to set the root password doesn't work
need to setup policy based routing, to enable LAN to TUN internet sharing (NAT)
Need to create macvlan alias for each VPN connection and route it properly via policy based routing / luci-app-pbr
Need to decide if eth1 and the WAN zone it really needed for this
Add a transparent and SOCKS5 proxy to each VPN connection/macvlan
Figure out how to make port forwarding work with azire vpn
maybe setup upnp
maybe setup IPban and other traffic filtering such as adblocking ?
find provision for website caching/saving ala archivebox
maybe setup snort and other traffic monitoring
figure out how to multiwan/ combine multiple VPN connection to reach reliably 3gbps speeds through the VPN




Code:
# print full container config with detail of net
# print out minimal vpn config
# in general, more verbosity

#----------------------------------------
# shell function to create --net variable
addnet() { CT_net_count=${CT_net_count:-0}; local net_name=$1; shift; local _CT_new_config="--net$CT_net_count name=$net_name"; local valid_params=("bridge" "firewall" "gw" "gw6" "hwaddr" "ip" "ip6" "link_down" "mtu" "rate" "tag" "trunks" "type"); while [ $# -gt 0 ]; do key=$1; value=$2; if [[ " ${valid_params[*]} " =~ " $key " ]]; then _CT_new_config="$_CT_new_config,$key=$value"; shift 2; else shift 1; fi; done; _CT_net_config="$_CT_net_config $_CT_new_config"; echo "Interface added: $_CT_new_config"; CT_net_count=$((CT_net_count + 1)); }
# shell function for create each file line variables
addline() { file_line_ubound=$((file_line_ubound + 1)); eval "file_line_${file_line_ubound}_${file_ubound}=\"$1\""; eval "file_line_count_${file_ubound}=$file_line_ubound"; }
addfile() { file_ubound=$((file_ubound + 1)); eval "file_name_${file_ubound}=\"$1\""; [ -n "$2" ] && [[ "$2" =~ ^[0-9]+$ ]] && eval "filepermission_${file_ubound}=\"$2\""; [ -n "$3" ] && eval "fileowner_${file_ubound}=\"$3\""; unset file_line_ubound; }
pct_append_text() { local file=$1; local text_or_var=$2; if [ -n "${!text_or_var}" ]; then local text=${!text_or_var}; elif [[ "$text_or_var" == file_line* ]]; then local text=$(eval echo \${$text_or_var}); else local text="$text_or_var"; fi; local command="echo \"$text\" >> \"$file\""; [ "$VERBOSE" -gt 0 ] && echo "pct exec $CT_ID -- /bin/sh -c \"$command\""; pct exec $CT_ID -- /bin/sh -c "$command"; }
writefile() { local file_index=$1; local file_name=$(eval echo \${file_name_${file_index}}); local file_permission=$(eval echo \${filepermission_${file_index}}); local file_owner=$(eval echo \${fileowner_${file_index}}); local file_line_count=$(eval echo \${file_line_count_${file_index}}); for i in $(seq 1 $file_line_count); do local file_line_var="file_line_${i}_${file_index}"; pct_append_text "$file_name" "$file_line_var"; done; [ -n "$file_permission" ] && pct_exec "chmod $file_permission $file_name"; [ -n "$file_owner" ] && pct_exec "chown $file_owner $file_name"; }
# shell function to add a VPN and define its parameters
addvpn() { vpn_ubound=$((vpn_ubound + 1)); }
vpn() { eval vpn_${1}_${vpn_ubound}=\"$2\"; }
apply_vpn_config() { local vpn_index=$1 vpn_name vpn_type var_name var_value sanitized_vpn_name; vpn_name=$(eval echo \${vpn_name_${vpn_index}}); vpn_type=$(eval echo \${vpn_type_${vpn_index}}); sanitized_vpn_name=$(echo "$vpn_name" | sed 's/-/_/g'); pct_exec "uci set $vpn_type.$sanitized_vpn_name=$vpn_type"; for var in $(compgen -A variable | grep "vpn_.*_${vpn_index}$"); do var_name=$(echo $var | sed -r 's/vpn_(.*)_'${vpn_index}'/\1/'); if [ "$var_name" = "name" ] || [ "$var_name" = "type" ]; then continue; fi; var_value=$(eval echo \${$var}); pct_exec "uci set $vpn_type.$sanitized_vpn_name.$var_name=$var_value"; done; pct_exec "uci commit $vpn_type.$sanitized_vpn_name"; echo "VPN $vpn_name configuration applied."; }
#copyvpn() { local source_name=$1; local source_index=""; for i in $(seq 1 $vpn_ubound); do if [ "$(eval echo \${vpn_name_${i}})" = "$source_name" ]; then source_index=$i; break; fi; done; [ -z "$source_index" ] && { echo "Error: VPN with name '$source_name' not found."; return 1; }; vpn_ubound=$((vpn_ubound + 1)); for var in $(compgen -A variable | grep "vpn_.*_${source_index}$"); do var_name=$(echo $var | sed -r "s/vpn_(.*)_${source_index}/\1/"); var_value=$(eval echo \${$var}); eval vpn_${var_name}_${vpn_ubound}=\"$var_value\"; done; echo "VPN '$source_name' copied to new VPN index $vpn_ubound."; }
copyvpn() { local s=$1 n=${2:-} r=${3:-} p=${4:-} i=; for x in $(seq 1 "$vpn_ubound"); do [ "$(eval echo \${vpn_name_${x}})" = "$s" ] && i=$x && break; done; [ -z "$i" ] && { echo "Error: VPN '$s' not found."; return 1; }; vpn_ubound=$((vpn_ubound + 1)); for v in $(compgen -A variable | grep "vpn_.*_${i}$"); do k=${v#vpn_}; k=${k%_${i}}; eval "vpn_${k}_${vpn_ubound}=\${$v}"; done; [ -n "$n" ] && eval "vpn_name_${vpn_ubound}='$n'"; [ -n "$r" ] && eval "vpn_remote_${vpn_ubound}='$r'"; [ -n "$p" ] && eval "vpn_port_${vpn_ubound}='$p'"; echo "VPN '$s' copied to new VPN index $vpn_ubound."; }
update_vpn_dev_names() { for var in $(compgen -A variable | grep '^vpn_name_[0-9]*$'); do i=${var#vpn_name_}; vpn_name=${!var}; sanitized_vpn_name="tun_$(echo "$vpn_name" | sed 's/-/_/g')"; eval vpn_dev_${i}=\"$sanitized_vpn_name\"; echo "vpn_dev_${i} set to $sanitized_vpn_name"; done; }
# shell function to type pct exec commands
pct_exec() { [ "$VERBOSE" -gt 0 ] && echo "pct exec $CT_ID -- /bin/sh -c \"$*\""; pct exec $CT_ID -- /bin/sh -c "$*"; }
#function to set link_down to 0
replace_link_down() { _CT_net_config=${_CT_net_config//link_down=1/link_down=0}; echo "Updated _CT_net_config: $_CT_net_config"; pct set "$CT_ID" $_CT_net_config; }

VERBOSE=1  # Enable verbose mode

echo "------------------------------ Creation of openwrt LXC container ------------------------------"

CT_ID="1002"  # Adjust the container ID
CT_hostname="vpn"
CT_root_password="qwerty"
CT_memory="1024"
CT_cores="4"
CT_rootfs_size="2"

addnet eth0 hwaddr "DE:AD:BE:EF:01:95" ip dhcp ip6 manual firewall 0 bridge vmbr0 #link_down 1 # LAN interface (eth0)
addnet eth1 hwaddr "DE:AD:BE:EF:01:96" ip dhcp ip6 manual firewall 0 bridge vmbr0 #link_down 1 # WAN interface (eth1)
#addnet eth2 hwaddr "DE:AD:BE:EF:01:97" ip dhcp ip6 dhcp bridge vmbr1 firewall 0 # Extra network interface 2 (eth2)
#addnet eth3 hwaddr "DE:AD:BE:EF:01:99" ip dhcp ip6 dhcp bridge vmbr1 firewall 0 # Extra network interface 3 (eth3)


# Add VPN configuration for OpenVPN
addvpn
vpn name "asia-jakarta-5-beetvpn"
vpn remote "asia-id5.321inter.net"
#vpn allow-compression "1"  # might be wrong syntax
#vpn compress "lz4-v2"
#vpn remote_cert_eku "\"TLS Web Server Authentication\"" # might be wrong syntax
#vpn remote_cert_tls server
vpn auth "SHA256"
vpn auth_nocache 1
vpn auth_user_pass "/etc/openvpn/beetvpn.auth"
vpn ca "/etc/openvpn/beetvpn.ca"
vpn cipher "AES-256-GCM"
vpn client 1
vpn compress "stub-v2"
vpn dev "tun0"
vpn dev_type "tun"
vpn enabled 0
vpn nobind 1
vpn persist_key 1
vpn persist_tun 1
vpn port 1194
vpn proto "udp"
vpn tls_cipher "TLS-ECDHE-ECDSA-WITH-AES-256-GCM-SHA384"
vpn tls_client 1
vpn tls_crypt "/etc/openvpn/beetvpn.tlscrypt"
vpn type "openvpn"
vpn verb 3

addvpn
vpn name "asia-hongkong-azirevpn"
#vpn allow-compression "1"  # might be wrong syntax
#vpn auth_nocache 1
#vpn compress "lz4-v2"
#vpn compress "stub-v2"
#vpn keepalive 10
#vpn mute_replay_warnings
#vpn remote_cert_eku "\"TLS Web Server Authentication\"" # might be wrong syntax
#vpn remote_cert_tls='server'
#vpn tls_cipher "TLS-ECDHE-ECDSA-WITH-AES-256-GCM-SHA384"
#vpn tls_client 1
vpn auth "SHA512"
vpn auth_user_pass "/etc/openvpn/azire.auth"
vpn ca "/etc/openvpn/azire.ca"
vpn cipher "AES-256-CBC"
vpn client 1
vpn dev "tun0"
vpn dev_type "tun"
vpn enabled 0
vpn explicit_exit_notify 3
vpn key_direction 1
vpn nobind 1
vpn persist_key 1
vpn persist_tun 1
vpn port 1194
vpn proto "udp"
vpn remote "hk-hkg.ovpn.azirevpn.net"
vpn remote_cert_tls server
vpn reneg_sec 0
vpn resolv_retry infinite
vpn tls_auth "/etc/openvpn/azire.tlsauth"
vpn type "openvpn"
vpn verb 3



copyvpn "asia-hongkong-azirevpn" "asia-hongkong-azirevpn" "hk-hkg.ovpn.azirevpn.net"
copyvpn "asia-jakarta-5-beetvpn" "asia-jakarta-6-beetvpn" "asia-id6.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "aus-sydney-beetvpn" "oc-syd.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "aus-sydney-2-beetvpn" "oc-syd2.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "ca-montreal-beetvpn" "us-ca-mon.321inter.net"
copyvpn "asia-hongkong-azirevpn" "ca-toronto-azirevpn" "ca-tor.ovpn.azirevpn.net"
copyvpn "asia-jakarta-5-beetvpn" "ca-toronto-beetvpn" "us-ca-tor.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "ca-vancouver-beetvpn" "ca-van.321inter.net"
copyvpn "asia-hongkong-azirevpn" "eu-amsterdan-azirevpn" "nl-ams.ovpn.azirevpn.net"
copyvpn "asia-jakarta-5-beetvpn" "eu-amsterdam-beetvpn" "eu-nl.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "eu-barcelona-beetvpn" "eu-es.321inter.net"
copyvpn "asia-hongkong-azirevpn" "eu-berlin-azirevpn" "de-ber.ovpn.azirevpn.net"
copyvpn "asia-jakarta-5-beetvpn" "eu-brussels-beetvpn" "eu-be.321inter.net"
copyvpn "asia-hongkong-azirevpn" "eu-bucharest-azirevpn" "ro-buh.ovpn.azirevpn.net"
copyvpn "asia-hongkong-azirevpn" "eu-copenhagen-azirevpn" "dk-cph.ovpn.azirevpn.net"
copyvpn "asia-jakarta-5-beetvpn" "eu-dublin-beetvpn" "eu-ie-dub.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "eu-dusseldorf-beetvpn" "eu-de.321inter.net"
copyvpn "asia-hongkong-azirevpn" "eu-frankfurt-azirevpn" "de-fra.ovpn.azirevpn.net"
copyvpn "asia-jakarta-5-beetvpn" "eu-frankfurt-beetvpn" "eu-de-fra.321inter.net"
copyvpn "asia-hongkong-azirevpn" "eu-helsinki-azirevpn" "fi-hel.ovpn.azirevpn.net"
copyvpn "asia-jakarta-5-beetvpn" "eu-helsinki-beetvpn" "eu-fi.321inter.net"
copyvpn "asia-hongkong-azirevpn" "eu-kyiv-azirevpn" "ua-iev.ovpn.azirevpn.net"
copyvpn "asia-jakarta-5-beetvpn" "eu-kyiv-beetvpn" "eu-ua.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "eu-ljubljana-beetvpn" "eu-si-lju.321inter.net"
copyvpn "asia-hongkong-azirevpn" "eu-madrid-azirevpn" "es-mad.ovpn.azirevpn.net"
copyvpn "asia-hongkong-azirevpn" "eu-malaga-azirevpn" "es-mal.ovpn.azirevpn.net"
copyvpn "asia-hongkong-azirevpn" "eu-milan-azirevpn" "it-mil.ovpn.azirevpn.net"
copyvpn "asia-hongkong-azirevpn" "eu-oslo-azirevpn" "no-osl.ovpn.azirevpn.net"
copyvpn "asia-jakarta-5-beetvpn" "eu-palermo-beetvpn" "eu-it-syc.321inter.net"
copyvpn "asia-hongkong-azirevpn" "eu-paris-azirevpn" "fr-par.ovpn.azirevpn.net"
copyvpn "asia-jakarta-5-beetvpn" "eu-paris-beetvpn" "eu-fr.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "eu-prague-beetvpn" "eu-cz-pra.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "eu-rotterdam-beetvpn" "eu-nl-rtm.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "eu-seville-beetvpn" "eu-es-sev.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "eu-sophia-beetvpn" "eu-bg-sof.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "eu-stockholm-beetvpn" "eu-se.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "eu-thessaloniki-beetvpn" "eu-gr-the.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "eu-warsaw-beetvpn" "eu-pl3.321inter.net"
copyvpn "asia-hongkong-azirevpn" "eu-zurich-azirevpn" "ch-zrh.ovpn.azirevpn.net"
copyvpn "asia-jakarta-5-beetvpn" "eu-zurich-beetvpn" "eu-ch.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "mena-bursa-beetvpn" "asia-tr-bur.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "mena-mumbai-beetvpn" "asia-in.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "mena-tel-aviv-beetvpn" "asia-il-tel.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "ru-moscow-beetvpn" "asia-ru.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "ru-st-petersburg-beetvpn" "asia-ru-spe.321inter.net"
copyvpn "asia-hongkong-azirevpn" "sa-argentina-azirevpn" "ua-iev.ovpn.azirevpn.net"
copyvpn "asia-hongkong-azirevpn" "sa-buenos-aires-azirevpn" "ar-bue.ovpn.azirevpn.net"
copyvpn "asia-jakarta-5-beetvpn" "sa-sao-paulo-beetvpn" "sa-br.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "sea-bangkok-beetvpn" "asia-th.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "sea-hong-kong-beetvpn" "asia-hk2.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "sea-manila-beetvpn" "ph-man.321inter.net"
copyvpn "asia-hongkong-azirevpn" "sea-rawai-azirevpn" "th-hkt.ovpn.azirevpn.net"
copyvpn "asia-hongkong-azirevpn" "sea-singapore-azirevpn" "sg-sin.ovpn.azirevpn.net"
copyvpn "asia-jakarta-5-beetvpn" "sea-singapore-beetvpn" "asia-sg.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "sea-singapore-2-beetvpn" "sg2.ipcover.net"
vpn data_ciphers "AES-256-GCM"
copyvpn "asia-jakarta-5-beetvpn" "sea-tokyo-beetvpn" "asia-jp4.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "sea-tokyo-2-beetvpn" "asia-jp5.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "sea-tokyo-6-beetvpn" "asia-jp6.321inter.net"
copyvpn "asia-hongkong-azirevpn" "uk-london-azirevpn" "gb-lon.ovpn.azirevpn.net"
copyvpn "asia-jakarta-5-beetvpn" "uk-london-beetvpn" "uk-lon.321inter.net"
copyvpn "sea-singapore-2-beetvpn" "uk-london-2-beetvpn" "uk2.ipcover.net"
copyvpn "asia-hongkong-azirevpn" "us-chicago-azirevpn" "us-chi.ovpn.azirevpn.net"
copyvpn "asia-hongkong-azirevpn" "us-dallas-azirevpn" "us-dal.ovpn.azirevpn.net"
copyvpn "asia-hongkong-azirevpn" "us-gothenburg -azirevpn" "se-got.ovpn.azirevpn.net"
copyvpn "asia-jakarta-5-beetvpn" "us-los-angeles-beetvpn" "us-fl-la.321inter.net"
copyvpn "asia-hongkong-azirevpn" "us-miami-azirevpn" "us-mia.ovpn.azirevpn.net"
copyvpn "asia-jakarta-5-beetvpn" "us-miami-beetvpn" "us-fl-mia.321inter.net"
copyvpn "sea-singapore-2-beetvpn" "us-miami-2-beetvpn" "us2.ipcover.net"
copyvpn "asia-hongkong-azirevpn" "us-new-york-azirevpn" "us-nyc.ovpn.azirevpn.net"
copyvpn "asia-jakarta-5-beetvpn" "us-new-york-beetvpn" "us-nyc.321inter.net"
copyvpn "asia-hongkong-azirevpn" "us-san-francisco-azirevpn" "us-sfo.ovpn.azirevpn.net"
copyvpn "asia-hongkong-azirevpn" "us-seattle-azirevpn" "us-sea.ovpn.azirevpn.net"
copyvpn "asia-jakarta-5-beetvpn" "za-johannesburg-beetvpn" "za-joh.321inter.net"
copyvpn "asia-jakarta-5-beetvpn" "za-johannesburg-2-beetvpn" "za-joh2.321inter.net"


# Create the file and set its metadata
addfile "/etc/openvpn/beetvpn.ca" "600" "root:root"
addline "<ca>"
addline "-----BEGIN CERTIFICATE-----"
addline "MIIB6TCCAW+gAwIBAgIJAO7HEvJxfUUCMAoGCCqGSM49BAMCMBcxFTATBgNVBAMM"
addline "DDMyMWludGVyLm5ldDAeFw0xOTA1MjExMzI3NDlaFw0yOTA1MTgxMzI3NDlaMBcx"
addline "FTATBgNVBAMMDDMyMWludGVyLm5ldDB2MBAGByqGSM49AgEGBSuBBAAiA2IABGja"
addline "TAidcTxY9ud7w3Jr1y6BSS7trkeu3kZqDg/TDCxE4k0Ay6AXVkooORyidfco+SGx"
addline "zR8oxcit7JGjCf5+JCufjKjl3s/yULt7gYfQnfBYN4ULcr1gpKCZQMIlORnvHaOB"
addline "hjCBgzAdBgNVHQ4EFgQUThoKRpgMcQwcQwlfjfzf5vE2mOUwRwYDVR0jBEAwPoAU"
addline "ThoKRpgMcQwcQwlfjfzf5vE2mOWhG6QZMBcxFTATBgNVBAMMDDMyMWludGVyLm5l"
addline "dIIJAO7HEvJxfUUCMAwGA1UdEwQFMAMBAf8wCwYDVR0PBAQDAgEGMAoGCCqGSM49"
addline "BAMCA2gAMGUCMCL6jOfO1j5lC6q0DN5Z8Aw0GQ5SAFlmlvyAkk1/dGSgA1gzV5/T"
addline "4c53qemB1vz4SQIxAN7onHBiSvGwnCePjDSoonHA9CUlWUX9hurwIdFFqLWyRQHn"
addline "Nqxoy1tXLIfKApc8CQ=="
addline "-----END CERTIFICATE-----"
addline "</ca>"

Cut here due to character limit
 
  • Like
Reactions: enigmacarpc
continued here due to character limit

Code:
addfile "/etc/openvpn/azire.ca" "600" "root:root"

addline "<ca>"

addline "-----BEGIN CERTIFICATE-----"

addline "MIIG9DCCBNygAwIBAgIJALTRm7uk+qsqMA0GCSqGSIb3DQEBCwUAMIGsMQswCQYD"

addline "VQQGEwJTRTESMBAGA1UECBMJU3RvY2tob2xtMRIwEAYDVQQHEwlTdG9ja2hvbG0x"

addline "ETAPBgNVBAoTCEF6aXJlVlBOMREwDwYDVQQLEwhBemlyZVZQTjEaMBgGA1UEAxMR"

addline "b3Zwbi5hemlyZXZwbi5uZXQxETAPBgNVBCkTCEF6aXJlVlBOMSAwHgYJKoZIhvcN"

addline "AQkBFhFpbmZvQGF6aXJldnBuLmNvbTAeFw0xNTAzMTgyMDAzMjNaFw0yNTAzMTUy"

addline "MDAzMjNaMIGsMQswCQYDVQQGEwJTRTESMBAGA1UECBMJU3RvY2tob2xtMRIwEAYD"

addline "VQQHEwlTdG9ja2hvbG0xETAPBgNVBAoTCEF6aXJlVlBOMREwDwYDVQQLEwhBemly"

addline "ZVZQTjEaMBgGA1UEAxMRb3Zwbi5hemlyZXZwbi5uZXQxETAPBgNVBCkTCEF6aXJl"

addline "VlBOMSAwHgYJKoZIhvcNAQkBFhFpbmZvQGF6aXJldnBuLmNvbTCCAiIwDQYJKoZI"

addline "hvcNAQEBBQADggIPADCCAgoCggIBAOB++h0/Gt/C8fqmA65V0BjY8bsjWUeRzgHr"

addline "HSkbApqsBry+JBPYhZcGVpSsVOYzrd8C9Q0yE4ebYBWhIzwdckA+puJUDsuiDMPs"

addline "k5d7QIrVsb/l+ugJkOUkM+ODSThl7bdIHAT30pS8OdrDHn2x70axAh1byakdEmAy"

addline "w+Tzqi29Q4hMe5h5w4YUZkNdRtK8u11gH4ROsPUGqbgE1qA37D78LXwMN5vJorQE"

addline "yzYPmZj8dqNYAhhdAijVGaVs4CwGm1GQL2paKhnxDrzhISl4bEyIHNsPvc7WDEal"

addline "wuo3LC9HyXAPykqAdCTd092GgRQY4WKF/uKBHJPBe0N+eGOL5MIxUzq87LLETBlP"

addline "Fiwznn2OdPLnYru/dpMcYKQ4arw359sKrh4WdjMep5468DlCLAATRdFaXuqwcou2"

addline "N5iWD1OltnzXpGb4Wp/EjNeKe4oWwXdyytKc0p3gzlH3x5WKP/QO7kJwHFrjfLFv"

addline "aSsI34Z1VEFGwb9q9TMXaOeV0iQISqZGfpAvQHeWnkkEDMomAnjST6P1GnIpWJFm"

addline "8+tSf859Lsjlqbja+zhlWKlkxbE5+qxSYCXoxl9HZv6zrmlZTkLbjeV8A/cJEpBw"

addline "D2ytYA8sOxtSHyOLyxrrjj4xN8RuRbW0vIDGDFgzobrdJaXWn5GFwgTV3ZkOC1fp"

addline "6eOJnx1RAgMBAAGjggEVMIIBETAdBgNVHQ4EFgQUuF98V2arTcaROqFD+BcloIRC"

addline "d7IwgeEGA1UdIwSB2TCB1oAUuF98V2arTcaROqFD+BcloIRCd7KhgbKkga8wgawx"

addline "CzAJBgNVBAYTAlNFMRIwEAYDVQQIEwlTdG9ja2hvbG0xEjAQBgNVBAcTCVN0b2Nr"

addline "aG9sbTERMA8GA1UEChMIQXppcmVWUE4xETAPBgNVBAsTCEF6aXJlVlBOMRowGAYD"

addline "VQQDExFvdnBuLmF6aXJldnBuLm5ldDERMA8GA1UEKRMIQXppcmVWUE4xIDAeBgkq"

addline "hkiG9w0BCQEWEWluZm9AYXppcmV2cG4uY29tggkAtNGbu6T6qyowDAYDVR0TBAUw"

addline "AwEB/zANBgkqhkiG9w0BAQsFAAOCAgEATo1N6VG58Rz+ar2O31BoYHkYtFpkVSOj"

addline "tO/TorB9FFrKCQ/4nQevj0IKezQziRSctrHE2Mj+ZK0OyPI6jFzAfsUbOA6y5WY0"

addline "AMnaiq0d2oMs/NtsgyL7EOftr5sDVGPUR8uvtlhxz10zUEQ/iPrdrH/1FMoBwZG6"

addline "bnW3TWS8LZlVEoj7lFKuFyzF8KM330JFPpNDjvm2LbZfx9otAKnyLpdtzRyWLLvA"

addline "FAMx5Io+EIQZc6IREQrllPgToOLOf9psWCAr2a6AuVml2fEBalRq1dw4mwd6BUO3"

addline "b43ah27BnWbv9Jk8TdiGXGmKzPRy2VXJPp0Ck0yMCHlSsg0W8VZOPwEFMarTYF7x"

addline "wFsTFnnfi/UnhMVa/4Cc1PsnIXH5RJHgb+QcxanTP2ZjxD03pEe2mbzRGCI0xVli"

addline "5y0oxWPjx5JZqeEc9Ui+vQZ1pD2jj/65BzzPCBALYGdm4TlanpjB9LeAyGgpM7AC"

addline "qBALu7GG8djkoEID0htVVh61jt87bTvlc9gCUdCpnKpXLopmWN8T++qau/GnmyAc"

addline "Y0lBt5TCtDvj0S/TS7BtS9pnUlFYBEKNWPHZhu7eaj3scXUjWktjGeOQF7OEjExR"

addline "lQUHOp+Ox8bx0oIyd8FsoYqby1SIht+xppgGwIz3jhdkLZdpiZEhcxqRRLGUEaos"

addline "eORQL7iEUWI="

addline "-----END CERTIFICATE-----"

addline "</ca>"


addfile "/etc/openvpn/beetvpn.auth" "600" "root:root"

addline "myusername"

addline "mypassword"


addfile "/etc/openvpn/azire.auth" "600" "root:root"

addline "myusername"

addline 'mypassword'


addfile "/etc/openvpn/beetvpn.tlscrypt" "600" "root:root"

addline "<tls-crypt>"

addline "#"

addline "# 2048 bit OpenVPN static key"

addline "#"

addline "-----BEGIN OpenVPN Static key V1-----"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "-----END OpenVPN Static key V1-----"

addline "</tls-crypt>"


addfile "/etc/openvpn/azire.tlsauth" "600" "root:root"

addline "<tls-auth>"

addline "-----BEGIN OpenVPN Static key V1-----"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"

addline "-----END OpenVPN Static key V1-----"

addline "</tls-auth>"



CT_template_download="https://jenkins.linuxcontainers.org/job/image-openwrt/architecture=amd64,release=23.05,variant=default/lastSuccessfulBuild/artifact/rootfs.tar.xz"

CT_template_filename="openwrt-amd64,23.05,default.tar.xz"

CT_template_file="local:vztmpl/$CT_template_filename"

CT_key="ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQCIWFBY0G/lbORqeMXI2PfIcVBuDO66KeCzFr4IqXOFC1ehuC573tXRW6TQTAAR6nlYTXrzw4Mw+1y2lgwP3rkibH/RpkCIu96hPygad2ZrxObNoM44Hpzxq6Jq/S8sXNjpsb7Q0yN7yqjAwQIKA9eDvRaC/03yPz9pLcZ3gjk3YUVPZuZ3zUrjJV+n4XeCmw1HvMTkGRJ3SVCHw1tyB1K8rCxu6sGw55HK3P70moPj8JiAvxe2y+V84DGU9n4vWuwVMWcpISrubaQIeUo2WQebRB5C3qCkNyGzwTdTR6v6gBy+aiL1VvL2qUiNGQ3LE1FgnLnvwQZk5IubPMjfoyvT rsa-key-20240925"

CT_key_file="/ssh_key.openwrt.pub"


#Only download template file if it is not already present

[ ! -f /var/lib/vz/template/cache/$CT_template_filename ] && wget "$CT_template_download" -O /var/lib/vz/template/cache/$CT_template_filename


#Obtain the next CT_ID if not already set

: ${CT_ID:=$(pct list | awk 'NR>1 {print $1}' | sort -n | awk 'NR==1{prev=$1} NR>1 && $1>prev+1{print prev+1; exit} {prev=$1} END{if (prev+1 > $1) print prev+1}')}


echo "$CT_key" > $CT_key_file


# Create the container

echo ""; echo Creating LXC Container for $CT_template_filename

[ "$VERBOSE" -gt 0 ] && echo "pct create $CT_ID $CT_template_file --arch amd64 --cores $CT_cores --memory $CT_memory --hostname $CT_hostname $_CT_net_config --rootfs local-lvm:$CT_rootfs_size --features nesting=1 --unprivileged 1 --ostype unmanaged"

pct create $CT_ID $CT_template_file --arch amd64 --cores $CT_cores --memory $CT_memory --hostname $CT_hostname $_CT_net_config --rootfs local-lvm:$CT_rootfs_size --features nesting=1 --unprivileged 1 --ostype unmanaged


rm $CT_key_file


# If vpn enabled, then add tun

# Define the LXC configuration file path

LXC_CONF_FILE="/etc/pve/nodes/proxmox/lxc/$CT_ID.conf"


# Add permissions mapping for tun/tap devices

[ "$vpn_ubound" -gt 0 ] && echo "lxc.cgroup2.devices.allow: c 10:200 rwm" >> "$LXC_CONF_FILE"

[ "$vpn_ubound" -gt 0 ] && echo "lxc.mount.entry: /dev/net/tun dev/net/tun none bind,create=file" >> "$LXC_CONF_FILE"



# Start the container

pct start $CT_ID


#Wait until container is finished booting

: ${CT_ID:=101}; while [[ $(pct status $CT_ID) != *"running"* ]]; do echo "Waiting for container $CT_ID to start..."; sleep 2; done; echo "Container $CT_ID is running."


#Wait a bit more to make sure it is done booting (it might still not be)

sleep 5


# Disable DHCP server on LAN

pct_exec uci set dhcp.lan.ignore='1'


# Set LAN interface to use DHCP (so eth1 will act as a DHCP client)

pct_exec uci set network.lan=interface

pct_exec uci set network.lan.proto='dhcp'

# Making LAN on eth0 so that it received the hostname on the LAN first

pct_exec uci set network.lan.ifname='eth0'

pct_exec uci set network.wan.ifname='eth1'

pct_exec uci set network.wan6.ifname='eth1'

#echo running replace_link_down

#replace_link_down

pct_exec uci set network.lan.hostname='vpn.lan'

pct_exec uci set network.wan.hostname='wan.vpn'

pct_exec uci set network.wan6.hostname='wan.vpn'

pct_exec uci commit network

pct_exec /etc/init.d/network restart

pct_exec /etc/init.d/firewall restart


pct_exec mkdir /etc/openvpn


#write all the files into the container

for i in $(seq 1 $file_ubound); do writefile ${i} ; done


pct_exec opkg update -q


pct_exec opkg install openssh-sftp-server # enable sftp

pct_exec opkg install nano # install nano

pct_exec opkg install openvpn-openssl luci-app-openvpn

#pct_exec opkg install luci-app-pbr

pct_exec uci del openvpn.custom_config

pct_exec uci del openvpn.sample_server

pct_exec uci del openvpn.sample_client


#change dev name to vpn name

for i in $(seq 1 $vpn_ubound); do update_vpn_dev_names $i; done


#create all vpn settings (only if there is a vpn)

for i in $(seq 1 $vpn_ubound); do apply_vpn_config ${i} ; done


pct_exec uci changes

pct_exec uci commit


pct_exec /etc/init.d/openvpn start

pct_exec passwd root -d '$CT_root_password'
[/CODE]
 
  • Like
Reactions: enigmacarpc

About

The Proxmox community has been around for many years and offers help and support for Proxmox VE, Proxmox Backup Server, and Proxmox Mail Gateway.
We think our community is one of the best thanks to people like you!

Get your subscription!

The Proxmox team works very hard to make sure you are running the best software and getting stable updates and security enhancements, as well as quick enterprise support. Tens of thousands of happy customers have a Proxmox subscription. Get yours easily in our online shop.

Buy now!