Skip to content

bug: Using convert_query_response only converts nodes one level deep #389

@ogenstad

Description

@ogenstad

Component

Python SDK

Infrahub SDK version

1.12.0

Current Behavior

When using convert_query_response with transforms and generators only nodes one level deep within the response are converted to InfrahubNode objects. It's because the InfrahubNode._process_relationships() method isn't recursive.

Expected Behavior

Given a query like this:

query MyQuery {
  InfraDevice(name__value: "atl1-edge1") {
    edges {
      node {
        __typename
        id
        name {
          value
        }
        interfaces {
          edges {
            node {
              id
              __typename
              ... on InfraInterfaceL3 {
                name {
                  value
                }
                ip_addresses {
                  edges {
                    node {
                      id
                      __typename
                      address {
                        value
                      }
                    }
                  }
                }
              }
            }
          }
        }
      }
    }
  }
}

We currently create Infrahub node objects for "InfraDevice" and any of the Infra interfaces, however we don't create nodes for the ip addresses.

Steps to Reproduce

  1. Load an instance of Infrahub with the demo schema and data
  2. Run a script like this:
from infrahub_sdk import InfrahubClient
from infrahub_sdk.graphql import Query
from infrahub_sdk.node import InfrahubNode

client = InfrahubClient()

q = """
query MyQuery {
  InfraDevice(name__value: "atl1-edge1") {
    edges {
      node {
        __typename
        id
        name {
          value
        }
        interfaces {
          edges {
            node {
              id
              __typename
              ... on InfraInterfaceL3 {
                name {
                  value
                }
                ip_addresses {
                  edges {
                    node {
                      id
                      __typename
                      address {
                        value
                      }
                    }
                  }
                }
              }
            }
          }
        }
      }
    }
  }
}
"""

response = await client.execute_graphql(query=q)


edges = response["InfraDevice"]["edges"] or []

entries = []
related = []
for edge in edges:
    node = await InfrahubNode.from_graphql(client=client, branch="main", data=edge)
    entries.append(node)
    await node._process_relationships(node_data=edge, branch="main", related_nodes=related)


for entry in entries + related:
    if entry.id:
        client.store.set(node=entry)

Now note that the ip address objects won't exist within the related list or within the client store.

Additional Information

No response

Metadata

Metadata

Assignees

Labels

type/bugSomething isn't working as expected

Type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions