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

Duplicate completion candidates for for_each & for collections #170

Open
radeksimko opened this issue Dec 1, 2022 · 1 comment
Open
Assignees
Labels
bug Something isn't working

Comments

@radeksimko
Copy link
Member

radeksimko commented Dec 1, 2022

Currently we return two duplicate completion candidates when completing for_each under a dynamic block, in a block which also has the "standalone" for_each:

Screenshot 2022-12-01 at 12 19 10

resource "aws_ec2_fleet" "name" {
  for_each = ["value"]
  dynamic "spot_options" {
    for_each = # HERE
  }
}

We should only provide one completion candidate.

@radeksimko radeksimko added the bug Something isn't working label Dec 1, 2022
@radeksimko radeksimko self-assigned this Dec 6, 2022
@radeksimko
Copy link
Member Author

radeksimko commented Dec 6, 2022

This appears to be slightly more complicated than I originally expected.

Basically, the problem is that we first gather constraints and then do completion for each constraint individually.

Specifically for the mentioned example, the trigger is that for_each has multiple open constraints

hcl-lang/decoder/decoder.go

Lines 258 to 263 in 9f07ba7

Expr: schema.ExprConstraints{
schema.TraversalExpr{OfType: cty.Map(cty.DynamicPseudoType)},
schema.TraversalExpr{OfType: cty.Set(cty.String)},
schema.LiteralTypeExpr{Type: cty.Map(cty.DynamicPseudoType)},
schema.LiteralTypeExpr{Type: cty.Set(cty.String)},
},

and these are compared against the reference target of (also open) type cty.Dynamic results in the two duplicate matches.

constraints, editRng := constraintsAtPos(attr.Expr, ExprConstraints(schema.Expr), pos)
candidates := lang.NewCandidates()
candidates.IsComplete = true
if len(schema.CompletionHooks) > 0 {
candidates.IsComplete = false
candidates.List = append(candidates.List, d.candidatesFromHooks(ctx, attr, schema, outerBodyRng, pos)...)
}
count := len(candidates.List)
if len(constraints) > 0 && uint(count) < d.maxCandidates {
prefixRng := editRng
prefixRng.End = pos
for _, cons := range constraints {
if uint(count) >= d.maxCandidates {
return candidates, nil
}
candidates.List = append(candidates.List, d.constraintToCandidates(ctx, cons, attr, outerBodyRng, prefixRng, editRng)...)
count++
}
}

They both represent the same reference target (i.e. reference target collection works as expected), but first is a match against cty.Map(cty.DynamicPseudoType) and the second is a match against cty.Set(cty.String).

@radeksimko radeksimko changed the title Duplicate each.value completion for dynamic for_each Duplicate completion candidates for for_each & for collections Jan 24, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working
Projects
None yet
Development

No branches or pull requests

1 participant