1

I'm trying to compare two different objects and return the ID of the user from Object 1 if their email address exists in object 2.

I.e. Object 1

|   user    |    id      |   emailaddress    |
+-----------+------------+--------------------+
| test user | asfasfasdf | test.user@test.com |
| ima test  | bsvxcffasd | ima.test@test.com  |
+-----------+------------+--------------------+

    Object 2
+--------------------+
|   email   |
+--------------------+
| test.user@test.com |
| ima.test@test.com  |
+--------------------+

Consider the 2 objects above, my goal objective is to check if a user exists in Object 2 and Object 1. If they exist in Object 2 then I want to return their ID value.

This code is where i'm up to, this will return the users who email address exists in both objects but not their ID:


$x = $object1 | Select-Object -ExpandProperty emailaddress
$y = $object2 | Select-Object -ExpandProperty email

$z = Compare-Object $x $y -IncludeEqual -ExcludeDifferent

$userids = @()

foreach($a in $z.inputobject){

    if($object2.email -contains $a){

        $userids += $a
    }
}

Attempt 2 based on Olaf's reply:

$object1 = New-Object -Typename psobject
$object1 | Add-Member -MemberType NoteProperty -Name email -Value $otherobject.members.email
$object1 | Add-Member -MemberType NoteProperty -Name id -Value $otherobject.members.id

$object2 = New-Object -Typename psobject
$object2 | Add-Member -MemberType NoteProperty -Name email -Value $otherobject2.emailaddress

$ComparedUsers = Compare-Object -ReferenceObject $object1 -DifferenceObject $object2 -IncludeEqual -ExcludeDifferent -PassThru
user3509273
  • 31
  • 2
  • 5
  • "*Attempt 2 based on Olaf's reply*", I think you misunderstood the answer from @Olaf. You don't have to recreate `$object1` and `$object2` from other objects. Olaf, just given you a way to build two sample objects from a CSV representation (rather then a markdown table). – iRon Sep 02 '20 at 07:12
  • Hi iRon, in any case when I compare on the email property, Nothing is returned. At first I thought it was because the data isn't the same but the email and emailaddress properties are both strings so i cant see why i'm getting no output when using compare-object. – user3509273 Sep 02 '20 at 07:53
  • There are a lot of questions and answers already at StackOverflow with regards to joining two objects. Take for instance: [**In Powershell, what's the best way to join two tables into one?**](https://stackoverflow.com/q/1848821/1701026). If you do not want to reinvent the wheel, you might want to use the purposed [**`Join-Object`**](https://www.powershellgallery.com/packages/Join) which has an easier syntax and is faster than `Compare-Object` on large objects. E.g.: `$Object1 | Join $Object2 -on email -Property id` – iRon Sep 02 '20 at 08:46
  • Please add ***how you create the `Object1` and `Object2`*** to the question because what you do under "*Attempt 2 based on Olaf's reply:*" is not the same as what you show in the markdown tables. – iRon Sep 02 '20 at 08:56

1 Answers1

1

You should not use -ExpandProperty when you want to use other properties of the object as well. And I'd recommend to use the same property names for both objects.

Something like this should push you to the right direction:

$object1 = 
@'
user,id,email
testuser,asfasfasdf,test.user@test.com
imatest,bsvxcffasd,ima.test@test.com
other,lkjshfdlakjs,other.test@test.com
'@ |
    ConvertFrom-Csv
$object2 =
@'
email
test.user@test.com
ima.test@test.com
any.test@test.com
'@ |
    ConvertFrom-Csv

Compare-Object -ReferenceObject $object1 -DifferenceObject $object2 -Property 'email' -IncludeEqual -ExcludeDifferent -PassThru

The output of that would be ...

user     id         email              SideIndicator
----     --         -----              -------------
testuser asfasfasdf test.user@test.com ==
imatest  bsvxcffasd ima.test@test.com  ==
Olaf
  • 4,690
  • 2
  • 15
  • 23
  • Hey Olaf, the issue is that the variables are dynamic and not static like your example. You gave me an idea though and I created some custom objects, the problem is when i specify the email property it doesnt work and when I don't the compared values are totally wrong. See the bottom of my OP for the updated code i'm trying. – user3509273 Sep 02 '20 at 07:08
  • Like iRon already mentioned that's just an example. How do you create your objects initially? – Olaf Sep 02 '20 at 07:53
  • Hi Olaf, pulling from the API and storing that as data. I noticed in the initial objects that one is a System.Management.Automation.PSCustomObject and the other is a Selected.System.Management.Automation.PSCustomObject. Perhaps thats causing the issue? – user3509273 Sep 02 '20 at 07:58
  • I don't think so. If you're pulling it from an API you could change the name of the properties to the desired value with a calculated property. Than you can compare it as needed. – Olaf Sep 02 '20 at 08:28
  • Just as a side note: you might want to add `... | Select-Object -ExpandProperty id` if you want an *array* of strings (`[String[]]` rather than `[PSCustomObject[]]` with a single `id` property) as a result. – iRon Sep 02 '20 at 08:51