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

Add switch port aggregation support #142

Closed
Cellivar opened this issue May 26, 2021 · 2 comments · Fixed by #182
Closed

Add switch port aggregation support #142

Cellivar opened this issue May 26, 2021 · 2 comments · Fixed by #182
Assignees
Labels
enhancement New feature or request

Comments

@Cellivar
Copy link

Cellivar commented May 26, 2021

We have a US-24-POE switch that uses link aggregation for a couple of devices. It'd be very nice to be able to configure that setup as part of Terraform, however presently that doesn't appear to work.

I hit "apply" in a similar configuration to the screenshot below, this is the example request that was set to the UDM-P that I use as my controller:

URI: https://unifi.my.network/proxy/network/api/s/default/rest/device/5fa75def5318bd035aa209bd
METHOD: PUT
{
    "port_overrides": [
        {
            "port_idx": 11,
            "portconf_id": "5f3d11ec5318bd051a842c6e",
            "port_security_mac_address": [],
            "op_mode": "aggregate",
            "aggregate_num_ports": 2
        },
        {
            "port_idx": 9,
            "portconf_id": "5f3d11ec5318bd051a842c6e",
            "op_mode": "aggregate",
            "port_security_mac_address": [],
            "aggregate_num_ports": 2
        }
    ]
}

On my machine the portconf_id there is the default "All" configuration as seen here from my terraform state:

data "unifi_port_profile" "all" {
    id   = "5f3d11ec5318bd051a842c6e"
    name = "All"
    site = "default"
}

And the device in the request URI is the US-24-POE, also as seen from my terraform state:

# unifi_device.us_24_poe:
resource "unifi_device" "us_24_poe" {
    disabled = false
    id       = "5fa75def5318bd035aa209bd"
    mac      = "de:vi:ce:ma:cn:um"
    site     = "default"

    port_override {
        number          = 11
        port_profile_id = "5f3d11ec5318bd051a842c6e"
    }
    port_override {
        number          = 9
        port_profile_id = "5f3d11ec5318bd051a842c6e"
    }
}

This doesn't seem too difficult to add, alas I don't know golang very well so I'm not of much use here :)

Let me know if you need any additional details.

Screenshot of relevant configuration:

image

@paultyng paultyng added the enhancement New feature or request label Jun 1, 2021
@paultyng
Copy link
Owner

paultyng commented Jun 1, 2021

I have a USW-24-PoE as well and I didn't realize this was possible 😅, I'll have to poke around to see what the API request looks like.

@paultyng paultyng self-assigned this Sep 13, 2021
paultyng added a commit that referenced this issue Sep 13, 2021
@paultyng
Copy link
Owner

Opened #182 to support this. Let me know if it works for you. I can't easily test this without hardware it seems, still trying to figure that out.

paultyng added a commit that referenced this issue Sep 13, 2021
joshuaspence added a commit that referenced this issue Mar 8, 2023
joshuaspence added a commit that referenced this issue Mar 8, 2023
* Add support for port aggregation

Fixes #142

* Return `*unifi.Device` from `allocateDevice`

* Merge `TestAccDevice_switch_portOverrides` and `TestAccDevice_remove_portOverrides`

* Add tests

Note that only switches with a Broadcom, Microsemi or Nephos chipset support both port mirroring and port aggregation.

```java
package com.ubnt.data;

public class Device extends X implements Sanitizable
{

  // ...

  public int getMaxMirrorSession() {
    int n = 0;
    if (this.getModel() == Model.\u00f8\u00f50000) {
      n = 2;
    }
    else if (this.isBroadcomSwitch() || this.isMicrosemiSwitch() || this.isMediaTekSwitch() || this.isNephosSwitch()) {
      n = 1;
    }
    return this.thisforObject().getInt("max_mirror_sessions", n);
  }

  public int getMaxAggregation() {
    int n = 0;
    if (this.isBroadcomSwitch() || this.isMicrosemiSwitch() || this.isNephosSwitch()) {
      n = 6;
    }
    return this.thisforObject().getInt("max_aggregate_sessions", n);
  }

  // ...

  public boolean isBroadcomSwitch() {
    final Model model = this.getModel();
    return model.getChipset().typeOf(Chipset.\u00f400000) && model.getType() == DeviceType.if;
  }

  public boolean isMicrosemiSwitch() {
    final Model model = this.getModel();
    return model.getChipset().typeOf(Chipset.o00000) && model.getType() == DeviceType.if;
  }

  public boolean isMediaTekSwitch() {
    final Model model = this.getModel();
    return model.getChipset().typeOf(Chipset.\u00d3O0000) && model.getType() == DeviceType.if;
  }

  public boolean isNephosSwitch() {
    final Model model = this.getModel();
    return model.getChipset().typeOf(Chipset.\u00d5O0000) && model.getType() == DeviceType.if;
  }

  // ...

}
```

To extract the list of models that use one of these chipsets I used the following script (executed as `java --class-path path/to/ace.jar main.java`):

```java
import com.ubnt.data.Model;

class UniFiModels {
  public static void main(String[] args) {
    /*
    for (Model model : Model.values()) {
      System.out.printf(
          "Model = %s\nSKU = %s\nType = %s\nFeatures = %s\nChipset = %s\nSysId = %s\nPortNum = %s\n\n",
          model,
          model.getSku(),
          model.getType(),
          model.getFeatures(),
          model.getChipset(),
          model.getSysId(),
          model.getPortNum());
    }
    */

    for (Model model : Model.values()) {
      System.out.printf("%s: %s (%s)\n", model.getChipset(), model, model.getSku());
    }
  }
}

```

---------

Co-authored-by: Joshua Spence <josh@spence.com.au>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request
Projects
None yet
Development

Successfully merging a pull request may close this issue.

2 participants