Skip to content

Commit a4b6062

Browse files
authored
Merge pull request #10 from DaanSelen/tag_test
Added targeting tags.
2 parents b0f34e9 + de4fe02 commit a4b6062

File tree

3 files changed

+30
-16
lines changed

3 files changed

+30
-16
lines changed

README.md

+5
Original file line numberDiff line numberDiff line change
@@ -119,6 +119,11 @@ Related is the yaml option: `powershell: True`.
119119
I have made the program so it can have a filter with the Operating systems. If you have a mixed group, please read:
120120
[This explanation](./docs/operating_system_filtering.md)
121121

122+
### Tag filtering:
123+
124+
Filtering on MeshCentral tags is also possible with `target_tag` inside the meshbook. This string is case-sensitive, lower- and uppercase must match.<br>
125+
This is done because its human made and therefor needs to be keps well administrated.
126+
122127
# Example:
123128

124129
For the example, I used the following yaml file (you can find more in [this directory](./examples/)):

meshbook.py

+25-16
Original file line numberDiff line numberDiff line change
@@ -42,7 +42,7 @@ def console(message: str, final: bool=False):
4242

4343
async def load_config(segment: str = 'meshcentral-account') -> dict:
4444
'''
45-
Function that loads the segment from the meshbook.conf (by default) file and returns the it in a dict.
45+
Function that loads the segment from the config.conf (by default) file and returns the it in a dict.
4646
'''
4747

4848
conf_file = args.conf
@@ -186,13 +186,20 @@ def get_os_variants(category: str, os_map: dict) -> set:
186186
allowed_os = get_os_variants(target_os, os_categories[key])
187187
break # Stop searching once a match is found
188188

189-
# Filter out unreachable devices
189+
# Filter out unwanted or unreachable devices.
190190
for device in devices:
191191
if not device["reachable"]:
192192
continue # Skip unreachable devices.
193193

194-
if not target_os or device["device_os"] in allowed_os:
195-
valid_devices.append(device["device_id"])
194+
print(target_tag)
195+
print(device["device_tags"])
196+
if target_tag and target_tag not in device["device_tags"]:
197+
continue
198+
199+
if device["device_os"] not in allowed_os:
200+
continue
201+
202+
valid_devices.append(device["device_id"])
196203

197204
return valid_devices
198205

@@ -203,6 +210,7 @@ async def gather_targets(meshbook: dict, group_list: dict[str, list[dict]], os_c
203210

204211
target_list = []
205212
target_os = meshbook.get("target_os")
213+
target_tag = meshbook.get("target_tag")
206214

207215
async def process_device_or_group(pseudo_target, group_list, os_categories, target_os) -> list[str]:
208216
'''
@@ -216,7 +224,7 @@ async def process_device_or_group(pseudo_target, group_list, os_categories, targ
216224
matched_devices.append(device)
217225

218226
if matched_devices:
219-
return await filter_targets(matched_devices, os_categories, target_os)
227+
return await filter_targets(matched_devices, os_categories, target_os, target_tag)
220228
return []
221229

222230
match meshbook:
@@ -238,7 +246,7 @@ async def process_device_or_group(pseudo_target, group_list, os_categories, targ
238246

239247
case {"group": pseudo_target}: # Single group target
240248
if isinstance(pseudo_target, str) and pseudo_target in group_list:
241-
matched_devices = await filter_targets(group_list[pseudo_target], os_categories, target_os)
249+
matched_devices = await filter_targets(group_list[pseudo_target], os_categories, target_os, target_tag)
242250
target_list.extend(matched_devices)
243251
elif pseudo_target not in group_list:
244252
console(text_color.yellow + "Targeted group not found on the MeshCentral server.", True)
@@ -249,11 +257,11 @@ async def process_device_or_group(pseudo_target, group_list, os_categories, targ
249257
if isinstance(pseudo_target, list):
250258
for sub_pseudo_target in pseudo_target:
251259
if sub_pseudo_target in group_list:
252-
matched_devices = await filter_targets(group_list[sub_pseudo_target], os_categories, target_os)
260+
matched_devices = await filter_targets(group_list[sub_pseudo_target], os_categories, target_os, target_tag)
253261
target_list.extend(matched_devices)
254262
if pseudo_target.lower() == "all":
255263
for group in group_list:
256-
matched_devices = await filter_targets(group_list[group], os_categories, target_os)
264+
matched_devices = await filter_targets(group_list[group], os_categories, target_os, target_tag)
257265
target_list.extend(matched_devices)
258266
else:
259267
console(text_color.yellow + "The 'groups' method is being used, but only one string is given. Did you mean 'group'?", True)
@@ -289,7 +297,7 @@ async def execute_meshbook(session: meshctrl.Session, targets: dict, meshbook: d
289297
}
290298
round += 1
291299

292-
console(("-" * 40))
300+
console(text_color.reset + ("-" * 40))
293301
if args.indent:
294302
console((json.dumps(responses_list,indent=4)), True)
295303

@@ -306,7 +314,7 @@ async def main():
306314
parser.add_argument("-mb", "--meshbook", type=str, help="Path to the meshbook yaml file.", required=True)
307315

308316
parser.add_argument("-oc", "--oscategories", type=str, help="Path to the Operating System categories JSON file.", required=False, default="./os_categories.json")
309-
parser.add_argument("--conf", type=str, help="Path for the API configuration file (default: ./meshbook.conf).", required=False, default="./meshbook.conf")
317+
parser.add_argument("--conf", type=str, help="Path for the API configuration file (default: ./config.conf).", required=False, default="./config.conf")
310318
parser.add_argument("--nograce", action="store_true", help="Disable the grace 3 seconds before running the meshbook.", required=False)
311319
parser.add_argument("-i", "--indent", action="store_true", help="Use an JSON indentation of 4 when this flag is passed.", required=False)
312320
parser.add_argument("-s", "--silent", action="store_true", help="Suppress terminal output", required=False)
@@ -328,7 +336,7 @@ async def main():
328336
The following section mainly displays used variables and first steps of the program to the console.
329337
'''
330338

331-
console(("-" * 40))
339+
console(text_color.reset + ("-" * 40))
332340
console("meshbook: " + text_color.yellow + args.meshbook)
333341
console("Operating System Categorisation file: " + text_color.yellow + args.oscategories)
334342
console("Configuration file: " + text_color.yellow + args.conf)
@@ -347,7 +355,7 @@ async def main():
347355
console("Silent: " + text_color.yellow + "False") # Can be pre-defined because if silent flag was passed then none of this would be printed.
348356

349357
session = await init_connection(credentials)
350-
console(("-" * 40))
358+
console(text_color.reset + ("-" * 40))
351359
console(text_color.italic + "Trying to load the MeshCentral account credential file...")
352360
console(text_color.italic + "Trying to load the meshbook yaml file and compile it into something workable...")
353361
console(text_color.italic + "Trying to load the Operating System categorisation JSON file...")
@@ -363,10 +371,10 @@ async def main():
363371

364372
if len(targets_list) == 0:
365373
console(text_color.red + "No targets found or targets unreachable, quitting.", True)
366-
console(("-" * 40), True)
374+
console(text_color.reset + ("-" * 40), True)
367375

368376
else:
369-
console(("-" * 40))
377+
console(text_color.reset + ("-" * 40))
370378

371379
match meshbook:
372380
case {"group": candidate_target_name}:
@@ -390,8 +398,9 @@ async def main():
390398
console(text_color.yellow + "{}...".format(x+1)) # Countdown!
391399
await asyncio.sleep(1)
392400

393-
console(("-" * 40))
394-
await execute_meshbook(session, targets_list, meshbook, group_list)
401+
console(text_color.reset + ("-" * 40))
402+
print(json.dumps(targets_list,indent=4))
403+
#await execute_meshbook(session, targets_list, meshbook, group_list)
395404

396405
await session.close()
397406

File renamed without changes.

0 commit comments

Comments
 (0)