Salesforce-aware knowledge graph: parse SFDX metadata (Apex, Flow, LWC, CPQ, Governor Limits, Order-of-Execution) into a queryable NetworkX graph — fully offline, no org connection required.
Project description
graphify-sf
⚡ A Salesforce-native knowledge-graph library — turn any Enterprise (CPQ) Salesforce org's metadata into a token-minimized graph for onboarding, analysis, impact review, and development. Inspired by graphify; rebuilt in Python for Apex, Flow, LWC, CPQ data, and the realities of Governor Limits.
What it is
graphify-sf is a Python library (not an on-platform package). It statically
parses a Salesforce metadata repository — and CPQ rule data — into a NetworkX
knowledge graph, runs Salesforce-aware analysis passes, then serves a
token-minimized view so an LLM (or a person) can answer "what breaks if I change
X?", "how is a Quote created from an Opportunity?", or "where are the Governor-Limit
risks?" without reading the raw org.
The North Star: any Enterprise CPQ org → SF-specific KB graph → token-minimized consumption → onboarding, analysis, impact review, and development.
Capabilities
- Parsers (
graphify/salesforce/): Apex (regex, ADR-019), Flow (typed record tags), LWC (@wire+ imperative Apex), Custom Object/Field, Profile/Permission Set, Validation Rule, Record Type, Permission Set Group, Workflow, Custom Metadata records, Sharing Rules, Custom Labels, Custom Settings. - CPQ rule data ingest (
cpq_data.py): SBQQ Price/Product Rules, Conditions, Actions from SFDX JSON or Gearset*.gs.json, plus JavaScript QCP custom scripts — the logic that lives as data records, not metadata. __mdtfield mappings (mdt_mapping.py): turns mapping records (e.g.Opportunity_To_Quote_Mapping__mdt) into traversablemaps_tofield→field edges so impact follows the Opp→Quote boundary.- Analysis passes (whole-graph): Order of Execution, Governor Limits, recursive triggers, Profile/FLS permission impact, Flow↔CPQ infinite loops, CPQ↔Validation Rule conflicts.
- Token-minimized consumption (
pipeline.py/query.py/cli.py/viz.py): Leiden community clustering,token_budget-bounded queries, an MCP server, and a focused self-contained HTML visualization.
Every node/edge carries a confidence (EXTRACTED / INFERRED / AMBIGUOUS) so you know
what is certain vs. heuristic. See docs/ARCHITECTURE.md,
docs/ADR.md, and docs/PRD.md.
Install
pip install -e .
Requires Python 3.11+. networkx is required; graspologic (Leiden), mcp (serve),
and tree-sitter are optional and degrade gracefully when absent.
Quick start
# 1. Extract + enrich a graph (optionally merge CPQ rule data)
python -m graphify.salesforce extract path/to/sf-repo \
--output-dir graphify-out --cpq-data path/to/cpq-records
# 2. Ask SF-aware questions (token-bounded)
python -m graphify.salesforce impact <node-id> --direction downstream
python -m graphify.salesforce violations --severity HIGH
python -m graphify.salesforce cpq-chain SBQQ__Quote__c
python -m graphify.salesforce ooe Opportunity
# 3. Visualize a focused subgraph (self-contained HTML)
python -m graphify.salesforce viz graphify-out/graph.json --focus <node-id>
# 4. Serve over MCP for an LLM client
python -m graphify.serve graphify-out/graph.json
Run the test suite with pytest tests/test_salesforce.py -v.
Use it from an AI agent (Claude, Copilot, Cursor, …)
The point of graphify-sf is that an agent answers Salesforce questions from the
graph instead of reading raw metadata — so it stays accurate and token-cheap. The
flow is always: extract once → expose the graph → the agent queries it.
Step 1 — build the graph (once per org snapshot)
python -m graphify.salesforce extract path/to/sf-repo \
--output-dir graphify-out --cpq-data path/to/cpq-records
# → graphify-out/graph.json
Re-run after a metadata pull to refresh it.
Option A — MCP server (recommended)
Serve the graph over MCP; the agent gets token-bounded Salesforce tools
(sf_impact, sf_violations, sf_cpq_chain, sf_ooe) plus the base graph tools
(query_graph, graph_stats, god_nodes, shortest_path, get_neighbors, …).
# stdio transport (default — what desktop agents launch)
python -m graphify.serve graphify-out/graph.json
# or the console script after `pip install -e .`
graphify-mcp graphify-out/graph.json
# shared HTTP transport (team / remote)
python -m graphify.serve graphify-out/graph.json --transport http --port 8080
Claude Code — one command (use an absolute path to graph.json):
claude mcp add graphify-sf -- python -m graphify.serve /abs/path/to/graphify-out/graph.json
Claude Desktop / Cursor / Windsurf — add to the MCP config
(claude_desktop_config.json, .cursor/mcp.json, …); they share this shape:
{
"mcpServers": {
"graphify-sf": {
"command": "python",
"args": ["-m", "graphify.serve", "/abs/path/to/graphify-out/graph.json"]
}
}
}
VS Code / GitHub Copilot — .vscode/mcp.json uses the servers key:
{
"servers": {
"graphify-sf": {
"type": "stdio",
"command": "python",
"args": ["-m", "graphify.serve", "/abs/path/to/graphify-out/graph.json"]
}
}
}
Then just ask, e.g. "What breaks if I change Opportunity.Amount? Use graphify-sf."
Option B — no MCP (CLI the agent shells out to)
For agents that run shell commands but have no MCP, point them at the CLI — each command prints a token-bounded answer to stdout:
python -m graphify.salesforce impact <node-id> --direction downstream
python -m graphify.salesforce violations --severity HIGH
python -m graphify.salesforce cpq-chain SBQQ__Quote__c
python -m graphify.salesforce ooe Opportunity
Tell the agent to use it on every task
Drop a short rule into the agent's project-instructions file — CLAUDE.md (Claude
Code), .github/copilot-instructions.md (Copilot), .cursorrules (Cursor), or
AGENTS.md:
## Salesforce knowledge graph
Before answering Salesforce impact / CPQ / Order-of-Execution / Governor-Limit
questions, consult the graphify-sf graph instead of reading raw metadata:
- If the `graphify-sf` MCP server is connected, call `sf_impact` / `sf_violations` /
`sf_cpq_chain` / `sf_ooe`.
- Otherwise run `python -m graphify.salesforce <impact|violations|cpq-chain|ooe> …`.
Rebuild it with `python -m graphify.salesforce extract <repo> --cpq-data <dir>`
after pulling fresh metadata.
Coverage
| Area | Module | Status |
|---|---|---|
| Core parsers (Apex/Flow/LWC/Objects/Profiles) | apex_enhanced, flow, lwc, objects, profiles |
✅ |
| Metadata coverage (RecordType/PSG/Workflow/Custom Metadata/Sharing/Label/Setting) | metadata, objects |
✅ |
| CPQ rule data (SFDX + Gearset + JS QCP) | cpq_data |
✅ |
__mdt field mapping (Opp→Quote) |
mdt_mapping |
✅ |
| Token-minimized consumption (cluster/query/CLI/viz/MCP) | pipeline, query, cli, viz |
✅ |
| Neo4j export | neo4j_sf |
✅ |
| Apex cross-class call resolution | tree-sitter promotion | ⏸ deferred (ADR-019) |
Inspiration & Credits
This project stands on the shoulders of graphify
by Safi Shamsi. The core idea, architecture, and
API ergonomics are theirs — graphify-sf is an independent, Salesforce-tailored
adaptation built with deep respect for the original work. If you need a
platform-agnostic solution, please use and support the upstream project.
본 프로젝트는 graphify의 아이디어와 아키텍처에서 출발했습니다. 핵심 개념에 대한 모든 공로는 원작자에게 있으며,
graphify-sf는 이를 Salesforce 플랫폼(Apex/Flow/LWC/CPQ) 환경에 맞게 재구현한 독립적인 파생 프로젝트입니다. 원작자의 노고에 깊이 감사드립니다. 범용 환경이 필요하다면 원본 프로젝트를 사용하시길 권장합니다.
The upstream project's original README is preserved in this repo as
README.upstream.md.
License
MIT © Safi Shamsi (graphify) · MIT © JeremyKo95 (graphify-sf). See LICENSE.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file graphify_sfdx-0.1.1.tar.gz.
File metadata
- Download URL: graphify_sfdx-0.1.1.tar.gz
- Upload date:
- Size: 1.0 MB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: uv/0.11.23 {"installer":{"name":"uv","version":"0.11.23","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"macOS","version":null,"id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
d16a28dba93b57c559acd722c527e6d4c74d9047de5b4212fd2e30ff52baeb18
|
|
| MD5 |
b3d75582543eee00d255765166ab765f
|
|
| BLAKE2b-256 |
982d6cad0b4560ee29c8b3e38e63578a57a97f297e3095807ff98387583f704d
|
File details
Details for the file graphify_sfdx-0.1.1-py3-none-any.whl.
File metadata
- Download URL: graphify_sfdx-0.1.1-py3-none-any.whl
- Upload date:
- Size: 863.4 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: uv/0.11.23 {"installer":{"name":"uv","version":"0.11.23","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"macOS","version":null,"id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
e93408a7386861d0682b22bf18692856c8b3090ab9cd4221e9da2c5a30452cd6
|
|
| MD5 |
47e98b72830b858452d25cc5d494edcc
|
|
| BLAKE2b-256 |
4e66ea6b620c373c6829db5d00886c39b38b8bd0a10cf998e423078b34c2da00
|