Running up Vless+WS+TLS+CDN server with Singbox core

 Running up Vless+WS+TLS+CDN server with Singbox core

Today I’d want to discuss another approach to avoid filtering. In this regard, it is a more older model than REALITY protocol. We connect to our server via Cloudflare, which decreases the possibility of the server’s IP getting blocked, and the detection system just sees the domain. Of course, if there is a lot of traffic or the filtering system is suspicious, it blocks the domain as well, but there is a solution for that as well.

Using SingBox deb file and install it with dpkg is not particularly useful in this approach since we need a certificate for TLS, which Singbox obtains directly from Let’s Encrypt, and it requires the installation of a module that does not install with that method. Of course, if you are technically inclined, you can use the same procedure and manually enter the certificate. However, this post is intended for the everyone who is not familiar with TLS certificate.

I installed it in an Ubuntu 20.04 VPS. Continue by upgrading the packages and installing Go from the links below:

sudo su
apt update && apt install -y build-essential
curl -fsL https://raw.githubusercontent.com/jetsung/golang-install/main/install.sh | bash
source /root/.bashrc

Install the Singbox core with all its modules with the following command:

go install -v -tags "with_clash_api with_reality_server with_quic with_grpc with_wireguard with_shadowsocksr with_ech with_utls with_acme with_v2ray_api with_gvisor with_lwip" github.com/sagernet/sing-box/cmd/sing-box@dev-next

Allow all users access:

cp ~/go/bin/sing-box /usr/local/bin/

Create a folder where Singbox will put its stuff:

mkdir /etc/sing-box/ && cd $_

Create a systemctl config for singbox:

cat <<EOF > /etc/systemd/system/sing-box.service
[Unit]
Description=sing-box Service
Documentation=https://sing-box.sagernet.org/
After=network.target nss-lookup.target
Wants=network.target
[Service]
Type=simple
ExecStart=/usr/local/bin/sing-box run -c /etc/sing-box/config.json
Restart=always
RestartSec=3s
RestartPreventExitStatus=23
LimitNPROC=10000
LimitNOFILE=1000000
[Install]
WantedBy=multi-user.target
EOF

You can start, restart and stop the Singbox service with the following commands. Remember to enter the enable command only once so that when the server is turned off, the singbox will run automatically again.

Systemctl enable sing-box.service
Systemctl start sing-box.service
Systemctl restart sing-box.service
Systemctl stop sing-box.service

Create a config file with nano or any other program: (delete everything if there is something in it)

nano /etc/sing-box/config.json

and put the following config in it then I will explain it:

{
  "log": {
    "level": "info",
    "timestamp": true
	,"disabled": true
  },
  "dns": {
    "servers": [
      { 
        "tag": "local",
        "address": "https://1.1.1.1/dns-query",
        "detour": "direct"
      },
      {
        "tag": "block",
        "address": "rcode://success"
      }
    ]
  },
  "inbounds": [{
	"type": "vless",
	"tag": "vless-in",
	"listen": "::",
	"listen_port": 443,
	"users": [
		{
      "name": "user1",
      "uuid": "8337f541-d602-46f0-9da6-23516ab4c6a7"
		},
		{
      "name": "user2",
      "uuid": "1d4584c5-6293-4a92-0262-b448835166b7"
		}
	],
	"tls": {
		"enabled": true,
		"server_name": "sub1.example.com",
		"alpn": [
			"http/1.1","h2"
		],
		"min_version": "1.3",
		"max_version": "1.3",
		"acme": {
			"domain": ["sub1.example.com"],
			"data_directory": "/etc/sing-box",
			"default_server_name": "",
			"email": "[email protected]",
			"provider": "letsencrypt"
		}
	},
	"transport": {
		"type": "ws",
		"path": "/speedtest",
		"max_early_data": 0,
		"early_data_header_name": "Sec-WebSocket-Protocol"
	}
}],

  "outbounds": [
    {
      "type": "direct",
      "tag": "direct"
    },
    {
      "type": "block",
      "tag": "block"
    }
  ],
  "route": {
	"geosite": {
      "path": "/var/lib/sing-box/geosite.db",
      "download_url": "https://github.com/SagerNet/sing-geosite/releases/latest/download/geosite.db"
    },
	"geoip": {
      "path": "/var/lib/sing-box/geoip.db",
      "download_url": "https://github.com/SagerNet/sing-geoip/releases/latest/download/geoip.db"
    },
    "rules": [
      {
		"domain_keyword": [],
        "domain_suffix": [
          ".cn"
        ],
        "geoip": [
          "cn"
        ],
        "invert": false,
        "outbound": "block"
      }
    ]
  }
}

To add users, you can change the same user1 and user2 and create a new user with any desired name and in the same json format. Each user has his own UUID. This way, you don’t need a X-UI or Hiddify panel anymore.

In the server_name field, enter a domain that you registered in Cloudflare. My suggestion is to create a subdomain to be more flexible later. Connect the subdomain with the A record to the servers IP and turn off the Cloudflare proxy option for now. The cloud icon should be black and white.

Everyone agrees that the minimum TLS version should be 1.2 and the maximum should be 1.3. However, my opinion is that all should be 1.3. If no one can connect, change it to 1.2.

Re-enter the same sub-domain as the domain and enter an email. It doesn’t matter if it is fake.

In the transport and path sections, I put “speedtest” so that it is more similar to real traffic. Anything you want is acceptable.

After these changes, you can run the service manually to see what can be done, then run the service with systemctl.

sing-box run -c /etc/sing-box/config.json

It will inform you that it will obtain an SSL certificate for the subdomain you specified. At the end, it says Verification Successfully, indicating that the certificate was received and the service was performed. edit the config and make sure that log is disabled by editing “disabled”: true to false, as it slows down the server in my experience. By the way, the certificate is only received once and saved in the sing-box folder. If you want to modify the subdomain, you must obtain a new certificate.

Now it’s time to activate the proxy option in Cloudflare and the cloud icon will turn orange.

The configuration section of the client, like Windows, is as follows:

One step further…

If you are in a high-restricted nation where your ISP has set up GFW, the firewall system will block the Cloudflare IP address in the “Address” field, preventing you from connecting. Cloudflare has an enormous number of IPs, and while blocking them is straightforward, it affects many other services and causes them to fail. So there are many scanners 1, 2, 3, and even online can provide you with a list of “clean” IPs that are not currently blocked. This clean ip can also be blocked or slowed, but as previously said, this is only temporary and will unblock after a few hours or days. You can also look for another IP.

Another step further…
Because the GFW system has improved, this strategy may no longer function or may be blocked more quickly due to SNI, which is your domain and it is not well-known, and because a large amout of traffic is routed through it, it recognized as a VPN or proxy. The solution is to utilize a well-known website SNI, which is not possible because we don’t have the website’s private key. Cloudflare’s Worker, which allows you to run JavaScript code on Cloudflare servers, is the solution. Go to your Cloudflare account, open the worker area, and enter the following code:

export default {
  async fetch(req) {
    try {
      const url = new URL(req.url);
      const splitted = url.pathname.replace(/^\/*/, '').split('/');
      const address = splitted[0];
      url.pathname = splitted.slice(1).join('/');
      url.hostname = address;
      url.protocol = 'https';
      return await fetch(new Request(url, req));
    } catch (e) {
      return new Response(e);
    }
  }
};

This code forwards all incoming traffic to the VPS. How does the code know what and where the primary server is? In our our configuration, the Path part of the config contains the primary server address, and this code separates and detects that portion! As a result, your configuration will look like this:

The address in the above picture is the Cloudflare IP retrieved through scanning. The project you created in Worker Cloudflare will be SNI and Host. blocking this domain is costly for the Country Operation Internet and rarely done.

There was another way that is no longer useful with this method. It uses nginx and you create a blog page so that if the GFW system makes a request to the domain, the blog will run and the domain will act like a normal website. If you are interested, see here. There are two other methods without having a VPS or server, and Cloudflare itself becomes a VPS. here and here (use Google translate) But the problem is that every time the output IP is changed and one of the IPs is Cloudflare and it doesn’t work for trading in Binance.

Resources:

ircf.space

Installation and description of singbox on vpnrouter.homes website

4 Comments

  • Is there a way for me to use Zoom.us SNI ?

    • Yes you can. i checked and Zoom.us uses x25519 key which is suitable for reality protocol

  • Not working:

    maintenance stopped background certificate maintenance {“cache”: “0xc0000e5300”}
    FATAL[0000] start service:

    • which section this error occurred?

Leave a Reply

Your email address will not be published. Required fields are marked *