ID:1906439
 
(See the best response by Ter13.)
I was planning on creating web applications using the web client. I wanted to integrate them into my website and have the account data passed via client.Topic.

I was under the impression I could generate it via the web url like so:
http://www.byond.com/play/embed/ 50.141.102.160:3333?account=asdf&account_password=hash

I haven't really taken a look at the reference in a while so I may be wrong. After that, the server would connect to the database and verify everything.

Is something like this possible, and better yet is it secure? I'd really like the data sent over SSL as well.

It's a very vague idea I really got to think on to ensure everything will be secure and such. Like, I'm not so sure I want the password hash being sent over the internet at all because I'm not sure if that's really the most secure way of doing it.

Perhaps a unique session id being stored in the database that's generated every time someone logs in. I don't know, I'm still developing my web platform and I've never done anything like that before so-

I'm really fond of the idea on creating a web platform for my future that I can use to distribute games and software. Not relying on the BYOND's web-end is the end goal here. Being able to integrate my website into BYOND is very important to me, and makes me feel like I wont be at risk if BYOND ever goes lights out.

Any feedback from the more experienced developers is greatly appreciated.
Best response
SSL is on the horizon:

http://www.byond.com/forum/?post=1860399

But honestly, you probably don't want to connect players using a Topic link containing a hash with their password.

Honestly, you probably want to have a database on your website (I'm assuming that you are trying to bridge your website's login credentials with the game's.)

Allow accounts a session_id field and then generate a longish string for the current session. An added level of security would be generating a new string the moment a person tries to connect to a world, and then invalidating the session immediately on connection success or failure and generating a new session token, since your old one has been exposed via communication. Don't generate the session token before linking the user to the game. Use a redirect to generate the session token as you transfer the user. The current game connection doesn't have to be aware of the new session token. Let the website handle the generation of the new session token and keep it private.

So:

1) Generate secure session token on web log-in. Make sure to tie it to IP address to keep tokens from being transferred.

2) Generate transfer token on redirect to game. Pass via topic.

3) Confirm transfer token on redirect. Ensure that IP remains the same. Invalidate transfer token immediately after checking. Do this on the webserver. Don't wait for the client to tell you to invalidate it.

3a) If IP is different from transfer token, present password challenge, send hash to webserver to check password, accept connection if hashes match.

3b) If IP is the same as transfer token and transfer token matches, permit the login without checking password hash. Transfer tokens are only valid for <5 minutes.

4) Proceed normally based off the DM server's information.
Thanks for the advice, Ter13.

Basically, the goal is to have the web client auto play when a certain page loads. This page will of course require the user to be logged in to even access. The web client should be able to load and automatically associate a username or such so it knows which accounts data to load from the database.

For example I could create a client dashboard in DM.

User logs in and then navigates to the dashboard page. After in which the web client loads and pulls up all of their data seamlessly, as if the page was written in PHP itself and not DM.

Using client.Topic was the first thing I thought of to accomplish this. The only problem being is players can spoof topic via url, right? So I'd need some way to ensure that the data is coming from my website and not an external site such as BYOND with a query string being simply edited in the url. Obviously leading to a huge security risk that any 10 year old could abuse.
Using client.Topic was the first thing I thought of to accomplish this. The only problem being is players can spoof topic via url, right? So I'd need some way to ensure that the data is coming from my website and not an external site such as BYOND with a query string being simply edited in the url. Obviously leading to a huge security risk that any 10 year old could abuse.

Yeah, that's exactly what I was talking about. Session IDs are used for exactly this. The trick is to invalidate the session transfer id when it's no longer valid, in other words, after it's been used. By the time the client is able to see the transfer id, and thus abuse it, it's already been used and invalidated.

In the off chance that they do manage to intercept it without invalidating it, keeping the user's last known IP address on the webserver's database associated with the transfer token is going to keep anyone not on the same network from getting into the game using that token.

It's not the safest thing in the world, but it's basically not possible to abuse provided you ensure that transfer tokens are exceedingly short-lived and actual website session ids use proper safety measures with cookies and whatnot, you'll be ok.
In response to Ter13
Ter13 wrote:
Using client.Topic was the first thing I thought of to accomplish this. The only problem being is players can spoof topic via url, right? So I'd need some way to ensure that the data is coming from my website and not an external site such as BYOND with a query string being simply edited in the url. Obviously leading to a huge security risk that any 10 year old could abuse.

Yeah, that's exactly what I was talking about. Session IDs are used for exactly this. The trick is to invalidate the session transfer id when it's no longer valid, in other words, after it's been used.

Perfect, I can create a table for that and set it up similar to password reset tokens. I'll review your advice as I write it, but I think I'm comfortable with the concept.

I think I'll have the login tokens generated on page load and restrict to their ip address. Not sure if BYOND can auto load the web client yet though. Regardless I'll have it invalidate after being used.

Surely allowing the token to expire only after use or after the web session expires is safe assuming its bound to their ip?

Sorry for the quality of my posts. 6 am and I havent found my bed.
Surely allowing the token to expire only after use or after the web session expires

Probably, but I really prefer the idea of a redirect generating the token and tokens expiring after <5 minutes. IPs can be spoofed, but it's unlikely anybody is going to be able to do it in just a few minutes with a reliable token without access to the user's machine in the first place. Leaving hanging tokens around that are still valid for extended periods of time is definitely inadvisable, though.
In response to Ter13
Ter13 wrote:
Surely allowing the token to expire only after use or after the web session expires

Probably, but I really prefer the idea of a redirect generating the token and tokens expiring after <5 minutes. IPs can be spoofed, but it's unlikely anybody is going to be able to do it in just a few minutes with a reliable token without access to the user's machine in the first place. Leaving hanging tokens around that are still valid for extended periods of time is definitely inadvisable, though.

Ah, that makes sense. What do you mean redirect generating? I was going to generate it with php server side.
I feel like Doohl, Lummox, Nadrew, and ATHK will be the most experienced hands at this. I'm sure there are better techniques than what I have offered and those four will know about them.
You can open a window pointing to another address in the web client and cookies will still work (something you can't do in DS, it resets cookies every connection)

So, simply just open a browse window with an iframe pointing to your site, and a token (md5 of ckey, ip, and rand(1,1000000))

Something like <iframe src="http://sitehere.net/checkaccount.php?token=blah"/>

On the site side, you can have it take that token, store it in a database with their info, then you just have a loop in game, check the database for that hash, and get their info.

This way, if they are already logged in in the browser, no need to log in.

I do the reverse on my website, All forum accounts have to be linked to a valid byond account, I use a webclient to validate the account in a way where the users don't have to give me their byond password (because most of my users wouldn't)

https://tgstation13.org/phpBB/viewtopic.php?f=29&t=2777 (feel free to make a forum account just to try it out)

Option 2:

http://javascript.info/tutorial/ cross-window-messaging-with-postmessage

If you embed the game, you can add javascript to your webclient skin to communicate between the webpage, and the game.