Petra Liljecrantz
Apr 14, 2016
  3892
(7 votes)

Common security issues with a CMS application

This is the fourth and final post about issues I encounterd working for Episerver Managed Services. We (and the entire support organization) often saw some security issues in applications and I wanted to share the four most common ones.

Exposed web services with debug tracing on

The attribute includeExceptionDetailInFaults is set default to true and a default value is often transferred to a production environment as well, it should be set to false so exceptions are not included in the packages when, for example, a cache invalidation broadcast occurs in Episerver CMS.

Set it like this:

<configuration>
    …
    <system.serviceModel>
        ... 
        <behaviors>
            <serviceBehaviors>
                ...
                <serviceDebug includeExceptionDetailInFaults="false" />

Username and passwords are sent in plain text

This is one of those things that most developers actually know is bad but somehow it gets down prioritized or just forgotten, so I can´t stress this enough.

Username and password are sent as plain text over the internet when logging in to edit mode, this makes it easier to listen to and get access to the servers. Use an SSL certificate to protect at least the login if not the entire site, the most common way is to terminate the SSL certificate in the server or load balancer with a wildcard certificate that can handle sub domains.

Unused role- and membership providers are exposed

An application should only use the SqlServerRoleProvider as the means of logging in (or ADFS) but usually both MultiplexingRoleProvider and WindowsRoleProvider are still loaded as role providers, the same goes for the membership providers. To minimize the attack surface it’s recommended to only expose active providers.

The WindowsMembershipProvider will expose the administrator account directly out on the internet available for brute force attacks. Therefore it´s recommended to simply remove the role- and membership providers not used from web.config.

Here is an example of web.config transformations you can use to force this behavior:

<!-- Set "SqlServerMembershipProvider" as default and remove the other providers -->
<membership defaultProvider="SqlServerMembershipProvider" xdt:Transform="SetAttributes(defaultProvider)" >
    <providers>
        <clear />
        <add name="MultiplexingMembershipProvider" xdt:Transform="Remove" xdt:Locator="Match(name)" type="EPiServer.Security.MultiplexingMembershipProvider, EPiServer.Framework" />
        <add name="WindowsMembershipProvider" xdt:Transform="Remove" xdt:Locator="Match(name)" type="EPiServer.Security.WindowsMembershipProvider, EPiServer" />
    </providers>
</membership>

<!-- Set "SqlServerRoleProvider" as default and remove the other providers -->
<roleManager defaultProvider="SqlServerRoleProvider" xdt:Transform="SetAttributes(defaultProvider)" >
    <providers>
        <clear />
        <add name="MultiplexingRoleProvider" xdt:Transform="Remove" xdt:Locator="Match(name)" type="EPiServer.Security.MultiplexingRoleProvider, EPiServer.Framework"  />
        <add name="WindowsRoleProvider" xdt:Transform="Remove" xdt:Locator="Match(name)" type="EPiServer.Security.WindowsRoleProvider, EPiServer" />
    </providers>
</roleManager>

Open edit mode on webfronts

All public servers expose EPiServer’s largest attack surface: the editorial and administrator interface, this is a security risk and in an environment that has one separate server for administrators to do their work and another (or several) servers acting as web fronts it´s a good recommendation to deny access to edit mode for all users (including editors and administrators as they should use the other server and that server should be protected by IP restriction or domain restriction).

This is done by replacing the location path configuration in web.config to deny all users access to the paths “episerver/”, “episerver/CMS/admin/” and “/util”. Since the methods HasEditAccess and HasAdminAccess in PrincipalInfo is based on this path you need to explicitly deny acces and not just remove the location path.

Example of deny access to all:

<configuration> 
  ...
  <location path="episerver">
    <system.web>
      <authorization>
        <deny users="*" />
      </authorization>
    </system.web>
  </location>

If there´s no separate admin server then you´ll want to restrict the edit and admin location path to only allow certain IP numbers. Episerver Managed Services provide IP restrictions in the firewall, but a better way (in my opintion) to do it is in the application, through a setting in web.config. Then the customer or you as the developer can control that yourselves.

This is all you need:

<system.webServer>
    <security>
        <ipSecurity allowUnlisted="false" denyAction="NotFound">
            <add allowed="true" ipAddress="123.456.0.0" subnetMast="255.255.0.0"/>
        </ipSecurity>
    </security>
</system.webServer>

The example configuration snippet shows an ipSecurity configuration that only allows access to addresses originating from the range specified by the combination of the ipAddress and subnetMask attributes. Setting allowUnlisted to false means that only those individual addresses, or address ranges, explicitly specified will be allowed to make HTTP requests to the website. Setting the allowed attribute to true in the child add element indicates that the address and subnet together define an address range that is allowed to access the website. If a request is made to a website from an address outside of the allowed IP address range, then a HTTP 404 Not Found error is returned as defined in the denyAction attribute.

Stay safe out there!

Apr 14, 2016

Comments

Saif
Saif Apr 15, 2016 10:17 AM

Awesome Petra! Thanks for pointing these out.

Petra Liljecrantz
Petra Liljecrantz Apr 15, 2016 11:32 AM

Thanks! I think it´s really important stuff to know about and implement our solutions :)

Please login to comment.
Latest blogs
Opti ID overview

Opti ID allows you to log in once and switch between Optimizely products using Okta, Entra ID, or a local account. You can also manage all your use...

K Khan | Jul 26, 2024

Getting Started with Optimizely SaaS using Next.js Starter App - Extend a component - Part 3

This is the final part of our Optimizely SaaS CMS proof-of-concept (POC) blog series. In this post, we'll dive into extending a component within th...

Raghavendra Murthy | Jul 23, 2024 | Syndicated blog

Optimizely Graph – Faceting with Geta Categories

Overview As Optimizely Graph (and Content Cloud SaaS) makes its global debut, it is known that there are going to be some bugs and quirks. One of t...

Eric Markson | Jul 22, 2024 | Syndicated blog

Integration Bynder (DAM) with Optimizely

Bynder is a comprehensive digital asset management (DAM) platform that enables businesses to efficiently manage, store, organize, and share their...

Sanjay Kumar | Jul 22, 2024

Frontend Hosting for SaaS CMS Solutions

Introduction Now that CMS SaaS Core has gone into general availability, it is a good time to start discussing where to host the head. SaaS Core is...

Minesh Shah (Netcel) | Jul 20, 2024

Optimizely London Dev Meetup 11th July 2024

On 11th July 2024 in London Niteco and Netcel along with Optimizely ran the London Developer meetup. There was an great agenda of talks that we put...

Scott Reed | Jul 19, 2024