or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

Files

docs

cli-tools.mdcollections.mdexcel-export.mdindex.mdnavigation-layers.mdstix20-data-access.mdversion-comparison.mdversion-management.md

navigation-layers.mddocs/

0

# ATT&CK Navigator Layers

1

2

Create, manipulate, and export ATT&CK Navigator layer files for data visualization. This module provides comprehensive tools for generating layer files that can be imported into the MITRE ATT&CK Navigator for visual analysis, including programmatic layer creation, SVG export, Excel export, and advanced layer manipulation operations.

3

4

## Capabilities

5

6

### Core Layer Management

7

8

Main classes for creating and managing ATT&CK Navigator layers.

9

10

```python { .api }

11

class Layer:

12

def __init__(self, init_data=None, name=None, domain=None, strict=True):

13

"""

14

Create a new ATT&CK Navigator layer.

15

16

Args:

17

init_data: Optional base Layer JSON or string data on initialization

18

name (str, optional): Layer name for display

19

domain (str, optional): ATT&CK domain ("enterprise-attack", "mobile-attack", "ics-attack")

20

strict (bool): Whether to use strict validation. Defaults to True.

21

"""

22

23

def from_file(self, filepath: str) -> None:

24

"""

25

Load layer from JSON file.

26

27

Args:

28

filepath (str): Path to layer JSON file

29

"""

30

31

def to_file(self, filepath: str) -> None:

32

"""

33

Save layer to JSON file.

34

35

Args:

36

filepath (str): Output file path

37

"""

38

39

def to_excel(self, path: str, **kwargs) -> None:

40

"""

41

Export layer to Excel format.

42

43

Args:

44

path (str): Output Excel file path

45

**kwargs: Additional export options

46

"""

47

48

def to_svg(self, path: str, **kwargs) -> None:

49

"""

50

Export layer to SVG format.

51

52

Args:

53

path (str): Output SVG file path

54

**kwargs: SVG formatting options

55

"""

56

```

57

58

### Layer Component Classes

59

60

Classes representing different components of a Navigator layer.

61

62

```python { .api }

63

class Technique:

64

def __init__(self, techniqueID: str = "", color: str = "", comment: str = "",

65

enabled: bool = True, score: int = None):

66

"""

67

Individual technique representation in a layer.

68

69

Args:

70

techniqueID (str): ATT&CK technique ID (e.g., "T1055")

71

color (str): Hex color code for visualization

72

comment (str): Comment or note for the technique

73

enabled (bool): Whether technique is enabled in the layer

74

score (int): Numeric score for the technique

75

"""

76

77

class Metadata:

78

def __init__(self, name: str = "", value: str = ""):

79

"""

80

Layer metadata key-value pair.

81

82

Args:

83

name (str): Metadata field name

84

value (str): Metadata field value

85

"""

86

87

class Filter:

88

def __init__(self, platforms: List[str] = None, stages: List[str] = None):

89

"""

90

Layer filtering options.

91

92

Args:

93

platforms (List[str]): Platforms to include in layer

94

stages (List[str]): Kill chain stages to include

95

"""

96

97

class Gradient:

98

def __init__(self, colors: List[str] = None, minValue: float = 0, maxValue: float = 100):

99

"""

100

Color gradient for score-based visualization.

101

102

Args:

103

colors (List[str]): List of hex color codes

104

minValue (float): Minimum score value

105

maxValue (float): Maximum score value

106

"""

107

108

class Layout:

109

def __init__(self, layout: str = "side", showID: bool = False, showName: bool = True):

110

"""

111

Layer display layout configuration.

112

113

Args:

114

layout (str): Layout type ("side", "flat", "mini")

115

showID (bool): Whether to show technique IDs

116

showName (bool): Whether to show technique names

117

"""

118

119

class LegendItem:

120

def __init__(self, label: str = "", color: str = ""):

121

"""

122

Legend item for layer visualization.

123

124

Args:

125

label (str): Legend item label

126

color (str): Hex color code

127

"""

128

129

class Link:

130

def __init__(self, label: str = "", url: str = ""):

131

"""

132

External link associated with layer.

133

134

Args:

135

label (str): Link display text

136

url (str): Target URL

137

"""

138

139

class Versions:

140

def __init__(self, attack: str = "", navigator: str = "", layer: str = ""):

141

"""

142

Version information for layer compatibility.

143

144

Args:

145

attack (str): ATT&CK version

146

navigator (str): Navigator version

147

layer (str): Layer format version

148

"""

149

```

150

151

### Layer Generators

152

153

Automated layer generation based on ATT&CK data analysis.

154

155

```python { .api }

156

class OverviewLayerGenerator:

157

def __init__(self, data: 'MitreAttackData'):

158

"""

159

Generate overview layers showing object type distributions.

160

161

Args:

162

data (MitreAttackData): ATT&CK data source

163

"""

164

165

def generate_overview_layers(self) -> Dict[str, Layer]:

166

"""

167

Generate overview layers for different object types.

168

169

Returns:

170

Dict[str, Layer]: Dictionary mapping layer names to Layer objects

171

"""

172

173

class UsageLayerGenerator:

174

def __init__(self, data: 'MitreAttackData'):

175

"""

176

Generate layers showing technique usage patterns.

177

178

Args:

179

data (MitreAttackData): ATT&CK data source

180

"""

181

182

def generate_usage_layers(self, group_filter: List[str] = None) -> Dict[str, Layer]:

183

"""

184

Generate usage-based layers highlighting technique adoption.

185

186

Args:

187

group_filter (List[str], optional): Filter to specific group IDs

188

189

Returns:

190

Dict[str, Layer]: Dictionary mapping layer names to Layer objects

191

"""

192

```

193

194

### Layer Export Classes

195

196

Export layers to different formats with customization options.

197

198

```python { .api }

199

class ToExcel:

200

def __init__(self, layer: Layer, template: str = "default"):

201

"""

202

Excel export functionality for layers.

203

204

Args:

205

layer (Layer): Layer to export

206

template (str): Excel template to use

207

"""

208

209

def export(self, filepath: str, **kwargs) -> None:

210

"""

211

Export layer to Excel file.

212

213

Args:

214

filepath (str): Output Excel file path

215

**kwargs: Additional formatting options

216

"""

217

218

class ToSvg:

219

def __init__(self, layer: Layer, config: 'SVGConfig' = None):

220

"""

221

SVG export functionality for layers.

222

223

Args:

224

layer (Layer): Layer to export

225

config (SVGConfig, optional): SVG rendering configuration

226

"""

227

228

def export(self, filepath: str) -> None:

229

"""

230

Export layer to SVG file.

231

232

Args:

233

filepath (str): Output SVG file path

234

"""

235

236

class SVGConfig:

237

def __init__(self, width: int = 1200, height: int = 800, font_size: int = 12):

238

"""

239

Configuration for SVG export formatting.

240

241

Args:

242

width (int): SVG width in pixels

243

height (int): SVG height in pixels

244

font_size (int): Text font size

245

"""

246

```

247

248

### Layer Manipulation

249

250

Advanced operations for modifying and combining layers.

251

252

```python { .api }

253

class LayerOps:

254

@staticmethod

255

def merge_layers(layers: List[Layer], merge_technique_scores: str = "max") -> Layer:

256

"""

257

Merge multiple layers into one.

258

259

Args:

260

layers (List[Layer]): Layers to merge

261

merge_technique_scores (str): How to handle score conflicts ("max", "min", "avg")

262

263

Returns:

264

Layer: Merged layer

265

"""

266

267

@staticmethod

268

def filter_layer_by_platforms(layer: Layer, platforms: List[str]) -> Layer:

269

"""

270

Filter layer to show only specified platforms.

271

272

Args:

273

layer (Layer): Source layer

274

platforms (List[str]): Platforms to include

275

276

Returns:

277

Layer: Filtered layer

278

"""

279

280

@staticmethod

281

def apply_colormap(layer: Layer, colormap: Dict[str, str]) -> Layer:

282

"""

283

Apply color mapping to layer techniques.

284

285

Args:

286

layer (Layer): Layer to colorize

287

colormap (Dict[str, str]): Mapping of technique IDs to colors

288

289

Returns:

290

Layer: Colorized layer

291

"""

292

```

293

294

### Generator Helper Functions

295

296

Utility functions for layer generation workflows.

297

298

```python { .api }

299

def remove_revoked_depreciated(stix_objects: List[dict]) -> List[dict]:

300

"""

301

Filter out revoked and deprecated STIX objects.

302

303

Args:

304

stix_objects (List[dict]): List of STIX objects

305

306

Returns:

307

List[dict]: Filtered objects

308

"""

309

310

def construct_relationship_mapping(data: 'MitreAttackData', source_type: str,

311

target_type: str, relationship_type: str) -> Dict[str, List[str]]:

312

"""

313

Build relationship mapping between ATT&CK objects.

314

315

Args:

316

data (MitreAttackData): ATT&CK data source

317

source_type (str): Source object type

318

target_type (str): Target object type

319

relationship_type (str): Relationship type to map

320

321

Returns:

322

Dict[str, List[str]]: Mapping of source IDs to target ID lists

323

"""

324

325

def get_attack_id(stix_object: dict) -> str:

326

"""

327

Extract ATT&CK ID from STIX object.

328

329

Args:

330

stix_object (dict): STIX object

331

332

Returns:

333

str: ATT&CK ID (e.g., "T1055")

334

"""

335

336

def build_data_strings(stix_objects: List[dict], field_name: str) -> List[str]:

337

"""

338

Extract specific field values from STIX objects.

339

340

Args:

341

stix_objects (List[dict]): List of STIX objects

342

field_name (str): Field name to extract

343

344

Returns:

345

List[str]: List of field values

346

"""

347

```

348

349

### Exception Classes

350

351

Exception types for layer operations and validation.

352

353

```python { .api }

354

class InvalidFormat(Exception):

355

"""Raised when layer format is invalid."""

356

357

class BadLambda(Exception):

358

"""Raised when lambda expression is malformed."""

359

360

class MismatchedDomain(Exception):

361

"""Raised when layer domain doesn't match data domain."""

362

363

class BadInput(Exception):

364

"""Raised when input parameters are invalid."""

365

366

class BadType(Exception):

367

"""Raised when object type is incorrect."""

368

369

class UninitializedLayer(Exception):

370

"""Raised when layer is not properly initialized."""

371

372

class UnknownLayerProperty(Exception):

373

"""Raised when accessing undefined layer property."""

374

375

class UnknownTechniqueProperty(Exception):

376

"""Raised when accessing undefined technique property."""

377

378

class MissingParameters(Exception):

379

"""Raised when required parameters are missing."""

380

```

381

382

### Utility Constants and Functions

383

384

```python { .api }

385

UNSETVALUE = "UNSET_VALUE" # Constant for unset layer values

386

387

def handler(exception_type: Exception, message: str) -> None:

388

"""

389

Centralized exception handling.

390

391

Args:

392

exception_type (Exception): Exception type to raise

393

message (str): Error message

394

"""

395

396

def typeChecker(value: object, expected_type: type, field_name: str) -> None:

397

"""

398

Validate object type with descriptive error messages.

399

400

Args:

401

value (object): Value to check

402

expected_type (type): Expected type

403

field_name (str): Field name for error context

404

"""

405

406

def categoryChecker(value: str, valid_categories: List[str], field_name: str) -> None:

407

"""

408

Validate value against allowed categories.

409

410

Args:

411

value (str): Value to check

412

valid_categories (List[str]): List of valid values

413

field_name (str): Field name for error context

414

"""

415

```

416

417

## Usage Examples

418

419

### Basic Layer Creation and Export

420

421

```python

422

from mitreattack.navlayers import Layer, Technique

423

from mitreattack.stix20 import MitreAttackData

424

425

# Create a new layer

426

layer = Layer(name="Threat Group Analysis", domain="enterprise-attack")

427

428

# Add techniques with scores and colors

429

layer.techniques = [

430

Technique(techniqueID="T1055", score=85, color="#ff6b6b", comment="Process Injection"),

431

Technique(techniqueID="T1059", score=92, color="#ff8e53", comment="Command and Scripting"),

432

Technique(techniqueID="T1083", score=78, color="#ffab00", comment="File Discovery")

433

]

434

435

# Configure layer display

436

layer.layout.showName = True

437

layer.layout.showID = True

438

439

# Save layer file

440

layer.to_file("apt29_techniques.json")

441

442

# Export to SVG

443

layer.to_svg("apt29_techniques.svg")

444

```

445

446

### Automated Layer Generation

447

448

```python

449

from mitreattack.navlayers.generators import OverviewLayerGenerator, UsageLayerGenerator

450

from mitreattack.stix20 import MitreAttackData

451

452

# Load ATT&CK data

453

attack_data = MitreAttackData("enterprise-attack")

454

455

# Generate overview layers

456

overview_gen = OverviewLayerGenerator(attack_data)

457

overview_layers = overview_gen.generate_overview_layers()

458

459

# Save overview layers

460

for layer_name, layer_obj in overview_layers.items():

461

layer_obj.to_file(f"overview_{layer_name}.json")

462

463

# Generate usage layers for specific groups

464

usage_gen = UsageLayerGenerator(attack_data)

465

usage_layers = usage_gen.generate_usage_layers(group_filter=["G0016", "G0028"]) # APT29, Lazarus

466

467

for layer_name, layer_obj in usage_layers.items():

468

layer_obj.to_file(f"usage_{layer_name}.json")

469

```

470

471

### Layer Manipulation and Analysis

472

473

```python

474

from mitreattack.navlayers.manipulators import LayerOps

475

from mitreattack.navlayers import Layer

476

477

# Load multiple layers

478

layer1 = Layer()

479

layer1.from_file("apt29_layer.json")

480

481

layer2 = Layer()

482

layer2.from_file("lazarus_layer.json")

483

484

# Merge layers

485

merged_layer = LayerOps.merge_layers([layer1, layer2], merge_technique_scores="max")

486

merged_layer.name = "Combined Threat Analysis"

487

merged_layer.to_file("combined_threats.json")

488

489

# Filter by platform

490

windows_layer = LayerOps.filter_layer_by_platforms(merged_layer, ["Windows"])

491

windows_layer.to_file("windows_threats.json")

492

493

# Apply custom color scheme

494

color_mapping = {

495

"T1055": "#ff0000", # High priority - red

496

"T1059": "#ff8800", # Medium priority - orange

497

"T1083": "#ffff00" # Low priority - yellow

498

}

499

colored_layer = LayerOps.apply_colormap(merged_layer, color_mapping)

500

colored_layer.to_file("prioritized_threats.json")

501

```

502

503

### CLI Layer Tools

504

505

```bash

506

# Generate layers from ATT&CK data

507

layerGenerator_cli --data-source enterprise-attack --output ./layers/ --type overview

508

509

# Generate usage layers for specific groups

510

layerGenerator_cli --data-source enterprise-attack --groups G0016,G0028 --output ./usage-layers/

511

512

# Export layer to different formats

513

layerExporter_cli --input my_layer.json --format svg --output my_layer.svg

514

layerExporter_cli --input my_layer.json --format excel --output my_layer.xlsx

515

```

516

517

### Advanced Layer Customization

518

519

```python

520

from mitreattack.navlayers import Layer, Gradient, Filter, LegendItem

521

522

# Create layer with advanced configuration

523

layer = Layer(name="Detection Coverage Analysis", domain="enterprise-attack")

524

525

# Set up color gradient for coverage scores

526

layer.gradient = Gradient(

527

colors=["#ffffff", "#73c6b6", "#2e8b57"], # White to green gradient

528

minValue=0,

529

maxValue=100

530

)

531

532

# Configure filtering

533

layer.filters = Filter(

534

platforms=["Windows", "Linux", "macOS"],

535

stages=["initial-access", "execution", "persistence"]

536

)

537

538

# Add legend

539

layer.legendItems = [

540

LegendItem(label="High Coverage", color="#2e8b57"),

541

LegendItem(label="Medium Coverage", color="#73c6b6"),

542

LegendItem(label="Low Coverage", color="#ffffff")

543

]

544

545

# Set techniques with coverage scores

546

coverage_data = [

547

("T1055", 85), ("T1059", 92), ("T1083", 45), ("T1105", 78)

548

]

549

550

layer.techniques = [

551

Technique(techniqueID=tid, score=score, enabled=True)

552

for tid, score in coverage_data

553

]

554

555

layer.to_file("detection_coverage.json")

556

```