Autonomous Persona Management using 1E Tachyon’s PowerShell Toolkit

Published:23 February 2022 - 6 min. read

Grouping devices into different categories or sub-groups is a staple of endpoint management. Whether you’re tagging devices for a project pilot or giving them a persona classification, a good solution should allow you to do so programmatically.

Manual tagging or using a static list is counterproductive, and administrators always look for opportunities to automate tasks. Lucky for you, 1E’s PowerShell integration module called PSTachyonToolkit allows you to step it up.

This article explores how PSTachyonToolkit can help automate the dynamic creation of endpoints lists and apply persona tags to those devices based on specific criteria — all within PowerShell.

Determining the Tachyon Device Persona

In this use-case scenario, my goal is to apply different persona tags to devices in the Tachyon environment. Later on, I can use these personas to target corresponding endpoints for whatever Tachyon instruction I need to run.

My solution will determine each persona type by checking the number of distinct processes executed within a specific number of days on the device. The different personas in this example are as follows.

  • Knowledge Worker – devices that executed 1 to 3 distinct processes total.
  • Task Worker – devices that executed 4 to 8 distinct processes total.
  • Power User – devices that executed 9 or more distinct processes total.

Tachyon has a Tachyon Activity Record (TAR) feature, which keeps historical data of all endpoints. The data I need is already available, and I only need to perform the appropriate Tachyon query using the Invoke-TachyonDynamic cmdlet with the -Query parameter.

First, I’ll set the oldest activity date of the query.

## Import the PSTachyonToolkit module
Import-Module PSTachyonToolkit
## Connect to the Tachyon server
Set-TachyonServer' 1E01.corp.1EDemoLab.com'
## Set the licensed instruction prefix
Set-TachyonInstructionPrefix '1E-Demo'

## Define the past number of days to query
$numDays = 7
## Calculate the oldest activity date to query
$startDate = ((Get-Date).AddDays(-$numDays)).ToString('yyyy-MM-dd')

Next, I’ll create a splat to build the dynamic instruction. To better understand the code, here are the parameters I am using:

  • TargetScope – This parameter accepts the filter expression to specify which endpoint devices will be the target. The targets for this example are Windows devices only ("ostype=Windows").
  • Query – This parameter accepts the SQL-based query string. This example counts the total ProcessName rows from the $SoftwareInteraction_Daily table.
  • Schema – Overrides the default output schema. The custom schema in this example only returns the ProcessCount field value as an integer (int32) data type.
## Build the dynamic instruction
$dynamicSplat = @{
    # Target only Windows devices
    TargetScope = "ostype=Windows"
    # Count process names SoftwareInteraction_Daily table that from the last $numDays
    Query = "SELECT Count(ProcessName) AS ProcessCount FROM `$SoftwareInteraction_Daily WHERE DATETIME(TS, 'unixepoch') >= '$($startDate)'"
    # Override the schema and return only the ProcessCount field as an integer
    Schema = 'ProcessCount int32'
}
## Invoke the dynamic instruction
$result = Invoke-TachyonDynamic @dynamicSplat

As you can see below, running the activity query returned the results in a hashtable.

Getting distinct process count
Getting distinct process count

At this point, the result only shows the process count for each endpoint. Now would be the best time to insert additional properties to assign a persona to each device based on my defined persona table.

## Merge Fqdn and values and add the persona
$result.Keys |
ForEach-Object {
    $result[$_] | Add-Member -MemberType NoteProperty -Name Fqdn -Value $_ -Force
    $result[$_] | Add-Member -MemberType NoteProperty -Name Persona -Value $(
        if ($result[$_].ProcessCount -in 1..3) { 'Knowledge Worker' }
        if ($result[$_].ProcessCount -in 4..8) { 'Task Worker' }
        if ($result[$_].ProcessCount -ge 9) { 'Power User' }
    ) -Force
}
## Convert result from Hashtable to custom object and group by persona
$result = $result.Values.ToArray() | Sort-Object ProcessCount
$result

I have now converted the result to a custom object, clearly adding the Fqdn and Persona properties.

Converting the result and adding the Persona value
Converting the result and adding the Persona value

Removing Existing Device Persona Tags

Assuming that devices already have persona tags, I will first clear out any existing persona tags on every device. I can do that by running a dynamic Tachyon instruction that calls the Tagging.Delete() method.

The below code contains the instruction, which I saved as DeletePersona.scale.

/* Delete the 'Persona' device tag*/
@result = Tagging.Delete(Name: "Persona", Scopable: true);

Next, I’ll invoke the dynamic instruction by running the following commands.

## Delete 'Persona' tags from all devices matching the '1EDemoLab.com' domain
Invoke-TachyonDynamic -Scale .\\DeletePersona.scale -TargetScope '1EDemoLab.com'

The result below confirms that the dynamic instruction deleted the device persona tag where the value contains “Present":true. If the device persona tag did not exist, the value would have been “Present":false.

Deleting the device persona tag
Deleting the device persona tag

Updating Tachyon Device Persona Tags

Now I will run another dynamic instruction that will update each Tachyon device with their corresponding Persona tag using Tagging.Set() method.

As of PSTachyonToolkit v1.0.0, the Invoke-TachyonDynamic cmdlet ignores the -Parameters parameter when used with the -Scale parameter. Meaning I cannot pass a parameter to the dynamic SCALE code.

While working in PowerShell, I favor running dynamic instructions instead of published instructions. If 1E can consider allowing parameters with dynamic SCALE in future module releases, that would be a significant feature upgrade, in my opinion.

To workaround that limitation for now, I am composing the SCALE code inside the script instead and writing it out to a file.

## Set the dynamic scale file path
$scaleFile = '.\\SetPersonaTag.scale'
## Group devices by Persona
$result | Group-Object Persona |
## Process each device persona group
ForEach-Object {
    ## Create the dynamic SCALE code file for the current device persona group
    '@result = Tagging.Set(Name:"Persona",Value:"' + $_.Name + '",Scopable:true);' | Out-File $scaleFile -Force
    ## Invoke the dynamic SCALE instruction
    Invoke-TachyonDynamic -Scale $scaleFile -TargetFqdns $_.Group.Fqdn
}

The image below shows the result of running the dynamic SCALE. As you can see, each device persona tag now has a value based on the conditions I set earlier.

Updating the device Persona tag
Updating the device Persona tag

To further confirm, I’m running the Get-TachyonDevice command below to display the device tags.

Get-TachyonDevice -Full | Format-Table Fqdn, CoverageTags, Tags
Displaying device tags
Displaying device tags

Creating or Updating Management Groups Based On Persona

So now I’ve tagged the devices with their new Persona. My next step is to create new or update existing Management Groups based on each Persona and add each device as a member. This way, I can group the devices with the same Persona.

To create the management groups, I’ll be running the Set-TachyonSLADirectManagementGroup cmdlet. Instead of running three separate commands to create the three management groups, I’ll instead loop through each Persona and run the command inside the loop.

@('Knowledge Worker', 'Task Worker', 'Power User') |
ForEach-Object {
    $persona = $PSItem
    if ($fqdn = (Get-TachyonDevice -Full | Where-Object { $_.CoverageTags.Persona -eq $persona }).Fqdn) {
        Set-TachyonSLADirectManagementGroup -Name $persona -FqdnList $fqdn
    }
}
Creating the Management Groups based on Persona
Creating the Management Groups based on Persona

I can now confirm that the new groups exist by running the Get-TachyonManagementGroup cmdlet.

Get-TachyonManagementGroup | Format-Table Name,UsableId,TachyonDeviceCount
Listing the Management Groups
Listing the Management Groups

Now I can create a scheduled task to run this script at an interval if needed, like once a week.

You can download the complete script from this Gist.

Additionally, I can now run instructions and target devices based on their persona or management group ID.

For example, if I want to determine the PowerShell script execution policy of the Task Worker devices, I would run the below command.

$instructionSplat = @{
    TargetScope = 'tagtxt=[Persona=Task Worker]'
    instruction = '1E-Explorer-TachyonCore-GetExecutionPolicyPowershellCommandLine'
    Drilldown   = $true
}
Invoke-TachyonInstruction @instructionSplat

Or target the member devices of the Task Worker management group.

$instructionSplat = @{
    TargetScope = 'managementgroup=47'
    instruction = '1E-Explorer-TachyonCore-GetExecutionPolicyPowershellCommandLine'
    Drilldown   = $true
}
Invoke-TachyonInstruction @instructionSplat

My Conclusion

Using static lists or manually tagging devices is tedious, inefficient, and outdated. Being able to script your way into building device inventory is something that admins should be doing right now!

Having 1E’s Tachyon and PSTachyonToolkit module in your arsenal, I dare say that you’ve already won half the battle. Chances are, there are already out-of-the-box instructions that fit your use-case requirements.

If not, you can also check out the Tachyon Exchange community, where you can find 84 product packs, 799 verified instructions, and 18 policies, as of this writing.

Hate ads? Want to support the writer? Get many of our tutorials packaged as an ATA Guidebook.

Explore ATA Guidebooks

Looks like you're offline!