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
Fix completion crash for the SCCM provider #20915
base: master
Are you sure you want to change the base?
Conversation
…letionCompleters.cs Co-authored-by: Ilya <darpa@yandex.ru>
| // but some providers don't have it (like the Variable provider) | ||
| // So we use a substring of "PSPath" instead. | ||
| string childName = psObject.PSPath ?? string.Empty; | ||
| if (((PSObject)psObject).BaseObject is string result) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Have you considered PSObject.Base(psObject)?
Do we really need the cast?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
No I didn't consider that. I've looked at the Base method and it does some unnecessary checks that makes it slower than just casting it. And I think the cast is needed because how else would I check that it's a string?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
how else would I check that it's a string?
psObject is dynamic.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Elaborate please, I don't understand how the code would be written. Are you saying that: psObject is string result (where psObject is the variable name) would work the same way as the current code? My understanding is that I need to unwrap the PSObject before I can do the type check.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think if ((psObject.BaseObject is string result) should work because old code was string childName = psObject.PSPath ?? string.Empty; - without cast.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I just tested it and it does not seem to work. I guess it's because the dynamic implementation on PSObject only looks for members on the unwrapped object with no fallback to the original PSObject properties. My psObject is string result idea also doesn't work.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I just tested it and it does not seem to work.
I wonder that string childName = psObject.PSPath ?? string.Empty; work. Exactly works? Or it is bug?
Maybe follow works:
object tmp = psObject.BaseObject;
if (tmp is string result)
...I don't understand difference between psObject.PSPath and psObject.BaseObject. PSPath says that psObject is always PSObject. Why do we define it as dynamic?
I tend to think that this code either doesn't work correctly or it's too gimmicky and at the very least needs refactoring.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I wonder that string childName = psObject.PSPath ?? string.Empty; work. Exactly works? Or it is bug?
The null check can probably be removed. I don't remember why I put it there but if it's null then there's something wrong so it's better to just throw.
I don't understand difference between psObject.PSPath and psObject.BaseObject. PSPath says that psObject is always PSObject. Why do we define it as dynamic?
It's so we can access the dynamic members more easily. We could make it a PSObject and use the appropriate properties/methods to access those members but the old code used dynamic so I figured it was fine to use here during the rewrite.
|
@MartinGC94 #20815 was already merged, can you please rebase this PR against the master branch, so it's easier to see the changes on top? |
|
@MartinGC94 Thanks for rebasing. A question before moving on to review the code: are the changes from #20815 still relevant? I assume those changes are relevant to the fix and should be kept but want you to confirm. |
|
@daxian-dbw They are not. I tried reverting them with ab72ca7 but I don't see that in the changes overview https://github.com/PowerShell/PowerShell/pull/20915/files so I must be doing something wrong.
|
|
This PR has Quantification details
Why proper sizing of changes matters
Optimal pull request sizes drive a better predictable PR flow as they strike a
What can I do to optimize my changes
How to interpret the change counts in git diff output
Was this comment helpful? 👍 :ok_hand: :thumbsdown: (Email) |
|
@alexlarner could you please try this fix again and see if it solves the problem? Thanks! |
Yep, that did the trick. Thanks! |
|
This pull request has been automatically marked as Review Needed because it has been there has not been any activity for 7 days. |


PR Summary
Supersedes #20815 and actually fixes the issue this time:

It turns out that the SCCM provider returns the items as strings and adds all the various PS* properties as NoteProperties and none of the PS* properties include the actual value, see:

PR Context
Fixes #20803 (for real this time)
PR Checklist
.h,.cpp,.cs,.ps1and.psm1files have the correct copyright headerWIP:or[ WIP ]to the beginning of the title (theWIPbot will keep its status check atPendingwhile the prefix is present) and remove the prefix when the PR is ready.(which runs in a different PS Host).