Appearance
End-to-End Example
A single HCL file that wires together a connector, an agent, a role, a Rego policy, a scheduled task, and a memory entry. Apply it on a fresh tenant to see the whole shape of the provider.
hcl
terraform {
required_providers {
agentcy = { source = "agentcy/agentcy" }
}
}
provider "agentcy" {
endpoint = var.endpoint
api_key = var.api_key
}
variable "endpoint" {
type = string
default = "http://localhost:18080"
}
variable "api_key" {
type = string
sensitive = true
}
# 1. Org-wide LLM defaults.
resource "agentcy_settings" "this" {
organization_name = "Acme"
llm_provider = "openai"
llm_model = "gpt-4o"
llm_base_url = "https://api.openai.com/v1"
embedding_model = "all-MiniLM-L6-v2"
auto_embed_on_ingest = true
}
# 2. A realm — graph namespace.
resource "agentcy_realm" "engineering" {
name = "engineering"
display_name = "Engineering"
color = "#3b82f6"
}
# 3. A CSV connector ingesting into the engineering realm.
resource "agentcy_source" "team_roster" {
source_type = "csv"
name = "team-roster"
realm = agentcy_realm.engineering.name
config = jsonencode({
delimiter = ","
node_label = "Person"
content = "id,name,role\n1,Alice,Eng\n2,Bob,PM\n"
})
}
# 4. An enrichment agent over the engineering realm.
resource "agentcy_agent" "enricher" {
agent_type = "enrichment"
name = "team-enricher"
enabled = true
}
# 5. A scheduled task that fires the agent every weekday morning.
resource "agentcy_task" "morning_summary" {
name = "morning-summary"
description = "Daily team summary at 09:00 UTC"
cron_expression = "0 9 * * 1-5"
timezone = "UTC"
message_template = "Summarize yesterday's commits and PRs."
source_ids = [agentcy_source.team_roster.id]
}
# 6. RBAC: a read-only role.
resource "agentcy_role" "viewer" {
name = "viewer"
description = "Read-only access to graph + memory"
permissions = ["graph:read", "agent:manage"]
}
# 7. A Rego policy denying writes outside business hours. Validated at plan time.
resource "agentcy_policy" "business_hours_only" {
name = "business-hours-only"
package_path = "agentcy.business_hours"
description = "Block writes outside 9–17 UTC weekdays."
rego_code = <<-EOT
package agentcy.business_hours
default allow := true
deny[msg] if {
input.action == "write"
hour := time.clock([time.now_ns(), "UTC"])[0]
hour < 9
msg := "Writes blocked before 09:00 UTC"
}
deny[msg] if {
input.action == "write"
hour := time.clock([time.now_ns(), "UTC"])[0]
hour >= 17
msg := "Writes blocked after 17:00 UTC"
}
EOT
}
# 8. A memory entry seeding org context.
resource "agentcy_memory" "house_style" {
content = "Default response tone: concise, technical, no marketing fluff."
title = "House style"
memory_type = "guideline"
tags = ["style", "tone"]
}
# 9. Programmatic API key scoped to this team's source.
resource "agentcy_api_key" "ci" {
name = "ci-pipeline"
permissions = ["agent:manage", "source:manage"]
source_ids = [agentcy_source.team_roster.id]
expires_in_days = 90
}
output "ci_api_key" {
value = agentcy_api_key.ci.key
sensitive = true
}
output "agent_id" { value = agentcy_agent.enricher.id }
output "policy_id" { value = agentcy_policy.business_hours_only.id }Apply
bash
terraform plan
terraform applyYou'll get a plan summary like:
Plan: 9 to add, 0 to change, 0 to destroy.Apply takes a few seconds — most resources are pure DB writes. Realm creation auto-runs Neo4j label setup, and source creation does config validation against the connector registry.
What to inspect after apply
- The Agentcy UI shows all nine resources under their respective tabs.
terraform state listenumerates them in TF state.terraform output -raw ci_api_keyprints the API key plaintext (it's only available at create — store it now or rotate).terraform planagain should reportNo changes.— that's the reproducibility test every resource passes in v1.
Update path
Edit any field, run terraform apply again. The provider does in-place updates everywhere it can: name, schedule, permissions, Rego code, etc. Two attributes force replacement:
agentcy_agent.agent_type— agent kind is immutableagentcy_skill.slug,agentcy_skill.scope— slug is the natural key, scope is fixed at createagentcy_policy_source.source_type—git_repovsinlineis fundamental to how the source is wired
Destroy
bash
terraform destroyAll nine resources are removed, in dependency order. The agentcy_api_key is a soft revoke (the row stays in the DB with active = false); everything else is a hard delete.