I'm in the final stages of implementing a CodeIgniter site which requires a really simple login system. One user, and one password to protect the admin area. I think I will be using one of the many CodeIgniter authentication libraries, which should allow me to ensure that people can't read from the database without being logged in as admin (hopefully).
Are there any glaring holes in a setup like this?
Should I take further measures beyond using a library like this to
ensure the security of the data in the MySQL database?
It will be hosted on a shared server; meaning little, or no server config will be possible.
There is a long discussion about the authentication systems available here: How should I choose an authentication library for CodeIgniter?
The latest version of Redux seems to be the favorite.
http://code.google.com/p/reduxauth/
I have used in the past (with excellent results) DX Auth 1.0.6.
You can find it at http://codeigniter.com/forums/viewthread/98465/
I would create simple form-based authentication and use a strong password.
HTTP authentication has too many problems IMHO:
Easier to brute force hack.
Anyone who sniffs the request can determine the username and password being used, but they don't even need to; they can just use an identical HTTP themselves.
Once that dialog pops up, it's difficult to dismiss, which can be irritating.
Many browsers will ask twice for a password before letting you in.
It's difficult to log out or change users, you usually have to quit the browser.
Easy to forget that you've let the browser save your credentials, which is another potential security risk.
If it is on an apache server, then I would consider just setting up an htpasswd protected directory. Read more about it here.
Related
I am trying to build a web CMS application using php and SQL. I haven't fully learned Laravel yet and I may need more time to complete my course. My question is, does Laravel come in with built-in extra security or is it the same as coding in our php. No one told me this, I have a feeling, I would have to do a lot of manual coding to secure my app using pure php.
Please fill me in with your expert suggestions.
Moen
Using a framework does not secure your code magically. You still have to protect it.
you can see your web app as a house with many doors. with pure PHP, you will have to build your doors before using them. On the other side, Laravel (or any framework) comes with built-in doors but if you don't use them, your app will not be secured.
Example of protections simplified with Laravel
CSRF protection https://laravel.com/docs/5.3/csrf
SQL injections using Eloquent https://laravel.com/docs/5.3/eloquent
Form validation https://laravel.com/docs/5.3/validation
All protections listed above can be done with pure PHP but you will have to write a lot of code.
I know this is several years too late but figured I would add in, locking down your laravel project once in production does not take too much effort. If you utilize #csrf and form validation as stated above that will cover your "doors" there. On top of using something like fail2ban on the server and pointing everything to the public folder within your laravel application will reduce Brute forcing and deter a lot of the common PHP web scans that come in daily from malicious IP addresses. On my servers I typically see certain IP addresses scanning for common php, phpmyadmin, and mysql.php files that do not turn up any 200 http responses. In addition, having the final product/compiled version of the site in it's own directory and implementing all your 3rd party creds within the .env (which is required to link your laravel project to a db) file, make it hard for malicious actors to find system files and credentials.
In addition, the authentication out of the box does all the hashing for you "secure Bcrypt and Argon2 hashing". In addition to hashing, it has been noted that the Hash::make function creates and uses a 22-length random string as a salt to generate the password, from question Where are laravel password salts stored?. Which references a Wordpress article on laravel hashing and salting Laravel Hash::make() explained. Hopefully that helps anyone reading this.
If you are deploying a laravel site to a VPS or whatever, then I would highly recommend daily or at least every two days coming the access logs and deny ##IP address##; anything that is trying to access URIs they are not suppose to access (since you built it you will know what they should and shouldn't be accessing), and implementing fail2ban to greatly reduce ssh brute force. If anyone needs more info or has more questions about maintaining a laravel website in the wild/linux server, I am always here. Coming from someone in the Cyber Sec industry , that freelances web development
I used to work for a bank, that had a very cool feature in it's intranet. Once you logged in your computer, there were global variables set in PHP through Apache, and they contained the identity of the user that was logged on on the computer. Now I'm at a new job, and I'm wondering, how this thing worked! I would like to implement this kind of thing once again.
What I'm working with here:
FreeBSD server, version is unknown to me.
Apache 2.2 web server
PHP 5, some custom compilation, that for various reasons, I can't upgrade or modify.
MS AD
All of the users logging on to their computers are using active directory, all are in the same domain.
What I used to have was something like this:
echo $_SERVER['username']
which would print the username of the user currently logged in.
Could someone explain, how this could be done?
P.S. If any of my server settings are not what is required, say so, because then I will have a reason to ask the bosses to give me one of my own, with more control.
There's lots of ways this might be implemented. However a lot of them depend on having control over the client as well as the server.
Obvious sources of data include:
NTLM
Client side certificates
The Ident protocol (not very secure without the encryption extensions)
A long lasting cookie (again, not secure)
HTTP authentication methods
However none of these explain how the value appeared in the session - this must have been implemented within the PHP code.
So without knowing how it was implemented at your previous site we can't tell you:
Whether it was secure and correctly implemented
how to replicate the behaviour
Given your resource list, while it would be possible to implement authentication based on direct LDAP calls, passing the username and password through your application, I would strongly recommend using (e.g.) openId - but restricting the providers to just your openid provider - which would use the MSAD as the backend.
I did not understand correctly the question, so I edit my post...
you could use apache auth, you can make auth by ip's or hostnames
http://httpd.apache.org/docs/2.0/en/howto/auth.html
I have a website developed in PHP. There are 2 classes (in 2 seperate php files) that contain the siteadmin's gmail user id and password (in plain text) and database password (again in plain text). Though none of these classes are displayed on the browser ( like index.php). These files contain only php classes and no html code and the references to those plain text passwords is only through objects of those classes.
Off late, I have started to wonder if this is secure enough? I have tried my best (acting as a malicious person) to try and read the contents of the two said php files but was not able to do so. I am not very conversant with developing secure code, so not sure what should be my approach to make sure that these passwords never get exposed.
Could any one please suggest best practices to develop php code that can contain such sensitive information securely.
Put configurable items in a separate configuration file, above your public web directory
Make sure you have set correct file permissions to your files
Check your web application for local (and remote) file inclusion
Have your server up-to-date
Having your passwords at a safe spot is not the complete solution, you'll need to have your complete PHP application secure, and nobody unauthorized should be able to get root/administrator access to the server.
Firstly, I'd look at using OAuth for accessing GMail if at all possible - it means you don't have to store credentials at all, and provides some level of protection in case your server does get compromised.
I would also look at the answers to this question.
Finally, if your site is on the public internet, it's worth reading up on at least the basics of internet security, and especially securing web applications. There are all sorts of ways things can go wrong. I like the "hacking exposed" books.
Don't store passwords in files, because someone will eventually check that file into source control. Or someone will set a permission incorrectly.
Run the application with its own O/S user account
Put the passwords in an O/S environment variable for the application user (not a system environment variable)
I am creating a website with multiple sections--admin, client, user, and anonymous--each user group having less access then the next. I am wondering what form of authentication would be best for my use?
I have heard the if you are just dealing with a websites then a web form is for you (because it's prettier). HTTP header authentication with PHP is said to get clunky/sloppy. htAcess is pretty much the hard core of various authentication methods I have looked up, but is it too much?
You're confusing things.
Your three options are basically two:
Use HTTP authentication
Do not use HTTP authentication
Whether it's handled by an .htaccess file or not is another matter. You can do HTTP authentication with Apache and PHP, and you can do non-HTTP authentication with Apache and PHP (though usually you do non-HTTP auth with PHP and HTTP auth with Apache).
Apache can defer the authentication to several backend and frontend modules (e.g. you can use CAS). Apache provides out-of-the-box (no dated sourceforge module...) for the following database backends: FreeTDS, MySQL, Oracle, PostgreSQL, SQLite 2/3 and an ODBC connector.
Personally, I dislike HTTP authentication. Usually a form will is more user friendly and you can provide links such as "Forgot your password?" and "Username not found".
I'd also go with implementing the authentication in PHP, because it's more portable (you can swap the web server).
Go for the form (a session really).
Nowadays it's the only option.
First off, for your application you should go for the simpler login form / session method. Because you want in-application user groups, it's only senseful to also use in-application authentication. Technically for the permission system it makes no difference which auth method is used. But you know, for simplicity and keeping all authorization stuff together...
The hatred against HTTP authentication is misgued, btw. It's the stronger authentication method, if you use HTTP Digest; which OTH is difficult to implement in PHP.
It's a usability nightmare only if you do it wrong. Practically a HTTP logon can be initiated with a login form as well. Using XMLHttpRequest can successfully trigger HTTP Authentication. And with a little more work (401 and new realm), pretty logouts are possible too. If no Javascript is enabled it falls back on the boring login dialog / readline obviously. But I've personally used a text-only browser for a while, and I tended to like that more.
Also, if your admin group is serious business (raw database access tools etc.), you should apply both methods. Make the admin interface separate from the application, apply login form and .htaccess restrictions. Better safe than sorry.
What is the best way to secure an intranet website developed using PHP from outside attacks?
That's a stunningly thought-provoking question, and I'm surprised that you haven't received better answers.
Summary
Everything you would do for an external-facing application, and then some.
Thought Process
If I'm understanding you correctly, then you are asking a question which very few developers are asking themselves. Most companies have poor defence in depth, and once an attacker is in, he's in. Clearly you want to take it up a level.
So, what kind of attack are we thinking about?
If I'm the attacker and I'm attacking your intranet application, then I must have got access to your network somehow. This may not be as difficult as it sounds - I might try spearphishing (targetting email to individuals in your organisation, containing either malware attachements or links to sites which install malware) to get a trojan installed on an internal machine.
Once I've done this (and got control of an internal PC), I'll try all the same attacks I would try against any internet application.
However, that's not the end of the story. I've got more options: if I've got one of your user's PCs, then I might well be able to use a keylogger to gather usernames and passwords, as well as watching all your email for names and phone numbers.
Armed with these, I may be able to log into your application directly. I may even learn an admin username/password. Even if I don't, a list of names and phone numbers along with a feel for company lingo gives me a decent shot at socially engineering my way into wider access within your company.
Recommendations
First and foremost, before all technical solutions: TRAIN YOUR USERS IN SECURITY
The common answers to securing a web app:
Use multi-factor authentication
e.g. username/password and some kind of pseudo-random number gadget.
Sanitise all your input.
to protect against cross-site scripting and SQL injection.
Use SSL (otherwise known as HTTPS).
this is a pain to set up (EDIT: actually that's improving), but it makes for much better security.
Adhere to the principals of "Segregation of Duties" and "Least Priviledge"
In other words, by ensuring that all users have only the permissions they need to do their jobs (and nobody else's jobs) you make sure they have the absolute minimum ability to do damage.
If it is on an internal network, why is it even possible to get to the app from the outside? Firewall rules should be in place at the very least.
The best way? Disable direct external access!
If employees need to use it (like an extranet-style site), you should make them VPN in. Through VPN you have a lot more authentication options and most of them are a great deal more secure than leaving your intranet server accessible from the internet.
Another option, and this only works if the data is public-safe, is scheduling your intranet server to push the data to another server that is externally accessible. I say push because you really don't want this server to have access to your network. Let your network server do the work.
The best way to secure it? Don't connect it to a network. Make your users physically enter a guarded room with a single console, running Mosaic.
Oh, you want it to be easy to use?
Always verify every single input that can come from an untrusted source.
Don't trust any data sources.
When storing passwords, ALWAYS store an encrypted hash of the password.
When storing passwords, NEVER store passwords directly.
Never collect or store any data that you don't actually need.
Never allow yourself to be tempted into adding additional bells & whistles.
Read everything that Bruce Schneier has written on security and encryption.
If you forget these simple rules, you could find your application starring on the front pages of newspapers everywhere, just like Yahoo mail.
I would echo #Oli and favour the VPN method if possible. However, if for any reason you need more arbitrary access than this, you should use SSL to secure any authentication. And in addition to password authentication / IP address authentication it would be well worth looking at using SSL with client side certificates.
You could only allow access from internal IPs from the php app itself. Also dont ignore the usual security and best practices. Input validation and output encoding(whitelisting only), user accounts with hashed passwords etc.