In my community, every user should only have one account.
So I need a solution to verify that the specific account is the only one the user owns. For the time being, I use email verification. But I don't really need the users' email adresses. I just try to prevent multiple accounts per person.
But this doesn't work, of course. People create temporary email addresses or they own several addresses, anyway. So they register using different email addresses and so they get more than one account - which is not allowed.
So I need a better solution than the (easy to circumvent) email verification. By the way, I do not want to use OpenID, Facebook Connect etc.
The requirements:
verification method must be accessible for all users
there should be no costs for the user (at least 1$)
the verification has to be safe (safer than the email approach)
the user should not be demanded to expose too much private details
...
Do you have ideas for good approaches? Thank you very much in advance!
Additional information:
My community is a browser game, namely a soccer manager game. The thing which makes multiple accounts attractive is that users can trade their players. So if you have two accounts, you can buy weak players for excessive prices which no "real" buyer would pay. So your "first account" gets huge amounts of money while the "second account" becomes poor. But you don't have to care: Just create another account to make the first one richer.
You should ask for something more unique than an email. But there is no way to be absolutly sure a player don't own two account.
The IP solution is not a solution, as people playing from a compagny/school/3G will have the same IP. Also, Changing IP is easy (reset the router, proxy, use your 3G vs wifi)
Some web site (job-offer, ...) ask you for an official ID number (ID, passport, social security, driver licence, visa (without the security number, so peolple will feel safe that you won't charge them), ...)
This solution got a few draw back:
minor don't always have an ID / visa
pepole don't like to give away this kind of info. (in fact, depending where you live: in spain for example, it is very common to ask for ID number)
people own more than one visa.
it is possible to generate valide ID/visa number.
Alternative way:
ask for a fee of 1$
to be allow to trade more than X players / spend more than X money.
people that pay the fee got some advantage : less ads, extra players, ...
paying a fee, will limitate creation of multiple account.
fee can be payed using taxed phone number (some compagny provide international system)
the payment medium could be use as an ID (visa number)
put some restriction in new account (like SO).
eg: "you have to play at least 1 hour before trading a player"
eg: "you have to play at least 3 hour before trading more than 3 players"
Use logic to detect multiple account
use cookie to detect multiple account
check last connection time of both player before a transaction. (if player A logout 1 minute before player B login : somethings is going on)
My recommandation :
Use a mix of all thoses methode, but keep the user experience fluide without "form to fill now to continue"
Very interesting question! The basic problem here is multi-part -
Opening an account is trivial (because creating new email IDs is trivial).
But the effect of opening an account in the game is NOT trivial. Opening a new account basically gives you a certain sum of money with which to buy players.
Transferring money to another account is trivial (by trading players).
Combining 1 & 2, you have the problem that new players have an unfair advantage (which they would not have in the real world). This is probably okay, as it drives new users to your site.
However adding 3 to the mix, you have the problem that new players are easily able to transfer their advantage to the old players. This allows old users to game the system, ruining fun for others.
The solution can be removing either 1,2,3.
Remove 1 - This is the part you are focusing on. As others have suggested, this is impossible to do with 100% accuracy. But there are ways that will be good enough, depending on how stringent your criterion for "good enough" is. I think the best compromise is to ask the user for their mobile phone numbers. It's effective and allows you to contact your users in one more way. Another way would be to make your service "invite only" - assuring that there is a well defined "trail" of invites that can uniquely identify users.
Remove 2 - No one has suggested this which is a bit surprising. Don't give new users a bunch of money just for signing up! Make them work for it, similar to raising seed capital in the real world. Does your soccer simulation have social aspects? How about only giving the users money once their "friend" count goes above a certain number (increasing the number of potential investors who will give them money)?
Remove 3 - Someone else has already posted the best solution for this. Adopt an SO like strategy where a new user has to play for 3 hours before they are allowed to transfer players. Or maybe add a "training" stage to your game which forces a new player to prove their worth by making enough money in a simulated environment before they are allowed to play with the real users.
Or any combination of the above! Combined with heuristics like matching IP addresses and looking for suspicious transactions, it is possible to make cheating on the game completely unviable.
Of course a final thing you need to keep in mind is that it is just a game. If someone goes to a lot of trouble just to gain a little bit of advantage in your simulation, they probably deserve to keep it. As long as everyone is having fun!
I know this is probably nothing you have expected, but...
My suggestion would be to discourage people from creating another account by offering some bonus values if they use the same account for a longer period, a kind of loyalty program. For some reason using a new account gives some advantages. Let's eliminate them. There are a lot of smart people here, so if you share more details on the advantages someone could come up with some idea. I am fully convinced this is on-topic on SO though.
We have implemented this by hiding the registration form. Our customers only see the login form where we use their mobile number as username and send the password by text message.
The backend systems match the mobile number to our master customer database which enforces that the mobile number is unique.
Here is an idea:
Store UUID in a cookie at clients. Each user login store the UUID from Cookie in relation to the account entity in the databse.
Do the same with the IP adresses instead of UUID.
After that write a program interface for your game masters that:
Show up different account names but same IP (within last x hours)
Show up different account names but same UUID (nevertheless how long ago)
Highlight datasets from the two point above where actions (like player transfers) happened which can be abused by using multiple accounts
I do not think you should solve that problem by preventing people having two or more accounts. This is not possible and ineffective. Make it easier to find that evil activities and (automatically temporarly) ban these people.
It's impossible to accomplish this with a program.
The closest you can do is to check the ip address. But it can change, and proxies exist.
Then you could get the computer MAC address, but a network card can be changed. And a computer too.
Then, there is one way to do this, but you need to see the people face to face. Hand them a piece of paper with a unique code. They can only subscribe if they have the code.
The most effective solution might be the use of keystroke biometrics. A person can be identified by the way the person writes a sentence.
This company provides a product which can be used to implement your requirements: http://www.psylock.com/en
I think 1 account per email address should be good enough for your needs. After all, account verification doesn't have to end right after signup.
You can publish the IP address of the computer each message was posted from to help your users detect when someone is using multiple accounts from the same computer, and you can use a ranking system to discourage people from using temporary accounts.
Do your game dynamics allow for you to require that both users be online for a trade to occur? If so, you can verify the IP addresses of both users involved in a trade, which would be the same unless the user was paying for multiple internet connections and accessing two accounts from separate machines.
Address the exact scenario that you're saying is a problem.
Keep track of the expected/fair trade value of players and prevent blatantly lope-sided trades, esp. for new accounts. Assume the vast majority of users in your system are non-cheaters.
You can also do things like trickle in funds/points for non-trading actions/automatically overtime, etc.
Have them enter their phone number and send a text message to it. Then, keep a unique of all the cell phone numbers. Most people have one cell phone, and aren't going to ask their friend to borrow it just to create a second account.
http://en.wikipedia.org/wiki/List_of_SMS_gateways
I would suggest an approach using two initiatives:
1) Don't allow brand new accounts to perform trades. Accounts must go through a waiting period and prove that the account is legitimate by performing some non-trade actions.
2) Publicize the fact that cheaters will be disqualified and punished. Periodically perform searches for accounts being used to dump bad players and investigate. Ban/disqualify cheaters and publicize the bans so that people know the rules are being enforced.
No method would be foolproof but the threat of punishment should minimize cheating.
actually you can use fingerprintjs to track every user, use js encrypt the fingerprint in browser and decrypt in server
Related
I'm thinking through how to develop a validation on my Rails app that essentially checks to make sure that the credit card used for any given transaction by any user is unique in our system, such that all credit card may be used to purchase an item only once across the entire application for all users, for all time.
The thinking behind this restriction is that this app will sometimes run time-sensitive promotional deals, and we want to do our best to institute a "one purchase per credit card" system for these deals.
I was thinking of hashing the credit card number and just storing that hash in the db, then cross-referencing it at the time of each new purchase (so my payment gateway keeps the actual number, and I just keep a hash in the DB), but on further research, this seems like a bad idea.
So I'm back to the drawing board and looking for new ideas. Anyone know a good approach to this problem, while keeping as PCI-compliant as I can be?
I'm developing with Rails 3 and using ActiveMerchant to integrate with my payment gateway, Authorize.net, if that helps at all.
Certainly some hashing is a bad idea - either because it's low security, has some intercepts, or so commonly used there's rainbow tables. That doesn't mean all hashing is a bad idea - the only way to cross reference is going to be some way of uniquely and predictably identifying the information. Unless PCI specifically prohibits it - hashing is still the way to go.
Salt
Make sure you salt your hash - this prevents rainbow attacks, or at least requires the rainbow-attacker build a table with your salt in mind. In particular if you can keep the salt reasonably secure {I say only reasonably because in order to generate you need to have the salt which means it'll be in code somewhere}.
Choose a Good Algorithm
While MD5 is now infamous, and implemented in all kinds of languages, it's also so common that you can find pre-made rainbow tables. It's also extremely quick to generate a hash. Your system can probably tolerate a small amount of delay, and use a much more processor-intensive hash. This makes the cost of generating a rainbow table much more expensive. Check out the Tiger algorithm for example.
Hash more than once
If you have multiple related data points, multiple hashes are going to make it way harder to do a rainbow attack. For example: Hash(Hash(Card#+salt1)+expireDate+salt2) - requires knowledge of both the card # and the date to generate (easy for you) but can't easily be reverse-engineered (rainbow requires for every card # * every useful expire date + knowledge of both salts).
Edit: (your comments)
Reasonably secure: Only transmit it over an encrypted connection (SFTP, SSH), don't store it unencrypted - including live/iterative and backup copies, keep the file with the salt outside of the web tree (cannot be directly accessed/accidentally released), make sure permissions on the file are as restrictive as possible (don't allow group/global file access).
Dynamic salt throwing a random value into the hash is great for reducing rainbow attacks - you store that random piece in the table with the hashed value - now when building a rainbow you have to build one for every dynamic salt. However for your needs you can't do this - you need to know the right random salt to use the second time you create the hash (otherwise you'll never get an intercept on the second card use)... for that to be predictable/repeatable you'd then have to base the dynamic salt on some part of the number... which is effectively what multiple hashing with another data point does. The more data points you have the more you can hash in this direction - if you have the CVV for example (3 hashes), or perhaps you hash 8 digits at a time (for a total of 3 hashes: hash(hash(hash(1..8+salt1)+9..16+salt2)+expDate+salt3)).
Best Hash it's a moving target, but there's a good discussion on security.stackexchange. Which points to SHA-512.
faking your true credit card number online is the best way to prevent this from happening. Citibank clients can login and make use of this tool provided with all accounts. Just generate a number and exp date for use online, and all is fine , for now.
I think you are looking in the wrong direction. I would just check last 4 of card, ip and shipping addresses. The risks of storing that data versus the damage if a small number of users gamed the last 4 & ip solution is not worth it. (He says not knowing the nature of the purchases.)
Since address isn't collected...First 4, Last 4 and 4 Digit Expiration (all hashed of course) should provide the uniqueness you need to ensure that card was only used once.
If you want a "one purchase per user" system then why don't you just check the user's purchase history whenever they try to buy a special-purchase item to ensure that they haven't bought it previously?
user could register for multiple accounts.
although by checking users history, as well as enforcing 1 item per address for each purchase- you will likely be fine- you could also limit things by users name/ birthday/ whatever other identifying information.
Credit Card information can also change by the way- its actually very easy to purchase 100 gift credit cards with unique numbers so if you want to police things down to the most minute level... I dont think you will be able to just by cc numbers
I'm looking for ideas on how to implement some type of fast login scenario for an application that will allow employees to quickly login.
I work with an organization that has employees rotate every 30 minutes to a different location. If there are 3 employees, then the first employee won't come back to the checkout station for an hour. The checkout station is a higher traffic area where different things are borrowed by customers. Right now they have a generic login, but the organization wants to track which employee checked out/in a borrowed item. The problem is when they rotate there are customers there many times and having them logoff and login either via a workstation login or an application login is too slow for customer service.
Any suggestions?
I think a fingerprint reader would work well for logging in users. Then, they wouldn't have to type anything to log in.
There are plenty of biometric SDKs online that should be able to help you with this. And, I think some commercial readers will do something similar already, so you wouldn't even need to write any code.
Here's an article on Microsoft's Upgraded Fingerprint Reader
Also, you can have them scan once to log in, and once they are logged in, they can scan again to get logged completely out of the system (instead of just locking the screen or forgetting to log out and walk away.)
Use an application-level login, but make it only based on typing in their employee ID. This will simply identify who they are, exchanging security for speed while not giving up identity. Using employee ID's for this is a good way of guaranteeing uniqueness. I've seen systems like this work in retail, and it's really fast. Employees get used to typing this number into the console.
I'm not sure if it's in your budget but this sounds like a good use for those little button 1-wire devices. Basically it's an electronic "key" that is about the size of a button and can be read very quickly.
So Employee A goes to the station, puts his button on the pad(takes like 2 seconds) and he's logged in. When he needs to leave he pushes one button to log out, then employee B can come and log in, etc etc.
a picture of the button:
Is there a best practice for using email/user accounts for 3rd part APIs in a business scenario?
For example say my company domain is foo.com, and I need to access data from Flicker, youtube, twitter, facebook, jigsaw, Amazon, ebay, and many others.
Should I have seperate email addresses/user names like flickerapi#foo.com,youtubeaip#foo.com, facebookapi#foo.com or something like apiuser#foo.com and have a consitent username used across services if they require a seperate user name? What do you do? Are there any disadvantages or advantages to one or the other? The obvious disadvantage to me of multiple would be remembering all the email addresses.
There are many facets to the answer for this question, and I dont think there is obviously any single superior way.
To be safe you should plan on having multiple, just in case the one you are trying to reserve is already taken (its rare, but it happens). That way you can plan on using a single one but you are prepared if something in your design has to change.
The rest is about visibility, and how risk-averse you want to be. Having one account per service means that if one is compromised (password is discovered, etc) its the only one affected (assuming you use different credentials for each). The downside is that its very obvious these all point to the same place (not necessarily bad) and abuse of one could lead to problems in other places.
Having multiple accounts mitigates some of this, but you have other headaches, such as multiple passwords, managing multiple expiration processes, and auditing to make sure the accounts all still work, etc.
I'm considering asking for credit card details BEFORE an address for a physical product with average purchase price between $10-$50
What might be the technical (or non technical) issues surrounding doing this?
What comes to mind is :
This seems a little non-standard from the users perspective
We cant do address verification if we find we're having issues with fraud (not an issue so far)
Users may be more likely to complete the sale since they've committed to their most important piece of information first
By asking for zipcode we can populate city/state when we do ask for the address
Are there any dealbreakers i'm missing or things I'm not considering?
I'm trying to make the system as flexible as possible, but would prefer to getit right first time without barking up the wrong tree.
My advice to you is don't do it.
I often cancelled buy attempts and abandoned the sites when I got asked for my credit card number right in the face.
Often, the site is so poorly designed with no answers to obvious questions that you have to go through the complete form hoping to find answer in the process. Do they offer this particular shipment option? How much does this cost? Do they send to a package station or only to my home address? Do they provide an extra line for an address for me to use the "c/o" technique? I often could not find answers to these question anywhere on the site. So I either found them in the form before entering my payment details, in very few cases I did call them, in most others I just chose other places to buy from.
One more use case. In many places I've seen they only show you if they have an item on stock on the very last page of the order form. Not many people would want to "commit" to the payment right away without getting all the required information. You enter your credit card number, then on the second page you see they don't offer the shipment option you need, on the last page it says "the item is currently out of stock - delivery awaited in 3-4 weeks". And the order is already placed. Then it is a commitment from the user but not from the company, many will react emotionally to this approach as to scam and request their money back immediately.
The important thing is to behave friendly to your customers, don't scare them away, don't raise suspicions in them, don't make them regret they committed to their buying. Make them feel relaxed and happy and never with their arms bound.
This may seem non-standard from a consumer perspective, but this is perfectly normal in B2B systems. You can collect personal/company & payment details, then shipping & payment addresses, and then present the user with a final confirmation screen showing tax & delivery charges before processing the order. Only then do you process the credit card payment.
However, the issue that "New in town" mentions is a very valid one, where the customer is left thinking:
Hang on, why are you asking for my credit card details when I haven't seen the final amount yet?
I think this is perhaps down to a site not having a clearly defined order creation process (or at least one that is not clearly communicated to the customer), so that the customer is under the impression that by entering their CC details at that point, the payment will be processed there and then.
It may be best to do things the way other popular online stores do, Principle of Least Astonishment and all that, but if you really want to do it in this order then perhaps a simple progress bar to indicate order creation flow would help allay customer fears. Don't bet on it though, online consumers are rightly paranoid when it comes to their credit card details these days. ;)
As someone who has done quite a bit of online purchases, I can say that I would be extremely worried if a site first asks for my creditcard information before it asks for anything else. It tends to trigger my "Fraud Detector". Am not sure why this is, but I just get worried that the site is going to forget about asking for my address.
As mentioned, in B2B environments, this is a bit more common, though. Then again, in many B2B environments, the visitor first creates a business account before he even starts ordering. Part of setting up this business account is providing the creditcard information. To be honest, many B2B also provide services and digital downloads which don't even need a shipping address.
Many people use the ship to address page to determine if the site will ship to their region/country. They are not likely to bother giving CC info before they even know you'll ship to them.
I live in outside the US and MOST sites fail to recognize that there are customers outside of the US. Often the only way to determine if they will ship to me is to go through the order process to find out they have a finite list of "states" they will ship to and no "country" drop down.
Out of interest and because it infuriates me, I was wondering if SOmebody here might happen to work for a bank or otherwise know the answer to this.
I've used a few online banking sites (UK and N.America) and they universally enforce a password pattern of /[\w\d]{6,8}/ Sometimes, maybe you get to use underscore, but never ever do you get to have /.{6,20}/ that you get (more or less) with just about every !banking site you'll encounter.
I have been told that this is to do with storage space, but the maths don't seem to support that. Assuming that banks keep shadow tables for your password record, let's generously say an average of 10 per account, then doubling the allowed length of the password and doubling the bit width of the character set based on an 8char 8bit existing format means an extra 11*2*8 = 176 bytes per account, so ~168Mb per 1M accounts. Let's say it's a gigantic bank supporting 100M accounts - that's still only 16Gb!
It can't be that simple can it? Surely my numbers are off base.
Or is the answer here that banks being banks they have no better reason for this than they're plodding dinosaurs.
Does anyone know a technical reason why my password for www.random.com/forum is stronger than the one for my bank?
If the stories I've heard about certain banks are true...
It's because whenever you enter your password:
The web server sends it over a half-kilometre-long serial cable to an old 386 in an abandoned office, running the UI (Compiled using a custom-hacked version of Borland C 1.0) that was used by bank managers in 1989, which doesn't have a serial interface so it has to go through another device that simulates keypresses on an AT keyboard.
This program inserts your request including your password (encrypted using a custom algorithm that's too weak to be used anymore but which cannot be disabled in the software) into a FoxPro database on a NetWare file server in a different abandoned office at the opposite end of the building (just because it would fall to bits if they tried to move it.)
Back in the 1st abandoned office another old 386, constantly polling the FoxPro database for new records, detects this request and forwards it over an even slower serial cable (this time in EBCDIC) to another box in a 3rd office that is emulating a PDP11 running the actual COBOL program that maintains the accounts.
Unfortunately they also still need the real PDP11, because it had custom microcode for another secure encryption algorithm (which they can't extract or the anti-tamper device will erase it.) The PDP11 can't handle the increased workload of all accounts opened since 1981 (the year of their first unsuccessful attempt to retire it) so now (via another layer of screen scrapers and emulated hard disks) it is tricked into performing a subset of functions (including password verification) on behalf of the main server.
So your password can only use the common subset of the character sets supported by all these systems, and can only be as long as the shortest database field involved.
I actually work in a bank right now, and have worked in quite a few in the past.
The primary reason that this happens is that in general the people who are ultimately responsible for making these decisions are not the people who end up implementing them.
The "Business Unit" of a bank are the non-technical business experts who end up making these decisions.
In many cases, technical objections will be overruled for political or business reasons. But this isn't exclusive to banking. It happens in any industry where technical considerations are often not the primary concern.
Banks use online services primarily as an interface to legacy systems. Your password is probably being processed by an IBM mainframe somewhere, written in Cobol, and the password structure may have been designed in the 70's.
In addition, because banks are such political structures, the management primarily sees "concrete" results so issues such as security are not addressed until it becomes a hot issue and then there is an "initiative" to address it.
At one bank I worked for, the production password was the same as the userid (same idea as logging in with "root" "root"). The user passwords could be reset online to a combination of first N letters of your last name + last 4 digits of your SSN, so any user could reset your password if they knew your name and SSN and loginas you .
Probably most of banking systems were developed long time ago, when 8 character passwords were considered secured. I don't think anyone would consider brute forcing passwords from banking accounts anyway, 8 characters it still a lot. I bet all banks block an account after 3 attempts or so.
Here is a "bug" I got logged in Bugzilla regarding a site I'd built for a client recently (not a bank, thankfully!):
"It seems that the user is forced to use a ! or _ in their password* which seems a bit odd to me. Can this ben updated so that it is a 6 - 8 digit password that can only use alphanumerics?"
Actually, it was at least one non alpha-numeric character