Skip to content

Commit

Permalink
[dns] Implement config and show commands for static DNS. (#2737)
Browse files Browse the repository at this point in the history
- What I did
Implement config and show commands for static DNS feature. According to sonic-net/SONiC#1262 HLD.

- How I did it
Static DNS config commands are implemented in the new config/dns.py file. DNS config commands are available under config dns ... sub-command.
Show commands are implemented in the new show/dns.py file. DNS show commands are available under show dns ... sub-command.

- How to verify it
Compile sonic-utilities package. The unit tests will run automatically during the compilation.
Coverage for config/dns.py : 94%
Coverage for show/dns.py : 86%

- Previous command output (if the output of a command-line utility has changed)

- New command output (if the output of a command-line utility has changed)
# config dns nameserver add 1.1.1.1
# config dns nameserver add 8.8.8.8
# show dns nameserver
  Nameserver
------------
     1.1.1.1
     8.8.8.8
  • Loading branch information
oleksandrivantsiv authored Jun 25, 2023
1 parent 8414a70 commit dc2945b
Show file tree
Hide file tree
Showing 6 changed files with 381 additions and 1 deletion.
96 changes: 96 additions & 0 deletions config/dns.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,96 @@

import click
from swsscommon.swsscommon import ConfigDBConnector
from .validated_config_db_connector import ValidatedConfigDBConnector
import ipaddress


ADHOC_VALIDATION = True
NAMESERVERS_MAX_NUM = 3


def to_ip_address(address):
"""Check if the given IP address is valid"""
try:
ip = ipaddress.ip_address(address)

if ADHOC_VALIDATION:
if ip.is_reserved or ip.is_multicast or ip.is_loopback:
return

invalid_ips = [
ipaddress.IPv4Address('0.0.0.0'),
ipaddress.IPv4Address('255.255.255.255'),
ipaddress.IPv6Address("0::0"),
ipaddress.IPv6Address("0::1")
]
if ip in invalid_ips:
return

return ip
except Exception:
return


def get_nameservers(db):
nameservers = db.get_table('DNS_NAMESERVER')
return [ipaddress.ip_address(ip) for ip in nameservers]


# 'dns' group ('config dns ...')
@click.group()
@click.pass_context
def dns(ctx):
"""Static DNS configuration"""
config_db = ValidatedConfigDBConnector(ConfigDBConnector())
config_db.connect()
ctx.obj = {'db': config_db}


# dns nameserver config
@dns.group('nameserver')
@click.pass_context
def nameserver(ctx):
"""Static DNS nameservers configuration"""
pass


# dns nameserver add
@nameserver.command('add')
@click.argument('ip_address_str', metavar='<ip_address>', required=True)
@click.pass_context
def add_dns_nameserver(ctx, ip_address_str):
"""Add static DNS nameserver entry"""
ip_address = to_ip_address(ip_address_str)
if not ip_address:
ctx.fail(f"{ip_address_str} invalid nameserver ip address")

db = ctx.obj['db']

nameservers = get_nameservers(db)
if ip_address in nameservers:
ctx.fail(f"{ip_address} nameserver is already configured")

if len(nameservers) >= NAMESERVERS_MAX_NUM:
ctx.fail(f"The maximum number ({NAMESERVERS_MAX_NUM}) of nameservers exceeded.")

db.set_entry('DNS_NAMESERVER', ip_address, {})

# dns nameserver delete
@nameserver.command('del')
@click.argument('ip_address_str', metavar='<ip_address>', required=True)
@click.pass_context
def del_dns_nameserver(ctx, ip_address_str):
"""Delete static DNS nameserver entry"""

ip_address = to_ip_address(ip_address_str)
if not ip_address:
ctx.fail(f"{ip_address_str} invalid nameserver ip address")

db = ctx.obj['db']

nameservers = get_nameservers(db)
if ip_address not in nameservers:
ctx.fail(f"DNS nameserver {ip_address} is not configured")

db.set_entry('DNS_NAMESERVER', ip_address, None)
4 changes: 4 additions & 0 deletions config/main.py
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,7 @@
from .config_mgmt import ConfigMgmtDPB, ConfigMgmt
from . import mclag
from . import syslog
from . import dns

# mock masic APIs for unit test
try:
Expand Down Expand Up @@ -1198,6 +1199,9 @@ def config(ctx):
# syslog module
config.add_command(syslog.syslog)

# DNS module
config.add_command(dns.dns)

@config.command()
@click.option('-y', '--yes', is_flag=True, callback=_abort_if_false,
expose_value=False, prompt='Existing files will be overwritten, continue?')
Expand Down
57 changes: 56 additions & 1 deletion doc/Command-Reference.md
Original file line number Diff line number Diff line change
Expand Up @@ -194,12 +194,15 @@
* [MACsec config command](#macsec-config-command)
* [MACsec show command](#macsec-show-command)
* [MACsec clear command](#macsec-clear-command)

* [Static DNS Commands](#static-dns-commands)
* [Static DNS config command](#static-dns-config-command)
* [Static DNS show command](#static-dns-show-command)

## Document History

| Version | Modification Date | Details |
| --- | --- | --- |
| v7 | Jun-22-2023 | Add static DNS show and config commands |
| v6 | May-06-2021 | Add SNMP show and config commands |
| v5 | Nov-05-2020 | Add document for console commands |
| v4 | Oct-17-2019 | Unify usage statements and other formatting; Replace tabs with spaces; Modify heading sizes; Fix spelling, grammar and other errors; Fix organization of new commands |
Expand Down Expand Up @@ -12442,3 +12445,55 @@ Clear MACsec counters which is to reset all MACsec counters to ZERO.
```
Go Back To [Beginning of the document](#) or [Beginning of this section](#macsec-commands)
# Static DNS Commands
This sub-section explains the list of the configuration options available for static DNS feature.
## Static DNS config command
- Add static DNS nameserver entry
```
admin@sonic:~$ config dns nameserver add -h
Usage: config dns nameserver add [OPTIONS] <ip_address>
Add static DNS nameserver entry
Options:
-?, -h, --help Show this message and exit.
```
- Delete static DNS nameserver entry
```
admin@sonic:~$ config dns nameserver del -h
Usage: config dns nameserver del [OPTIONS] <ip_address>
Delete static DNS nameserver entry
Options:
-h, -?, --help Show this message and exit.
```
## Static DNS show command
- Show static DNS configuration
```
admin@sonic:~$ show dns nameserver -h
Usage: show dns nameserver [OPTIONS]
Show static DNS configuration
Options:
-h, -?, --help Show this message and exit.
```
```
admin@sonic:~$ show dns nameserver
Nameserver
------------
1.1.1.1
8.8.8.8
```
30 changes: 30 additions & 0 deletions show/dns.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
import click
import utilities_common.cli as clicommon
from natsort import natsorted
from tabulate import tabulate

from swsscommon.swsscommon import ConfigDBConnector
from utilities_common.cli import pass_db


# 'dns' group ("show dns ...")
@click.group(cls=clicommon.AliasedGroup)
@click.pass_context
def dns(ctx):
"""Show details of the static DNS configuration """
config_db = ConfigDBConnector()
config_db.connect()
ctx.obj = {'db': config_db}


# 'nameserver' subcommand ("show dns nameserver")
@dns.command()
@click.pass_context
def nameserver(ctx):
""" Show static DNS configuration """
header = ["Nameserver"]
db = ctx.obj['db']

nameservers = db.get_table('DNS_NAMESERVER')

click.echo(tabulate([(ns,) for ns in nameservers.keys()], header, tablefmt='simple', stralign='right'))
2 changes: 2 additions & 0 deletions show/main.py
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,7 @@
from . import warm_restart
from . import plugins
from . import syslog
from . import dns

# Global Variables
PLATFORM_JSON = 'platform.json'
Expand Down Expand Up @@ -295,6 +296,7 @@ def cli(ctx):
cli.add_command(vxlan.vxlan)
cli.add_command(system_health.system_health)
cli.add_command(warm_restart.warm_restart)
cli.add_command(dns.dns)

# syslog module
cli.add_command(syslog.syslog)
Expand Down
Loading

0 comments on commit dc2945b

Please sign in to comment.