pihole package - github.com/awaybreaktoday/lib-pihole-go - Go Packages

pihole

package module
v1.0.1 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Sep 21, 2025 License: MIT Imports: 13 Imported by: 0

README

go-pihole

A Golang Pi-hole client

Requires Pi-hole Web Interface >= 6. For <6, use tag <= v0.0.4

Usage

import (
	"context"
	"errors"
	"log"
	"os"

	"github.com/awaybreaktoday/go-pihole"
)

client, err := pihole.New(pihole.Config{
	BaseURL:  "https://pi.hole/api",
	APIToken: os.Getenv("PIHOLE_API_TOKEN"),
	// Password remains supported for session logins when no API token is provided.
	Password: os.Getenv("PIHOLE_PASSWORD"),
})
if err != nil {
	log.Fatal(err)
}

record, err := client.LocalDNS.Create(context.Background(), "my-domain.com", "127.0.0.1")
if err != nil {
	log.Fatal(err)
}
log.Printf("%s -> %s (ttl=%d comment=%q)", record.Domain, record.IP, record.TTL, record.Comment)

alias, err := client.LocalCNAME.CreateRecord(context.Background(), &pihole.CNAMERecord{
	Domain: "www.example.com",
	Target: "example.com",
	TTL:    3600,
	HasTTL: true,
})
if err != nil {
	log.Fatal(err)
}
log.Printf("%s -> %s (ttl=%d)", alias.Domain, alias.Target, alias.TTL)

_, err = client.LocalDNS.Create(context.Background(), record.Domain, record.IP)
if err != nil {
	var dnsErr *pihole.DNSAPIError
	if errors.As(err, &dnsErr) {
		log.Printf("pihole rejected request: key=%s message=%s", dnsErr.Key, dnsErr.Message)
	}
}
Authentication

Config accepts either APIToken or APIKey to enable Pi-hole's API token authentication. When supplied, the client automatically sends the X-FTL-APIKEY header and skips session negotiation. Supplying Password continues to work for legacy session-based flows, providing a fallback when no token is present.

DNS and CNAME helpers
  • DNSRecord now exposes optional TTL and Comment fields so callers can observe and persist Pi-hole's additional metadata.
  • CNAMERecord tracks whether a TTL is supplied (HasTTL) and retains Pi-hole's original tuple, ensuring deletes round-trip exactly what the server expects.
  • Use LocalCNAME.CreateRecord to submit a structured CNAMERecord and include TTLs when required.

Mutation helpers in both packages return typed errors (*DNSAPIError, *CNAMEAPIError) that surface Pi-hole's structured error.key, message, and hint values for improved diagnostics.

Test

make test
Acceptance
docker compose up -d
export PIHOLE_URL=http://localhost:8080
export PIHOLE_PASSWORD=test
make acceptance

Documentation

Index

Constants

This section is empty.

Variables

View Source
var (
	ErrorSessionNotFound        = errors.New("session not found")
	ErrorSessionUnauthorized    = errors.New("unauthorized session request")
	ErrorSessionBadRequest      = errors.New("bad session request")
	ErrorSessionTooManyRequests = errors.New("too many session requests")
)
View Source
var ErrClientValidation = errors.New("invalid client configuration")
View Source
var (
	ErrorLocalCNAMENotFound = errors.New("local CNAME record not found")
)
View Source
var (
	ErrorLocalDNSNotFound = errors.New("local dns record not found")
)

Functions

This section is empty.

Types

type CNAMEAPIError added in v1.0.1

type CNAMEAPIError struct {
	StatusCode int
	Key        string
	Message    string
	Hint       interface{}
}

func (*CNAMEAPIError) Error added in v1.0.1

func (e *CNAMEAPIError) Error() string

type CNAMERecord

type CNAMERecord struct {
	Domain string
	Target string
	TTL    int
	HasTTL bool
	// contains filtered or unexported fields
}

type CNAMERecordList

type CNAMERecordList []CNAMERecord

type Client

type Client struct {
	LocalDNS   LocalDNS
	LocalCNAME LocalCNAME
	SessionAPI SessionAPI
	// contains filtered or unexported fields
}

func New

func New(config Config) (*Client, error)

New returns a new Pi-hole client

func (*Client) Delete

func (c *Client) Delete(ctx context.Context, path string) (*http.Response, error)

func (*Client) Get

func (c *Client) Get(ctx context.Context, path string) (*http.Response, error)

func (*Client) Post

func (c *Client) Post(ctx context.Context, path string, body interface{}) (*http.Response, error)

func (*Client) Put

func (c *Client) Put(ctx context.Context, path string, body interface{}) (*http.Response, error)

func (*Client) Request

func (c *Client) Request(ctx context.Context, vals url.Values) (*http.Request, error)

type Config

type Config struct {
	BaseURL    string
	Password   string
	SessionID  string
	HttpClient *http.Client
	Headers    http.Header
	APIToken   string
	APIKey     string
}

type DNSAPIError added in v1.0.1

type DNSAPIError struct {
	StatusCode int
	Key        string
	Message    string
	Hint       interface{}
}

func (*DNSAPIError) Error added in v1.0.1

func (e *DNSAPIError) Error() string

type DNSRecord

type DNSRecord struct {
	IP      string
	Domain  string
	TTL     int
	HasTTL  bool
	Comment string
	// contains filtered or unexported fields
}

type DNSRecordList

type DNSRecordList []DNSRecord

type LocalCNAME

type LocalCNAME interface {
	// List all CNAME records.
	List(ctx context.Context) (CNAMERecordList, error)

	// Create a CNAME record.
	Create(ctx context.Context, domain string, target string) (*CNAMERecord, error)

	// CreateRecord creates a CNAME record using the provided record definition.
	CreateRecord(ctx context.Context, record *CNAMERecord) (*CNAMERecord, error)

	// Get a CNAME record by its domain.
	Get(ctx context.Context, domain string) (*CNAMERecord, error)

	// Delete a CNAME record by its domain.
	Delete(ctx context.Context, domain string) error
}

type LocalDNS

type LocalDNS interface {
	// List all DNS records.
	List(ctx context.Context) (DNSRecordList, error)

	// Create a DNS record.
	Create(ctx context.Context, domain string, IP string) (*DNSRecord, error)

	// Get a DNS record by its domain.
	Get(ctx context.Context, domain string) (*DNSRecord, error)

	// Delete a DNS record by its domain.
	Delete(ctx context.Context, domain string) error
}

type Session

type Session struct {
	SID        string
	TOTP       bool
	CSRF       string
	Expiration time.Time
}

type SessionAPI

type SessionAPI interface {
	Post(ctx context.Context) (Session, error)
	Login(ctx context.Context) (Session, error)
	Delete(ctx context.Context, sessionID string) error
	Logout(ctx context.Context) error
}

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL