cancel
Showing results for 
Search instead for 
Did you mean: 

Extract User ID from Record Permissions Search on WS

PaulCasey2
Collaborator II

If you used web services to run a report that only listed users in a Record permission field, how would you limit the results to only returning the user id of the users in the report.

 

powershell

 

$api_url = $base_url + "/ws/search.asmx"
$ws = New-WebServiceProxy -Uri $api_url -Class Search -Namespace webservice
$report_id = 12012
$page = 1

 

Do   {
   "Page " + $page
   [xml] $xdoc = $ws.SearchRecordsByReport($session_token, $report_id, $page)
   $xdoc.InnerXml
   $page++
}
While ($xdoc.Records.Record.Count -gt 0)

 

 

The results are basically laid out simply enough but I can't seem to figure out how to access the Users level to grab the @id when the report returns more than one name. There are roughly 11 users in the list but it basically looks like this, with 11 entries of <users>.

 

When the report returns only 1 name, it is easy to do but the web services call seems to change when there are multiple users and does not allow me to get to the <User> level, or at least I haven't found a way.

 

<?xml version="1.0" encoding="utf-16"?>

<Records count="6">
<Metadata>
<FieldDefinitions>
<FieldDefinition id="21548" guid="bd906ce7-296a-4f7f-b9dc-367f46aa51f8" name="Information Owner(s)" alias="Information_Owners" />
<FieldDefinition id="18049" guid="61ae6903-9017-43df-bdb0-f72b1a9971ea" name="System Name" alias="Authorization_Package_Name" />
</FieldDefinitions>
</Metadata>
<LevelCounts>
<LevelCount id="270" guid="086d9857-bfdf-4541-8464-10d2e0e588d9" count="6" />
</LevelCounts>
<Record contentId="273528" levelId="270" levelGuid="086d9857-bfdf-4541-8464-10d2e0e588d9" moduleId="472" parentId="0">
<Field id="21548" guid="bd906ce7-296a-4f7f-b9dc-367f46aa51f8" type="8">
<Users>
<User id="202" firstName="General User Info Owner HHSC" lastName="Test User">tuser6</User>
</Users>
<Groups />
</Field>
</Record>

</Records>

 

 

 

The call to web services also adds the key field to the results despite not being in the report. Is that standard?

 

Thanks. I am attempting to have a report return users to be added to a group by web services.

1 ACCEPTED SOLUTION

Accepted Solutions

JeffLetterman
Archer Employee
Archer Employee

Yes, the key field will be returned in the results by SearchRecordsByReport‌ and ExecuteSearch‌.  The <Groups /> line is an empty XML Element which means no groups.

 

Here is a snippet on how to loop thru the records and pull the users from a specific field.

Do {
    "Page " + $page + "`r`n"
    [xml] $xdoc = $ws.SearchRecordsByReport($session_token, $report_id, $page)
   
    $recs = $xdoc.SelectNodes("/Records/Record")
    foreach($rec in $recs)
    {
        "Content Id: " + $rec.contentId

        $field = $rec.SelectSingleNode("Field[@id='21548']")
        foreach($user in $field.SelectNodes("Users/User"))
        {
            $tmp_userid = $user.GetAttribute("id")
            $tmp_username = $user.InnerText
            $tmp_fullname = $user.GetAttribute("firstName") + " " + $user.GetAttribute("lastName")

            "User Id: " + $tmp_userid + "   Username: " + $tmp_username + "   Name: " + $tmp_fullname
        }

        "`r"
    }

    #$xdoc.InnerXml

    "`r"
    $page++
} While ($xdoc.Records.Record.Count -gt 0)‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍

 

Sample output:

1.png

View solution in original post

2 REPLIES 2

JeffLetterman
Archer Employee
Archer Employee

Yes, the key field will be returned in the results by SearchRecordsByReport‌ and ExecuteSearch‌.  The <Groups /> line is an empty XML Element which means no groups.

 

Here is a snippet on how to loop thru the records and pull the users from a specific field.

Do {
    "Page " + $page + "`r`n"
    [xml] $xdoc = $ws.SearchRecordsByReport($session_token, $report_id, $page)
   
    $recs = $xdoc.SelectNodes("/Records/Record")
    foreach($rec in $recs)
    {
        "Content Id: " + $rec.contentId

        $field = $rec.SelectSingleNode("Field[@id='21548']")
        foreach($user in $field.SelectNodes("Users/User"))
        {
            $tmp_userid = $user.GetAttribute("id")
            $tmp_username = $user.InnerText
            $tmp_fullname = $user.GetAttribute("firstName") + " " + $user.GetAttribute("lastName")

            "User Id: " + $tmp_userid + "   Username: " + $tmp_username + "   Name: " + $tmp_fullname
        }

        "`r"
    }

    #$xdoc.InnerXml

    "`r"
    $page++
} While ($xdoc.Records.Record.Count -gt 0)‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍

 

Sample output:

1.png

Thank you Jeff.

 

In an effort to share, this is my rough draft of my first attempt at a script to use ws (with some help from a colleague). Happy to take thoughts. I am now going to go through it and writing more text for informational purposes and maybe look for some efficiencies.

 

Intent: Read a list of users from a report. Assign them to a group. Remove any users in the group not listed in the report.

 

Powershell

 

$base_url = "http://server/Archer"
$instance = "Archer"
$user_domain = ""
$username = "apiuser"
$password = "password"
$groupid = "229"

try
{
$api_url_general = $base_url + "/ws/general.asmx"
if ($user_domain -eq "") {
$ws = New-WebServiceProxy -Uri $api_url_general -Class General -Namespace webservice -ErrorAction Stop
$session_token = $ws.CreateUserSessionFromInstance($username, $instance, $password)
}
else {
$ws = New-WebServiceProxy -Uri $api_url_general -Class General -Namespace webservice -ErrorAction Stop
$session_token = $ws.CreateDomainUserSessionFromInstance($username, $instance, $password, $user_domain)
}
$session_token
}
catch {
$session_token = $null
$_.Exception|Format-List -Force
exit
}

#run report, return user id in a list
[System.Collections.ArrayList] $UserList = @()
$api_url_search = $base_url + "/ws/search.asmx"
$ws = New-WebServiceProxy -Uri $api_url_search -Class Search -Namespace webservice
$report_id = 12012
$page = 1

do
{
[xml] $xdoc = $ws.SearchRecordsByReport($session_token, $report_id, $page)
Foreach($User in $xdoc.Records.Record.Field.Users.User)
{ if ($userlist.indexof($user.id) -eq -1) { $UserList.Add($User.id) | out-null} }
$page++
}
while ($xdoc.Records.record.count -gt 0)

#add to group
$api_url_ac = $base_url + "/ws/accesscontrol.asmx"
$ws = New-WebServiceProxy -Uri $api_url_ac -Class AccessControl -Namespace webservice

("Adding users to group: " + $ws.getgroup($session_token,$groupid))

ForEach ($id in $userlist) {
$ws.AddUsersToGroup($session_token, $id, $groupid)
#$id
}

#get group information, return user id

$ws = New-WebServiceProxy -Uri $api_url_ac -Class AccessControl -Namespace webservice

[xml] $GroupInfo = $ws.GetGroupInformation($session_token, $groupid)
$GroupUserId = $GroupInfo.Group.Members.Users.User.Id

#remove user from group by user id

$ws = New-WebServiceProxy -Uri $api_url_ac -Class AccessControl -Namespace webservice


Foreach ($IdListed in $GroupUserId) {
If ($Userlist -notcontains $IdListed) {
$ws.RemoveUserFromGroup($session_token, $IdListed, $groupid)
}
}