├── docs
├── vale
│ ├── styles
│ │ ├── Google
│ │ │ ├── vocab.txt
│ │ │ ├── meta.json
│ │ │ ├── Will.yml
│ │ │ ├── Parens.yml
│ │ │ ├── Colons.yml
│ │ │ ├── Semicolons.yml
│ │ │ ├── Ordinal.yml
│ │ │ ├── Quotes.yml
│ │ │ ├── OxfordComma.yml
│ │ │ ├── Ellipses.yml
│ │ │ ├── Periods.yml
│ │ │ ├── Ranges.yml
│ │ │ ├── Gender.yml
│ │ │ ├── AMPM.yml
│ │ │ ├── Spacing.yml
│ │ │ ├── Units.yml
│ │ │ ├── Slang.yml
│ │ │ ├── Spelling.yml
│ │ │ ├── EmDash.yml
│ │ │ ├── We.yml
│ │ │ ├── Exclamation.yml
│ │ │ ├── LyHyphens.yml
│ │ │ ├── Latin.yml
│ │ │ ├── OptionalPlurals.yml
│ │ │ ├── FirstPerson.yml
│ │ │ ├── HeadingPunctuation.yml
│ │ │ ├── DateFormat.yml
│ │ │ ├── Headings.yml
│ │ │ ├── Contractions.yml
│ │ │ ├── Acronyms.yml
│ │ │ ├── GenderBias.yml
│ │ │ ├── WordList.yml
│ │ │ └── Passive.yml
│ │ ├── config
│ │ │ └── vocabularies
│ │ │ │ └── LogCraft
│ │ │ │ ├── reject.txt
│ │ │ │ └── accept.txt
│ │ └── proselint
│ │ │ ├── Very.yml
│ │ │ ├── Hyperbole.yml
│ │ │ ├── Currency.yml
│ │ │ ├── DateMidnight.yml
│ │ │ ├── But.yml
│ │ │ ├── Annotations.yml
│ │ │ ├── DateSpacing.yml
│ │ │ ├── Apologizing.yml
│ │ │ ├── DateCase.yml
│ │ │ ├── Hedging.yml
│ │ │ ├── P-Value.yml
│ │ │ ├── Airlinese.yml
│ │ │ ├── Malapropisms.yml
│ │ │ ├── Jargon.yml
│ │ │ ├── Typography.yml
│ │ │ ├── Cursing.yml
│ │ │ ├── Skunked.yml
│ │ │ ├── LGBTOffensive.yml
│ │ │ ├── DateRedundancy.yml
│ │ │ ├── Spelling.yml
│ │ │ ├── Oxymorons.yml
│ │ │ ├── RASSyndrome.yml
│ │ │ ├── meta.json
│ │ │ ├── LGBTTerms.yml
│ │ │ ├── CorporateSpeak.yml
│ │ │ ├── Archaisms.yml
│ │ │ ├── Uncomparables.yml
│ │ │ ├── Nonwords.yml
│ │ │ ├── AnimalLabels.yml
│ │ │ ├── README.md
│ │ │ ├── GenderBias.yml
│ │ │ ├── GroupTerms.yml
│ │ │ ├── Diacritical.yml
│ │ │ └── DenizenLabels.yml
│ └── .vale.ini
├── src
│ ├── public
│ │ ├── robots.txt
│ │ ├── logo.png
│ │ ├── favicon.ico
│ │ └── img
│ │ │ ├── logcraft-cli.webp
│ │ │ ├── gitlab-3-stages.png
│ │ │ ├── gitlab-cicd-variables.png
│ │ │ └── logcraft-cli-overview.png
│ ├── .vitepress
│ │ ├── theme
│ │ │ ├── components
│ │ │ │ └── plugins
│ │ │ │ │ ├── common.js
│ │ │ │ │ ├── plugins.data.js
│ │ │ │ │ ├── PluginsIndexPage.vue
│ │ │ │ │ └── PluginStatus.vue
│ │ │ └── index.ts
│ │ └── config.mts
│ ├── plugins
│ │ ├── index.md
│ │ ├── sekoia.md
│ │ ├── tanium.md
│ │ ├── yara.md
│ │ ├── crowdstrike.md
│ │ ├── paloalto-cortex.md
│ │ ├── limacharlie.md
│ │ ├── google-chronicle.md
│ │ ├── sigma.md
│ │ └── microsoft-sentinel.md
│ ├── developers
│ │ ├── docker-images.md
│ │ ├── compiling.md
│ │ ├── state.md
│ │ └── how-to-create-plugins.md
│ ├── index.md
│ ├── support.md
│ ├── essentials
│ │ ├── configuration.md
│ │ ├── installation.md
│ │ └── gitlab.md
│ ├── commands
│ │ ├── destroy.md
│ │ ├── ping.md
│ │ ├── apply.md
│ │ ├── validate.md
│ │ ├── init.md
│ │ ├── plan.md
│ │ └── services.md
│ └── concepts
│ │ ├── plugins.md
│ │ ├── identifiers.md
│ │ └── detections.md
├── package.json
└── moon.yml
├── plugins
├── splunk
│ ├── README.md
│ ├── src
│ │ └── schemas
│ │ │ ├── mod.rs
│ │ │ ├── types.rs
│ │ │ └── settings.rs
│ ├── moon.yml
│ └── Cargo.toml
├── sentinel
│ ├── README.md
│ ├── src
│ │ ├── schemas
│ │ │ └── mod.rs
│ │ ├── helpers.rs
│ │ └── lib.rs
│ ├── moon.yml
│ └── Cargo.toml
└── sample
│ ├── moon.yml
│ ├── Cargo.toml
│ └── src
│ ├── backend.rs
│ ├── schema.rs
│ └── lib.rs
├── .prototools
├── libs
├── lgc-common
│ ├── moon.yml
│ ├── src
│ │ ├── plugins
│ │ │ └── mod.rs
│ │ ├── lib.rs
│ │ ├── detections.rs
│ │ ├── state
│ │ │ ├── backends
│ │ │ │ ├── mod.rs
│ │ │ │ └── local.rs
│ │ │ └── mod.rs
│ │ └── utils.rs
│ └── Cargo.toml
├── lgc-policies
│ ├── moon.yml
│ ├── src
│ │ ├── lib.rs
│ │ ├── helpers.rs
│ │ ├── policy.rs
│ │ └── schema.rs
│ └── Cargo.toml
├── lgc-runtime
│ ├── moon.yml
│ ├── Cargo.toml
│ └── src
│ │ └── lib.rs
└── bindings
│ ├── world.wit
│ └── plugin.wit
├── apps
└── lgc
│ ├── src
│ ├── lib.rs
│ ├── commands.rs
│ ├── commands
│ │ ├── init.rs
│ │ └── validate.rs
│ └── lgc.rs
│ ├── Cargo.lock
│ ├── moon.yml
│ ├── Cargo.toml
│ └── tests
│ ├── common.rs
│ └── test_init.rs
├── .moon
├── tasks
│ ├── tag-plugin.yml
│ └── rust.yml
├── toolchain.yml
└── workspace.yml
├── .dockerignore
├── .gitignore
├── .github
└── workflows
│ ├── license-enforcement.yml
│ ├── validate.yml
│ ├── release-plugins.yml
│ ├── release-docs.yml
│ ├── release-image.yml
│ └── release-lgc.yml
├── README.md
├── .licenserc.yaml
├── scripts
├── package-plugins.sh
└── package.sh
├── Cargo.toml
└── Dockerfile
/docs/vale/styles/Google/vocab.txt:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/docs/src/public/robots.txt:
--------------------------------------------------------------------------------
1 | User-agent: *
2 | Allow: /
3 |
--------------------------------------------------------------------------------
/docs/vale/styles/config/vocabularies/LogCraft/reject.txt:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/plugins/splunk/README.md:
--------------------------------------------------------------------------------
1 | # Splunk
2 |
3 | The documentation is available at https://docs.logcraft.io
--------------------------------------------------------------------------------
/docs/src/public/logo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/LogCraftIO/logcraft-cli/HEAD/docs/src/public/logo.png
--------------------------------------------------------------------------------
/plugins/sentinel/README.md:
--------------------------------------------------------------------------------
1 | # Sentinel
2 |
3 | The documentation is available at https://docs.logcraft.io
--------------------------------------------------------------------------------
/docs/src/public/favicon.ico:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/LogCraftIO/logcraft-cli/HEAD/docs/src/public/favicon.ico
--------------------------------------------------------------------------------
/docs/src/public/img/logcraft-cli.webp:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/LogCraftIO/logcraft-cli/HEAD/docs/src/public/img/logcraft-cli.webp
--------------------------------------------------------------------------------
/.prototools:
--------------------------------------------------------------------------------
1 | moon = "1.31.2"
2 |
3 | [plugins]
4 | moon = "https://raw.githubusercontent.com/moonrepo/moon/master/proto-plugin.toml"
5 |
--------------------------------------------------------------------------------
/docs/src/public/img/gitlab-3-stages.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/LogCraftIO/logcraft-cli/HEAD/docs/src/public/img/gitlab-3-stages.png
--------------------------------------------------------------------------------
/docs/vale/styles/Google/meta.json:
--------------------------------------------------------------------------------
1 | {
2 | "feed": "https://github.com/errata-ai/Google/releases.atom",
3 | "vale_version": ">=1.0.0"
4 | }
5 |
--------------------------------------------------------------------------------
/docs/src/public/img/gitlab-cicd-variables.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/LogCraftIO/logcraft-cli/HEAD/docs/src/public/img/gitlab-cicd-variables.png
--------------------------------------------------------------------------------
/docs/src/public/img/logcraft-cli-overview.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/LogCraftIO/logcraft-cli/HEAD/docs/src/public/img/logcraft-cli-overview.png
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/Very.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Remove '%s'."
3 | ignorecase: true
4 | level: error
5 | tokens:
6 | - very
7 |
--------------------------------------------------------------------------------
/libs/lgc-common/moon.yml:
--------------------------------------------------------------------------------
1 | language: 'rust'
2 | type: 'library'
3 |
4 | project:
5 | name: 'lgc-common'
6 | description: 'LogCraft CLI common library'
--------------------------------------------------------------------------------
/apps/lgc/src/lib.rs:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2023 LogCraft.io.
2 | // SPDX-License-Identifier: MPL-2.0
3 |
4 | // Export commands module
5 | pub mod commands;
6 |
--------------------------------------------------------------------------------
/libs/lgc-policies/moon.yml:
--------------------------------------------------------------------------------
1 | language: 'rust'
2 | type: 'library'
3 |
4 | project:
5 | name: 'lgc-policies'
6 | description: 'LogCraft CLI policies library'
--------------------------------------------------------------------------------
/.moon/tasks/tag-plugin.yml:
--------------------------------------------------------------------------------
1 | tasks:
2 | build:
3 | command: 'cargo build --release --target wasm32-wasip2'
4 | inputs:
5 | - 'src/**/*'
6 | - 'Cargo.toml'
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/Hyperbole.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "'%s' is hyperbolic."
3 | level: error
4 | nonword: true
5 | tokens:
6 | - '[a-z]+[!?]{2,}'
7 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/Currency.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Incorrect use of symbols in '%s'."
3 | ignorecase: true
4 | raw:
5 | - \$[\d]* ?(?:dollars|usd|us dollars)
6 |
--------------------------------------------------------------------------------
/libs/lgc-policies/src/lib.rs:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2023 LogCraft.io.
2 | // SPDX-License-Identifier: MPL-2.0
3 |
4 | pub(crate) mod helpers;
5 | pub mod policy;
6 | pub(crate) mod schema;
7 |
--------------------------------------------------------------------------------
/plugins/sentinel/src/schemas/mod.rs:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2023 LogCraft.io.
2 | // SPDX-License-Identifier: MPL-2.0
3 |
4 | pub(super) mod rule;
5 | pub(super) mod settings;
6 | mod types;
7 |
--------------------------------------------------------------------------------
/plugins/splunk/src/schemas/mod.rs:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2023 LogCraft.io.
2 | // SPDX-License-Identifier: MPL-2.0
3 |
4 | pub(super) mod rule;
5 | pub(super) mod settings;
6 | mod types;
7 |
--------------------------------------------------------------------------------
/libs/lgc-runtime/moon.yml:
--------------------------------------------------------------------------------
1 | language: 'rust'
2 | type: 'library'
3 |
4 | project:
5 | name: 'lgc-runtime'
6 | description: 'LogCraft CLI runtime library'
7 |
8 | dependsOn:
9 | - 'bindings'
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/DateMidnight.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Use 'midnight' or 'noon'."
3 | ignorecase: true
4 | level: error
5 | nonword: true
6 | tokens:
7 | - '12 ?[ap]\.?m\.?'
8 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/Will.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Avoid using '%s'."
3 | link: 'https://developers.google.com/style/tense'
4 | ignorecase: true
5 | level: warning
6 | tokens:
7 | - will
8 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/But.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Do not start a paragraph with a 'but'."
3 | level: error
4 | scope: paragraph
5 | action:
6 | name: remove
7 | tokens:
8 | - ^But
9 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/Annotations.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "'%s' left in text."
3 | ignorecase: false
4 | level: error
5 | tokens:
6 | - XXX
7 | - FIXME
8 | - TODO
9 | - NOTE
10 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/DateSpacing.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "It's standard to put a space before '%s'"
3 | ignorecase: true
4 | level: error
5 | nonword: true
6 | tokens:
7 | - '\d{1,2}[ap]\.?m\.?'
8 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/Apologizing.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Excessive apologizing: '%s'"
3 | ignorecase: true
4 | level: error
5 | action:
6 | name: remove
7 | tokens:
8 | - More research is needed
9 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/DateCase.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: With lowercase letters, the periods are standard.
3 | ignorecase: false
4 | level: error
5 | nonword: true
6 | tokens:
7 | - '\d{1,2} ?[ap]m\b'
8 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/Hedging.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "'%s' is hedging."
3 | ignorecase: true
4 | level: error
5 | tokens:
6 | - I would argue that
7 | - ', so to speak'
8 | - to a certain degree
9 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/P-Value.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "You should use more decimal places, unless '%s' is really true."
3 | ignorecase: true
4 | level: suggestion
5 | tokens:
6 | - 'p = 0\.0{2,4}'
7 |
--------------------------------------------------------------------------------
/libs/lgc-common/src/plugins/mod.rs:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2023 LogCraft.io.
2 | // SPDX-License-Identifier: MPL-2.0
3 |
4 | // Local modules
5 | pub mod manager;
6 |
7 | pub const LGC_PLUGINS_PATH: &str = ".logcraft/plugins";
8 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/Parens.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Use parentheses judiciously."
3 | link: 'https://developers.google.com/style/parentheses'
4 | nonword: true
5 | level: suggestion
6 | tokens:
7 | - '\(.+\)'
8 |
--------------------------------------------------------------------------------
/plugins/splunk/moon.yml:
--------------------------------------------------------------------------------
1 | language: 'rust'
2 | type: 'library'
3 |
4 | project:
5 | name: 'splunk'
6 | description: 'LogCraft CLI Splunk plugin'
7 |
8 | dependsOn:
9 | - 'bindings'
10 |
11 | tags:
12 | - 'plugin'
13 |
--------------------------------------------------------------------------------
/.moon/toolchain.yml:
--------------------------------------------------------------------------------
1 | rust:
2 | version: '1.82.0'
3 | targets:
4 | - 'wasm32-wasip2'
5 | - 'x86_64-unknown-linux-gnu'
6 |
7 | node:
8 | version: '20.9.0'
9 | packageManager: 'pnpm'
10 | pnpm:
11 | version: '10.5.0'
--------------------------------------------------------------------------------
/plugins/sample/moon.yml:
--------------------------------------------------------------------------------
1 | language: 'rust'
2 | type: 'library'
3 |
4 | project:
5 | name: 'sample'
6 | description: 'LogCraft CLI demonstration plugin'
7 |
8 | dependsOn:
9 | - 'bindings'
10 |
11 | tags:
12 | - 'plugin'
13 |
--------------------------------------------------------------------------------
/plugins/sentinel/moon.yml:
--------------------------------------------------------------------------------
1 | language: 'rust'
2 | type: 'library'
3 |
4 | project:
5 | name: 'sentinel'
6 | description: 'LogCraft CLI Sentinel plugin'
7 |
8 | dependsOn:
9 | - 'bindings'
10 |
11 | tags:
12 | - 'plugin'
13 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/Colons.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "'%s' should be in lowercase."
3 | link: 'https://developers.google.com/style/colons'
4 | nonword: true
5 | level: warning
6 | scope: sentence
7 | tokens:
8 | - ':\s[A-Z]'
9 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/Semicolons.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Use semicolons judiciously."
3 | link: 'https://developers.google.com/style/semicolons'
4 | nonword: true
5 | scope: sentence
6 | level: suggestion
7 | tokens:
8 | - ';'
9 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/Airlinese.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "'%s' is airlinese."
3 | ignorecase: true
4 | level: error
5 | tokens:
6 | - enplan(?:e|ed|ing|ement)
7 | - deplan(?:e|ed|ing|ement)
8 | - taking off momentarily
9 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/Malapropisms.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "'%s' is a malapropism."
3 | ignorecase: true
4 | level: error
5 | tokens:
6 | - the infinitesimal universe
7 | - a serial experience
8 | - attack my voracity
9 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/Ordinal.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Spell out all ordinal numbers ('%s') in text."
3 | link: 'https://developers.google.com/style/numbers'
4 | level: error
5 | nonword: true
6 | tokens:
7 | - \d+(?:st|nd|rd|th)
8 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/Quotes.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Commas and periods go inside quotation marks."
3 | link: 'https://developers.google.com/style/quotation-marks'
4 | level: error
5 | nonword: true
6 | tokens:
7 | - '"[^"]+"[.,?]'
8 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/OxfordComma.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Use the Oxford comma in '%s'."
3 | link: 'https://developers.google.com/style/commas'
4 | scope: sentence
5 | level: warning
6 | tokens:
7 | - '(?:[^,]+,){1,}\s\w+\s(?:and|or)'
8 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/Ellipses.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "In general, don't use an ellipsis."
3 | link: 'https://developers.google.com/style/ellipses'
4 | nonword: true
5 | level: warning
6 | action:
7 | name: remove
8 | tokens:
9 | - '\.\.\.'
10 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/Periods.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Don't use periods with acronyms or initialisms such as '%s'."
3 | link: 'https://developers.google.com/style/abbreviations'
4 | level: error
5 | nonword: true
6 | tokens:
7 | - '\b(?:[A-Z]\.){3,}'
8 |
--------------------------------------------------------------------------------
/libs/lgc-common/src/lib.rs:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2023 LogCraft.io.
2 | // SPDX-License-Identifier: MPL-2.0
3 |
4 | //LogCraft common library
5 | pub mod configuration;
6 | pub mod detections;
7 | pub mod diff;
8 | pub mod plugins;
9 | pub mod state;
10 | pub mod utils;
11 |
--------------------------------------------------------------------------------
/apps/lgc/src/commands.rs:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2023 LogCraft.io.
2 | // SPDX-License-Identifier: MPL-2.0
3 |
4 | // Export all commands
5 | pub mod apply;
6 | pub mod destroy;
7 | pub mod init;
8 | pub mod ping;
9 | pub mod plan;
10 | pub mod services;
11 | pub mod validate;
12 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/Jargon.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "'%s' is jargon."
3 | ignorecase: true
4 | level: error
5 | tokens:
6 | - in the affirmative
7 | - in the negative
8 | - agendize
9 | - per your order
10 | - per your request
11 | - disincentivize
12 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/Ranges.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Don't add words such as 'from' or 'between' to describe a range of numbers."
3 | link: 'https://developers.google.com/style/hyphens'
4 | nonword: true
5 | level: warning
6 | tokens:
7 | - '(?:from|between)\s\d+\s?-\s?\d+'
8 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/Gender.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Don't use '%s' as a gender-neutral pronoun."
3 | link: 'https://developers.google.com/style/pronouns#gender-neutral-pronouns'
4 | level: error
5 | ignorecase: true
6 | tokens:
7 | - he/she
8 | - s/he
9 | - \(s\)he
10 |
--------------------------------------------------------------------------------
/libs/bindings/world.wit:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2023 LogCraft.io.
2 | // SPDX-License-Identifier: MPL-2.0
3 |
4 | package logcraft:lgc@0.1.0;
5 |
6 | /// The logcraft world for the component to target.
7 | world plugins {
8 | // Imports
9 |
10 | // Exports
11 | export plugin;
12 | }
13 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/Typography.yml:
--------------------------------------------------------------------------------
1 | extends: substitution
2 | message: Consider using the '%s' symbol instead of '%s'.
3 | level: error
4 | nonword: true
5 | swap:
6 | '\.\.\.': …
7 | '\([cC]\)': ©
8 | '\(TM\)': ™
9 | '\(tm\)': ™
10 | '\([rR]\)': ®
11 | '[0-9]+ ?x ?[0-9]+': ×
12 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/AMPM.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Use 'AM' or 'PM' (preceded by a space)."
3 | link: "https://developers.google.com/style/word-list"
4 | level: error
5 | nonword: true
6 | tokens:
7 | - '\d{1,2}[AP]M\b'
8 | - '\d{1,2} ?[ap]m\b'
9 | - '\d{1,2} ?[aApP]\.[mM]\.'
10 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/Spacing.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "'%s' should have one space."
3 | link: 'https://developers.google.com/style/sentence-spacing'
4 | level: error
5 | nonword: true
6 | action:
7 | name: remove
8 | tokens:
9 | - '[a-z][.?!] {2,}[A-Z]'
10 | - '[a-z][.?!][A-Z]'
11 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/Units.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Put a nonbreaking space between the number and the unit in '%s'."
3 | link: "https://developers.google.com/style/units-of-measure"
4 | nonword: true
5 | level: error
6 | tokens:
7 | - \b\d+(?:B|kB|MB|GB|TB)
8 | - \b\d+(?:ns|ms|s|min|h|d)
9 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/Cursing.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Consider replacing '%s'."
3 | level: error
4 | ignorecase: true
5 | tokens:
6 | - shit
7 | - piss
8 | - fuck
9 | - cunt
10 | - cocksucker
11 | - motherfucker
12 | - tits
13 | - fart
14 | - turd
15 | - twat
16 |
--------------------------------------------------------------------------------
/apps/lgc/Cargo.lock:
--------------------------------------------------------------------------------
1 | # This file is automatically @generated by Cargo.
2 | # It is not intended for manual editing.
3 | version = 3
4 |
5 | [[package]]
6 | name = "lgc"
7 | version = "0.1.0"
8 | dependencies = [
9 | "lgc-core",
10 | ]
11 |
12 | [[package]]
13 | name = "lgc-core"
14 | version = "0.1.0"
15 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/Slang.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Don't use internet slang abbreviations such as '%s'."
3 | link: 'https://developers.google.com/style/abbreviations'
4 | ignorecase: true
5 | level: error
6 | tokens:
7 | - 'tl;dr'
8 | - ymmv
9 | - rtfm
10 | - imo
11 | - fwiw
12 |
--------------------------------------------------------------------------------
/docs/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "type": "module",
3 | "devDependencies": {
4 | "vitepress": "^1.6.3"
5 | },
6 | "scripts": {
7 | "dev": "vitepress dev src",
8 | "build": "vitepress build src",
9 | "preview": "vitepress preview src"
10 | },
11 | "dependencies": {
12 | "vuetify": "^3.7.14"
13 | }
14 | }
--------------------------------------------------------------------------------
/docs/vale/styles/Google/Spelling.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "In general, use American spelling instead of '%s'."
3 | link: 'https://developers.google.com/style/spelling'
4 | ignorecase: true
5 | level: warning
6 | tokens:
7 | - '(?:\w+)nised?'
8 | - 'colour'
9 | - 'labour'
10 | - 'centre'
11 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/EmDash.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Don't put a space before or after a dash."
3 | link: "https://developers.google.com/style/dashes"
4 | nonword: true
5 | level: error
6 | action:
7 | name: edit
8 | params:
9 | - trim
10 | - " "
11 | tokens:
12 | - '\s[—–]\s'
13 |
14 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/We.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Try to avoid using first-person plural like '%s'."
3 | link: 'https://developers.google.com/style/pronouns#personal-pronouns'
4 | level: warning
5 | ignorecase: true
6 | tokens:
7 | - we
8 | - we'(?:ve|re)
9 | - ours?
10 | - us
11 | - let's
12 |
--------------------------------------------------------------------------------
/apps/lgc/moon.yml:
--------------------------------------------------------------------------------
1 | language: 'rust'
2 | type: 'application'
3 |
4 | project:
5 | name: 'lgc'
6 | description: 'LogCraft Command Line Interface (CLI)'
7 |
8 | dependsOn:
9 | - 'lgc-common'
10 | - 'lgc-runtime'
11 |
12 | tasks:
13 | run:
14 | command: 'cargo run'
15 | deps:
16 | - '#plugin:build'
17 |
--------------------------------------------------------------------------------
/.dockerignore:
--------------------------------------------------------------------------------
1 | # Version control
2 | .git
3 | .gitignore
4 | .github
5 |
6 | # Docker-related files
7 | Dockerfile
8 | .dockerignore
9 |
10 | # Documentation and miscellaneous files
11 | docs
12 | README.md
13 | licenserc.toml
14 | .prototools
15 | .moon
16 | scripts
17 |
18 | # Cargo build output (generated artifacts)
19 | target
--------------------------------------------------------------------------------
/docs/vale/styles/Google/Exclamation.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Don't use exclamation points in text."
3 | link: "https://developers.google.com/style/exclamation-points"
4 | nonword: true
5 | level: error
6 | action:
7 | name: edit
8 | params:
9 | - trim_right
10 | - "!"
11 | tokens:
12 | - '\w+!(?:\s|$)'
13 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/Skunked.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "'%s' is a bit of a skunked term — impossible to use without issue."
3 | ignorecase: true
4 | level: error
5 | tokens:
6 | - bona fides
7 | - deceptively
8 | - decimate
9 | - effete
10 | - fulsome
11 | - hopefully
12 | - impassionate
13 | - Thankfully
14 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/LyHyphens.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "'%s' doesn't need a hyphen."
3 | link: "https://developers.google.com/style/hyphens"
4 | level: error
5 | ignorecase: false
6 | nonword: true
7 | action:
8 | name: edit
9 | params:
10 | - regex
11 | - "-"
12 | - " "
13 | tokens:
14 | - '\b[^\s-]+ly-\w+\b'
15 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/LGBTOffensive.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "'%s' is offensive. Remove it or consider the context."
3 | ignorecase: true
4 | tokens:
5 | - fag
6 | - faggot
7 | - dyke
8 | - sodomite
9 | - homosexual agenda
10 | - gay agenda
11 | - transvestite
12 | - homosexual lifestyle
13 | - gay lifestyle
14 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/Latin.yml:
--------------------------------------------------------------------------------
1 | extends: substitution
2 | message: "Use '%s' instead of '%s'."
3 | link: 'https://developers.google.com/style/abbreviations'
4 | ignorecase: true
5 | level: error
6 | nonword: true
7 | action:
8 | name: replace
9 | swap:
10 | '\b(?:eg|e\.g\.)(?=[\s,;])': for example
11 | '\b(?:ie|i\.e\.)(?=[\s,;])': that is
12 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/OptionalPlurals.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Don't use plurals in parentheses such as in '%s'."
3 | link: "https://developers.google.com/style/plurals-parentheses"
4 | level: error
5 | nonword: true
6 | action:
7 | name: edit
8 | params:
9 | - trim_right
10 | - "(s)"
11 | tokens:
12 | - '\b\w+\(s\)'
13 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | # rust
2 | target/
3 | debug/
4 | **/*.rs.bk
5 |
6 | # moon
7 | .moon/cache
8 | .moon/docker
9 |
10 | # Editor
11 | *.swp
12 | *.swo
13 | .idea
14 | .vscode
15 |
16 | # Vue/JS
17 | node_modules/
18 | dist/
19 | cache/
20 |
21 | # MISC
22 | .DS_Store
23 |
24 | # Custom releases
25 | releases/
26 |
27 | # Dev folder for testing purposes
28 | dev/
--------------------------------------------------------------------------------
/docs/vale/styles/Google/FirstPerson.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Avoid first-person pronouns such as '%s'."
3 | link: 'https://developers.google.com/style/pronouns#personal-pronouns'
4 | ignorecase: true
5 | level: warning
6 | nonword: true
7 | tokens:
8 | - (?:^|\s)I\s
9 | - (?:^|\s)I,\s
10 | - \bI'm\b
11 | - \bme\b
12 | - \bmy\b
13 | - \bmine\b
14 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/DateRedundancy.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "'a.m.' is always morning; 'p.m.' is always night."
3 | ignorecase: true
4 | level: error
5 | nonword: true
6 | tokens:
7 | - '\d{1,2} ?a\.?m\.? in the morning'
8 | - '\d{1,2} ?p\.?m\.? in the evening'
9 | - '\d{1,2} ?p\.?m\.? at night'
10 | - '\d{1,2} ?p\.?m\.? in the afternoon'
11 |
--------------------------------------------------------------------------------
/docs/src/.vitepress/theme/components/plugins/common.js:
--------------------------------------------------------------------------------
1 | export const getCategoryColor = (stage) => {
2 | switch (stage.toLowerCase()) {
3 | case "siem":
4 | return "teal";
5 | case "xdr":
6 | return "blue";
7 | case "edr":
8 | return "indigo";
9 | case "format":
10 | return "purple";
11 | default:
12 | return "grey";
13 | }
14 | };
15 |
--------------------------------------------------------------------------------
/libs/lgc-policies/Cargo.toml:
--------------------------------------------------------------------------------
1 | [package]
2 | name = "lgc-policies"
3 | version = "0.1.0"
4 | edition.workspace = true
5 | rust-version.workspace = true
6 | repository.workspace = true
7 |
8 | [dependencies]
9 | serde.workspace = true
10 | serde_json.workspace = true
11 |
12 | [dev-dependencies]
13 | rstest = "0.25.0"
14 | jsonschema.workspace = true
15 | serde_yaml_ng.workspace = true
16 |
--------------------------------------------------------------------------------
/docs/vale/.vale.ini:
--------------------------------------------------------------------------------
1 | StylesPath = styles
2 | MinAlertLevel = warning
3 |
4 | # installed packages, use `vale sync` to install/update
5 | Packages = Google, proselint
6 |
7 | # LogCraft terms (case sensitive)
8 | # `styles/config/vocabularies/LogCraft/{accept.txt,reject.txt}`
9 | Vocab = LogCraft
10 |
11 | [*.{md}]
12 | BasedOnStyles = Vale, Google, proselint
13 | TokenIgnores = (\w+@logcraft\.io)
14 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/HeadingPunctuation.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Don't put a period at the end of a heading."
3 | link: "https://developers.google.com/style/capitalization#capitalization-in-titles-and-headings"
4 | nonword: true
5 | level: warning
6 | scope: heading
7 | action:
8 | name: edit
9 | params:
10 | - trim_right
11 | - "."
12 | tokens:
13 | - '[a-z0-9][.]\s*$'
14 |
--------------------------------------------------------------------------------
/docs/src/plugins/index.md:
--------------------------------------------------------------------------------
1 | # Plugins
2 |
3 | LogCraft can support a wide range of technologies.
4 |
5 |
6 |
7 |
8 |
9 | ::: tip What about vendor/technology X?
10 | Contact us at hello@logcraft.io if your favorite technology is not listed there, we'll be happy to review if that's a good fit.
11 | :::
12 |
13 |
14 |
--------------------------------------------------------------------------------
/docs/src/plugins/sekoia.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: Sekoia
3 | category: XDR
4 | stage: planning
5 | ---
6 |
7 | # Sekoia
8 |
9 |
10 |
11 | ::: tip Need This?
12 | [Open a ticket](https://github.com/LogCraftIO/logcraft-cli/issues) or [reach out](mailto:hello@logcraft.io) to initiate the integration of this technology :tada:
13 | :::
14 |
--------------------------------------------------------------------------------
/docs/src/plugins/tanium.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: Tanium
3 | category: EDR
4 | stage: planning
5 | ---
6 |
7 | # Tanium
8 |
9 |
10 |
11 | ::: tip Need This?
12 | [Open a ticket](https://github.com/LogCraftIO/logcraft-cli/issues) or [reach out](mailto:hello@logcraft.io) to initiate the integration of this technology :tada:
13 | :::
14 |
--------------------------------------------------------------------------------
/docs/src/plugins/yara.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: Yara
3 | category: Format
4 | stage: planning
5 | ---
6 |
7 | # Yara rules
8 |
9 |
10 |
11 | ::: tip Need This?
12 | [Open a ticket](https://github.com/LogCraftIO/logcraft-cli/issues) or [reach out](mailto:hello@logcraft.io) to initiate the integration of this technology :tada:
13 | :::
14 |
--------------------------------------------------------------------------------
/docs/src/plugins/crowdstrike.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: CrowdStrike
3 | category: EDR
4 | stage: planning
5 | ---
6 |
7 | # CrowdStrike
8 |
9 |
10 |
11 | ::: tip Need This?
12 | [Open a ticket](https://github.com/LogCraftIO/logcraft-cli/issues) or [reach out](mailto:hello@logcraft.io) to initiate the integration of this technology :tada:
13 | :::
14 |
--------------------------------------------------------------------------------
/libs/lgc-common/src/detections.rs:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2023 LogCraft.io.
2 | // SPDX-License-Identifier: MPL-2.0
3 |
4 | use serde_json::Value;
5 | use std::collections;
6 |
7 | // Helper types to store detections per service
8 | pub type PluginsDetections = collections::HashMap>;
9 |
10 | /// Detection type alias for a detection path and its content.
11 | pub type Detection = (String, Vec);
12 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/DateFormat.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "Use 'July 31, 2016' format, not '%s'."
3 | link: 'https://developers.google.com/style/dates-times'
4 | ignorecase: true
5 | level: error
6 | nonword: true
7 | tokens:
8 | - '\d{1,2}(?:\.|/)\d{1,2}(?:\.|/)\d{4}'
9 | - '\d{1,2} (?:Jan(?:uary)?|Feb(?:ruary)?|Mar(?:ch)?|Apr(?:il)|May|Jun(?:e)|Jul(?:y)|Aug(?:ust)|Sep(?:tember)?|Oct(?:ober)|Nov(?:ember)?|Dec(?:ember)?) \d{4}'
10 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/Spelling.yml:
--------------------------------------------------------------------------------
1 | extends: consistency
2 | message: "Inconsistent spelling of '%s'."
3 | level: error
4 | ignorecase: true
5 | either:
6 | advisor: adviser
7 | centre: center
8 | colour: color
9 | emphasise: emphasize
10 | finalise: finalize
11 | focussed: focused
12 | labour: labor
13 | learnt: learned
14 | organise: organize
15 | organised: organized
16 | organising: organizing
17 | recognise: recognize
18 |
--------------------------------------------------------------------------------
/.moon/tasks/rust.yml:
--------------------------------------------------------------------------------
1 | tasks:
2 | build:
3 | command: 'cargo build --release'
4 | deps:
5 | - '^:build'
6 | inputs:
7 | - 'src/**/*'
8 | - 'Cargo.toml'
9 | format:
10 | command: 'cargo fmt --all -- --check'
11 | test:
12 | command: 'cargo test'
13 | clippy:
14 | command: 'cargo clippy'
15 | check:
16 | command: 'cargo check'
17 | run:
18 | command: 'cargo run'
19 | preset: 'server'
20 | clean:
21 | command: 'cargo clean'
22 |
--------------------------------------------------------------------------------
/.github/workflows/license-enforcement.yml:
--------------------------------------------------------------------------------
1 | on:
2 | push:
3 | branches:
4 | - main
5 | pull_request:
6 | branches:
7 | - main
8 |
9 | name: License enforcement
10 |
11 | permissions:
12 | contents: read
13 |
14 | jobs:
15 | licenses:
16 | runs-on: ubuntu-latest
17 | timeout-minutes: 10
18 | env:
19 | FORCE_COLOR: 1
20 | steps:
21 | - uses: actions/checkout@v4
22 | - name: Check License Header
23 | uses: apache/skywalking-eyes/header@main
--------------------------------------------------------------------------------
/docs/src/plugins/paloalto-cortex.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: Palo Alto Cortex
3 | category: XDR
4 | stage: planning
5 | ---
6 |
7 |
8 |
9 | # Palo Alto Cortex
10 |
11 |
12 |
13 |
14 |
15 | ::: tip Need This?
16 | [Open a ticket](https://github.com/LogCraftIO/logcraft-cli/issues) or [reach out](mailto:hello@logcraft.io) to initiate the integration of this technology :tada:
17 | :::
18 |
--------------------------------------------------------------------------------
/docs/vale/styles/config/vocabularies/LogCraft/accept.txt:
--------------------------------------------------------------------------------
1 | # LogCraft
2 | LogCraft
3 | lgc
4 |
5 | # Security Vendors
6 | CrowdStrike
7 | LimaCharlie
8 | Microsoft
9 | Palo
10 | Sekoia
11 | Splunk
12 | Tanium
13 |
14 | # Version Control Systems
15 | Bitbucket
16 | GitHub
17 | GitLab
18 |
19 | # MISC
20 | [tT]ada
21 |
22 | # Tech terms
23 | bool
24 | boolean
25 | dev
26 | enum
27 | https?
28 | (?i)jwt
29 | (?i)local
30 | [mM]onorepo
31 | moonrepo
32 | prod
33 | string
34 | Yara
35 | (?i)wasm
36 | Wolfi
37 | camelCase
38 |
39 | # Splunk
40 | savedsearches
41 |
--------------------------------------------------------------------------------
/plugins/sample/Cargo.toml:
--------------------------------------------------------------------------------
1 | [package]
2 | name = "sample"
3 | description = "LogCraft CLI testing plugin"
4 | version = "0.1.0"
5 | edition.workspace = true
6 | repository.workspace = true
7 | rust-version.workspace = true
8 |
9 | [lib]
10 | crate-type = ["cdylib"]
11 |
12 | [dependencies]
13 | # Utils
14 | serde.workspace = true
15 | serde_json.workspace = true
16 | serde_yaml_ng = "0.10"
17 | once_cell = "1.20"
18 |
19 | # Schema related
20 | schemars.workspace = true
21 | jsonschema.workspace = true
22 |
23 | # WASM Related
24 | wit-bindgen.workspace = true
25 |
--------------------------------------------------------------------------------
/docs/src/developers/docker-images.md:
--------------------------------------------------------------------------------
1 | # Docker Image
2 |
3 | Pre-built Docker images that includes lgc are accessible through GitHub registry:
4 |
5 | ```bash
6 | docker pull ghcr.io/logcraftio/logcraft-cli:latest
7 | ```
8 |
9 | LogCraft's containers use [Wolfi "Zero-CVE" images](https://www.chainguard.dev), which are specifically designed to minimize the attack surface and enhance the security of the software supply chain.
10 |
11 | ::: tip Packages
12 | Docker images are available at: https://github.com/LogCraftIO/logcraft-cli/pkgs/container/logcraft-cli
13 | :::
14 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/Oxymorons.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "'%s' is an oxymoron."
3 | ignorecase: true
4 | level: error
5 | tokens:
6 | - amateur expert
7 | - increasingly less
8 | - advancing backwards
9 | - alludes explicitly to
10 | - explicitly alludes to
11 | - totally obsolescent
12 | - completely obsolescent
13 | - generally always
14 | - usually always
15 | - increasingly less
16 | - build down
17 | - conspicuous absence
18 | - exact estimate
19 | - found missing
20 | - intense apathy
21 | - mandatory choice
22 | - organized mess
23 |
--------------------------------------------------------------------------------
/docs/moon.yml:
--------------------------------------------------------------------------------
1 | language: 'typescript'
2 | type: 'application'
3 |
4 | project:
5 | name: 'docs'
6 | description: 'LogCraft User Documentation'
7 |
8 | tasks:
9 | build:
10 | command: 'pnpm build'
11 | deps:
12 | - '^:build'
13 | inputs:
14 | - 'src/**/*'
15 | - 'package.json'
16 | outputs:
17 | - 'src/.vitepress/dist/**/*'
18 | dev:
19 | command: 'pnpm dev'
20 | check:
21 | # passthrough arguments:
22 | # `lgc docs:check -- --minAlertLevel=suggestion`
23 | command: 'vale --config ./vale/.vale.ini src'
24 | inputs:
25 | - 'src/**/*.md'
26 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/RASSyndrome.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "'%s' is redundant."
3 | level: error
4 | action:
5 | name: edit
6 | params:
7 | - split
8 | - ' '
9 | - '0'
10 | tokens:
11 | - ABM missile
12 | - ACT test
13 | - ABM missiles
14 | - ABS braking system
15 | - ATM machine
16 | - CD disc
17 | - CPI Index
18 | - GPS system
19 | - GUI interface
20 | - HIV virus
21 | - ISBN number
22 | - LCD display
23 | - PDF format
24 | - PIN number
25 | - RAS syndrome
26 | - RIP in peace
27 | - please RSVP
28 | - SALT talks
29 | - SAT test
30 | - UPC codes
31 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/Headings.yml:
--------------------------------------------------------------------------------
1 | extends: capitalization
2 | message: "'%s' should use sentence-style capitalization."
3 | link: "https://developers.google.com/style/capitalization#capitalization-in-titles-and-headings"
4 | level: warning
5 | scope: heading
6 | match: $sentence
7 | indicators:
8 | - ":"
9 | exceptions:
10 | - Azure
11 | - CLI
12 | - Cosmos
13 | - Docker
14 | - Emmet
15 | - gRPC
16 | - I
17 | - Kubernetes
18 | - Linux
19 | - macOS
20 | - Marketplace
21 | - MongoDB
22 | - REPL
23 | - Studio
24 | - TypeScript
25 | - URLs
26 | - Visual
27 | - VS
28 | - Windows
29 | - JSON
30 |
--------------------------------------------------------------------------------
/docs/src/.vitepress/theme/components/plugins/plugins.data.js:
--------------------------------------------------------------------------------
1 | import { createContentLoader } from "vitepress";
2 |
3 | const pages = createContentLoader("plugins/*.md", {
4 | includeSrc: false,
5 | render: false,
6 | excerpt: false,
7 | transform(rawData) {
8 | return rawData
9 | .filter((item) => {
10 | // do not return the index page
11 | return item.url !== "/plugins/";
12 | })
13 | .sort((a, b) => {
14 | // sort by title alphabetically
15 | return a.frontmatter.title.localeCompare(b.frontmatter.title);
16 | });
17 | },
18 | });
19 |
20 | export default pages;
21 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # LogCraft CLI
2 |
3 | LogCraft CLI `lgc` is an opensource utility that simplifies the adoption of Detection as Code principles with legacy SIEM, EDR, XDR and any other modern security solutions while leveraging native capabilities of GitLab, GitHub, Bitbucket and other Version Control Systems (VCS).
4 |
5 | ---
6 |
7 | **Documentation**: https://docs.logcraft.io
8 |
9 | **Source Code**: https://github.com/LogCraftIO/logcraft-cli
10 |
11 | ---
12 |
13 | 
14 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/meta.json:
--------------------------------------------------------------------------------
1 | {
2 | "author": "jdkato",
3 | "description": "A Vale-compatible implementation of the proselint linter.",
4 | "email": "support@errata.ai",
5 | "lang": "en",
6 | "url": "https://github.com/errata-ai/proselint/releases/latest/download/proselint.zip",
7 | "feed": "https://github.com/errata-ai/proselint/releases.atom",
8 | "issues": "https://github.com/errata-ai/proselint/issues/new",
9 | "license": "BSD-3-Clause",
10 | "name": "proselint",
11 | "sources": [
12 | "https://github.com/amperser/proselint"
13 | ],
14 | "vale_version": ">=1.0.0",
15 | "coverage": 0.0,
16 | "version": "0.1.0"
17 | }
18 |
--------------------------------------------------------------------------------
/docs/src/index.md:
--------------------------------------------------------------------------------
1 | # Overview
2 |
3 | `lgc` is an open source tool that simplifies the creation of Detection-as-Code pipelines while leveraging native capabilities of GitLab, GitHub, Bitbucket and other Version Control Systems (VCS).
4 |
5 | With `lgc`, easily deploy your security detections into your SIEM, EDR, XDR, and other modern security solutions.
6 |
7 |
8 |
9 | 
10 |
11 |
12 |
13 | At a high level, lgc is pretty straightforward as it reads detection files and manage them individually and programmatically through a plugin system.
14 |
--------------------------------------------------------------------------------
/docs/src/.vitepress/theme/components/plugins/PluginsIndexPage.vue:
--------------------------------------------------------------------------------
1 |
2 |
14 |
15 |
16 |
21 |
--------------------------------------------------------------------------------
/libs/lgc-runtime/Cargo.toml:
--------------------------------------------------------------------------------
1 | [package]
2 | name = "lgc-runtime"
3 | version = "0.1.0"
4 | edition.workspace = true
5 | rust-version.workspace = true
6 | repository.workspace = true
7 |
8 | [dependencies]
9 | # Utils
10 | anyhow.workspace = true
11 | tracing.workspace = true
12 | tracing-subscriber.workspace = true
13 |
14 | # Async
15 | tokio.workspace = true
16 | crossbeam-channel = "0.5"
17 |
18 | # HTTP related
19 | http.workspace = true
20 | hyper = { version = "1.0.1", features = ["full"] }
21 | tokio-native-tls = "0.3.1"
22 | http-body-util = "0.1.1"
23 |
24 | # WASM Related
25 | wasmtime.workspace = true
26 | wasmtime-wasi.workspace = true
27 | wasmtime-wasi-http.workspace = true
28 |
--------------------------------------------------------------------------------
/.github/workflows/validate.yml:
--------------------------------------------------------------------------------
1 | on:
2 | push:
3 | branches:
4 | - main
5 | pull_request:
6 | branches:
7 | - main
8 |
9 | name: Code testing and formatting
10 |
11 | jobs:
12 | validate:
13 | runs-on: macos-15
14 | steps:
15 | - name: Checkout code
16 | uses: actions/checkout@v4
17 | with:
18 | fetch-depth: 0
19 | # Prepare the toolchain
20 | - uses: 'moonrepo/setup-toolchain@v0'
21 | # Check code formatting
22 | - run: "moon :format --affected --remote"
23 | # Linting with clippy
24 | - run: "moon :clippy --affected --remote"
25 | # Run tests
26 | - run: "moon :test --affected --remote"
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/LGBTTerms.yml:
--------------------------------------------------------------------------------
1 | extends: substitution
2 | message: "Consider using '%s' instead of '%s'."
3 | ignorecase: true
4 | action:
5 | name: replace
6 | swap:
7 | homosexual man: gay man
8 | homosexual men: gay men
9 | homosexual woman: lesbian
10 | homosexual women: lesbians
11 | homosexual people: gay people
12 | homosexual couple: gay couple
13 | sexual preference: sexual orientation
14 | (?:admitted homosexual|avowed homosexual): openly gay
15 | special rights: equal rights
16 |
--------------------------------------------------------------------------------
/docs/src/support.md:
--------------------------------------------------------------------------------
1 | ---
2 | vale:
3 | Google.We: NO
4 | Google.Will: NO
5 | ---
6 |
7 | # Getting help
8 |
9 |
10 |
11 |
12 | Reach out if you are experiencing any issue, have a suggestion for improvement, or need any other type of assistance. We will be happy to connect.
13 |
14 |
15 |
16 |
17 | ## Customer support
18 |
19 | Contact the customer service team at [support@logcraft.io](mailto:support@logcraft.io)
20 |
21 | ## Community support
22 |
23 | [Open a ticket](https://github.com/LogCraftIO/logcraft-cli/issues) with enough details about the issue encountered or the feature requested. You now the drill ;)
24 |
--------------------------------------------------------------------------------
/plugins/splunk/Cargo.toml:
--------------------------------------------------------------------------------
1 | [package]
2 | name = "splunk"
3 | description = "LogCraft CLI Splunk plugin"
4 | version = "0.2.0"
5 | edition.workspace = true
6 | repository.workspace = true
7 | rust-version.workspace = true
8 |
9 | [lib]
10 | crate-type = ["cdylib"]
11 |
12 | [dependencies]
13 | # Utils
14 | serde.workspace = true
15 | serde_json.workspace = true
16 | serde_with_macros.workspace = true
17 | serde_path_to_error.workspace = true
18 | once_cell.workspace = true
19 |
20 | # Schema related
21 | schemars.workspace = true
22 | jsonschema.workspace = true
23 |
24 | # WASM Related
25 | wit-bindgen.workspace = true
26 |
27 | # HTTP
28 | waki = { workspace = true, features = ["json"] }
29 | url.workspace = true
30 | http.workspace = true
31 |
--------------------------------------------------------------------------------
/docs/vale/styles/Google/Contractions.yml:
--------------------------------------------------------------------------------
1 | extends: substitution
2 | message: "Use '%s' instead of '%s'."
3 | link: 'https://developers.google.com/style/contractions'
4 | level: suggestion
5 | ignorecase: true
6 | action:
7 | name: replace
8 | swap:
9 | are not: aren't
10 | cannot: can't
11 | could not: couldn't
12 | did not: didn't
13 | do not: don't
14 | does not: doesn't
15 | has not: hasn't
16 | have not: haven't
17 | how is: how's
18 | is not: isn't
19 | it is: it's
20 | should not: shouldn't
21 | that is: that's
22 | they are: they're
23 | was not: wasn't
24 | we are: we're
25 | we have: we've
26 | were not: weren't
27 | what is: what's
28 | when is: when's
29 | where is: where's
30 | will not: won't
31 |
--------------------------------------------------------------------------------
/.licenserc.yaml:
--------------------------------------------------------------------------------
1 | # Copyright (c) 2023 LogCraft.io.
2 | # SPDX-License-Identifier: MPL-2.0
3 |
4 | header:
5 | license:
6 | content: |
7 | Copyright (c) 2023 LogCraft.io.
8 | SPDX-License-Identifier: MPL-2.0
9 |
10 | paths-ignore:
11 | # Moon
12 | - ".moon/**"
13 | # Documentation
14 | - "docs/**"
15 | # Scripts
16 | - "scripts/**"
17 | # Unneeded
18 | - "Dockerfile"
19 | # Generated files
20 | - ".github/**"
21 | # Unmanaged
22 | - "**/Cargo.*"
23 | - ".prototools"
24 | - ".dockerignore"
25 | - ".gitignore"
26 | - "LICENSE"
27 | - "**/moon.yml"
28 | - "**/README.md"
29 |
30 | comment: on-failure
31 |
32 | dependency:
33 | files:
34 | - Cargo.toml
35 |
--------------------------------------------------------------------------------
/libs/lgc-policies/src/helpers.rs:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2023 LogCraft.io.
2 | // SPDX-License-Identifier: MPL-2.0
3 |
4 | use serde_json::{json, Value};
5 |
6 | /// Parses the target field into a list of parts for path composition.
7 | pub(crate) fn parse_field(field: &str) -> Vec<&str> {
8 | if field.starts_with('/') {
9 | field.trim_start_matches('/').split('/').collect()
10 | } else {
11 | field.split('.').collect()
12 | }
13 | }
14 |
15 | /// Builds a nested JSON Schema.
16 | pub(crate) fn build_nested(parts: &[&str], leaf: Value) -> Value {
17 | parts.iter().rev().fold(leaf, |acc, &part| {
18 | json!({
19 | "type": "object",
20 | "properties": { part: acc },
21 | "required": [part]
22 | })
23 | })
24 | }
25 |
--------------------------------------------------------------------------------
/docs/src/.vitepress/theme/index.ts:
--------------------------------------------------------------------------------
1 | import type { Theme } from "vitepress";
2 | import DefaultTheme from "vitepress/theme";
3 |
4 | // Custom components
5 | import PluginsIndexPage from "./components/plugins/PluginsIndexPage.vue";
6 | import PluginStatus from "./components/plugins/PluginStatus.vue";
7 |
8 | // Vuetify
9 | import "vuetify/styles";
10 | import { createVuetify } from "vuetify";
11 | import { VChip } from "vuetify/components";
12 |
13 | const vuetify = createVuetify({
14 | components: {
15 | VChip,
16 | },
17 | });
18 |
19 | export default {
20 | extends: DefaultTheme,
21 | enhanceApp({ app }) {
22 | app.use(vuetify);
23 | app.component("PluginsIndexPage", PluginsIndexPage);
24 | app.component("PluginStatus", PluginStatus);
25 | },
26 | } satisfies Theme;
27 |
--------------------------------------------------------------------------------
/docs/src/plugins/limacharlie.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: LimaCharlie
3 | category: EDR
4 | stage: planning
5 | ---
6 |
7 | # LimaCharlie
8 |
9 |
10 |
11 | ::: tip Need This?
12 | [Open a ticket](https://github.com/LogCraftIO/logcraft-cli/issues) or [reach out](mailto:hello@logcraft.io) to initiate the integration of this technology :tada:
13 | :::
14 |
15 | ## Example
16 |
17 | ```yaml
18 | # Detection
19 | op: ends with
20 | event: NEW_PROCESS
21 | path: event/FILE_PATH
22 | value: wanadecryptor.exe
23 | case sensitive: false
24 |
25 | # Response
26 | - action: report
27 | name: wanacry
28 | - action: task
29 | command: history_dump
30 | - action: task
31 | command:
32 | - deny_tree
33 | - <>
34 | ```
35 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/CorporateSpeak.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "'%s' is corporate speak."
3 | ignorecase: true
4 | level: error
5 | tokens:
6 | - at the end of the day
7 | - back to the drawing board
8 | - hit the ground running
9 | - get the ball rolling
10 | - low-hanging fruit
11 | - thrown under the bus
12 | - think outside the box
13 | - let's touch base
14 | - get my manager's blessing
15 | - it's on my radar
16 | - ping me
17 | - i don't have the bandwidth
18 | - no brainer
19 | - par for the course
20 | - bang for your buck
21 | - synergy
22 | - move the goal post
23 | - apples to apples
24 | - win-win
25 | - circle back around
26 | - all hands on deck
27 | - take this offline
28 | - drill-down
29 | - elephant in the room
30 | - on my plate
31 |
--------------------------------------------------------------------------------
/plugins/sentinel/Cargo.toml:
--------------------------------------------------------------------------------
1 | [package]
2 | name = "sentinel"
3 | description = "LogCraft CLI Sentinel plugin"
4 | version = "0.2.0"
5 | edition.workspace = true
6 | repository.workspace = true
7 | rust-version.workspace = true
8 |
9 | [lib]
10 | crate-type = ["cdylib"]
11 |
12 | [dependencies]
13 | # Utils
14 | serde.workspace = true
15 | serde_json.workspace = true
16 | serde_with_macros.workspace = true
17 | serde_path_to_error.workspace = true
18 | once_cell.workspace = true
19 | uuid = { version = "1.14", features = ["v4", "serde"] }
20 |
21 | # Schema related
22 | schemars = { workspace = true, features = ["uuid1"] }
23 | jsonschema.workspace = true
24 |
25 | # WASM Related
26 | wit-bindgen.workspace = true
27 |
28 | # HTTP
29 | waki = { workspace = true, features = ["json"] }
30 | url.workspace = true
31 | http.workspace = true
32 |
--------------------------------------------------------------------------------
/docs/src/essentials/configuration.md:
--------------------------------------------------------------------------------
1 | # Configuration
2 |
3 | This section details the core options of `lgc.toml`. For services options, please refer to the appropriate [plugin documentation](../plugins/index.md).
4 |
5 |
6 |
7 | ## `workspace`
8 |
9 | ```toml
10 | [core]
11 | workspace = "rules"
12 | ```
13 |
14 | This parameter defines the base directory in which detections are stored (default: rules). This parameter can be overridden with the environment variable `LGC_CORE_WORKSPACE`.
15 |
16 | ## `base_dir`
17 |
18 | ```toml
19 | [core]
20 | base_dir = "/opt/logcraft-cli"
21 | ```
22 |
23 | This parameter defines the home directory of lgc, where the binary and plugins directory are located (default: `/opt/logcraft-cli`). This shouldn't be changed in most situations. This parameter can be overridden with the environment variable `LGC_CORE_BASE_DIR`.
24 |
--------------------------------------------------------------------------------
/docs/src/.vitepress/theme/components/plugins/PluginStatus.vue:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
Category
5 |
6 | {{ category }}
7 |
8 |
9 |
10 |
Stage
11 |
12 | {{ stage }}
13 |
14 |
15 |
16 |
17 |
18 |
26 |
27 |
34 |
--------------------------------------------------------------------------------
/scripts/package-plugins.sh:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env bash
2 | set -euo pipefail
3 |
4 | #############################################################
5 | # This script creates a tarball (`plugins.tar.gz`) #
6 | # containing all plugins and their checksums. #
7 | # The resulting files are moved to a `releases/` directory. #
8 | #############################################################
9 |
10 | # Create a `releases` directory
11 | mkdir -p releases
12 |
13 | # Create a tarball with the plugins, placing them under a `plugins/` folder in the tarball
14 | find target/wasm32-wasip2/release/ \
15 | -type f \( -name "*.wasm" \) -print0 \
16 | | tar --null --transform 's|.*/|plugins/|' -czvf plugins.tar.gz --files-from -
17 |
18 | # Move the tarball to the releases directory and generate its checksum
19 | sha256sum plugins.tar.gz > releases/plugins.tar.gz.sha256
20 | mv plugins.tar.gz releases/
21 |
22 | echo "Tarball created successfully."
--------------------------------------------------------------------------------
/docs/src/commands/destroy.md:
--------------------------------------------------------------------------------
1 | # lgc destroy
2 |
3 | This command is a convenient way to clean up remote services, especially ephemeral environments often encountered for development purposes. This command removes all detections from the target services.
4 |
5 | ```sh
6 | % lgc destroy
7 | ```
8 |
9 | ## Options
10 |
11 |
12 |
13 | ### --auto-approve
14 |
15 |
16 |
17 | The `--auto-approve` flag skips the prompt and immediately remove the detections from the remote services. This is especially handy in CI/CD workflows.
18 |
19 | Normal (interactive) run:
20 |
21 | ```bash
22 | % lgc destroy dev
23 | ... list of suppression ...
24 | Apply changes? (y/n)
25 | // changes are applied if the user confirm 'yes'
26 | %
27 | ```
28 |
29 | Non-interactive run:
30 |
31 | ```bash
32 | % lgc destroy --auto-approve
33 | ... list of changes ...
34 | // changes are applied automatically
35 | %
36 | ```
37 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/Archaisms.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "'%s' is archaic."
3 | ignorecase: true
4 | level: error
5 | tokens:
6 | - alack
7 | - anent
8 | - begat
9 | - belike
10 | - betimes
11 | - boughten
12 | - brocage
13 | - brokage
14 | - camarade
15 | - chiefer
16 | - chiefest
17 | - Christiana
18 | - completely obsolescent
19 | - cozen
20 | - divers
21 | - deflexion
22 | - fain
23 | - forsooth
24 | - foreclose from
25 | - haply
26 | - howbeit
27 | - illumine
28 | - in sooth
29 | - maugre
30 | - meseems
31 | - methinks
32 | - nigh
33 | - peradventure
34 | - perchance
35 | - saith
36 | - shew
37 | - sistren
38 | - spake
39 | - to wit
40 | - verily
41 | - whilom
42 | - withal
43 | - wot
44 | - enclosed please find
45 | - please find enclosed
46 | - enclosed herewith
47 | - enclosed herein
48 | - inforce
49 | - ex postfacto
50 | - foreclose from
51 | - forewent
52 | - for ever
53 |
--------------------------------------------------------------------------------
/docs/src/concepts/plugins.md:
--------------------------------------------------------------------------------
1 | # Plugins
2 |
3 | LogCraft rely on plugins to connect to remote security systems.
4 |
5 |
6 |
7 | ## Web Assembly (WASM)
8 |
9 |
10 |
11 | LogCraft plugins are built on the open standard WebAssembly (WASM).
12 |
13 | **These plugins run in memory-safe sandboxes**, making them secure by design. Beyond security, WASM modules offer exceptional performance due to their low-level binary format, optimized for modern processors. **This enables near-native execution speeds**.
14 |
15 | Additionally, WASM supports a wide range of programming languages, allowing LogCraft plugins to be [developed](../developers/how-to-create-plugins.md) in almost any language.
16 |
17 | ::: tip NIST
18 | In a recent study, [NIST](https://csrc.nist.gov/) emphasized the use of WebAssembly to enhance data protection strategies ([NIST IR 8505](https://csrc.nist.gov/News/2024/nist-has-published-nist-ir-8505))
19 | :::
20 |
--------------------------------------------------------------------------------
/docs/vale/styles/proselint/Uncomparables.yml:
--------------------------------------------------------------------------------
1 | extends: existence
2 | message: "'%s' is not comparable"
3 | ignorecase: true
4 | level: error
5 | action:
6 | name: edit
7 | params:
8 | - split
9 | - ' '
10 | - '1'
11 | raw:
12 | - \b(?:absolutely|most|more|less|least|very|quite|largely|extremely|increasingly|kind of|mildy|hardly|greatly|sort of)\b\s*
13 | tokens:
14 | - absolute
15 | - adequate
16 | - complete
17 | - correct
18 | - certain
19 | - devoid
20 | - entire
21 | - 'false'
22 | - fatal
23 | - favorite
24 | - final
25 | - ideal
26 | - impossible
27 | - inevitable
28 | - infinite
29 | - irrevocable
30 | - main
31 | - manifest
32 | - only
33 | - paramount
34 | - perfect
35 | - perpetual
36 | - possible
37 | - preferable
38 | - principal
39 | - singular
40 | - stationary
41 | - sufficient
42 | - 'true'
43 | - unanimous
44 | - unavoidable
45 | - unbroken
46 | - uniform
47 | - unique
48 | - universal
49 | - void
50 | - whole
51 |
--------------------------------------------------------------------------------
/libs/bindings/plugin.wit:
--------------------------------------------------------------------------------
1 | // Copyright (c) 2023 LogCraft.io.
2 | // SPDX-License-Identifier: MPL-2.0
3 |
4 | interface plugin {
5 | type bytes = list;
6 |
7 | /// The metadata for a plugin used for registration and setup
8 | record metadata {
9 | /// The friendly name of the plugin
10 | name: string,
11 | /// The version of the plugin
12 | version: string,
13 | }
14 |
15 | // Plugin actions
16 | load: func() -> metadata;
17 | settings: func() -> result;
18 | schema: func() -> result;
19 | validate: func(detection: bytes) -> result<_, string>;
20 |
21 | // Service actions
22 | // CRUD definition
23 | create: func(config: bytes, detection: bytes) -> result<_, string>;
24 | read: func(config: bytes, detection: bytes) -> result