Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Ability to edit "DHCP static leases" entry after its saved #1700

Closed
sesipod opened this issue May 18, 2020 · 20 comments
Closed

Ability to edit "DHCP static leases" entry after its saved #1700

sesipod opened this issue May 18, 2020 · 20 comments

Comments

@sesipod
Copy link

sesipod commented May 18, 2020

Can we please have the ability to edit DHCP static leases after they are added to AdGuard Home.
Another idea: It would be nice to have a description field added :) So there can be notes added to each device. For example mac / ip / hostname / ( Description )

ee:6f:6d:85:0e:39 | 192.168.1.5 | Debian-AdGuard | VM_Server
ee:6f:1d:90:0e:39 | 192.168.1.9 | Android-s20 | WiFi

@mdehaas
Copy link

mdehaas commented Nov 9, 2020

Love to see this in the interface. If all else fails it can be implemented as a delete of the old record and a create of the new one, all under the hood. This would create a nicer user expierience.

@ameshkov ameshkov added this to the v0.108 milestone Nov 10, 2020
@MarsWarrior
Copy link

Does editing of the static leases list mean that this list will be added to the AdguardHome.yaml file?

This would be very nice.

Currently the static leases are part of the leased.db, which hashes orso the ip and mac address, making it impossible to provide this preconfigured file from Github for instance.

How are mac & ip address hashed btw?

@ainar-g
Copy link
Contributor

ainar-g commented Jun 16, 2021

@MarsWarrior, it will probably be put into some form of a database, although we haven't decided on the format yet. Once we do, exporting and importing the data should be easy. Also, a better place for questions are GitHub discussions. Thanks.

@mercyground
Copy link

mercyground commented Jul 10, 2021

Moving the static leases into the AdguardHome.yaml file so they are listed like the Client section would be wonderful.
I am running Adguard on a OpenWRT router and thus when it is reset the /tmp folder is wiped which looses AdGuard's lease.db file and i have to redo the leases all over again. Having them in the yaml file would survive the reset and save reconfiguration.

:edit: AdGuard Home, version 0.104.3, channel release, arch linux mips
Also Adguard doesnt like DHCP 9 requests. :edit2: never mind i see this is fixed in #3053

DECLINE | 9 | A client sends a Decline message to a server to indicate that the client has determined that one or more addresses assigned by the server are already in use on the link to which the client is connected.

Sat Jul 10 20:40:52 2021 daemon.err AdGuardHome[4402]: 2021/07/10 19:40:52 [error] DHCPv6: message type 9 not supported

@ainar-g ainar-g self-assigned this Jan 27, 2022
@ggear
Copy link

ggear commented Mar 2, 2022

+1

This feature is necessary and preventing me moving from PiHole where I can manage this nicely via dnsmasq configuration files.

A command line utility, API endpoints or addition to the YAML config are all reasonable approaches - I can work with anything :)

@ainar-g ainar-g mentioned this issue Oct 11, 2022
3 tasks
@Giulianini
Copy link

So there's a way to edit "DHCP static leases" entries? I'm moving from pihole and I have to recreate all the leases by hand

@jeeftor
Copy link

jeeftor commented Dec 20, 2022

I just took a look at this... the code is already basically in the repo to decode the leases in db.go - and i don't "really" have time but it wouldn't be too hard to get somebody who knows go well enough to write a CLI utility. (I've never actually written anything in go - so this literally was a 5 minute hack together attempt - mostly copying from db.go)

package main

import (
	"encoding/json"
	"fmt"
	"log"
	"net"
	"os"
	"time"
)

const dbFilename = "leases.db"

type leaseJSON struct {
	HWAddr   []byte `json:"mac"`
	IP       []byte `json:"ip"`
	Hostname string `json:"host"`
	Expiry   int64  `json:"exp"`
}

// Lease contains the necessary information about a DHCP lease
type Lease struct {
	// Expiry is the expiration time of the lease.  The unix timestamp value
	// of 1 means that this is a static lease.
	Expiry time.Time `json:"expires"`

	Hostname string           `json:"hostname"`
	HWAddr   net.HardwareAddr `json:"mac"`
	IP       net.IP           `json:"ip"`
}

func (l *Lease) UnmarshalJSON(data []byte) (err error) {
	type lease Lease
	aux := struct {
		*lease
		HWAddr string `json:"mac"`
	}{
		lease: (*lease)(l),
	}
	if err = json.Unmarshal(data, &aux); err != nil {
		return err
	}

	l.HWAddr, err = net.ParseMAC(aux.HWAddr)
	if err != nil {
		return fmt.Errorf("couldn't parse MAC address: %w", err)
	}

	return nil
}

func normalizeIP(ip net.IP) net.IP {
	ip4 := ip.To4()
	if ip4 != nil {
		return ip4
	}
	return ip
}

func main() {
	fmt.Println("HI")
	data, err := os.ReadFile(dbFilename)
	if err != nil {
		log.Fatal(err)
	}

	obj := []leaseJSON{}
	err = json.Unmarshal(data, &obj)

	fmt.Print(obj)
}

go run ./decode.go

and it will print out some stuff like this (which needs further decoding:

{[164 218 34 46 93 231] [192 168 1 116] 192-168-1-116 1671039717}

Its pretty straight forward: mac address ip name and a timestamp/expiration on the lease.

@jeeftor
Copy link

jeeftor commented Dec 21, 2022

So adguard home also has an api - which maybe is a better way to go:

To add a lease you would do something like:

curl -X 'POST' \
  'http://SERVER_IP/control/dhcp/add_static_lease' \
  -H 'accept: */*' \
  -u username:password
  -H 'Content-Type: application/json' \
  -d '{
  "mac": "00:11:09:b3:b3:b8",
  "ip": "192.168.1.22",
  "hostname": "dell"
}'

Whereas deleting is:

curl -X 'POST' \
  'http://SERVER_IP/control/dhcp/remove_static_lease' \
  -H 'accept: */*' \
  -u username:password
  -H 'Content-Type: application/json' \
  -d '{
  "mac": "00:11:09:b3:b3:b8",
  "ip": "192.168.1.22",
  "hostname": "dell"
}'

If you want to play with the api go to https://editor.swagger.io and paste in the contents of https://github.com/AdguardTeam/AdGuardHome/blob/master/openapi/openapi.yaml

@jeeftor
Copy link

jeeftor commented Dec 21, 2022

Oh even better hit the /control/status endpoint

@Giulianini
Copy link

Backup and restore of DHCP config and leases:

Get DHCP config and leases

import json

import requests
import yaml
from requests import Response

if __name__ == '__main__':
    STATIC_LEASES_FILE = "static-leases.yaml"
    DHCP_CONFIG_FILE = "dhcp-config.yaml"

    url = "http://192.168.1.1:8083/control/dhcp/status"

    headers = {
        'Accept': '*/*',
        'Content-Type': 'application/json',
        'Authorization': 'Basic blablablageneratedbyPostMan'
    }

    response: Response = requests.request("GET", url, headers=headers)
    response: dict = json.loads(response.text)
    static_leases: list = response.pop("static_leases")
    leases: list = response.pop("leases")
    config: dict = response
    with open(STATIC_LEASES_FILE, "w") as static_leases_file:
        yaml.dump(static_leases, static_leases_file)
    with open(DHCP_CONFIG_FILE, "w") as dhcp_config_file:
        yaml.dump(response, dhcp_config_file)

Restoring DCHP config and leases

import requests
import json

import yaml

if __name__ == '__main__':
    STATIC_LEASES_FILE = "static-leases.yaml"
    DHCP_CONFIG_FILE = "dhcp-config.yaml"


    headers = {
        'Accept': '*/*',
        'Content-Type': 'application/json',
        'Authorization': 'Basic blablablageneratedbyPostMan'
    }

    add_static_lease_url = "http://192.168.1.1:8083/control/dhcp/add_static_lease"
    with open(STATIC_LEASES_FILE, "r") as f:
        loaded_leases = yaml.load(f, Loader=yaml.FullLoader)
        for lease in loaded_leases:
            response = requests.request("POST", add_static_lease_url, headers=headers, data=json.dumps(lease))
            if response.status_code == 200:
                print(f"Added lease: {lease}")
    set_config_url = "http://192.168.1.100:8083/control/dhcp/set_config"
    with open(DHCP_CONFIG_FILE, "r") as f:
        dhcp_config = yaml.load(f, Loader=yaml.FullLoader)
        response = requests.request("POST", set_config_url, headers=headers, data=json.dumps(dhcp_config))
        if response.status_code == 200:
            print(f"Configuration updated")

@mikeeq
Copy link

mikeeq commented Jan 29, 2023

Some time ago, I prepared an Ansible role/tasks for managing static leases in my home setup, if anyone is interested here it is:

@nmvega
Copy link

nmvega commented Oct 1, 2023

Here's a script you can use to add AGH static DHCP clients either singularly or in batches. Modify the AGH API_URL as necessary:

#! /usr/bin/bash

# =====================================================================
# ./add_AGH_static_DHCP_clents.sh
# =====================================================================

# =====================================================================
STATIC_LEASES_FILE='./static_leases.txt'
# =====================================================================
# Example file and entry format:
# =====================================================================
# my-host-name-3		33:33:33:33:33:33	192.168.0.3
# [ ... snip (at least one entry should be provided) ... ]
# my-host-name-4		33:33:33:33:33:34	192.168.0.4
# my-host-name-5		33:33:33:33:33:35	192.168.0.5
# =====================================================================

# =====================================================================
USER='AGH-admin-user-name'
PASS='AGH-admin-password'
API_URL="http://192.168.0.1:3000/control/dhcp/add_static_lease" # AdGuard Home API URL.
# =====================================================================
#
cat ${STATIC_LEASES_FILE} | \
while read line 
do
{
   [[ -z ${line} ]] || [[ ${line} =~ ^[[:space:]]*\#.*$ ]] && continue # Ignore empty & comment lines.
   line=(${line})
   HOST_NAME="\"${line[0]}\""
   MAC="\"${line[1]}\""
   IP="\"${line[2]}\""
   echo "{"\"mac\"": ${MAC}, "\"ip"\": ${IP}, "\"hostname"\": ${HOST_NAME}}"
   #
   curl -X 'POST' ${API_URL} -u ${USER}:${PASS} -H 'accept: */*' -H 'Content-Type: application/json' \
   -d "{"\"mac\"": ${MAC}, "\"ip"\": ${IP}, "\"hostname"\": ${HOST_NAME}}"
}
done

adguard pushed a commit that referenced this issue Oct 5, 2023
Updates #1700.

Squashed commit of the following:

commit b3fdf0a
Merge: 507cb9b 4479b32
Author: Stanislav Chzhen <s.chzhen@adguard.com>
Date:   Thu Oct 5 12:53:30 2023 +0300

    Merge branch 'master' into 1700-update-static-lease

commit 507cb9b
Author: Stanislav Chzhen <s.chzhen@adguard.com>
Date:   Wed Oct 4 18:54:06 2023 +0300

    all: upd chlog

commit 0736b97
Author: Ildar Kamalov <ik@adguard.com>
Date:   Wed Oct 4 16:05:35 2023 +0300

    client: fix update action

commit 351986b
Author: Ildar Kamalov <ik@adguard.com>
Date:   Wed Oct 4 16:01:38 2023 +0300

    client: update static lease

commit 3c32828
Author: Stanislav Chzhen <s.chzhen@adguard.com>
Date:   Thu Sep 28 20:06:29 2023 +0300

    dhcpd: fix err msg

commit 5b2f8f5
Author: Stanislav Chzhen <s.chzhen@adguard.com>
Date:   Thu Sep 28 16:28:07 2023 +0300

    dhcpd: imp code

commit a9d24e8
Author: Stanislav Chzhen <s.chzhen@adguard.com>
Date:   Wed Sep 27 17:43:04 2023 +0300

    all: add tests

commit 4537857
Author: Stanislav Chzhen <s.chzhen@adguard.com>
Date:   Tue Sep 26 20:14:17 2023 +0300

    dhcpd: update static lease
@ainar-g ainar-g modified the milestones: v0.107.40, v0.107.39 Oct 11, 2023
@ainar-g
Copy link
Contributor

ainar-g commented Oct 11, 2023

@schzhn forgot to mention, but this should be available in the upcoming v0.107.39.

@ainar-g ainar-g closed this as completed Oct 11, 2023
@bastiitsab
Copy link

@schzhn forgot to mention, but this should be available in the upcoming v0.107.39.

where should I find this in the newest version?

@schzhn
Copy link
Member

schzhn commented Nov 7, 2023

@bastiitsab, Settings - DHCP settings - DHCP static leases - Actions tab - Edit button

@bastiitsab
Copy link

@bastiitsab, Settings - DHCP settings - DHCP static leases - Actions tab - Edit button

thanks! but its only possbile in the GUI? Not in yaml or anywhere on the filesystem? I would also love to bulk edit or export the entries.

@schzhn
Copy link
Member

schzhn commented Nov 7, 2023

@bastiitsab, ./data/leases.json.
Next time, please, if you have a question use discussions.

annguyen0 pushed a commit to annguyen0/AdGuardHome that referenced this issue Nov 27, 2023
Updates AdguardTeam#1700.

Squashed commit of the following:

commit b3fdf0a
Merge: 507cb9b 4479b32
Author: Stanislav Chzhen <s.chzhen@adguard.com>
Date:   Thu Oct 5 12:53:30 2023 +0300

    Merge branch 'master' into 1700-update-static-lease

commit 507cb9b
Author: Stanislav Chzhen <s.chzhen@adguard.com>
Date:   Wed Oct 4 18:54:06 2023 +0300

    all: upd chlog

commit 0736b97
Author: Ildar Kamalov <ik@adguard.com>
Date:   Wed Oct 4 16:05:35 2023 +0300

    client: fix update action

commit 351986b
Author: Ildar Kamalov <ik@adguard.com>
Date:   Wed Oct 4 16:01:38 2023 +0300

    client: update static lease

commit 3c32828
Author: Stanislav Chzhen <s.chzhen@adguard.com>
Date:   Thu Sep 28 20:06:29 2023 +0300

    dhcpd: fix err msg

commit 5b2f8f5
Author: Stanislav Chzhen <s.chzhen@adguard.com>
Date:   Thu Sep 28 16:28:07 2023 +0300

    dhcpd: imp code

commit a9d24e8
Author: Stanislav Chzhen <s.chzhen@adguard.com>
Date:   Wed Sep 27 17:43:04 2023 +0300

    all: add tests

commit 4537857
Author: Stanislav Chzhen <s.chzhen@adguard.com>
Date:   Tue Sep 26 20:14:17 2023 +0300

    dhcpd: update static lease
@WildByDesign
Copy link

@ainar-g

@schzhn forgot to mention, but this should be available in the upcoming v0.107.39.

This still does not appear to be implemented yet in the Stable branch on v0.107.42.

When you click on the Edit button for a Static DHCP lease, it brings up the New static lease dialog which is empty.

I believe that it may be a similar issue to (f44faa9) which was committed recently from issue (#6402).

@ainar-g
Copy link
Contributor

ainar-g commented Dec 14, 2023

@WildByDesign, that's likely what #6534 has reported. Also, it's better to file new issues, provided there are no duplicates, then to respond to closed ones, as they get less attention.

@WildByDesign
Copy link

Very good points. My apologies. I will follow those points in the future.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests