diff --git a/deployment/check/netbox-ips/nixosTest.nix b/deployment/check/netbox-ips/nixosTest.nix index 78cfb327..8e8e9aae 100644 --- a/deployment/check/netbox-ips/nixosTest.nix +++ b/deployment/check/netbox-ips/nixosTest.nix @@ -14,9 +14,20 @@ let (pkgs.callPackage ../../run { inherit sources; }) + tf-netbox-cluster-type + tf-netbox-cluster tf-netbox-store-ips tf-netbox-get-ip ; + netbox-cluster-type = evalOption tf-netbox-cluster-type { + httpBackend = tfBackend "proxmox-test/cluster-type"; + name = "test-type"; + }; + netbox-cluster = evalOption tf-netbox-cluster { + httpBackend = tfBackend "proxmox-test/cluster"; + cluster_type_name = "test-type"; + name = "cluster"; + }; netbox-store-ips = evalOption tf-netbox-store-ips { httpBackend = tfBackend "proxmox-test/store-ips"; startAddress = "192.168.10.236/24"; @@ -24,6 +35,9 @@ let }; netbox-get-ip = evalOption tf-netbox-get-ip { httpBackend = tfBackend "proxmox-test/get-ip"; + cluster_name = "cluster"; + vm_name = "vm"; + interface_name = "eth"; }; netboxUser = "netbox"; netboxPassword = "netbox"; @@ -47,6 +61,8 @@ in environment.systemPackages = [ pkgs.jq + (pkgs.callPackage ../../run/tf-netbox-cluster-type/tf.nix { }) + (pkgs.callPackage ../../run/tf-netbox-cluster/tf.nix { }) (pkgs.callPackage ../../run/tf-netbox-store-ips/tf.nix { }) (pkgs.callPackage ../../run/tf-netbox-get-ip/tf.nix { }) ]; @@ -76,14 +92,24 @@ in netbox_token = deployer.succeed(""" curl -X POST -H "Content-Type: application/json" -H "Accept: application/json" http://localhost:8001/api/users/tokens/provision/ --data '{"username":"${netboxUser}","password":"${netboxPassword}"}' | jq -r .key """).strip() - ip_range_id = deployer.succeed(f""" + netbox_vars = f""" export NETBOX_SERVER_URL="localhost:8001" export NETBOX_API_TOKEN="{netbox_token}" + """ + deployer.succeed(f""" + {netbox_vars} + ${lib.getExe netbox-cluster-type.run} + """) + cluster_id = deployer.succeed(f""" + {netbox_vars} + ${lib.getExe netbox-cluster.run} | jq -r '.id.value' + """).strip() + ip_range_id = deployer.succeed(f""" + {netbox_vars} ${lib.getExe netbox-store-ips.run} | jq -r '.id.value' """).strip() ipv4 = deployer.succeed(f""" - export NETBOX_SERVER_URL="localhost:8001" - export NETBOX_API_TOKEN="{netbox_token}" + {netbox_vars} export TF_VAR_ip_range_id={ip_range_id} ${lib.getExe netbox-get-ip.run} | jq -r '.ipv4.value' """).strip() diff --git a/deployment/run/default.nix b/deployment/run/default.nix index f1339c1d..e1e68f8d 100644 --- a/deployment/run/default.nix +++ b/deployment/run/default.nix @@ -588,6 +588,127 @@ in } ); }; + tf-netbox-cluster-type = mkOption { + description = "A cluster type represents a technology or mechanism by which a cluster is formed. For example, you might create a cluster type named 'VMware vSphere' for a locally hosted cluster or 'DigitalOcean NYC3' for one hosted by a cloud provider."; + type = submodule ( + { config, ... }: + { + options = { + inherit httpBackend; + name = mkOption { + description = ""; + type = str; + }; + slug = mkOption { + description = ""; + type = nullOr str; + default = null; + }; + run = mkOption { + type = types.package; + readOnly = true; + default = tfApply { + inherit (config) httpBackend; + directory = "tf-netbox-cluster-type"; + environment = { + inherit (config) + name + slug + ; + }; + }; + }; + }; + } + ); + }; + tf-netbox-cluster = mkOption { + description = "A cluster is a logical grouping of physical resources within which virtual machines run. Physical devices may be associated with clusters as hosts. This allows users to track on which host(s) a particular virtual machine may reside."; + type = submodule ( + { config, ... }: + { + options = { + inherit httpBackend; + cluster_type_name = mkOption { + description = ""; + type = str; + }; + name = mkOption { + description = ""; + type = str; + }; + cluster_group_id = mkOption { + description = ""; + type = nullOr int; + default = null; + }; + comments = mkOption { + description = ""; + type = str; + default = ""; + }; + description = mkOption { + description = ""; + type = str; + default = ""; + }; + location_id = mkOption { + description = "Conflicts with site_id, site_group_id and region_id."; + type = nullOr int; + default = null; + }; + region_id = mkOption { + description = "Conflicts with location_id, site_id and site_group_id."; + type = nullOr int; + default = null; + }; + site_group_id = mkOption { + description = "Conflicts with location_id, site_id and region_id."; + type = nullOr int; + default = null; + }; + site_id = mkOption { + description = "Conflicts with location_id, site_group_id and region_id."; + type = nullOr int; + default = null; + }; + tags = mkOption { + description = ""; + type = types.listOf str; + default = [ ]; + }; + tenant_id = mkOption { + description = ""; + type = nullOr int; + default = null; + }; + run = mkOption { + type = types.package; + readOnly = true; + default = tfApply { + inherit (config) httpBackend; + directory = "tf-netbox-cluster"; + environment = { + inherit (config) + cluster_type_name + name + cluster_group_id + comments + description + location_id + region_id + site_group_id + site_id + tags + tenant_id + ; + }; + }; + }; + }; + } + ); + }; tf-netbox-store-ips = mkOption { description = "Store a range of IPs in a Netbox instance."; type = submodule ( @@ -636,6 +757,18 @@ in { options = { inherit httpBackend; + cluster_name = mkOption { + description = ""; + type = str; + }; + vm_name = mkOption { + description = ""; + type = str; + }; + interface_name = mkOption { + description = ""; + type = str; + }; run = mkOption { type = types.package; readOnly = true; @@ -643,6 +776,11 @@ in inherit (config) httpBackend; directory = "tf-netbox-get-ip"; environment = { + inherit (config) + cluster_name + vm_name + interface_name + ; }; }; }; diff --git a/deployment/run/tf-netbox-cluster-type/main.tf b/deployment/run/tf-netbox-cluster-type/main.tf new file mode 100644 index 00000000..cb6be963 --- /dev/null +++ b/deployment/run/tf-netbox-cluster-type/main.tf @@ -0,0 +1,19 @@ +terraform { + required_providers { + netbox = { + source = "e-breuninger/netbox" + version = "= 5.0.0" + } + } + backend "http" { + } +} + +resource "netbox_cluster_type" "type" { + name = var.name + slug = var.slug +} + +output "id" { + value = netbox_cluster_type.type.id +} diff --git a/deployment/run/tf-netbox-cluster-type/tf.nix b/deployment/run/tf-netbox-cluster-type/tf.nix new file mode 100644 index 00000000..ec79dab2 --- /dev/null +++ b/deployment/run/tf-netbox-cluster-type/tf.nix @@ -0,0 +1,24 @@ +{ + pkgs, +}: +let + sources = import ../../../npins; + mkProvider = + args: + pkgs.terraform-providers.mkProvider ( + { mkProviderFetcher = { repo, ... }: sources.${repo}; } // args + ); +in +(pkgs.callPackage ../../tf.nix { }).withPlugins (_: [ + (mkProvider { + owner = "e-breuninger"; + repo = "terraform-provider-netbox"; + rev = "v5.0.0"; + spdx = "MPL-2.0"; + # hash = "sha256-iCaCt8ZbkxCk43QEyj3PeHYuKPCPVU2oQ78aumH/l6k="; + hash = null; + vendorHash = "sha256-Q3H/6mpkWn1Gw0NRMtKtkBRGHjPJZGBFdGwfalyQ4Z0="; + homepage = "https://registry.terraform.io/providers/e-breuninger/netbox"; + provider-source-address = "registry.opentofu.org/e-breuninger/netbox"; + }) +]) diff --git a/deployment/run/tf-netbox-cluster-type/variables.tf b/deployment/run/tf-netbox-cluster-type/variables.tf new file mode 100644 index 00000000..7c3211df --- /dev/null +++ b/deployment/run/tf-netbox-cluster-type/variables.tf @@ -0,0 +1,10 @@ +variable "name" { + description = "" + type = string +} + +variable "slug" { + description = "" + type = string + default = null +} diff --git a/deployment/run/tf-netbox-cluster/main.tf b/deployment/run/tf-netbox-cluster/main.tf new file mode 100644 index 00000000..ee9de744 --- /dev/null +++ b/deployment/run/tf-netbox-cluster/main.tf @@ -0,0 +1,32 @@ +terraform { + required_providers { + netbox = { + source = "e-breuninger/netbox" + version = "= 5.0.0" + } + } + backend "http" { + } +} + +data "netbox_cluster_type" "type" { + name = var.cluster_type_name +} + +resource "netbox_cluster" "cluster" { + cluster_type_id = data.netbox_cluster_type.type.id + name = var.name + cluster_group_id = var.cluster_group_id + comments = var.comments + description = var.description + location_id = var.location_id + region_id = var.region_id + site_group_id = var.site_group_id + site_id = var.site_id + tags = var.tags + tenant_id = var.tenant_id +} + +output "id" { + value = netbox_cluster.cluster.id +} diff --git a/deployment/run/tf-netbox-cluster/tf.nix b/deployment/run/tf-netbox-cluster/tf.nix new file mode 100644 index 00000000..ec79dab2 --- /dev/null +++ b/deployment/run/tf-netbox-cluster/tf.nix @@ -0,0 +1,24 @@ +{ + pkgs, +}: +let + sources = import ../../../npins; + mkProvider = + args: + pkgs.terraform-providers.mkProvider ( + { mkProviderFetcher = { repo, ... }: sources.${repo}; } // args + ); +in +(pkgs.callPackage ../../tf.nix { }).withPlugins (_: [ + (mkProvider { + owner = "e-breuninger"; + repo = "terraform-provider-netbox"; + rev = "v5.0.0"; + spdx = "MPL-2.0"; + # hash = "sha256-iCaCt8ZbkxCk43QEyj3PeHYuKPCPVU2oQ78aumH/l6k="; + hash = null; + vendorHash = "sha256-Q3H/6mpkWn1Gw0NRMtKtkBRGHjPJZGBFdGwfalyQ4Z0="; + homepage = "https://registry.terraform.io/providers/e-breuninger/netbox"; + provider-source-address = "registry.opentofu.org/e-breuninger/netbox"; + }) +]) diff --git a/deployment/run/tf-netbox-cluster/variables.tf b/deployment/run/tf-netbox-cluster/variables.tf new file mode 100644 index 00000000..80d01b31 --- /dev/null +++ b/deployment/run/tf-netbox-cluster/variables.tf @@ -0,0 +1,63 @@ +variable "cluster_type_name" { + description = "" + type = string +} + +variable "name" { + description = "" + type = string +} + +variable "cluster_group_id" { + description = "" + type = number + default = null +} + +variable "comments" { + description = "" + type = string + default = "" +} + +variable "description" { + description = "" + type = string + default = "" +} + +variable "location_id" { + description = "Conflicts with site_id, site_group_id and region_id." + type = number + default = null +} + +variable "region_id" { + description = "Conflicts with location_id, site_id and site_group_id." + type = number + default = null +} + +variable "site_group_id" { + description = "Conflicts with location_id, site_id and region_id." + type = number + default = null +} + +variable "site_id" { + description = "Conflicts with location_id, site_group_id and region_id." + type = number + default = null +} + +variable "tags" { + description = "" + type = set(string) + default = [] +} + +variable "tenant_id" { + description = "" + type = number + default = null +} diff --git a/deployment/run/tf-netbox-get-ip/main.tf b/deployment/run/tf-netbox-get-ip/main.tf index 24f8eb9e..a5ac35d1 100644 --- a/deployment/run/tf-netbox-get-ip/main.tf +++ b/deployment/run/tf-netbox-get-ip/main.tf @@ -9,7 +9,23 @@ terraform { } } +data "netbox_cluster" "cluster" { + name = var.cluster_name +} + +resource "netbox_virtual_machine" "vm" { + cluster_id = data.netbox_cluster.cluster.id + name = var.vm_name +} + +resource "netbox_interface" "interface" { + virtual_machine_id = netbox_virtual_machine.vm.id + name = var.interface_name +} + resource "netbox_available_ip_address" "get_ip" { + object_type = "virtualization.vminterface" + interface_id = netbox_interface.interface.id prefix_id = var.prefix_id ip_range_id = var.ip_range_id } diff --git a/deployment/run/tf-netbox-get-ip/variables.tf b/deployment/run/tf-netbox-get-ip/variables.tf index d46e238c..e8b4291d 100644 --- a/deployment/run/tf-netbox-get-ip/variables.tf +++ b/deployment/run/tf-netbox-get-ip/variables.tf @@ -9,3 +9,18 @@ variable "ip_range_id" { type = number default = null } + +variable "cluster_name" { + description = "" + type = string +} + +variable "vm_name" { + description = "" + type = string +} + +variable "interface_name" { + description = "" + type = string +}