Security Guidelines
The goal of this page is to offer guidance on how to use APOC securely. An insecure usage of APOC can result in many common software vulnerabilities, including Security Misconfiguration, Sensitive Data Exposure, Server Side Request Forgery, and Language Injection.
Our guidelines suggest taking a principle-based approach to security matters, and are split into three sections. In the first section, we will first explore our overarching principles. In the second section, we will discuss how to create a secure environment for APOC before executing queries. Finally, in the third section we will cover how to use APOC safely within queries.
Security Principles
The security principles covered in this section provide guiding rules for safely using APOC. Should any security challenges not covered on this page be encountered, users are encouraged to follow the principles outlined below.
Principle of Least Privilege
Also known as the principle of minimal privilege, the Principle of Least Privilege dictates that a workload should only be given the minimal set of permissions it requires in order to operate. APOC offers a wide range of functionality which is unlikely to be used in its entirety by any given APOC installation. Users are recommended to only enable those procedures and functions that are strictly needed. Users are recommended to disable any other procedures and functions.
By only enabling the bare minimum required, users will reduce the risk incurred by running vulnerable procedures, while also supporting their functional requirements.
Principle of Defense in Depth
Also known as the principle of redundancy, the Principle of Defence in Depth dictates that users secure their installations at every level of the software stack, even though it may seem redundant to do so.
APOC is built on top of interfaces that are exposed and controlled both by the database and by the operating system. By securing an APOC installation using the defense in depth approach, the installations are wrapped in multiple layers of protection, thus mitigating the risk of failure of the protection mechanisms at any layer. If installations are protected by APOC, by the database, and also by the operating system, then it is less likely that the protected workloads can be exploited by a single bug.
Installation
This section covers the steps to take to create a secure environment for APOC. It is concerned with securing APOC before writing queries.
Securing Neo4j
As the functionality provided by APOC is built on top of the database, installations cannot be secure unless the database is secure. The first point of order is therefore to ensure the database installation is secure, which can be achieved by following the existing database Security Checklist. This guide will revisit some steps that are covered by the checklist again in more detail.
Securing Neo4j Extensions
APOC is a Neo4j extension with a lot more functionality than any given workload is likely to need. As is the case for any Neo4j extension, there are several control mechanisms that help ensure only required functions and procedures are installed onto the database.
Securing Neo4j Extensions via Configuration Settings
The database exposes
Configuration Settings
which can be configured in the conf/neo4j.conf
configuration file.
The configuration file controls which procedures and functions can be loaded into the database and then unrestricted.
The configuration settings that control this behavior are shown below.
Setting | Description | Default |
---|---|---|
A list of functions and procedure names to be loaded. |
|
|
A list of functions and procedure names that are allowed full access to the database. |
|
It is recommended to adhere to the existing Installation Guidelines, which dictate how to load and unrestrict the minimal set of procedures that a workload requires.
Securing Neo4j Extensions via RBAC
The database exposes a Role-Based Access Control mechanism to fine-tune which user roles are allowed to carry out a given operation. This is a Neo4j Enterprise Edition feature which is not available to Community Edition users.
Role-Based Access Control also offers the ability to restrict which external sites the import and loading procedures can read data from. Load privileges apply to all APOC procedures where a URL can be provided.
There are Execute Procedure privileges concerning the ability users have to execute any given procedure. By default, all users have the privilege to execute any procedure with the users' own level of privilege. This means that users without read privileges are not able to read data via a procedure, and users without write privileges are not able to write data via a procedure. Similar privileges exist for Execute Functions.
There are also Execute Boosted Procedure privileges concerning the ability of users to execute any given procedure with full privileges. This means that users who would not otherwise be allowed to read or write to the database are allowed to do so if granted the boosted procedure privilege. The Execute Boosted Procedure privilege also overrides any load privileges on the procedure, allowing any URL to be accessed. These privileges are equivalent to the Execute Admin Procedure privileges. Similar privileges exist for Execute Boosted Functions.
The execute boosted privilege is a powerful feature that has the potential to be misused. There are several powerful APOC procedures that have the ability to run whole queries derived from user input against the database. If users are granted the boosted privilege to execute any of these procedures with full privileges, this is equivalent to giving users the ability to run any Cypher query. Examples of such procedures include: |
It is recommended to adhere to the default behavior where users are only allowed to execute procedures and functions with their own level of privilege, and to avoid boosted procedure execution in APOC. When a role requires the privilege to perform certain operations, there are usually other privileges that can be granted in order to achieve the desired restriction, without relying on boosted execution.
Securing the File System
APOC contains several procedures which can read or write to specific files on the file system. If misconfigured, these procedures can lead to high-impact vulnerabilities, such as Sensitive Data Exposure. If required by the workload, users need to enable procedures to be able to interact with the file system, but only in specific directories. If not required by the workload, users should restrict procedures from being able to interact with the file system altogether.
Examples of procedures that can read from the file system include apoc.import.*
and apoc.load.*
.
Examples of procedures that can write to the file system include apoc.export.*
.
Examples of Cypher clauses that allow the database to read from the file system include
LOAD CSV
.
Securing the File System at the Operating System Level
From the point of view of the operating system, there is only a single process being executed. APOC does not exist as a separate operating system process from the database process. This means that all operating system restrictions applied to the database will also be applied to APOC. Therefore, the guidance prescribed by the File Permission Guidelines for the database is also applicable to APOC.
It is recommended to configure the database process to have only the minimal set of file system permissions required to carry out the workload. This means restricting the database process so that it is only able to interact with the file system if needed, and even then only with specifically targeted directories rather than the whole file system.
Securing the File System at the Database Level
APOC exposes Configuration Settings that control whether interactions with the file system are
allowed, and from which directory. These settings can be configured in the conf/apoc.conf
file, and are described
below.
Setting | Description | Default |
---|---|---|
Enables writing files to the file system. |
|
|
Enables reading files from the file system. |
|
|
APOC will adhere to Neo4j configuration settings when reading or writing to the file system. |
|
The database also exposes
Configuration Settings that
control whether reading files from the file system is allowed, and from which directory.
The settings can be configured in the conf/neo4j.conf
file, and are described below.
Setting | Description | Default |
---|---|---|
Enables reading files from the file system. |
|
|
Restricts reading files to the given directory. |
|
When APOC verifies a file system interaction, it goes through a series of checks. It first checks whether it is allowed to read or write. If so, it then checks the directory in which it can perform the action.
In determining whether it is allowed to read or write, APOC first verifies that its own configuration settings have been
enabled, and then checks whether the database configuration setting has also been enabled.
APOC only checks whether the database configuration setting has also been enabled when the
apoc.import.file_use_neo4j_config
configuration setting has
been enabled.
In determining the directory to which it is allowed to read or write, APOC checks whether the
apoc.import.file_use_neo4j_config
configuration setting
has been enabled.
If so, it will use the same directory restrictions as the database.
If this configuration setting is not enabled, then APOC is allowed to read or write to anywhere on the file system.
Recommendations vary depending on whether a workload needs to read or write files. Some workloads do not require any file system interactions, others only require the database to be able to read files, and others require both the database and APOC to be able to read files.
If a workload does not require any read or write permissions for the file system, then users should not change any of the configuration settings in either of the configuration files. By default, neither Neo4j nor APOC queries are allowed to read or write files.
If a workload only requires the database to be able to read files and does not require APOC to be able to do the same,
then users should only grant this ability to the database by setting
dbms.security.allow_csv_import_from_file_urls=true
.
Users do not need to make any modifications to the APOC configuration settings since by default they do not allow APOC
to read or write files to the file system.
If a workload requires both the database and APOC to be able to read and write to the file system, then users should
still try to be as restrictive as possible.
While this will entail enabling read and write permissions in both configuration files, it is recommended to tune the
APOC configuration setting apoc.import.file_use_neo4j_config=true
along with the Neo4j configuration setting
server.directories.import=import
.
Usage
The previous section offered guidelines on securing an APOC installation before executing queries. This section will offer advice about writing queries that contain high-risk APOC procedures and functions.
Cypher Injection
The Neo4j Knowledge Base offers excellent introductory guidelines on Protecting Against Cypher Injection which are recommended learnings in order to better appreciate the challenges related to Cypher injection.
Many APOC procedures make direct use of Cypher, and under the hood, they will build and execute new queries derived from the inputs they receive. These procedures represent an additional challenge for APOC users, who need to be able to recognise them, and understand the limited safety guarantees they are able to provide.
In the first example below, an initial query invokes the
apoc.refactor.rename.label
procedure, which in turn
builds a second query behind the scenes and executes it.
The second query fetches all nodes, removes a label, and then reattaches a different label.
CALL apoc.refactor.rename.label("Person", "Actor", [])
// executes MATCH (n:`Person`) REMOVE n:`Person` SET n:`Actor`
In the second example below, an initial query invokes the
apoc.cypher.run
procedure, which in turn builds a second query behind
the scenes and then executes it.
The second query fetches all nodes and returns them.
CALL apoc.cypher.run("MATCH (n) RETURN n", {})
// executes MATCH (n) RETURN n
Both of the procedures in the above examples build and execute new queries derived from the inputs they receive. The only difference between these two procedures is the inputs they receive. In the first example, the procedure knows the inputs represent Cypher Literals. In the second example, the procedure knows the input represents a whole Cypher query. The inputs in the first example can be sanitized, whereas the input in the second example cannot be sanitized.
APOC guarantees it will sanitize inputs that correspond to a Cypher literal. However, APOC cannot offer the same guarantees for inputs which correspond to a whole Cypher query. In the latter case, the responsibility to sanitize the Cypher queries is delegated to the user, and users are recommended to carefully follow the aforementioned Cypher Injection guidance.
Cryptographic Functions
APOC provides a range of hashing functions that provide the ability to convert any object to a fixed-length uniform string. This capability has a number of applications, both cryptographic and non-cryptographic. Cryptographic applications may include message digests and password verifications, whereas non-cryptographic use cases may include distributing data uniformly and data deduplication. Using an APOC hashing function which is cryptographically unsafe for use cases that require cryptographic safety can lead to high-impact vulnerabilities such as Weak Encryption.
The key determinant in deciding whether a hashing function provided by APOC is cryptographically secure is whether it possesses the property of irreversibility. A hashing function is considered irreversible if it is easy to compute a hash given an input, but hard to compute the original input given its hash.
When using hashing functions it is important to first analyse whether a workload requires an irreversible hash, and to then determine whether the hashing algorithm provided by a given APOC function is able to provide this property. It is recommended to keep up to date with the latest security research, as weaknesses are sometimes found in hashing functions that were once believed to be irreversible.
If a workload does not require an irreversible hash, then the cryptographically unsafe hashing functions provided by APOC are preferable since they should execute faster.