{"id":46657097,"url":"https://github.com/tschaefer/conntrackd","last_synced_at":"2026-03-10T22:10:45.027Z","repository":{"id":325366806,"uuid":"1099616243","full_name":"tschaefer/conntrackd","owner":"tschaefer","description":"conntrack event fanout logger with GEO location 🌐","archived":false,"fork":false,"pushed_at":"2026-03-08T07:22:33.000Z","size":570,"stargazers_count":1,"open_issues_count":0,"forks_count":1,"subscribers_count":0,"default_branch":"main","last_synced_at":"2026-03-08T11:48:34.186Z","etag":null,"topics":["conntrack","grafana","linux","logging","loki","netlink"],"latest_commit_sha":null,"homepage":"https://blog.tschaefer.org/conntrackd","language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/tschaefer.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2025-11-19T08:15:12.000Z","updated_at":"2026-03-08T07:22:30.000Z","dependencies_parsed_at":null,"dependency_job_id":null,"html_url":"https://github.com/tschaefer/conntrackd","commit_stats":null,"previous_names":["tschaefer/conntrackd"],"tags_count":8,"template":false,"template_full_name":null,"purl":"pkg:github/tschaefer/conntrackd","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tschaefer%2Fconntrackd","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tschaefer%2Fconntrackd/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tschaefer%2Fconntrackd/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tschaefer%2Fconntrackd/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/tschaefer","download_url":"https://codeload.github.com/tschaefer/conntrackd/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tschaefer%2Fconntrackd/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":30357623,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-03-10T21:41:54.280Z","status":"ssl_error","status_checked_at":"2026-03-10T21:40:59.357Z","response_time":106,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.5:443 state=error: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["conntrack","grafana","linux","logging","loki","netlink"],"created_at":"2026-03-08T08:33:58.094Z","updated_at":"2026-03-10T22:10:45.019Z","avatar_url":"https://github.com/tschaefer.png","language":"Go","funding_links":[],"categories":[],"sub_categories":[],"readme":"# conntrackd\n\n[![Tag](https://img.shields.io/github/tag/tschaefer/conntrackd.svg)](https://github.com/tschaefer/conntrackd/releases)\n![Go Version](https://img.shields.io/badge/Go-%3E%3D%201.25-%23007d9c)\n[![Go Report Card](https://goreportcard.com/badge/github.com/tschaefer/conntrackd)](https://goreportcard.com/report/github.com/tschaefer/conntrackd)\n[![Coverage](https://img.shields.io/codecov/c/github/tschaefer/conntrackd)](https://codecov.io/gh/tschaefer/conntrackd)\n[![Contributors](https://img.shields.io/github/contributors/tschaefer/conntrackd)](https://github.com/tschaefer/conntrackd/graphs/contributors)\n[![License](https://img.shields.io/github/license/tschaefer/conntrackd)](./LICENSE)\n\n**conntrackd** is a small, efficient conntrack event fanout logger written in\nGo. It listens for Linux conntrack/netfilter connection tracking events and\noptional enriches them with GEO location information before emitting structured\nlogs. It's intended for lightweight monitoring, auditing, and integration with\nlog pipelines.\n\n## Features\n\n- Listen for conntrack events (new/updated/destroyed connections)\n- Enrich IP addresses with GEO location data\n- Fanout to multiple log sinks (stream, syslog,\n  [journald](https://www.freedesktop.org/software/systemd/man/latest/systemd-journald.html),\n  [Loki](https://grafana.com/docs/loki/latest/))\n\n# Getting Started\n\n## Prerequisites\n\n- Linux (netlink/conntrack support required)\n- Root privileges\n- (Optional) MaxMind GeoIP2/GeoLite2 City database\n\n## Installation and Usage\n\nDownload the latest release from the\n[releases page](https://github.com/tschaefer/conntrackd/releases).\n\nStart the event listener and logger.\n\n```bash\nsudo conntrackd run --sink.journal.enable\n```\nFor further configuration, see the command-line options below.\n\n## Filtering\n\nconntrackd logs conntrack events to various sinks.\n\n**Protocol Support:** Only TCP and UDP events are processed. All other protocols\n(ICMP, IGMP, etc.) are automatically ignored and never logged, regardless of filter rules.\n\nYou can use filters to control which TCP/UDP events are logged using\n[CEL (Common Expression Language)](https://cel.dev).\nThe `--filter` flag lets you specify filter rules:\n\n```bash\nsudo conntrackd run \\\n  --filter 'drop destination.address == \"8.8.8.8\"' \\\n  --filter 'log protocol == \"TCP\" \u0026\u0026 is_network(destination.address, \"PUBLIC\")' \\\n  --filter \"drop any\" \\\n  --sink.journal.enable\n```\n\n**Filter Rules:**\n- Rules are evaluated in order (first-match wins)\n- Events are **logged by default** when no rule matches\n- `--filter` flag can be repeated for multiple rules\n- Use `drop any` or `drop true` as a final rule to block all non-matching events from being logged\n\n**Important:** Filters control which conntrack events are **logged**,\nnot network traffic. Traffic always flows normally; filters only affect logging.\n\n**Common Filter Examples:**\n\n```bash\n# Don't log events to a specific IP\n--filter 'drop destination.address == \"8.8.8.8\"'\n\n# Log only NEW TCP connections (deny everything else)\n--filter 'log event.type == \"NEW\" \u0026\u0026 protocol == \"TCP\"'\n--filter \"drop any\"\n\n# Don't log DNS to specific server\n--filter 'drop destination.address == \"10.19.80.100\" \u0026\u0026 destination.port == 53'\n\n# Don't log any traffic to private networks\n--filter 'drop is_network(destination.address, \"PRIVATE\")'\n\n# Log only traffic from public IPs using TCP\n--filter 'log is_network(source.address, \"PUBLIC\") \u0026\u0026 protocol == \"TCP\"'\n--filter \"drop any\"\n```\n\nSee [docs/filter.md](docs/filter.md) for complete CEL documentation,\nincluding available variables, functions, operators, and advanced examples.\n\n## Configuration\n\nconntrackd can be configured via command-line flags, configuration files,\nenvironment variables, or a combination of these methods.\n\n### Configuration Files\n\nBy default, conntrackd searches for a configuration file named\n`conntrackd.(yaml|yml|json|toml)` in `/etc/conntrackd` directory.\n\nYou can also specify a custom config file using the `--config` flag:\n\n```bash\nsudo conntrackd run --config /path/to/config.yaml\n```\nConfiguration files support YAML, JSON, and TOML formats.\nSee [contrib/config.yaml](contrib/config.yaml) for a complete example\nconfiguration file.\n\n### Environment Variables\n\nConfiguration values can be set via environment variables with the\n`CONNTRACKD_` prefix:\n\n```bash\nexport CONNTRACKD_LOG_LEVEL=debug\nexport CONNTRACKD_SINK_STREAM_WRITER=discard\nsudo -E conntrackd run\n```\n\nUse underscores (`_`) to represent nested keys:\n`sink.stream.writer` → `CONNTRACKD_SINK_STREAM_WRITER`\n\n### Priority Order\n\nConfiguration values are applied in the following order\n(later overrides earlier):\n\n1. Default values\n2. Configuration file\n3. Environment variables\n4. Command-line flags\n\n**Note:** Command-line flags always have the highest priority.\n\n## Configuration Flags\n\n| Flag                    | Description                                       | Default                  |\n|-------------------------|---------------------------------------------------|--------------------------|\n| `--config`              | Path to configuration file                        |                          |\n| `--filter`              | Filter rule in DSL format (repeatable)            |                          |\n| `--geoip.database`      | Path to GeoIP database                            |                          |\n| `--log.level`           | Log level (debug, info, warn, error)              | info                     |\n| `--sink.journal.enable` | Enable journald sink                              |                          |\n| `--sink.syslog.enable`  | Enable syslog sink                                |                          |\n| `--sink.loki.enable`    | Enable Loki sink                                  |                          |\n| `--sink.stream.enable`  | Enable stream sink                                |                          |\n| `--sink.syslog.address` | Syslog address                                    | udp://localhost:514      |\n| `--sink.loki.address`   | Loki address                                      | http://localhost:3100    |\n| `--sink.loki.labels`    | Loki labels (comma-separated key=value pairs)     |                          |\n| `--sink.stream.writer`  | Stream writer (stdout, stderr, discard)           | stdout                   |\n| `--profiler.enable`     | Enable continous profiling                        |                          |\n| `--profiler.address`    | Pyroscope server address                          | http://localhost:4040    |\n\n## Logging format\n\nconntrackd emits structured logs for each conntrack event. A typical log entry\nincludes:\n\n- type (connection event type)\n- flow (connection flow identifier)\n- src_addr, dst_addr (IP addresses)\n- src_port, dst_port (port numbers)\n- prot (transport protocol)\n\nAdditionally TCP field:\n\n- state (TCP connection state)\n\nGEO location fields for source and destination if applicable with prefixes\n`src_` and `dst_`:\n\n- city (city name)\n- country (country name)\n- lat (latitude)\n- lon (longitude)\n\n\u003cdetails\u003e\n\u003csummary\u003eExample log entry recorded by sink `syslog`\u003c/summary\u003e\n\n```json\n{\n  \"event\": {\n    \"dst_port\": 443,\n    \"dst_addr\": \"2600:1901:0:b3ea::\",\n    \"flow\": 221193769,\n    \"prot\": \"TCP\",\n    \"src_port\": 41348,\n    \"src_addr\": \"2003:cf:1716:7b64:da80:83ff:fecd:da51\",\n    \"tcp_state\": \"LAST_ACK\",\n    \"type\": \"UPDATE\"\n  },\n  \"level\": \"INFO\",\n  \"logger.name\": \"samber/slog-syslog\",\n  \"logger.version\": \"v2.5.2\",\n  \"message\": \"UPDATE TCP connection from [2003:cf:1716:7b64:da80:83ff:fecd...\",\n  \"timestamp\": \"2025-11-15T09:55:25.647544937Z\"\n}\n```\n\u003c/details\u003e\n\n\u003cdetails\u003e\n\u003csummary\u003eExample log entry recorded by sink `journal`\u003c/summary\u003e\n\n```json\n{\n\t\"__CURSOR\" : \"s=b3c7821dbfce47a59b06797aea9028ca;i=6772d3;b=100da27bd...\",\n\t\"_CAP_EFFECTIVE\" : \"1ffffffffff\",\n\t\"EVENT_SRC_PORT\" : \"39790\",\n\t\"_SOURCE_REALTIME_TIMESTAMP\" : \"1763200187611509\",\n\t\"_SYSTEMD_CGROUP\" : \"/user.slice/user-1000.slice/session-1.scope\",\n\t\"_SYSTEMD_OWNER_UID\" : \"1000\",\n\t\"_SYSTEMD_SESSION\" : \"1\",\n\t\"_EXE\" : \"/home/tschaefer/.env/bin/conntrackd\",\n\t\"_HOSTNAME\" : \"bullseye\",\n\t\"_GID\" : \"0\",\n\t\"PRIORITY\" : \"6\",\n\t\"_SYSTEMD_UNIT\" : \"session-1.scope\",\n\t\"EVENT_DST_PORT\" : \"443\",\n\t\"SLOG_LOGGER\" : \"tschaefer/slog-journal:v1.0.0\",\n\t\"_TRANSPORT\" : \"journal\",\n\t\"EVENT_SRC_ADDR\" : \"2003:cf:1716:7b64:da80:83ff:fecd:da51\",\n\t\"_COMM\" : \"conntrackd\",\n\t\"__MONOTONIC_TIMESTAMP\" : \"352829248481\",\n\t\"EVENT_TCP_STATE\" : \"LAST_ACK\",\n\t\"_MACHINE_ID\" : \"75b649379b874beea04d95463e59c3a1\",\n\t\"_SYSTEMD_SLICE\" : \"user-1000.slice\",\n\t\"_SYSTEMD_USER_SLICE\" : \"-.slice\",\n\t\"__SEQNUM_ID\" : \"b3c7821dbfce47a59b06797aea9028ca\",\n\t\"__REALTIME_TIMESTAMP\" : \"1763200187611631\",\n\t\"__SEQNUM\" : \"6779603\",\n\t\"_SYSTEMD_INVOCATION_ID\" : \"021760b3373342b98aaeabf9d12d8d74\",\n\t\"EVENT_FLOW\" : \"3478798157\",\n\t\"_PID\" : \"3794900\",\n\t\"_CMDLINE\" : \"conntrackd run --service.log.level debug --service.log....\",\n\t\"EVENT_PROT\" : \"TCP\",\n\t\"_AUDIT_SESSION\" : \"1\",\n\t\"_BOOT_ID\" : \"100da27bd8b94096b5c80cdac34d6063\",\n\t\"_RUNTIME_SCOPE\" : \"system\",\n\t\"_SELINUX_CONTEXT\" : \"unconfined\\n\",\n\t\"EVENT_DST_ADDR\" : \"2600:1901:0:b3ea::\",\n\t\"_AUDIT_LOGINUID\" : \"1000\",\n\t\"_UID\" : \"0\",\n\t\"EVENT_TYPE\" : \"UPDATE\",\n\t\"MESSAGE\" : \"UPDATE TCP connection from [2003:cf:1716:7b64:da80:83ff:fe...\"\n}\n\n```\n\u003c/details\u003e\n\n\u003cdetails\u003e\n\u003csummary\u003eExample log entry recorded by sink `loki`\u003c/summary\u003e\n\nLoki allows maximum 15 labels per log entry. Therefore, location fields are\nattached as structured metadata to each log line.\n\n```json\n{\n  \"stream\": {\n    \"detected_level\": \"INFO\",\n    \"dst_addr\": \"2a01:4f8:160:5372::2\",\n    \"dst_addr_extracted\": \"2a01:4f8:160:5372::2\",\n    \"dst_city\": \"Falkenstein\",\n    \"dst_country\": \"Germany\",\n    \"dst_lat\": \"50.4777\",\n    \"dst_lon\": \"12.3649\",\n    \"dst_port\": \"443\",\n    \"dst_port_extracted\": \"443\",\n    \"flow\": \"4198226788\",\n    \"flow_extracted\": \"4198226788\",\n    \"host\": \"bullseye.u.coresec.zone\",\n    \"level\": \"INFO\",\n    \"prot\": \"TCP\",\n    \"prot_extracted\": \"TCP\",\n    \"service_name\": \"conntrackd\",\n    \"src_addr\": \"2003:cf:1716:7b64:da80:83ff:fecd:da51\",\n    \"src_addr_extracted\": \"2003:cf:1716:7b64:da80:83ff:fecd:da51\",\n    \"src_city\": \"Garmisch-Partenkirchen\",\n    \"src_country\": \"Germany\",\n    \"src_lat\": \"47.4906\",\n    \"src_lon\": \"11.1026\",\n    \"src_port\": \"56110\",\n    \"src_port_extracted\": \"56110\",\n    \"tcp_state\": \"SYN_SENT\",\n    \"tcp_state_extracted\": \"SYN_SENT\",\n    \"type\": \"NEW\",\n    \"type_extracted\": \"NEW\"\n  },\n  \"values\": [\n    [\n      \"1764163739570953291\",\n      \"NEW TCP connection from [2003:cf:1716:7b64:da80:83ff:fecd:da51]:56110...\"\n    ]\n  ]\n}\n```\n\u003c/details\u003e\n\n\u003cdetails\u003e\n\u003csummary\u003eExample log entry recorded by sink `stream`\u003c/summary\u003e\n\n```json\n{\n  \"time\": \"2025-11-25T12:35:11.082791653+01:00\",\n  \"level\": \"INFO\",\n  \"msg\": \"NEW TCP connection from [2003:cf:1716:7b64:da80:83ff:fecd:da51]:4...\",\n  \"type\": \"NEW\",\n  \"flow\": 4000057915,\n  \"prot\": \"TCP\",\n  \"src_addr\": \"2003:cf:1716:7b64:da80:83ff:fecd:da51\",\n  \"dst_addr\": \"2a01:4f8:160:5372::2\",\n  \"src_port\": 41756,\n  \"dst_port\": 443,\n  \"tcp_state\": \"SYN_SENT\",\n  \"src_city\": \"Garmisch-Partenkirchen\",\n  \"src_country\": \"Germany\",\n  \"src_lat\": 47.4906,\n  \"src_lon\": 11.1026,\n  \"dst_city\": \"Falkenstein\",\n  \"dst_country\": \"Germany\",\n  \"dst_lat\": 50.4777,\n  \"dst_lon\": 12.3649\n}\n```\n\u003c/details\u003e\n\n\n## Security Notes\n\n- Observing conntrack/netlink events typically requires elevated privileges.\n- Keep GeoIP databases updated.\n- Be careful with log storage; connection events may contain sensitive network\n  metadata.\n\n## Contributing\n\nContributions are welcome! Please fork the repository and submit a pull request.\nFor major changes, open an issue first to discuss what you would like to change.\n\nEnsure that your code adheres to the existing style and includes appropriate\ntests.\n\n## License\n\nThis project is licensed under the [MIT License](LICENSE).\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Ftschaefer%2Fconntrackd","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Ftschaefer%2Fconntrackd","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Ftschaefer%2Fconntrackd/lists"}