Rename labels, types, and properties

The APOC library contains procedures that can be used to rename labels, relationship types, and properties of nodes and relationships.

Procedures for renaming labels, types, and properties

Qualified Name Type

apoc.refactor.rename.label(oldLabel STRING, newLabel STRING, nodes LIST<NODE>) - renames the given label from oldLabel to newLabel for all NODE values. If a LIST<NODE> is provided, the renaming is applied to the NODE values within this LIST<NODE> only.

Procedure

apoc.refactor.rename.nodeProperty(oldName STRING, newName STRING, nodes LIST<NODE>, config MAP<STRING, ANY>) - renames the given property from oldName to newName for all NODE values. If a LIST<NODE> is provided, the renaming is applied to the NODE values within this LIST<NODE> only.

Procedure

apoc.refactor.rename.type(oldType STRING, newType STRING, rels LIST<RELATIONSHIP>, config MAP<STRING, ANY>) - renames all RELATIONSHIP values with type oldType to newType. If a LIST<RELATIONSHIP> is provided, the renaming is applied to the RELATIONSHIP values within this LIST<RELATIONSHIP> only.

Procedure

apoc.refactor.rename.typeProperty(oldName STRING, newName STRING, rels LIST<RELATIONSHIP>, config MAP<STRING, ANY>) - renames the given property from oldName to newName for all RELATIONSHIP values. If a LIST<RELATIONSHIP> is provided, the renaming is applied to the RELATIONSHIP values within this LIST<RELATIONSHIP> only.

Procedure

Config parameters

As the collection of data is processed in batches using apoc.periodic.iterate, these procedures support the following config parameters:

Table 1. Config
name type default description

batchSize

INTEGER

10000

run the specified number of operation statements in a single tx - params: {_count, _batch}

parallel

BOOLEAN

true

run operation statements in parallel (note that statements might deadlock if conflicting)
Please note that, in case of parallel: false, APOC is designed to reuse the same java.util.concurrent.ThreadPoolExecutor with a maximum pool size equal 1, in order to prevent parallelism; this means that if you want to execute multiple apoc.periodic.iterate each one will be executed when the previous one has been completed. Instead, with parallel: true, APOC will use a ThreadPoolExecutor with a configurable maximum pool size via the apoc.jobs.pool.num_threads config or as default with the number of available processor * 2. Therefore, if we execute multiple apoc.periodic.iterate each one will be executed in parallel if the queue pool size can accept new tasks. Furthermore, to be noted that running in parallel affects all databases, and not the single database you are using. So with e.g. 2 databases db1 and db2, the apoc.periodic.iterate on db1 will impact on performance if we execute an apoc.periodic.iterate on db2.

retries

INTEGER

0

if the operation statement fails with an error, sleep 100ms and retry until retries-count is reached - param {_retry}

batchMode

STRING

"BATCH"

how data-driven statements should be processed by operation statement. Valid values are:

* "BATCH" - execute operation statement once per batchSize. Operation statement is prefixed with the following, which extracts each field returned in the data-driven statement from the $_batch parameter: [source,cypher] ---- UNWIND $_batch AS _batch WITH _batch.field1 AS field1, _batch.field2 AS field2 ---- * "SINGLE" - execute operation statement one at a time * "BATCH_SINGLE" - execute operation statement once per batchSize, but leaves unpacking of batch to the operation statement. The operation query can access the batched values via the $_batch parameter.

concurrency

INTEGER

Number of processors available

number of concurrent tasks are generated when using parallel:true

Examples

The below examples will further explain these procedures.

The following creates a graph contains nodes with the label Engineer connected by COLLEAGUES relationships:
CREATE (mark:Engineer {name: "Mark", city: "London"})
CREATE (jennifer:Engineer {name: "Jennifer", city: "St Louis"})
CREATE (michael:Engineer {name: "Michael", city: "Dresden"})
CREATE (jim:Engineer {name: "Jim", city: "London"})
CREATE (alistair:Engineer {name: "Alistair", city: "London"})

MERGE (jim)-[:COLLEAGUES {since: date("2006-05-01")}]->(alistair)
MERGE (mark)-[:COLLEAGUES {since: date("2018-02-01")}]->(jennifer)
MERGE (mark)-[:COLLEAGUES {since: date("2013-05-01")}]->(michael)

If the above query is run, it will result in the following graph:

apoc.rename initial

Renaming node labels

The following changes the label on Mark, Jennifer, and Michael from Engineer to DevRel:
MATCH (person:Engineer)
WHERE person.name IN ["Mark", "Jennifer", "Michael"]
WITH collect(person) AS people
CALL apoc.refactor.rename.label("Engineer", "DevRel", people)
YIELD committedOperations
RETURN committedOperations

If the above query is run, it will result in the following graph:

apoc.rename update node labels

Renaming relationship types

The following changes the relationship type between Jim and Alistair from COLLEAGUES to FROLLEAGUES:
MATCH (:Engineer {name: "Jim"})-[rel]->(:Engineer {name: "Alistair"})
WITH collect(rel) AS rels
CALL apoc.refactor.rename.type("COLLEAGUES", "FROLLEAGUES", rels)
YIELD committedOperations
RETURN committedOperations
apoc.rename rename rel type

Renaming node properties

The following query changes the node property city to location for all nodes with the DevRel label:
MATCH (person:DevRel)
WITH collect(person) AS people
CALL apoc.refactor.rename.nodeProperty("city", "location", people)
YIELD committedOperations
RETURN committedOperations
The following query returns all the nodes in our graph after this refactoring has been done:
MATCH (n)
RETURN (n)
Table 2. Results
n

(:DevRel {name: "Jennifer", location: "St Louis"})

(:DevRel {name: "Michael", location: "Dresden"})

(:Engineer {city: "London", name: "Jim"})

(:DevRel {name: "Mark", location: "London"})

(:Engineer {city: "London", name: "Alistair"})

Renaming relationship properties

The following query changes the relationship property since to from for all relationships:
MATCH ()-[rel]->()
WITH collect(rel) AS rels
CALL apoc.refactor.rename.typeProperty("since", "from", rels)
YIELD committedOperations
RETURN committedOperations
The following query returns all the paths in our graph after this refactoring has been done:
MATCH path = ()-[]->()
RETURN path
Table 3. Results
path

[{"name":"Mark","location":"London"},{"from":"2018-02-01"},{"name":"Jennifer","location":"St Louis"}]

[{"name":"Mark","location":"London"},{"from":"2013-05-01"},{"name":"Michael","location":"Dresden"}]

[{"name":"Jim","city":"London"},{"from":"2006-05-01"},{"name":"Alistair","city":"London"}]