Chapter 7. Security

While Plone is quite fortunate to be built on top of the very safe and secure Zope 2 application server, there is always more we can do to make sure our site is running as safely and securely as possible.

Because security is such a big topic, there are many areas where we can perform audits and make improvements such as operating system (OS), filesystem (FS), through the web (TTW), and so on.

Lastly, there are some miscellaneous tasks that fall under the security umbrella; we can take this opportunity to learn them.

So let's get to it.

In this chapter, you will learn:

  • Restricting TCP/IP access to localhost or LAN host

  • Managing IP addresses and ports effectively

  • Configuring the Zope 2 effective user dynamically

  • Installing Cassandra to audit through the web (TTW) security

  • Applying security and bug fixes to Plone

Note

More about security

For a closer look at a variety of Plone-related security information, visit http://plone.org/products/plone/security/overview.

For Erik Rose and Steve McMahon's excellent Plone Conference 2008 talk, visit http://plone.org/events/conferences/2008-washington-dc/agenda/securing-zope-and-plone-against-the-big-bad-internet/.

Restricting TCP/IP access to localhost or LAN host

One of the simplest things we can do to secure our system is to operate our Zope 2 instances only on the IP addresses that they are required to listen on.

In most cases, it is 127.0.0.1 (or localhost, as it is commonly referred to) but it can also be a LAN host that is a private, non-routable IP address used only on your local area network (LAN).

In this chapter, we will not cover LAN hosts. However, we suggest you consider using them when you need to access instances from another host on the LAN; otherwise, just use localhost.

In the case of LAN hosts, once configured, they will protect ports from being accessed by the outside world (that is Internet). However, it will allow them to be accessible from the LAN where you may want to configure monitoring, for example via Munin (covered in Chapter 6), Zenoss (http://community.zenoss.org), and so on.

What we will cover is how to use the localhost IP address.

In 07-security-localhost.cfg, we have:

[buildout]
extends = 06-deployment-optimization-munin.cfg
[instance1]
http-address = 127.0.0.1:8081
[instance2]
http-address = 127.0.0.1:8082

You will notice we have re-configured the http-address parameter to include the entire HTTP address and not just the port number.

You will also notice we have used the private, non-routable localhost address 127.0.0.1.

Now run Buildout:

$ bin/buildout c 07-security-localhost.cfg

Afterward, in parts/instance1/etc/zope.conf, you should see:

…
<http-server>
# valid keys are "address" and "force-connection-close"
address 127.0.0.1:8081
# force-connection-close on
# You can also use the WSGI interface between ZServer and ZPublisher:
# use-wsgi on
</http-server>

This means that our instances will listen for connections only on 127.0.0.1; any attempt to connect from another host will fail.

Note

More about localhost

For more information about how the localhost really works, visit http://en.wikipedia.org/wiki/Localhost. For our purpose though, we can think of running the Plone site on localhost as "having a party that only your laptop or development workstation can join".

Managing IP addresses and ports effectively

As your production configuration grows, it may become more difficult to manage a large number of IP addresses and ports.

As such, it is often helpful to have them defined in their own section.

In 07-security-ports.cfg, we have:

[buildout]
extends = 07-security-localhost.cfg
[hosts]
localhost = 127.0.0.1
[ports]
instance1 = 8081
instance2 = 8082

Notice that we are not using these definitions for anything yet. But we can use them like this:

${hosts:localhost}:${ports:instance1}
${hosts:localhost}:${ports:instance2}

Effectively from now on, we have to change IP addresses and port numbers only in one place (assuming we change all static references such as 127.0.0.1:8080 to the new syntax).

Configuring the Zope 2 effective user dynamically

Another simple thing we can do to secure our system is to operate our Zope 2 instances with only those operating system users who have enough permission to execute the instances. In fact, Zope 2 will not run as root on UNIX-like systems.

However, we frequently forget to do this. More importantly, sometimes we want to be more explicit with our configuration. This is where the effective-user parameter comes in handy. If no effective user is set, then Zope 2 will run as whoever executes the process.

You could set the effective-user manually or you could use the gocept.recipe.env recipe (http://pypi.python.org/pypi/gocept.recipe.env) to set it. In the case of manual configuration, you may find it tedious to test your production configuration on systems that do not have the desired effective user (or you may not; this is mostly subjective). In the case of no configuration, you may find it annoying to be reminded that you cannot run Zope 2 as root when you get to production (or you may not; this is also subjective).

In any event, we can formalize the configuration and automate the username selection process as follows.

In 07-security-effective-user.cfg, we have:

[buildout]
extends = 07-security-ports.cfg
parts += env
[env]
recipe = gocept.recipe.env
[instance1]
effective-user = ${env:USER}
[instance2]
effective-user = ${env:USER}

Now run Buildout.

$ bin/buildout c 07-security-effective-user.cfg

Afterward, in parts/instance1/etc/zope.conf you should see:

…
effective-user aclark
…

This technique has several subtle, but important advantages over manual, or no configuration:

  • The effective user is always set, so even if you try to start Zope 2 as root, it will run as the effective user

  • The effective user is set to the user that runs the buildout, which means you can change the effective user easily

  • The ${env:USER} variable can be used to configure user settings for additional services such as Pound, Varnish, and so on.

Installing Cassandra to audit through the web (TTW) security

If you ask anyone familiar with Plone about the permissions settings in the Security section of the Zope Management Interface, you are likely to get the following response:

"DO NOT TOUCH!"

That is because with so many possible permutations of settings, it is almost impossible to manage them all effectively by pointing and clicking.

The next thing out of their mouth is likely to be:

"USE WORKFLOW INSTEAD!"

That is because Plone's workflow feature provides a much better way to effectively manage large amounts of permission changes.

However, people do not always use workflow. They point and click away anyway, despite the warnings. You, however, have been warned. It is much better to manage permissions with workflow as compared to pointing and clicking on Permissions in the ZMI.

Permissions and roles in the ZMI

If you do not believe me, consider this.

If you browse to http://localhost:8080/Plone and click on Site Setup | Zope Management Interface | Security, you will see almost two hundred permissions that look like the following (first ten):

Permissions and roles in the ZMI

Next to each group of 10 permissions are checkboxes that correspond to the possible role assignments:

Permissions and roles in the ZMI

Hopefully, enough has been said. The point again is two-fold:

  • The ZMI opens the gateway to enormous complexity (categorically, not just with roles and permissions)

  • In the case of roles and permissions, managing this complexity is best left to workflow (in which case, role-to-permission mappings are configured by the state)

Roles and groups

Similarly, the same Plone folks will often remind you to assign roles to groups and not users, and put users in groups to enable them to perform various tasks.

They might say:

"DO NOT ASSIGN ROLES TO INDIVIDUAL USERS!"

This may be followed by:

"ASSIGN THEM TO GROUPS INSTEAD!"

Why? This is because to manage intricacies such as which user can perform which tasks and where, you are better off using the right tool for the job, that is adding users to groups with proper role assignments.

Unfortunately, end users are still able to assign roles to individual users if they really want to via the Sharing tab or Local roles form in the ZMI. So, it is the site manager's responsibility to make sure they do not, to avoid having a site littered with individual role assignments.

Cassandra

For the task of auditing role assignments, we have Andreas Jung's Cassandra (http://pypi.python.org/pypi/zopyx.plone.cassandra).

You can perform a local roles security audit by installing Cassandra and following the steps given below.

In 07-security-cassandra.cfg, we have:

[buildout]
extends = 07-security-effective-user.cfg
[instance]
eggs +=
zopyx.plone.cassandra
zcml =
zopyx.plone.cassandra

Now run Buildout:

$ bin/buildout c 07-security-cassandra.cfg

You should see:

$ bin/buildout -c 07-security-cassandra.cfg
Getting distribution for 'zopyx.plone.cassandra'.
…
Got zopyx.plone.cassandra 0.2.0.
…

Browse to http://localhost:8080/Plone, click on Site Setup | Add-on Products to install Cassandra, and then browse to http://localhost:8080/Plone/@@cassandra.

On a new site, you should get no results (because no roles have been shared):

Cassandra

On an actively used site, you will see results similar to the following, where we use data from http://plone.org as an example.

For demonstration purposes, we present the output of http://plone.org/documentation/manual/plone-3-user-manual/@@cassandra.

In other words, we installed Cassandra on (a local copy of) plone.org, browsed to http://localhost:8080/plone.org, clicked on Documentation | Manuals | Plone 3 User Manual, and then added @@cassandra to the end of the URL (in the URL toolbar of your browser).

In the permission report (that took several minutes to generate), we see the following:

Cassandra

Since the output is recursive, we see local role assignments for the Current folder and everything below it.

Here are the results for the adding content subfolder (that is, /documentation/manual/plone-3-user-manual/adding-content):

Cassandra

The results for the rest of the subfolders are exactly the same (except for the folder name, of course).

So what does this tell you? Several things:

  • The Plone documentation team is awesome! Many people have dedicated their time and energy to writing (and rewriting) Plone's documentation for the benefit of the Plone community at large. If you know any of these folks (by their plone.org username), take a minute to thank them!

  • Though the Plone documentation team members are our documentation heroes, they have (apparently) not done a good job of assigning roles to groups. Instead, they have assigned them directly to the users.

  • The Cassandra output is (apparently) incomplete, as there are no roles listed after each colon. This may be due to the fact that Plone Help Center (http://pypi.python.org/pypi/Products.PloneHelpCenter) adds additional permissions, not available in default Plone.

  • All of the folders in the user manual have the same sharing settings, that is the same users and groups are listed for each folder. This suggests that local role settings are configured in a parent of the user manual folder, for example/documentation/manual or /documentation.

Applying security and bug fixes to Plone

Although it is extremely rare, vulnerabilities are found in Plone occasionally and fixes are released.

Less rare, but almost as important, are the occasional bug fix releases for various packages within the Plone software stack.

Here, we are referring to packages that contain bug fixes that were not released with a particular point release of Plone. They may also be a part of the next point release (for example, 3.3.6).

Often, you need those fixes now. Under such circumstances, it is the responsibility of all Plone site administrators to deploy these fixes to their production sites as soon as possible.

In some cases (for example with Python egg packages), the fix can be as simple as changing a package version and running Buildout to get the latest compatible release (which presumably addresses the security, or the bug issue).

In other cases, alternative methods are required.

Such was the case with the last known Zope 2 security issue, which occurred in early 2010 (http://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2010-1104).

Since many of the affected Plone sites had old style (non-egg package) Zope 2 software installations, that is, Zope 2 was installed from the gzipped and tarred source archive instead of using a "versionable" egg (starting from Zope 2.12, Zope 2 is packaged as an egg), it was necessary to update the URL of the Zope 2 source distribution in the buildout.

Using a newer Zope 2 with an older release of Plone

To demonstrate this, we are going to run an older (unsupported) version of Plone (2.1) with a newer version of Zope 2 (much newer than the version of Zope 2 Plone 2.1 was originally released with).

In general, it is safe to use the newest point release in a series. At the time of writing this, the newest point release for each (actively-maintained) series of Zope 2 releases is as follows:

Hold on to your buildouts

Throughout this book, we have built incrementally on examples from the previous chapter and from previous examples in the same chapter. As such, we were extending a single buildout all the time.

Because it does not extend any of the previous configuration files, when you run this example, it will undo everything that has been done before.

As such, you may wish to copy the 07-security-plone21.cfg file to another directory and run it from there instead. You have been warned!

Generally speaking, it is always a good idea to keep in mind that Buildout maintains its state. So whenever you execute Buildout, you are asking it to modify its state. Hopefully, you are giving it sensible instructions, but humans are often flawed; we make silly mistakes. The good news is that if you make a mistake, it is almost always easily undone simply by executing Buildout again with the correct configuration file.

A "modern" Plone 2.1 buildout

In 07-security-plone21.cfg, we have:

[buildout]
find-links = http://dist.plone.org/thirdparty/PILwoTk-1.1.6.4.tar.gz
versions = versions
parts =
instance
plone
[zope2]
recipe = plone.recipe.zope2install
url = http://www.zope.org/Products/Zope/2.8.12/Zope-2.8.12-final.tgz
[plone]
recipe = hexagonit.recipe.download
url = http://dist.plone.org/archive/Plone-2.1.4.tar.gz
strip-top-level-dir = true
[instance]
recipe = plone.recipe.zope2instance
zope2-location = ${zope2:location}
user = admin:admin
eggs =
PILwoTk
products =
${buildout:directory}/parts/plone
[versions]
plone.recipe.zope2instance = 3.6

You will notice that we specify the version of Zope 2 to install by setting the value of the url parameter to the URL of the Zope 2 gzipped and tarred archive on zope.org.

We use Zope 2.8.12 because it is the newest version of Zope 2 that will work with the very old release of Plone, Plone 2.1.4.

We demonstrate this for one very important reason to empower you to upgrade your Zope 2 installations in the event that a security issue is discovered. If and when this happens, a subsequent new version of Zope 2 will be released to address the issue, and you will need to know how to install it.

In case of many other packages (that is, those which are packaged as eggs) as we mentioned earlier, getting a newer package is often just a matter of specifying which version you want to install in your buildout.

Incidentally, we have not discussed in detail how to specify package versions yet (beyond specifying version numbers for Plone and its dependencies via the versions.cfg file), but we will get to that in the next (and final) chapter.

Summary

That is all for this important chapter. Here you have learned:

  • How to restrict TCP/IP access to localhost only

  • How to manage IP addresses and ports effectively with Buildout sections

  • How to configure the Zope 2 effective user dynamically with gocept.recipe.env

  • How to audit Plone security settings with Cassandra

  • How to upgrade Zope 2 in the event of a security or bug fix release

Up next we will enter the final chapter, wherein we will demonstrate an upgrade to Plone 4, summarize everything we have learned so far, and wrap up with a few important points we have not had the opportunity to discuss yet.

See you there!

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
3.14.142.194