shadowsocks / v2ray-plugin

A SIP003 plugin based on v2ray
MIT License
2.7k stars 577 forks source link

Authenticate using HTTP basic authentication #211

Open AlexSysadmin opened 4 years ago

AlexSysadmin commented 4 years ago

I was wondering if it is possible for V2ray users to authenticate using Nginx auth_basic method or other webservers before accessing the V2ray + ss-server backend .

or is it possible to have multiple password on the same port ? like port 443 .

beanslel commented 4 years ago

The path parameter can be used as a password with v2ray in TLS mode. E.g. you can assign each user a UUID and use that as a path, it should offer the same security as auth_basic over TLS since the path is also fully encrypted by TLS. You can point the root path (/) to a placeholder website or let it 404, so the user cannot access v2ray without knowing the path.

You can have multiple unique locationpaths in your nginx config pointing to the same backend v2ray instance, essentially accomplishing what you want. Paths can be updated in production with nginx reload command, so you can add or change 'passwords' without downtime.

AlexSysadmin commented 4 years ago

@beanslel wow that's a great idea, very intuitive , and fast to develop ,but when you have too many users , I suppose it could break the system or slow it down , unless you implement the auth_basic in something like Redis . but at the same time It would be nice to have an extension or an ability in the Android/Desktop versions, to first, ask you the credentials in a pop up or something like that , and then let you connect to the front HTTP service , like OpenResty /Nginx .

vanyaindigo commented 4 years ago

@beanslel you can specify different paths in Nginx, but how do you specify different paths in the v2ray-plugin properties?

AlexSysadmin commented 4 years ago

@vanyaindigo the paths in v2ray-plugin aren't important in this case ( when you use a Nginx frontend to handle request,manage alternate paths and pass the requests to the same path/backend. manage certs, and manage users+passwords ) , there should be a way to do the simple authentication for multiple users on the Nginx side , but also integrate it into v2ray before even connecting or establishing a WebSocket to the v2ray-plugin+ ss backend . I don't know if that's possible but it can be a nice solution to user managment .

beanslel commented 4 years ago

@beanslel you can specify different paths in Nginx, but how do you specify different paths in the v2ray-plugin properties?

Every user just puts their own path in the client plugin options. Your backend v2ray server only needs 1 path and that's where you point all your nginx locations to. Nginx is on the front end and then takes the user paths and passes it to the v2ray server backend.

@beanslel wow that's a great idea, very intuitive , and fast to develop ,but when you have too many users , I suppose it could break the system or slow it down

I'm not an expert on nginx, but it was designed to handle thousands of concurrent reverse proxy connections so I don't immediately see a problem. With nginx as front end, it has to reverse proxy every connection anyway. I don't think that having a unique location for each user adds that much overhead (if any).

By the way, don't forget that SS also has user management support. So you can just use the SS usermanager if you really want username + password authentication, and keep the v2ray config the same for everyone. I think that may have been the design rationale for v2ray-plugin not having the same authentication options as standalone v2ray.

vanyaindigo commented 4 years ago

Every user just puts their own path in the client plugin options. On the backend, your v2ray only listens on 1 path and all of your nginx locations point to that same path.

And what the differences with the same path-for-all settings? And btw that doesn't work.

beanslel commented 4 years ago

Every user just puts their own path in the client plugin options. On the backend, your v2ray only listens on 1 path and all of your nginx locations point to that same path.

And what the differences with the same path-for-all settings? And btw that doesn't work.

It works, I'm using a setup like this. Functionally it's exactly the same as a same-path-for-all and for v2ray it's fully transparent, all that v2ray sees is a connection on its own configured path, so of course it works.

The difference is that it gives you the ability to use the path as a method of authentication. You can give every user a unique path, and if you want to revoke access for that user you just remove it from your nginx config.

But like I mentioned in my previous comment, you already have the SS user manager which is probably a better way to go. But it can still be useful in situations where you want to segment your server in some way. You can also use different paths with different rate limit settings for bandwidth control etc. And all with the same v2ray backend.

vanyaindigo commented 4 years ago

I'm using a setup like this.

What do you have here: "plugin_opts": "server;tls;fast-open;path=/v2ray;host=domain.me;etc."? One path-for-all, no-path, main-path?

beanslel commented 4 years ago

I'm using a setup like this.

What do you have here: "plugin_opts": "server;tls;fast-open;path=/v2ray;host=domain.me;etc."? One path-for-all, no-path, main-path?

You can keep it as /v2ray, then in your nginx config you do something like this:

location /supersecretpath1 {
            proxy_redirect off;
            proxy_http_version 1.1;
            proxy_pass http://localhost:1234/v2ray/;  
            proxy_set_header Host $http_host;
            proxy_set_header Upgrade $http_upgrade;
            proxy_set_header Connection "upgrade";
        }

location /supersecretpath2 {
            proxy_redirect off;
            proxy_http_version 1.1;
            proxy_pass http://localhost:1234/v2ray/;    
            proxy_set_header Host $http_host;
            proxy_set_header Upgrade $http_upgrade;
            proxy_set_header Connection "upgrade";
        }

You can also just remove the path setting from the server completely, and your proxy_pass line then becomes proxy_pass http://localhost:1234/ (note the / at the end, this is deliberate). Both ways work the same.

Now, you let user1 connect with path=/supersecretpath1 and user2 with path=/supersecretpath2, you can add as many as you like and they all use the same v2ray server.

Btw with nginx as front end, you don't put tls in the v2ray-plugin server config.

vanyaindigo commented 4 years ago

You can also just remove the path setting from the server completely

Unfortunately I'm unable confirm this.

vanyaindigo commented 4 years ago

I figured out the TLS termination in Nginx, everything really works and it is possible to use path in the client to manage the connections.

aboka2k commented 4 years ago

hi, its an interesting idea, but how useful is this without ways to limit concurrent user or limiting bandwidth quota? thanks.

vanyaindigo commented 4 years ago

When used by trusted users, this is already something

aboka2k commented 4 years ago

When used by trusted users, this is already something

hi, it will be effective if for 'add/remove' users - instead of asking everyone to change a new password everytime. thanks for sharing the idea even though not suitable for our situation at this moment. just hope ss will hv max concurrent login feature in future.

cheers,