Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Metaschema: support event class and object attribute observables #993

Merged
merged 3 commits into from
Apr 3, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
14 changes: 11 additions & 3 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -84,9 +84,17 @@ Thankyou! -->

### Misc
1. New Extension registration for Sedara. #951
2. Add new ways to define observables to metaschema. #982
3. Corrected punctuation for the `transmit_time` attribute. #1001

2. Corrected punctuation for the `transmit_time` attribute. #1001
3. New ways to define observables in the metaschema. #982 and #993
* (Current) Dictionary types using `observable` property in dictionary types. This allows defining all occurrences of attributes of this type as an observable.
* (Current) Objects using top-level `observable` property. This allows defining all occurrences attributes whose type is this object as an observable.
* _**(New)**_ Dictionary attributes using `observable` property in attribute. This allows defining all occurrences of this attribute as an observable.
* _**(New)**_ Object-specific attributes using `observable` property class's attributes. This allows defining object attributes as observables _only_ within instances of this specific object.
* _**(New)**_ Event class-specific attributes using `observable` property class's attributes. This allows defining class attributes as observables _only_ within instances of this specific class.
* _**(New)**_ Event class-specific attribute _paths_ using top-level `observables` property. The `observables` property holds an object mapping from an dotted attribute path to an observable `type_id`. This allows defining an observables _only_ within instances of this specific class, and only for the attributes at these paths, even for attributes that are within nested objects and arrays. This can also be used for top-level class attributes, which can be more convenient that defining a class attribute observable for classes that extend another, but don't otherwise change a attribute definition.
4. Metaschema improvements. #993
* Detect unexpected top-level properties in object and event class definitions. This was added at this point to detect invalid observable definitions: invalid `observable` property in event classes, and invalid `observables` property in objects.
* Remove hard-coded list of categories from `metaschema/categories.schema.json`, leaving this to the `ocsf-validator`. This change makes testing with alternate schemas that may add extra categories easier, as well as making it possible to validate private extensions that contain new categories.
<!-- All available sections in the Changelog:

### Added
Expand Down
3 changes: 3 additions & 0 deletions metaschema/attribute.schema.json
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,9 @@
"sibling": {
"type": "string",
"description": "Sibling attributes are string attributes paired with a source enum id attribute. If the source attribute maps to a defined enumeration value, the sibling attribute should be populated with the label of the enum. In the case that the source attribute is `Other`, the sibling attribute is populated with a custom label."
},
"observable": {
"$ref": "observable.schema.json"
}
},
"if": {
Expand Down
84 changes: 84 additions & 0 deletions metaschema/common-event-object.schema.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
{
"$id": "https://schema.ocsf.io/common-event-object.schema.json",
"$schema": "https://json-schema.org/draft/2020-12/schema",
"title": "Object",
"description": "Common metaschema shared between objects and event classes.",
"type": "object",
"anyOf": [
{
"required": [
"description",
"caption",
"name",
"attributes"
]
},
{
"required": [
"extends"
]
}
],
"properties": {
"@deprecated": {
"$ref": "deprecated.schema.json"
},
"description": {
"type": "string",
"description": "A concise description of the object."
},
"caption": {
"type": "string",
"description": "A short, human friendly name for the object."
},
"name": {
"type": "string",
"description": "A name of the object. It must be a unique name. The name is all lower case letters, combine words using underscore.",
"pattern": "^[a-z0-9_]*$"
},
"extends": {
"type": "string",
"description": "An object that this one extends from."
},
"constraints": {
"type": "object",
"description": "Constraints that apply to the attribute requirements.",
"properties": {
"at_least_one": {
"type": "array",
"items": {"type": "string"}
},
"just_one": {
"type": "array",
"items": {"type": "string"}
}
},
"additionalProperties": false
},
"profiles": {
"type": "array",
"items": {"type": "string"},
"description": "The list of profiles used to create the event."
},
"attributes": {
"type": "object",
"description": "A dictionary of attributes for the object.",
"properties": {
"$include": {
"description": "A reference to another schema for attributes to include.",
"type": "array",
"items": {
"type": "string",
"format": "uri-reference"
}
}
},
"patternProperties": {
"^[a-z0-9_]*$": {
"$ref": "attribute.schema.json"
}
},
"additionalProperties": false
}
}
}
22 changes: 7 additions & 15 deletions metaschema/event.schema.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,20 +3,13 @@
"$schema": "https://json-schema.org/draft/2020-12/schema",
"title": "Event",
"description": "Event classes are particular sets of attributes and objects representing a log line or telemetry submission at a point in time. Event classes have semantics that describe what happened: either a particular activity, disposition or both.",
"allOf": [
"anyOf": [
{
"$ref": "object.schema.json"
"$ref": "common-event-object.schema.json"
},
{
"type": "object",
"properties": {
"@deprecated": true,
"description": true,
"caption": true,
"name": true,
"extends": true,
"constraints": true,
"profiles": true,
"attributes": true,
"associations": {
"type": "object",
"description": "Associations indicate attributes in a schema which 'go together'. For example, if a schema has multiple users and multiple endpoints, associations can indicate which user attribute goes with which endpoint.",
Expand All @@ -29,8 +22,7 @@
},
"category": {
"type": "string",
"description": "The category that the event belongs to.",
"enum": ["system", "findings", "iam", "network", "discovery", "application", "other"]
"description": "The category that the event belongs to."
},
"uid": {
"type": "integer",
Expand All @@ -48,8 +40,8 @@
},
"additionalProperties": false
}
},
"additionalProperties": false
}
}
]
],
"unevaluatedProperties": false
}
81 changes: 7 additions & 74 deletions metaschema/object.schema.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,85 +3,18 @@
"$schema": "https://json-schema.org/draft/2020-12/schema",
"title": "Object",
"description": "An object is a collection of contextually related attributes, usually representing an entity, and may include other objects. Each object is also a data type in OCSF. Examples of object data types are Process, Device, User, Malware and File.",
"type": "object",
"anyOf": [
{
"required": [
"description",
"caption",
"name",
"attributes"
]
"$ref": "common-event-object.schema.json"
},
{
"required": [
"extends"
]
}
],
"properties": {
"@deprecated": {
"$ref": "deprecated.schema.json"
},
"description": {
"type": "string",
"description": "A concise description of the object."
},
"caption": {
"type": "string",
"description": "A short, human friendly name for the object."
},
"name": {
"type": "string",
"description": "A name of the object. It must be a unique name. The name is all lower case letters, combine words using underscore.",
"pattern": "^[a-z0-9_]*$"
},
"extends": {
"type": "string",
"description": "An object that this one extends from."
},
"observable": {
"$ref": "observable.schema.json"
},
"constraints": {
"type": "object",
"description": "Constraints that apply to the attribute requirements.",
"properties": {
"at_least_one": {
"type": "array",
"items": {"type": "string"}
},
"just_one": {
"type": "array",
"items": {"type": "string"}
}
},
"additionalProperties": false
},
"profiles": {
"type": "array",
"items": {"type": "string"},
"description": "The list of profiles used to create the event."
},
"attributes": {
"type": "object",
"description": "A dictionary of attributes for the object.",
"properties": {
"$include": {
"description": "A reference to another schema for attributes to include.",
"type": "array",
"items": {
"type": "string",
"format": "uri-reference"
}
}
},
"patternProperties": {
"^[a-z0-9_]*$": {
"$ref": "attribute.schema.json"
}
},
"additionalProperties": false
"observable": {
"$ref": "observable.schema.json"
}
}
}
}
],
"unevaluatedProperties": false
}
Loading