Skip to content

Conversation

@eduardiazf
Copy link
Contributor

@eduardiazf eduardiazf commented Oct 23, 2025

Summary

Add a new client method to retrieve microgrid electrical components connections. For this a new ComponentConnection class is introduced. The CLI is also extended to add a command to list component-connections, for example: assets-cli component-connections 123 --source 5 --source 6 --destination 10

Resources

@eduardiazf eduardiazf requested review from a team as code owners October 23, 2025 08:13
@eduardiazf eduardiazf requested a review from Marenz October 23, 2025 08:13
@github-actions github-actions bot added the part:docs Affects the documentation label Oct 23, 2025
@eduardiazf eduardiazf added the cmd:skip-release-notes It is not necessary to update release notes for this PR label Oct 23, 2025
@github-actions github-actions bot added the part:tests Affects the unit, integration and performance (benchmarks) tests label Oct 23, 2025
@eduardiazf eduardiazf force-pushed the feat/electrical-component-connections branch 4 times, most recently from 4f8d31b to 97f65fc Compare October 23, 2025 10:04
Copy link
Contributor

@llucax llucax left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM, but I would improve the API as proposed. With this change not only it can accept lists of IDs, it can also accept tuples, sets, or any iterable, like dict.values() or dict.keys().

@eduardiazf eduardiazf force-pushed the feat/electrical-component-connections branch from 0b87c3a to 950965d Compare October 27, 2025 16:34

return [
component_connection_from_proto(connection)
for connection in response.connections
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

IIUC this would also collect Nones, is this intended?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

True, good catch. I have this in the microgrid API:

        return (
            conn
            for conn in map(
                component_connection_from_proto,
                response.electrical_component_connections,
            )
            if conn is not None
        )

An a more functional alternative 😄

        return list(
            map(
                component_connection_from_proto,
                filter(bool, response.electrical_component_connections),
            )
        )

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks, good catch.

)
else:
minor_issues.append(
"missing operational lifetime, considering it always operational",
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this an issue or a valid case?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In the microgrid API is valid, and for now it is always returned without a lifetime, but maybe this needs to change in the future, not sure.

We should probably document in the protobuf files what to expect though. Some of these issues I added them only to be notified if they happened or not because I couldn't find a strict definition.

Once we have a clear definition, we might want to remove them (for example, if it is a defined thing that a missing operational lifetime can happen and then the meaning is it is always operational, we don't need to be whining about it when we see it happen, it will be just noise.

@tiyash-basu-frequenz FYI

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is already documented in the latest API version: https://github.com/frequenz-floss/frequenz-api-common/blob/300bcb4296d679faa3b2aec33e7ea3d461d90beb/proto/frequenz/api/common/v1alpha8/microgrid/lifetime.proto#L21-L30

Therefore, the phrase "missing operational lifetime, considering it always operational" is technically correct. I do not think it should be classified as an issue though.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

is there a reason it is this concise? It's nice to reduce cognitive load of messages, but this is verging on being easily misunderstood.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Therefore, the phrase "missing operational lifetime, considering it always operational" is technically correct. I do not think it should be classified as an issue though.

Yeah, it is is expected behavior it is not an issue and we should remove it, as it will just spam the logs. I will remove it from the microgrid API client too.

is there a reason it is this concise? It's nice to reduce cognitive load of messages, but this is verging on being easily misunderstood.

What are you talking about exactly, what's concise?

except ValueError as exc:
major_issues.append(
f"invalid operational lifetime ({exc}), considering it as missing "
"(i.e. always operational)",
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we want to consider it as operational? If so, I don't see a way how we can detect these cases programatically. Maybe we add a way to check how many major issues were found to understand how reliable the connections are.

Copy link
Contributor

@llucax llucax Oct 28, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we want to consider it as operational?

Good question, this was done with the microgrid API in mind, where right now everything is operational all the time basically, but maybe it is not safe to assume it operational.

If so, I don't see a way how we can detect these cases programatically. Maybe we add a way to check how many major issues were found to understand how reliable the connections are.

The question for me is if there is anything we can do (and want to do) programatically. I think in general an error here is a misconfiguration, and the best we can do is tell the user (in this case an error should be logged) so they can fix it.

Then we probably need to try to recover as best as possible, so there is the question if we ignore the connection (consider it non-operational) or we add it (assume it is operational). Both cases will be wrong some times and right some other times, so I guess there is no good answer for this, but maybe ignoring it is more correct, as if one field is wrong, maybe other fields are wrong too.

Or back to your question, what else do you think it can be done by a client if the wrong connection would be passed to the user of the client? Do you envision clients applying some heuristics to try to do a better guess on how to treat a faulty connection?

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See here.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I agree that it makes sense to define missing as always operational. What I am not sure about is whether an invalid lifetime should be accepted and treated as missing. Invalid indicates a user error to me.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Or back to your question, what else do you think it can be done by a client if the wrong connection would be passed to the user of the client? Do you envision clients applying some heuristics to try to do a better guess on how to treat a faulty connection?

I guess my main point would be to have a way to validate whether the graph could be parsed without any issues or not, because atm we only have a warning message. It depends on the use-case if you prefer to have reliable data or better some data. Also you could try to recover it or have fallbacks in place if a problem was detected.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think the graph will be constructed from the UI, and there will be no way to construct it in an invalid way, so I guess this code is mostly about really weird situations, memory corruption or something like this, so I think as long as we log an error (I think major issues are logged as warnings now, we might want to reconsider that, or have a separate critical_issues that are logged as errors), it doesn't matter much how we deal with it.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That said, probably if part of a message is broken it would make sense to ignore the whole message instead try to guess fix it.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think you removed the wrong "issue", this issue should still be checked and reported (I think it would probably be better to just skip the whole connection object, so return None, if the operational lifetime is invalid. If it is missing, then that's OK, so that issue should not be reported.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If there is no supported way to construct invalid graphs and it's only weird cases, are these then valid at all? If not, why not just raise an exception in this case?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I didn't understand the last comment. Maybe we could meet to quickly discuss this.

@Marenz
Copy link
Contributor

Marenz commented Oct 29, 2025

Hmm a bit meta but it I found it a bit cumbersome to read every time "This commit introduced/updates/.." it feels very redundant. Nothing against AI generated if that is the case, but maybe ask it to cut it down a bit? :)

@llucax
Copy link
Contributor

llucax commented Oct 31, 2025

Hmm a bit meta but it I found it a bit cumbersome to read every time "This commit introduced/updates/.." it feels very redundant. Nothing against AI generated if that is the case, but maybe ask it to cut it down a bit? :)

I send this, I also find the PR description too verbose, to the point that my brain unconsciously tries to skip it. For me something more succinct would be more useful, like:

Add a new client method to retrieve microgrid electrical components connections. For this a new ComponentConnection class is introduced. The CLI is also extended to add a command to list component-connections, for example: assets-cli component-connections 123 --source 5 --source 6 --destination 10

I think the rest of the details can be read from the PR itself.

Maybe you can tweak the instructions to generate PRs/commit messages, which makes me think that maybe it is time to start providing custom instructions, as I guess we can all benefit from having good instructions to produce useful PR/commit messages.

@eduardiazf eduardiazf force-pushed the feat/electrical-component-connections branch from 9e75c3e to b5e92be Compare November 3, 2025 09:48
@github-actions github-actions bot added the part:tooling Affects the development tooling (CI, deployment, dependency management, etc.) label Nov 3, 2025
@eduardiazf eduardiazf force-pushed the feat/electrical-component-connections branch 2 times, most recently from 8c13c17 to 9c89de1 Compare November 3, 2025 10:43
except ValueError as exc:
major_issues.append(
f"invalid operational lifetime ({exc}), considering it as missing "
"(i.e. always operational)",
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think you removed the wrong "issue", this issue should still be checked and reported (I think it would probably be better to just skip the whole connection object, so return None, if the operational lifetime is invalid. If it is missing, then that's OK, so that issue should not be reported.

@eduardiazf eduardiazf force-pushed the feat/electrical-component-connections branch 2 times, most recently from daa19b6 to 0045825 Compare November 3, 2025 16:56
Comment on lines 54 to 55
operational_lifetime: Lifetime | None = None
"""The operational lifetime of the connection."""
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This should not accept None, otherwise we need to do special casing here, is better to keep it as it was before, that a Lifetime() is just always operational. Also in user code, if users need to access operational lifetime directly they will need to deal with None as a possibility now.

Suggested change
operational_lifetime: Lifetime | None = None
"""The operational lifetime of the connection."""
operational_lifetime: Lifetime
"""The operational lifetime of the connection."""

Comment on lines 64 to 65
if self.operational_lifetime is None:
return True
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
if self.operational_lifetime is None:
return True

"""Get the operational lifetime from a protobuf message."""
if message.HasField("operational_lifetime"):
return lifetime_from_proto(message.operational_lifetime)
return None
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
return None
return Lifetime()

"""Create a `ComponentConnection` from a protobuf message collecting issues.
This function is useful when you want to collect issues during the parsing
of multiple connections, rather than logging them immediately.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What is actually the motivation for collecting those messages instead of logging them immediately? I wonder why we need this additional complexity.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Flexibility. Doing this actually makes supporting your use case pretty trivial. The client could just return the issues instead of logging them. This code is supposed to go to client-common.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If this is the idea, then these issues are probably better tracked via enums instead of strings. If you prefer to not do it in this PR then it should come in the next one. Because in the current form we cannot use this endpoint in our trading app.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We can add it in the next one because this implementation should be moved to client-common.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sounds good!

@eduardiazf eduardiazf force-pushed the feat/electrical-component-connections branch from 0045825 to 06dd9d7 Compare November 4, 2025 14:30
dependabot bot and others added 5 commits November 4, 2025 15:30
Bumps [actions/labeler](https://github.com/actions/labeler) from 5.0.0 to 6.0.1.
- [Release notes](https://github.com/actions/labeler/releases)
- [Commits](actions/labeler@8558fd7...634933e)

---
updated-dependencies:
- dependency-name: actions/labeler
  dependency-version: 6.0.1
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <[email protected]>
Signed-off-by: eduardiazf <[email protected]>
Bumps the compatible group with 2 updates: [frequenz-floss/gh-action-nox](https://github.com/frequenz-floss/gh-action-nox) and [frequenz-floss/gh-action-setup-python-with-deps](https://github.com/frequenz-floss/gh-action-setup-python-with-deps).

Updates `frequenz-floss/gh-action-nox` from 1.0.0 to 1.0.1
- [Release notes](https://github.com/frequenz-floss/gh-action-nox/releases)
- [Commits](frequenz-floss/gh-action-nox@v1.0.0...v1.0.1)

Updates `frequenz-floss/gh-action-setup-python-with-deps` from 1.0.0 to 1.0.1
- [Release notes](https://github.com/frequenz-floss/gh-action-setup-python-with-deps/releases)
- [Commits](frequenz-floss/gh-action-setup-python-with-deps@v1.0.0...v1.0.1)

---
updated-dependencies:
- dependency-name: frequenz-floss/gh-action-nox
  dependency-version: 1.0.1
  dependency-type: direct:production
  update-type: version-update:semver-patch
  dependency-group: compatible
- dependency-name: frequenz-floss/gh-action-setup-python-with-deps
  dependency-version: 1.0.1
  dependency-type: direct:production
  update-type: version-update:semver-patch
  dependency-group: compatible
...

Signed-off-by: dependabot[bot] <[email protected]>
Signed-off-by: eduardiazf <[email protected]>
Add a new client method to retrieve microgrid electrical components connections.

Signed-off-by: eduardiazf <[email protected]>
Adds tests for list_microgrid_electrical_component_connections, covering success, empty results, and error cases to improve reliability.

Signed-off-by: eduardiazf <[email protected]>
Updates list_microgrid_electrical_component_connections to accept Iterable[int] for source/destination component IDs.

Signed-off-by: eduardiazf <[email protected]>
…ctions

To use map/filter for cleaner logic and to skip invalid connections.

Signed-off-by: eduardiazf <[email protected]>
missing operational lifetime, considering it always operational

Signed-off-by: eduardiazf <[email protected]>
@eduardiazf eduardiazf force-pushed the feat/electrical-component-connections branch from 06dd9d7 to 0fa7382 Compare November 4, 2025 14:30
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

cmd:skip-release-notes It is not necessary to update release notes for this PR part:docs Affects the documentation part:tests Affects the unit, integration and performance (benchmarks) tests part:tooling Affects the development tooling (CI, deployment, dependency management, etc.)

Projects

None yet

Development

Successfully merging this pull request may close these issues.

6 participants