Script IPAM GUI #14364
-
Hello, I have Netbox version 3.6.2 I managed to create a script in Python which works well when I launch it in CLI from the server. Now I'm trying to integrate it into the web part in >Customization>Scripts but it doesn't work. Could someone please advise me? Here is my code that I am trying to integrate into the web part:
|
Beta Was this translation helpful? Give feedback.
Replies: 11 comments 5 replies
-
There are some sample custom scripts you can compare with here: https://github.com/netbox-community/customizations/tree/master/scripts What error do you see? You definitely need to remove the You seem to have some broken lines where a trailing parenthesis is missing, e.g.
...but maybe this is just an artefact of how you're copy-pasting. You also should also not have the code indendent away from the left-hand side, as it appears to be. More generally: you would not normally use the REST API within a custom script, you would use the Django ORM instead. This lets you benefit from proper database features like transactions and rollback - and you wouldn't have all this Stylistically I would avoid Happy debugging! |
Beta Was this translation helpful? Give feedback.
-
Thanks for your response, I'll look into it and post the solution. |
Beta Was this translation helpful? Give feedback.
-
I'm almost there, here's where I am:
But this part doesn't work:
i try with I would like the addresses which are present in netbox and which did not respond to the ping of my script to be passed to "deprecated" unless they are to "reserved" |
Beta Was this translation helpful? Give feedback.
-
I believe that you should call object.full_clean() before object.save() to run any validation steps which are implemented in code, save() only validates at the level of the SQL schema and might not trigger webhooks, changelog entries, custom validation or other business rules (I think). I was looking for the documentation reference in https://demo.netbox.dev/static/docs/customization/custom-scripts/ to confirm the details of my faulty recollection but didn't find it.
—
Mark Tinberg ***@***.***>
Division of Information Technology-Network Services
University of Wisconsin-Madison
…________________________________
From: davidgib01 ***@***.***>
Sent: Thursday, November 30, 2023 9:06 AM
To: netbox-community/netbox ***@***.***>
Cc: Subscribed ***@***.***>
Subject: Re: [netbox-community/netbox] Script IPAM GUI (Discussion #14364)
I'm almost there, here's where I am:
import subprocess
import socket
from ipaddress import IPv4Network
from ipam.models import IPAddress
from ipam.choices import IPAddressStatusChoices
from extras.scripts import Script, IPAddressWithMaskVar
class NetworkScan(Script):
class Meta:
name = "Network IP Scan"
description = "Scans a specified network, updates IPAM in NetBox based on active addresses"
network_to_scan = IPAddressWithMaskVar(
label="Network to Scan",
description="Enter the network to scan (e.g., 192.168.1.0/24)",
required=True
)
def run(self, data, commit):
# Récupérer la plage réseau à scanner depuis la variable paramétrable
network = data['network_to_scan']
# Scanner le réseau
network_range = IPv4Network(network)
output = []
for ip_address in network_range.hosts():
ip_str = str(ip_address)
# Vérifier si l'adresse IP est active en effectuant un ping
ping_cmd = subprocess.run(['ping', '-c', '1', '-W', '1', ip_str], stdout=subprocess.PIPE, stderr=subprocess.PIPE)
try:
ip_obj = IPAddress.objects.get(address=ip_str)
if ping_cmd.returncode == 0:
if ip_obj.status == IPAddressStatusChoices.STATUS_RESERVED or ip_obj.status == IPAddressStatusChoices.STATUS_DEPRECATED:
ip_obj.status = IPAddressStatusChoices.STATUS_ACTIVE
ip_obj.save()
output.append(f"Address {ip_str} is now active.")
# Vérifier si on peut mettre à jour le nom DNS
try:
name = socket.gethostbyaddr(ip_str)[0]
if ip_obj.dns_name != name:
ip_obj.dns_name = name
ip_obj.save()
output.append(f"DNS updated for {ip_str}.")
except socket.error:
pass
elif ping_cmd.returncode != 0 and ip_obj.status == IPAddressStatusChoices.STATUS_ACTIVE:
ip_obj.status = IPAddressStatusChoices.STATUS_DEPRECATED
ip_obj.save()
output.append(f"Address {ip_str} is now deprecated.")
except IPAddress.DoesNotExist:
if ping_cmd.returncode == 0:
ip_obj = IPAddress.objects.create(address=ip_str, status=IPAddressStatusChoices.STATUS_ACTIVE)
output.append(f"Address {ip_str} is created and active.")
# Vérifier si on peut mettre à jour le nom DNS
try:
name = socket.gethostbyaddr(ip_str)[0]
ip_obj.dns_name = name
ip_obj.save()
output.append(f"DNS added for {ip_str}.")
except socket.error:
pass
else:
pass
return "\n".join(output) if output else "No actions performed."
But this part doesn't work:
elif ping_cmd.returncode != 0 and ip_obj.status == IPAddressStatusChoices.STATUS_ACTIVE:
ip_obj.status = IPAddressStatusChoices.STATUS_DEPRECATED
ip_obj.save()
output.append(f"Address {ip_str} is now deprecated.")
i try with else but i th same
i try with elif ping_cmd.returncode = 1 and not work
I would like the addresses which are present in netbox and which did not respond to the ping of my script to be passed to "deprecated" unless they are to "reserved"
—
Reply to this email directly, view it on GitHub<#14364 (comment)>, or unsubscribe<https://github.com/notifications/unsubscribe-auth/AAS7UM3DOHHDPHSK2KXNL53YHCOIRAVCNFSM6AAAAAA76HHE7OVHI2DSMVQWIX3LMV43SRDJONRXK43TNFXW4Q3PNVWWK3TUHM3TOMJYHE2TS>.
You are receiving this because you are subscribed to this thread.Message ID: ***@***.***>
|
Beta Was this translation helpful? Give feedback.
-
I tried both methods but I just got a return of addresses that already exist, here is the code I tried:
in return I have:
either my addresses which are already active and which respond to ping To be sure I tried this:
but I have no changes to my addresses which do not respond to ping and are already present in the IPAM and with this version:
i have:
|
Beta Was this translation helpful? Give feedback.
-
I tried with a simpler script to do what you asked me (well if I understood correctly, I'm sorry but I'm really not good at python) here is the script:
I got this kind of feedback:
But nothing changes. Active addresses which do not respond to ping therefore =1 are not deprecated |
Beta Was this translation helpful? Give feedback.
-
in my example the IPs are modified, because even if it remains from the lab they are IPs used in my work |
Beta Was this translation helpful? Give feedback.
-
Good morning, Thank you for your help, now I can put the IPs which do not respond to ping and which are in the active status of the IPAM in deprecated with this script:
I then wanted to put it in my complete script but it doesn't really work, because it creates duplicate IP addresses for me, I mean it creates IP addresses that already exist in the IPAM.
The code is starting to be really complex for me and as soon as I try to correct it it's worse than before, I tried to separate the two treatments but it doesn't work, I must probably be doing it wrong |
Beta Was this translation helpful? Give feedback.
-
Thank you for your answers, I will take a look on my own. As I told you I don't know python I try to make do with what little I understand. For me an ipam must be able to scan a network at any time, and give me feedback on the IPs which are already in the database, this is the core function of an ipam as do others like PHPipam, solarwinds... My cli script does it without problem so I thought I could adapt it to use it in the GUI part. |
Beta Was this translation helpful? Give feedback.
-
Thanks for your help. I found how to do this by separating the two processes with two separate scripts. |
Beta Was this translation helpful? Give feedback.
-
Here is my final code, I managed to put everything in one script.
Thank you again for your help |
Beta Was this translation helpful? Give feedback.
Here is my final code, I managed to put everything in one script.
I started from scratch with table logic, and the duplicate problem came although when creating new addresses it created them for me in /32 instead of using the mask of the scanned prefix: