CrewAI adapter
For CrewAI — register your tool functions on the adapter, then pass adapter.crewai_tools() to your Agent(tools=…). Every call routes through the Kite Logik policy gate before the underlying function executes.
Install
pip install kitelogik crewaicrewai is not a hard dependency — only imported when you call crewai_tools(). If missing, you get a clear ImportError with the install command.
Setup
from kitelogik import OPAClient, PolicyGate, SessionContext
from kitelogik.adapters.crewai import CrewAIAdapter
gate = PolicyGate(opa_client=OPAClient())
context = SessionContext(
session_id="sess_001",
user_role="research_agent",
session_scopes=["search_web", "read_customer"],
)
adapter = CrewAIAdapter(gate=gate, context=context)Register tools
register(name, fn, description="", action=None) — chainable.
def search_web(query: str) -> str:
return f"Top results for: {query}"
def read_customer(customer_id: str) -> str:
return f"Customer {customer_id}: Acme Corp"
adapter.register("search_web", search_web, description="Search the web")
adapter.register("read_customer", read_customer, description="Look up a customer")Tool functions are sync in CrewAI — the adapter bridges to the async governance pipeline via _run_coroutine_sync. Async functions also work.
Pass governed tools to a Crew Agent
from crewai import Agent, Crew, Task
researcher = Agent(
role="Research Analyst",
goal="Surface the most relevant customer signals",
tools=adapter.crewai_tools(), # ← only added line
)
task = Task(
description="Look up cust_001 and search the web for related news.",
agent=researcher,
)
crew = Crew(agents=[researcher], tasks=[task])
result = crew.kickoff()Every tool the model invokes through the agent loop is gated.
What happens on a deny
Denied calls return the string "[BLOCKED] <error>" from the tool — the agent loop continues, and the model sees the refusal in the next turn so it can react.
[BLOCKED] Tool 'approve_refund' denied by policy: Refunds over $200 require manager approvalConstructor parameters
CrewAIAdapter(
gate: PolicyGate,
context: SessionContext,
sanitize: bool = True,
)| Param | Default | Purpose |
|---|---|---|
sanitize | True | Run prompt-injection sanitiser on string return values |
CrewAI tools use the framework's own @crewai.tools.tool decorator under the hood, so the resulting tool object behaves like any other CrewAI tool — including how the agent introspects its name and docstring.
Source
kitelogik/adapters/crewai.py on GitHub.