Hello,
I am looking in google and also here in the forum for some help regarding hotspot feature (with external radius server) and api usage over an external captive portal.
I make a redirect with local html-files (login.html, status.html etc..) to an external portal.
There the client should register or login if he has already an account.
After having logged in the client could start his online session if he has online credit (the portal get this information also via radius) by clicking a button - now the radius session should start on the routerboard via API.
The modified login.html sends server-address and al related data - i am looking only for a unique session variable - maybe also in routeros - and than the problem is only to find an example how the captive portal had to sent back via api (maybe with pear2) the start of the radius session.
And in next step than how to get status information in a specific period
and
how to check if local routerboard hotspot feature realised an idle timeout - the portal has to get also this information - may the portal does a request every minute.
It would be very helpful to get some basic information and hints regarding this questions.
kind regards,
Paul
IMHO, the best approach would be to (ab)use cookie domain policies.
- In hotspot, set authentication with a cookie in addition to whatever else you have (PAP, CHAP… whatever).
- Make the router login page available at a certain DNS name. (e.g. “isp.net”)
- Keep serving the router pages (login, etc.) from the router.
- Make the whole portal, including the registration page, available from a subdomain of that name. (e.g. “portal.isp.net”)
- At your subdomain, check if the cookie is sent, and if sent, use the API to check if the same cookie is present at “/ip hotspot cookie”. If these two match, the user is authorized. Otherwise, they aren’t.
This should work, because a cookie set at a higher domain is available to subdomains as well.
Alternatively, you could set up an “on login” script that would send a certain HTTP request that would cause the creation of a session with the same cookie, and an “on logout” script that would destroy that same cookie. This is a little trickier, as you need to ensure users can’t possibly make those same HTTP requests (or at least that only the router’s request will have the intended effect). Otherwise, hackers could just bypass the login page, and into the control panel to control whatever username they please.
Thanks for the reply.
I thought of sending username and password from the portal to the local routerboard to start there the radius session.
But I didn’t find something in the API.
If possible I would avoid to use cookies and for sure I never would sent http-requests!
But at the moment I also have a problem with chap - my radius server is only accepting pap - maybe something not compatible or correct configured.
So if you have another idea I would aprecheate.
Thanks,
Paul
The approach above would ensure that you are not sending the username and password back and forth between the router and the server. The only device that knows whether a user is logged in or not is the router. The server would simply ask the router “Is the following cookie part of your cookie storage?” and nothing more.
The username and password will obviously have to flow between the client and another device (in the approach above - the router) at some point, via HTTP or HTTPS. The only way to ensure encryption (and by extension, security) at that one point is to use HTTPS, with all of its bells and whistles. There is simply not way to work around that.
If you can do that, you don’t even need to use CHAP. PAP over HTTPS is enough.
If you can’t do that, you’ll have to live with HTTP and/or cookies.
As for CHAP not working… that may be because CHAP requires that hashing is done at the client, using JavaScript. A compatible hashing function is available in the default login template called “md5.js”, but if you’ve deleted that, or redirect to another page, you’re probably not hashing the password at that other form.
Hi,
the chap problem with md5.. - I copied that javascript to my server where the login.php is.
the loal login.html redirects to the portal using https.
I have a well working certificate - also working for mobile devices.
The target is to substitute the api which is already in my portal code to another special session control gateway with the mikrotik api.
Ok, I am not very familiar with that api and what is about it - so in which way the data is secured on that way of the api…
That is another question.. - but only to know what might possible and in which way:
Additional info:
the local routerboard is connected over a vpn to the portal-server and it will be a https request.
The portal than replies over api to the local router also over the vpn - so there might be no security problem!
But at the moment I have plain passwords in database - that is not fine!
at the moment i am thinking about starting radius session on local routerboard over api.
but maybe there are other “dirty” ways to create a “bypass” user with his mac for the time of his session.
But when vpn is dropping the user can be still online.
So there had to be another control.
Also against mac cloning …
For sure there are many different ways to go, but also we have to reduce cpu work for the lokal router as many as possible.
kind regards,
Paul
Great. Disable CHAP then. This will allow you to store passwords as hashes instead of plain text.
CHAP is only useful when the network is not encrypted (i.e. when using HTTP, not HTTPS). Otherwise, it’s redundant, and in fact, as you’ve noted, it poses a danger in that it requires the storing of passwords in plain text.
Since you have HTTPS, then you could do the above approach (well OK… maybe minus the “Keep serving the router pages (login, etc.) from the router.” part), along with an “on login” script that will create the session back at the web server. Since the web server is connected to the router over VPN, it should be able to easily distinguish between the router and its client, and thus only honor its session creation/destruction requests.
And (as much as it pains me to say this), there’s no need to use the API in that scenario.
Hi boen,
thanks for the hint with chap - i will test it.
Regarding API: the problem is that the portal had to have 100% control over the routeraction - so i would apreachate to make it over an api which in can be triggered over the portal cronjobs f.ex.
To check continuosly if mabe the idle timeout took place or something like this.
Th portal has a status widget where time is counting down an where it is possible to stop inly session - not login in portal.
Session ist starting and stoping over a special button in that widget.
You don’t have a hint in which manner it could be possible to do this over the API?
kind regard,
Paul
ps: also not really working is dhcp Agent-Circuit-ID information.
i don’t get the information in my radius-server where the client is coming from.
only the nas-id information i can see in the radius-packets.
is there a special trick to activate this in thr rb?
The API can be used to “ask” the router anything (as in “retrieve data”), as well as command it to do anything for which there is a command.
There are no commands for logging in and logging out a hotspot user, but as you’ve already found out, those can be “emulated” by making the portal forms’ “action” point to the router pages, and making the router page redirect back to the portal page.
The problem from then on is in identifying the user after they’ve successfully logged in.
A session cookie is the most efficient method, and one that is actually used by PHP’s session extension. The problems with cookies are that it is send as part of the client’s HTTP request (and because of that, it’s not encrypted), and that a hacker could fake the contents of the cookie. You are in a good position to overcome both problems:
- You have HTTPS at the portal, so content being part of the HTTP request is not troubling at all.
- You can “lock” the cookie to the IP address from which the user logged in with. That way, a hacker faking the contents to match another user is not going to allow them hijack it. Most applications prompt the user before they do that, but for your purposes, it makes sense to not even ask, but do it unconditionally instead.
You have two ways of doing the IP lock:
- Check at every request using the API. This is not very efficient for both the router and web server, since they need to do this unnecessary exchange on every request. This appears to be what you want to do… you can, but I’m telling you it’s not a good idea.
- Upon login, notify the web server about the successful login, along with the IP address, which the server will later match the cookie against. This is what I’m proposing. It’s a lot more efficient, since the exchange between router and web server happens only once. Since the IP address will be part of the session data, the check at that point will be significantly faster.
Now… about not using a cookie at all. First stop, given the above - why? Anyway…
Using the API, you can check the “/ip/hotspot/user/active” menu to find users that are logged in from the IP that is accessing the portal. This can be somewhat error prone if more than one user can login from the same IP - the users in that menu are not ordered, so if that happens, it could happen that something users intended to do for username A they instead did over username B. You can overcome this only if the username is the MAC address.
But again, this is very inefficient, since you’re doing it for every HTTPS request.