Tagged with web

Changing your ssh server’s port from the default: Is it worth it?

Changing my ssh port from the default port (22) has been one of my standard processes for quite some time when I build new servers or virtual machines. However, I see arguments crop up regularly about it (like this reddit thread or this other one).

Before I go any further, let’s settle the “security through obscurity” argument. (This could probably turn into its own post but I’ll be brief for now.) Security should always be applied in layers. This provides multiple levels of protection from initial attacks, like information gathering attempts or casual threats against known vulnerabilities. In addition, these layers of security should be applied within the environment so that breaking into one server after getting a pivot point in the environment should be just as difficult (if not more difficult) than the original attack that created the pivot point. If “security through obscurity” tactics make up one layer of a multi-layered solution, I’d encourage you to obscure your environment as long as it doesn’t affect your availability.

The key takeaway is:

Security through obscurity is effective if it’s one layer in a multi-layer security solution

Let’s get back to the original purpose of the post.

The biggest benefit to changing the port is to avoid being seen by casual scans. The vast majority of people hunting for any open ssh servers will look for port 22. Some will try the usual variants, like 222 and 2222, but those are few and far between. I ran an experiment with a virtual machine exposed to the internet which had sshd listening on port 22. The server stayed online for one week and then I changed the ssh port to 222. The number of attacks dropped by 98%. Even though this is solely empirical evidence, it’s clear that moving off the standard ssh port reduces your server’s profile.

If it’s more difficult to scan for your ssh server, your chances of being attacked with an ssh server exploit are reduced. A determined attacker can still find the port if they know your server’s IP address via another means (perhaps via a website you host) and they can launch attacks once they find it. Paranoid server administrators might want to check into port knocking to reduce that probability even further.

Remembering the non-standard ssh port can be annoying, but if you have a standard set of workstations that you use for access your servers, just utilize your ~/.ssh/config file to specify certain ports for certain servers. For example:

Host *.mycompany.com
  Port 4321
 
Host nonstandard.mypersonalstuff.com
  Port 2345
 
Host *.mypersonalstuff.com
  Port 5432

If you run into SELinux problems with a non-standard ssh port, there are plenty of guides on this topic.. The setroubleshoot-server package helps out with this as well.

# semanage port -a -t ssh_port_t -p tcp 4321
# semanage port -l | grep ssh
ssh_port_t                     tcp      4321,22

Here is my list of ssh lockdown practices when I build a new server:

  • Update the ssh server package and ensure that automatic updates are configured
  • Enable SELinux and allow a non-standard ssh port
  • Add my ssh public key to the server
  • Disable password logins for ssh
  • Adjust my AllowUsers setting in sshd_config to only allow my user
  • Disable root logins
  • For servers with sensitive data, I install fail2ban
Tagged , , , , , , , , , , ,

Survive the Google Reader exodus with Tiny Tiny RSS

Tiny Tiny RSSIt’s no secret that Google Reader is a popular way to keep up with your RSS feeds, but it’s getting shelved later this year. Most folks suggested Feedly as a replacement but I found the UI quite clunky in a browser and on Android devices.

Then someone suggested Tiny Tiny RSS. I couldn’t learn more about it on the day Google Reader’s shutdown was announced because the site was slammed. In a nutshell, Tiny Tiny RSS is a well-written web UI for managing feeds and a handy API for using it with mobile applications. The backend code is written in PHP and it supports MySQL and Postgres.

There’s also an Android application that gives you a seven day trial once you install it. The pro key costs $1.99.

The installation took me a few minutes and then I was off to the races. I’d recommend implementing SSL for accessing your installation (unless you like passing credentials in the clear) and enable keepalive connections in Apache. The UI in the application drags down a ton of javascript as it works and enabling keepalives will keep your page load times low.

If you want to get your Google Reader feeds moved over in bulk, just export them from Google Reader:

  1. Click the settings cog at the top right of Google Reader and choose Reader Settings
  2. Choose Import/Export from the menu
  3. Press Export, head over to Google Takeout and download your zip file

Unzip the file and find the .xml file. Open up a browser, access Tiny Tiny RSS and do this:

  1. Click Actions > Preferences
  2. Click the Feeds tab
  3. Click the OPML button at the bottom
  4. Import the xml file that was in the zip file from Google

From there, just choose a method for updating feeds and you should be all set!

Tagged , , , , , , ,

Performance and redundancy boost for icanhazip.com

It’s been a few years since I started a little project to operate a service to return your IPv4 and IPv6 address. Although there are a bunch of other sites that offer this service as well, I’ve been amazed by the gradually increasing traffic to icanhazip.com.

Here’s a sample of the latest statistics:

  • Hits per day: 1.8 million (about 21 hits/second)
  • Unique IP addresses per day: 25,555
  • Hits per day from IPv6 addresses: 1,069 (a little sad)
  • Bandwidth used per day: ~ 400MB

The site is now running on multiple Cloud Servers at Rackspace behind a load balancer cluster. In addition, the DNS records are hosted with Rackspace’s Cloud DNS service.

This should allow the site to reply more quickly and reliably. If you have suggestions for other improvements, let me know!

Tagged ,

mysql-json-bridge: a simple JSON API for MySQL

My quest to get better at Python led me to create a new project on GitHub. It’s called mysql-json-bridge and it’s ready for you to use.

Why do we need a JSON API for MySQL?
The real need sprang from a situation I was facing daily at Rackspace. We have a lot of production and pre-production environments which are in flux but we need a way to query data from various MySQL servers for multiple purposes. Some folks need data in ruby or python scripts while others need to drag in data with .NET and Java. Wrestling with the various adapters and all of the user privileges on disparate database servers behind different firewalls on different networks was less than enjoyable.

That’s where this bridge comes in.

The bridge essentially gives anyone the ability to talk to multiple database servers across different environments by talking to a single endpoint with easily configurable security and encryption. As long as the remote user can make an HTTP POST and parse some JSON, they can query data from multiple MySQL endpoints.

How does it work?
It all starts with a simple HTTP POST. I’ve become a big fan of the Python requests module. If you’re using it, this is all you need to submit a query:

import requests
payload = {'sql': 'SELECT * FROM some_tables WHERE some_column=some_value'}
url = "http://localhost:5000/my_environment/my_database"
r = requests.post(url, data=payload)
print r.text

The bridge takes your query and feeds it into the corresponding MySQL server. When the results come back, they’re converted to JSON and returned via the same HTTP connection.

What technology does it use?
Flask does the heavy lifting for the HTTP requests and Facebook’s Tornado database class wraps the MySQLdb module in something a little more user friendly. Other than those modules, PyYAML and requests are the only other modules not provided by the standard Python libraries.

Is it fast?
Yes. I haven’t done any detailed benchmarks on it yet, but the overhead is quite low even with a lot of concurrency. The biggest slowdowns come from network latency between you and the bridge or between the bridge and the database server. Keep in mind that gigantic result sets will take a longer time to transfer across the network and get transformed into JSON.

I found a bug. I have an idea for an improvement. You’re terrible at Python.
All feedback (and every pull request) is welcome. I’m still getting the hang of Python (hey, I’ve only been writing in it seriously for a few weeks!) and I’m always eager to learn a new or better way to accomplish something. Feel free to create an issue in GitHub or submit a pull request with a patch.

Tagged , , , , , ,

Five years of rackerhacker.com

Today marks the fifth year that this blog has existed on the internet. I bought the domain on February 14th, 2007 and tossed together a quick WordPress installation (I can’t even remember the version now!) to hold my notes that I was gathering at work.

Birthday Cake

Photo credit: Will Clayton

At the time, I had recently parted ways with a very small internet startup and joined the ranks at Rackspace as an entry-level Linux system administrator. The abrupt change from “top dog at the startup” to “wow, I don’t know anything about Linux” caught me by surprise and I was trying to stuff as much knowledge into my brain as quickly as I could. My teammates at Rackspace were eager to show me the ropes of wrangling servers and supporting customers.

As I mentioned already, the blog started out just as a place to stuff my notes from the things I learned at work. I figured that it would be nice to store it in a searchable format but it would also be great if I could link other people to certain posts if they needed more information to fix a problem. It was a way to retain knowledge but yet give it back to the people around me who needed it.

The blog has hit 456 posts (this one is #457) and it’s gone from a few page views per day to just over 20,000 per day. Here are the top five most accessed posts (since I’ve been keeping stats):

  1. Syncing an iPhone with a new Mac without hassles
  2. ip_conntrack: table full, dropping packet
  3. Delete a single iptables rule
  4. Increase MySQL connection limit
  5. MySQL Error 1040: too many connections

I’d like to send out a big thanks to the people who read this blog, add comments (or complaints!), and suggest new topics. You are the reason why I take the time to keep this blog going.

Tagged , , , , ,