diff --git a/.gitignore b/.gitignore index 5781a1e43a3d..f990c862f53e 100644 --- a/.gitignore +++ b/.gitignore @@ -3,12 +3,13 @@ /.idea /.vscode /build -/*/data -/*/logs -/*/fields.yml /*/*.template*.json **/html_docs -/*/_meta/kibana.generated +*beat/fields.yml +*beat/_meta/kibana.generated +*beat/build +*beat/logs +*beat/data # Files .DS_Store @@ -19,6 +20,7 @@ coverage.out .python-version beat.db *.keystore +mage_output_file.go # Editor swap files *.swp diff --git a/Makefile b/Makefile index 82564069db31..2f7af9becd41 100644 --- a/Makefile +++ b/Makefile @@ -16,7 +16,7 @@ XPACK_SUFFIX=x-pack/ # PROJECTS_XPACK_PKG is a list of Beats that have independent packaging support # in the x-pack directory (rather than having the OSS build produce both sets # of artifacts). This will be removed once we complete the transition. -PROJECTS_XPACK_PKG=x-pack/auditbeat x-pack/filebeat x-pack/metricbeat +PROJECTS_XPACK_PKG=x-pack/auditbeat x-pack/filebeat x-pack/metricbeat x-pack/winlogbeat # PROJECTS_XPACK_MAGE is a list of Beats whose primary build logic is based in # Mage. For compatibility with CI testing these projects support a subset of the # makefile targets. After all Beats converge to primarily using Mage we can diff --git a/dev-tools/.gitignore b/dev-tools/.gitignore index 378eac25d311..796b96d1c402 100644 --- a/dev-tools/.gitignore +++ b/dev-tools/.gitignore @@ -1 +1 @@ -build +/build diff --git a/dev-tools/cmd/module_fields/module_fields.go b/dev-tools/cmd/module_fields/module_fields.go index 6c55f5f2f4bd..5c967ec9ecfd 100644 --- a/dev-tools/cmd/module_fields/module_fields.go +++ b/dev-tools/cmd/module_fields/module_fields.go @@ -23,7 +23,7 @@ import ( "io/ioutil" "log" "os" - "path" + "path/filepath" "github.com/elastic/beats/libbeat/asset" "github.com/elastic/beats/libbeat/generator/fields" @@ -73,6 +73,11 @@ func main() { log.Fatalf("Error fetching modules: %v", err) } + wd, err := os.Getwd() + if err != nil { + log.Fatalf("Failed to determine working directory: %v", err) + } + for _, module := range modules { files, err := fields.CollectFiles(module, dir) if err != nil { @@ -89,12 +94,17 @@ func main() { log.Fatalf("error fetching files for package %v: %v", module, err) } - bs, err := asset.CreateAsset(license, beatName, module, module, data, "asset.ModuleFieldsPri", dir+"/"+module) + p, err := filepath.Rel(wd, filepath.Join(dir, module)) + if err != nil { + log.Fatal(err) + } + + bs, err := asset.CreateAsset(license, beatName, module, module, data, "asset.ModuleFieldsPri", filepath.ToSlash(p)) if err != nil { log.Fatalf("Error creating golang file from template: %v", err) } - err = ioutil.WriteFile(path.Join(dir, module, "fields.go"), bs, 0644) + err = ioutil.WriteFile(filepath.Join(dir, module, "fields.go"), bs, 0644) if err != nil { log.Fatalf("Error writing fields.go: %v", err) } diff --git a/dev-tools/mage/.gitignore b/dev-tools/mage/.gitignore index 378eac25d311..796b96d1c402 100644 --- a/dev-tools/mage/.gitignore +++ b/dev-tools/mage/.gitignore @@ -1 +1 @@ -build +/build diff --git a/dev-tools/mage/dashboard.go b/dev-tools/mage/dashboard.go index 38f6a378e7ab..952efee6f0b0 100644 --- a/dev-tools/mage/dashboard.go +++ b/dev-tools/mage/dashboard.go @@ -19,8 +19,11 @@ package mage import ( "fmt" + "os" "path/filepath" + "strconv" + "github.com/magefile/mage/mg" "github.com/magefile/mage/sh" ) @@ -33,11 +36,9 @@ func ExportDashboard() error { id := EnvOr("ID", "") if id == "" { - return fmt.Errorf("Dashboad ID must be specified") + return fmt.Errorf("Dashboard ID must be specified") } - kibanaURL := EnvOr("KIBANA_URL", "") - beatsDir, err := ElasticBeatsDir() if err != nil { return err @@ -51,9 +52,37 @@ func ExportDashboard() error { "-output", file, "-dashboard", id, ) - if kibanaURL != "" { - return dashboardCmd("-kibana", kibanaURL) - } else { - return dashboardCmd() + return dashboardCmd() +} + +// ImportDashboards imports dashboards to Kibana using the Beat setup command. +// +// Depends on: build, dashboard +// +// Optional environment variables: +// - KIBANA_URL: URL of Kibana +// - KIBANA_ALWAYS: Connect to Kibana without checking ES version. Default true. +// - ES_URL: URL of Elasticsearch (only used with KIBANA_ALWAYS=false). +func ImportDashboards(buildDep, dashboardDep interface{}) error { + mg.Deps(buildDep, dashboardDep) + + setupDashboards := sh.RunCmd(CWD(BeatName+binaryExtension(GOOS)), + "setup", "--dashboards", + "-E", "setup.dashboards.directory="+kibanaBuildDir) + + kibanaAlways := true + if b, err := strconv.ParseBool(os.Getenv("KIBANA_ALWAYS")); err == nil { + kibanaAlways = b + } + + var args []string + if kibanaURL := EnvOr("KIBANA_URL", ""); kibanaURL != "" { + args = append(args, "-E", "setup.kibana.host="+kibanaURL) } + if esURL := EnvOr("ES_URL", ""); !kibanaAlways && esURL != "" { + args = append(args, "-E", "setup.elasticsearch.host="+esURL) + } + args = append(args, "-E", "setup.dashboards.always_kibana="+strconv.FormatBool(kibanaAlways)) + + return setupDashboards(args...) } diff --git a/dev-tools/mage/docs.go b/dev-tools/mage/docs.go index 51bd96c2f226..6734cddfe859 100644 --- a/dev-tools/mage/docs.go +++ b/dev-tools/mage/docs.go @@ -18,18 +18,57 @@ package mage import ( + "context" + "fmt" "log" + "net" + "net/http" + "os" + "os/exec" + "os/signal" + "path/filepath" + "runtime" + "strconv" + "syscall" "github.com/magefile/mage/sh" + "github.com/pkg/errors" +) + +const ( + elasticDocsRepoURL = "https://github.com/elastic/docs.git" ) type docsBuilder struct{} +type asciidocParams struct { + name string + indexFile string +} + +// DocsOption is a documentation generation option for controlling how the docs +// are built. +type DocsOption func(params *asciidocParams) + +// DocsName specifies the documentation's name (default to BeatName). +func DocsName(name string) DocsOption { + return func(params *asciidocParams) { + params.name = name + } +} + +// DocsIndexFile specifies the index file (defaults to docs/index.asciidoc). +func DocsIndexFile(file string) DocsOption { + return func(params *asciidocParams) { + params.indexFile = file + } +} + // Docs holds the utilities for building documentation. var Docs = docsBuilder{} // FieldDocs generates docs/fields.asciidoc from the specified fields.yml file. -func (b docsBuilder) FieldDocs(fieldsYML string) error { +func (docsBuilder) FieldDocs(fieldsYML string) error { // Run the docs_collector.py script. ve, err := PythonVirtualenv() if err != nil { @@ -46,6 +85,7 @@ func (b docsBuilder) FieldDocs(fieldsYML string) error { return err } + // TODO: Port this script to Go. log.Println(">> Generating docs/fields.asciidoc for", BeatName) return sh.Run(python, LibbeatDir("scripts/generate_fields_docs.py"), fieldsYML, // Path to fields.yml. @@ -53,3 +93,92 @@ func (b docsBuilder) FieldDocs(fieldsYML string) error { esBeats, // Path to general beats folder. "--output_path", OSSBeatDir()) // It writes to {output_path}/docs/fields.asciidoc. } + +func (b docsBuilder) AsciidocBook(opts ...DocsOption) error { + params := asciidocParams{ + name: BeatName, + indexFile: CWD("docs/index.asciidoc"), + } + for _, opt := range opts { + opt(¶ms) + } + + repo, err := GetProjectRepoInfo() + if err != nil { + return err + } + + cloneDir := CreateDir(filepath.Join(repo.RootDir, "build/elastic_docs_repo")) + + // Clone if elastic_docs_repo does not exist. + if _, err := os.Stat(cloneDir); err != nil { + log.Println("Cloning elastic/docs to", cloneDir) + if err = sh.Run("git", "clone", "--depth=1", elasticDocsRepoURL, cloneDir); err != nil { + return err + } + } else { + log.Println("Using existing elastic/docs at", cloneDir) + } + + // Render HTML. + htmlDir := CWD("build/html_docs", params.name) + args := []string{ + filepath.Join(cloneDir, "build_docs.pl"), + "--chunk=1", + "--doc", params.indexFile, + "--out", htmlDir, + } + fmt.Println(">> Building HTML docs at", filepath.Join(htmlDir, "index.html")) + if err := sh.Run("perl", args...); err != nil { + return err + } + + // Serve docs with and HTTP server and open the browser. + if preview, _ := strconv.ParseBool(os.Getenv("PREVIEW")); preview { + srv := b.servePreview(htmlDir) + url := "http://" + srv.Addr + fmt.Println("Serving docs preview at", url) + b.openBrowser(url) + + // Wait + fmt.Println("Ctrl+C to stop") + sigs := make(chan os.Signal, 1) + signal.Notify(sigs, syscall.SIGINT, syscall.SIGTERM) + <-sigs + srv.Shutdown(context.Background()) + } + return nil +} + +// open opens the specified URL in the default browser. +func (docsBuilder) openBrowser(url string) error { + var cmd string + var args []string + + switch runtime.GOOS { + case "darwin": + cmd = "open" + case "windows": + cmd = "cmd" + args = []string{"/c", "start"} + default: + cmd = "xdg-open" + } + args = append(args, url) + return exec.Command(cmd, args...).Start() +} + +func (docsBuilder) servePreview(dir string) *http.Server { + server := &http.Server{ + Addr: net.JoinHostPort("localhost", EnvOr("PREVIEW_PORT", "8000")), + Handler: http.FileServer(http.Dir(dir)), + } + + go func() { + if err := server.ListenAndServe(); err != nil && err != http.ErrServerClosed { + panic(errors.Wrap(err, "failed to start docs preview")) + } + }() + + return server +} diff --git a/dev-tools/mage/fields.go b/dev-tools/mage/fields.go index a8508a4d444a..bc4f6cee68ff 100644 --- a/dev-tools/mage/fields.go +++ b/dev-tools/mage/fields.go @@ -25,6 +25,35 @@ import ( "github.com/magefile/mage/sh" ) +const ( + // FieldsYML specifies the path to the file containing the field data for + // the Beat (formerly this was ./fields.yml). + FieldsYML = "build/fields/fields.yml" + // FieldsYMLRoot specifies the filename of the project's root level + // fields.yml file (this is being replaced by FieldsYML). + FieldsYMLRoot = "fields.yml" + // FieldsAllYML specifies the path to the file containing the field data for + // the Beat from all license types. It's generally used for making documentation. + FieldsAllYML = "build/fields/fields.all.yml" +) + +// FieldsBuilder is the interface projects to implement for building field data. +type FieldsBuilder interface { + // Generate all fields.go files. + FieldsGo() error + + // Generate build/fields/fields.yml containing fields for the Beat. This + // file may need be copied to fields.yml if tests depend on it, but those + // tests should be updated. + FieldsYML() error + + // Generate build/fields/fields.all.yml containing all possible fields + // for all license types. (Used for field documentation.) + FieldsAllYML() error + + All() // Build everything. +} + // GenerateFieldsYAML generates a fields.yml file for a Beat. This will include // the common fields specified by libbeat, the common fields for the Beat, // and any additional fields.yml files you specify. @@ -54,7 +83,7 @@ func generateFieldsYAML(baseDir, output string, moduleDirs ...string) error { filepath.Join(beatsDir, globalFieldsCmdPath), "-es_beats_path", beatsDir, "-beat_path", baseDir, - "-out", output, + "-out", CreateDir(output), ) return globalFieldsCmd(moduleDirs...) @@ -78,7 +107,7 @@ func GenerateFieldsGo(fieldsYML, out string) error { filepath.Join(beatsDir, assetCmdPath), "-pkg", "include", "-in", fieldsYML, - "-out", createDir(out), + "-out", CreateDir(out), "-license", toLibbeatLicenseName(BeatLicense), BeatName, ) @@ -97,11 +126,15 @@ func GenerateModuleFieldsGo(moduleDir string) error { return err } + if !filepath.IsAbs(moduleDir) { + moduleDir = CWD(moduleDir) + } + moduleFieldsCmd := sh.RunCmd("go", "run", filepath.Join(beatsDir, moduleFieldsCmdPath), "-beat", BeatName, "-license", toLibbeatLicenseName(BeatLicense), - filepath.Join(moduleDir), + moduleDir, ) return moduleFieldsCmd() @@ -110,9 +143,7 @@ func GenerateModuleFieldsGo(moduleDir string) error { // GenerateModuleIncludeListGo generates an include/list.go file containing // a import statement for each module and dataset. func GenerateModuleIncludeListGo() error { - return GenerateIncludeListGo(nil, []string{ - filepath.Join(CWD(), "module"), - }) + return GenerateIncludeListGo(nil, []string{"module"}) } // GenerateIncludeListGo generates an include/list.go file containing imports @@ -133,9 +164,15 @@ func GenerateIncludeListGo(importDirs []string, moduleDirs []string) error { var args []string for _, dir := range importDirs { + if !filepath.IsAbs(dir) { + dir = CWD(dir) + } args = append(args, "-import", dir) } for _, dir := range moduleDirs { + if !filepath.IsAbs(dir) { + dir = CWD(dir) + } args = append(args, "-moduleDir", dir) } diff --git a/dev-tools/mage/fmt.go b/dev-tools/mage/fmt.go index 0a2c04a42497..7f6a839d6216 100644 --- a/dev-tools/mage/fmt.go +++ b/dev-tools/mage/fmt.go @@ -45,7 +45,9 @@ var ( func Format() { // Don't run AddLicenseHeaders and GoImports concurrently because they // both can modify the same files. - mg.Deps(AddLicenseHeaders) + if BeatProjectType != CommunityProject { + mg.Deps(AddLicenseHeaders) + } mg.Deps(GoImports, PythonAutopep8) } diff --git a/dev-tools/mage/kibana.go b/dev-tools/mage/kibana.go index 1240d1ca5627..6592a339891b 100644 --- a/dev-tools/mage/kibana.go +++ b/dev-tools/mage/kibana.go @@ -25,12 +25,12 @@ import ( "github.com/pkg/errors" ) +const kibanaBuildDir = "build/kibana" + // KibanaDashboards collects the Kibana dashboards files and generates the // index patterns based on the fields.yml file. It outputs to build/kibana. // Use PackageKibanaDashboardsFromBuildDir() with this. func KibanaDashboards(moduleDirs ...string) error { - var kibanaBuildDir = "build/kibana" - if err := os.RemoveAll(kibanaBuildDir); err != nil { return err } @@ -66,7 +66,7 @@ func KibanaDashboards(moduleDirs ...string) error { return err } - // Convert 6.x dashboards to strings. + // Convert 7.x dashboards to strings. err = sh.Run("python", filepath.Join(esBeatsDir, "libbeat/scripts/unpack_dashboards.py"), "--glob="+filepath.Join(kibanaBuildDir, "7/dashboard/*.json")) diff --git a/dev-tools/mage/settings.go b/dev-tools/mage/settings.go index 75f8352445a0..57f731ece1ea 100644 --- a/dev-tools/mage/settings.go +++ b/dev-tools/mage/settings.go @@ -66,6 +66,8 @@ var ( BeatURL = EnvOr("BEAT_URL", "https://www.elastic.co/products/beats/"+BeatName) BeatUser = EnvOr("BEAT_USER", "root") + BeatProjectType ProjectType + Snapshot bool versionQualified bool @@ -102,12 +104,25 @@ func init() { Snapshot, err = strconv.ParseBool(EnvOr("SNAPSHOT", "false")) if err != nil { - panic(errors.Errorf("failed to parse SNAPSHOT env value", err)) + panic(errors.Wrap(err, "failed to parse SNAPSHOT env value")) } versionQualifier, versionQualified = os.LookupEnv("VERSION_QUALIFIER") } +// ProjectType specifies the type of project (OSS vs X-Pack). +type ProjectType uint8 + +// Project types. +const ( + OSSProject ProjectType = iota + XPackProject + CommunityProject +) + +// ErrUnknownProjectType is returned if an unknown ProjectType value is used. +var ErrUnknownProjectType = fmt.Errorf("unknown ProjectType") + // EnvMap returns map containing the common settings variables and all variables // from the environment. args are appended to the output prior to adding the // environment variables (so env vars have the highest precedence). diff --git a/dev-tools/mage/target/build/build.go b/dev-tools/mage/target/build/build.go new file mode 100644 index 000000000000..3e4d1f41ca7a --- /dev/null +++ b/dev-tools/mage/target/build/build.go @@ -0,0 +1,48 @@ +// Licensed to Elasticsearch B.V. under one or more contributor +// license agreements. See the NOTICE file distributed with +// this work for additional information regarding copyright +// ownership. Elasticsearch B.V. licenses this file to you under +// the Apache License, Version 2.0 (the "License"); you may +// not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, +// software distributed under the License is distributed on an +// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +// KIND, either express or implied. See the License for the +// specific language governing permissions and limitations +// under the License. + +package build + +import ( + "github.com/elastic/beats/dev-tools/mage" +) + +// Build builds the Beat binary. +func Build() error { + return mage.Build(mage.DefaultBuildArgs()) +} + +// GolangCrossBuild build the Beat binary inside of the golang-builder. +// Do not use directly, use crossBuild instead. +func GolangCrossBuild() error { + return mage.GolangCrossBuild(mage.DefaultGolangCrossBuildArgs()) +} + +// BuildGoDaemon builds the go-daemon binary (use crossBuildGoDaemon). +func BuildGoDaemon() error { + return mage.BuildGoDaemon() +} + +// CrossBuild cross-builds the beat for all target platforms. +func CrossBuild() error { + return mage.CrossBuild() +} + +// CrossBuildGoDaemon cross-builds the go-daemon binary using Docker. +func CrossBuildGoDaemon() error { + return mage.CrossBuildGoDaemon() +} diff --git a/dev-tools/mage/target/common/check.go b/dev-tools/mage/target/common/check.go new file mode 100644 index 000000000000..35d348c51e71 --- /dev/null +++ b/dev-tools/mage/target/common/check.go @@ -0,0 +1,41 @@ +// Licensed to Elasticsearch B.V. under one or more contributor +// license agreements. See the NOTICE file distributed with +// this work for additional information regarding copyright +// ownership. Elasticsearch B.V. licenses this file to you under +// the Apache License, Version 2.0 (the "License"); you may +// not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, +// software distributed under the License is distributed on an +// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +// KIND, either express or implied. See the License for the +// specific language governing permissions and limitations +// under the License. + +package common + +import ( + "github.com/magefile/mage/mg" + + "github.com/elastic/beats/dev-tools/mage" +) + +var checkDeps []interface{} + +// RegisterCheckDeps registers dependencies of the Check target. +func RegisterCheckDeps(deps ...interface{}) { + checkDeps = append(checkDeps, deps...) +} + +// Check formats code, updates generated content, check for common errors, and +// checks for any modified files. +func Check() { + deps := make([]interface{}, 0, len(checkDeps)+2) + deps = append(deps, mage.Format) + deps = append(deps, checkDeps...) + deps = append(deps, mage.Check) + mg.SerialDeps(deps...) +} diff --git a/dev-tools/mage/target/common/clean.go b/dev-tools/mage/target/common/clean.go new file mode 100644 index 000000000000..876722d8c62d --- /dev/null +++ b/dev-tools/mage/target/common/clean.go @@ -0,0 +1,25 @@ +// Licensed to Elasticsearch B.V. under one or more contributor +// license agreements. See the NOTICE file distributed with +// this work for additional information regarding copyright +// ownership. Elasticsearch B.V. licenses this file to you under +// the Apache License, Version 2.0 (the "License"); you may +// not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, +// software distributed under the License is distributed on an +// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +// KIND, either express or implied. See the License for the +// specific language governing permissions and limitations +// under the License. + +package common + +import "github.com/elastic/beats/dev-tools/mage" + +// Clean cleans all generated files and build artifacts. +func Clean() error { + return mage.Clean() +} diff --git a/dev-tools/mage/target/common/fmt.go b/dev-tools/mage/target/common/fmt.go new file mode 100644 index 000000000000..0068ab412b9d --- /dev/null +++ b/dev-tools/mage/target/common/fmt.go @@ -0,0 +1,29 @@ +// Licensed to Elasticsearch B.V. under one or more contributor +// license agreements. See the NOTICE file distributed with +// this work for additional information regarding copyright +// ownership. Elasticsearch B.V. licenses this file to you under +// the Apache License, Version 2.0 (the "License"); you may +// not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, +// software distributed under the License is distributed on an +// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +// KIND, either express or implied. See the License for the +// specific language governing permissions and limitations +// under the License. + +package common + +import ( + "github.com/magefile/mage/mg" + + "github.com/elastic/beats/dev-tools/mage" +) + +// Fmt formats source code (.go and .py) and adds license headers. +func Fmt() { + mg.Deps(mage.Format) +} diff --git a/dev-tools/mage/target/common/shared.go b/dev-tools/mage/target/common/shared.go new file mode 100644 index 000000000000..7db2e4d5d5f6 --- /dev/null +++ b/dev-tools/mage/target/common/shared.go @@ -0,0 +1,25 @@ +// Licensed to Elasticsearch B.V. under one or more contributor +// license agreements. See the NOTICE file distributed with +// this work for additional information regarding copyright +// ownership. Elasticsearch B.V. licenses this file to you under +// the Apache License, Version 2.0 (the "License"); you may +// not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, +// software distributed under the License is distributed on an +// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +// KIND, either express or implied. See the License for the +// specific language governing permissions and limitations +// under the License. + +package common + +import "github.com/elastic/beats/dev-tools/mage" + +// DumpVariables writes the template variables and values to stdout. +func DumpVariables() error { + return mage.DumpVariables() +} diff --git a/dev-tools/mage/target/dashboards/dashboards.go b/dev-tools/mage/target/dashboards/dashboards.go new file mode 100644 index 000000000000..943d6a8aab1b --- /dev/null +++ b/dev-tools/mage/target/dashboards/dashboards.go @@ -0,0 +1,64 @@ +// Licensed to Elasticsearch B.V. under one or more contributor +// license agreements. See the NOTICE file distributed with +// this work for additional information regarding copyright +// ownership. Elasticsearch B.V. licenses this file to you under +// the Apache License, Version 2.0 (the "License"); you may +// not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, +// software distributed under the License is distributed on an +// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +// KIND, either express or implied. See the License for the +// specific language governing permissions and limitations +// under the License. + +package dashboards + +import ( + "github.com/magefile/mage/mg" + "github.com/pkg/errors" + + "github.com/elastic/beats/dev-tools/mage" +) + +var ( + buildDep interface{} + collectDashboardsDep interface{} +) + +// RegisterImportDeps registers dependencies of the Import target. +func RegisterImportDeps(build, collectDashboards interface{}) { + buildDep = build + collectDashboardsDep = collectDashboards +} + +// Dashboards target namespace. +type Dashboards mg.Namespace + +// Import imports dashboards to Kibana using the Beat setup command. +// +// Depends on: build, dashboard +// +// Optional environment variables: +// - KIBANA_URL: URL of Kibana +// - KIBANA_ALWAYS: Connect to Kibana without checking ES version. Default true. +// - ES_URL: URL of Elasticsearch (only used with KIBANA_ALWAYS=false). +func (Dashboards) Import() error { + if buildDep == nil || collectDashboardsDep == nil { + return errors.New("dashboard.RegisterImportDeps() must be called") + } + return mage.ImportDashboards(buildDep, collectDashboardsDep) +} + +// Export exports a dashboard from Kibana and writes it into the correct +// directory. +// +// Required environment variables: +// - MODULE: Name of the module +// - ID: Dashboard ID +func (Dashboards) Export() error { + return mage.ExportDashboard() +} diff --git a/dev-tools/mage/target/docs/docs.go b/dev-tools/mage/target/docs/docs.go new file mode 100644 index 000000000000..cc3f950637df --- /dev/null +++ b/dev-tools/mage/target/docs/docs.go @@ -0,0 +1,40 @@ +// Licensed to Elasticsearch B.V. under one or more contributor +// license agreements. See the NOTICE file distributed with +// this work for additional information regarding copyright +// ownership. Elasticsearch B.V. licenses this file to you under +// the Apache License, Version 2.0 (the "License"); you may +// not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, +// software distributed under the License is distributed on an +// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +// KIND, either express or implied. See the License for the +// specific language governing permissions and limitations +// under the License. + +package docs + +import ( + "github.com/magefile/mage/mg" + + "github.com/elastic/beats/dev-tools/mage" +) + +var ( + docsDeps []interface{} +) + +// RegisterDeps registers dependencies of the Docs target. +func RegisterDeps(deps ...interface{}) { + docsDeps = append(docsDeps, deps...) +} + +// Docs generates the documentation for the Beat. Set PREVIEW=true to +// automatically open the browser to the docs. +func Docs() error { + mg.SerialDeps(docsDeps...) + return mage.Docs.AsciidocBook() +} diff --git a/dev-tools/mage/target/integtest/integtest.go b/dev-tools/mage/target/integtest/integtest.go new file mode 100644 index 000000000000..cc596f60b911 --- /dev/null +++ b/dev-tools/mage/target/integtest/integtest.go @@ -0,0 +1,82 @@ +// Licensed to Elasticsearch B.V. under one or more contributor +// license agreements. See the NOTICE file distributed with +// this work for additional information regarding copyright +// ownership. Elasticsearch B.V. licenses this file to you under +// the Apache License, Version 2.0 (the "License"); you may +// not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, +// software distributed under the License is distributed on an +// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +// KIND, either express or implied. See the License for the +// specific language governing permissions and limitations +// under the License. + +package integtest + +import ( + "context" + + "github.com/magefile/mage/mg" + + "github.com/elastic/beats/dev-tools/mage" + "github.com/elastic/beats/dev-tools/mage/target/test" +) + +func init() { + test.RegisterDeps(IntegTest) +} + +var ( + goTestDeps, pythonTestDeps []interface{} + whitelistedEnvVars []string +) + +// RegisterGoTestDeps registers dependencies of the GoIntegTest target. +func RegisterGoTestDeps(deps ...interface{}) { + goTestDeps = append(goTestDeps, deps...) +} + +// RegisterPythonTestDeps registers dependencies of the PythonIntegTest target. +func RegisterPythonTestDeps(deps ...interface{}) { + pythonTestDeps = append(pythonTestDeps, deps...) +} + +// WhitelistEnvVar whitelists an environment variable to enabled it to be +// passed into the clean integration test environment (Docker). +func WhitelistEnvVar(key ...string) { + whitelistedEnvVars = append(whitelistedEnvVars, key...) +} + +// IntegTest executes integration tests (it uses Docker to run the tests). +func IntegTest() { + mage.AddIntegTestUsage() + defer mage.StopIntegTestEnv() + mg.SerialDeps(GoIntegTest, PythonIntegTest) +} + +// GoIntegTest executes the Go integration tests. +// Use TEST_COVERAGE=true to enable code coverage profiling. +// Use RACE_DETECTOR=true to enable the race detector. +func GoIntegTest(ctx context.Context) error { + if !mage.IsInIntegTestEnv() { + mg.SerialDeps(goTestDeps...) + } + return mage.RunIntegTest("goIntegTest", func() error { + return mage.GoTest(ctx, mage.DefaultGoTestIntegrationArgs()) + }, whitelistedEnvVars...) +} + +// PythonIntegTest executes the python system tests in the integration environment (Docker). +func PythonIntegTest(ctx context.Context) error { + if !mage.IsInIntegTestEnv() { + mg.SerialDeps(pythonTestDeps...) + } + return mage.RunIntegTest("pythonIntegTest", func() error { + mg.Deps(mage.BuildSystemTestBinary) + return mage.PythonNoseTest(mage.DefaultPythonTestIntegrationArgs()) + }, whitelistedEnvVars...) +} diff --git a/dev-tools/mage/target/pkg/test.go b/dev-tools/mage/target/pkg/test.go new file mode 100644 index 000000000000..ded639fc5b3d --- /dev/null +++ b/dev-tools/mage/target/pkg/test.go @@ -0,0 +1,26 @@ +// Licensed to Elasticsearch B.V. under one or more contributor +// license agreements. See the NOTICE file distributed with +// this work for additional information regarding copyright +// ownership. Elasticsearch B.V. licenses this file to you under +// the Apache License, Version 2.0 (the "License"); you may +// not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, +// software distributed under the License is distributed on an +// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +// KIND, either express or implied. See the License for the +// specific language governing permissions and limitations +// under the License. + +package pkg + +import "github.com/elastic/beats/dev-tools/mage" + +// PackageTest tests the generated packages in build/distributions. It checks +// things like file ownership/mode, package attributes, etc. +func PackageTest() error { + return mage.TestPackages() +} diff --git a/dev-tools/mage/target/test/test.go b/dev-tools/mage/target/test/test.go new file mode 100644 index 000000000000..cab213de22d4 --- /dev/null +++ b/dev-tools/mage/target/test/test.go @@ -0,0 +1,35 @@ +// Licensed to Elasticsearch B.V. under one or more contributor +// license agreements. See the NOTICE file distributed with +// this work for additional information regarding copyright +// ownership. Elasticsearch B.V. licenses this file to you under +// the Apache License, Version 2.0 (the "License"); you may +// not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, +// software distributed under the License is distributed on an +// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +// KIND, either express or implied. See the License for the +// specific language governing permissions and limitations +// under the License. + +package test + +import "github.com/magefile/mage/mg" + +var ( + testDeps []interface{} +) + +// RegisterDeps registers dependencies of the Test target (register your targets +// that execute tests). +func RegisterDeps(deps ...interface{}) { + testDeps = append(testDeps, deps...) +} + +// Test runs all available tests (unitTest + integTest). +func Test() { + mg.SerialDeps(testDeps...) +} diff --git a/dev-tools/mage/target/unittest/unittest.go b/dev-tools/mage/target/unittest/unittest.go new file mode 100644 index 000000000000..69e68300d2ae --- /dev/null +++ b/dev-tools/mage/target/unittest/unittest.go @@ -0,0 +1,65 @@ +// Licensed to Elasticsearch B.V. under one or more contributor +// license agreements. See the NOTICE file distributed with +// this work for additional information regarding copyright +// ownership. Elasticsearch B.V. licenses this file to you under +// the Apache License, Version 2.0 (the "License"); you may +// not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, +// software distributed under the License is distributed on an +// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +// KIND, either express or implied. See the License for the +// specific language governing permissions and limitations +// under the License. + +package unittest + +import ( + "context" + + "github.com/magefile/mage/mg" + + "github.com/elastic/beats/dev-tools/mage" + "github.com/elastic/beats/dev-tools/mage/target/test" +) + +func init() { + test.RegisterDeps(UnitTest) +} + +var ( + goTestDeps, pythonTestDeps []interface{} +) + +// RegisterGoTestDeps registers dependencies of the GoUnitTest target. +func RegisterGoTestDeps(deps ...interface{}) { + goTestDeps = append(goTestDeps, deps...) +} + +// RegisterPythonTestDeps registers dependencies of the PythonUnitTest target. +func RegisterPythonTestDeps(deps ...interface{}) { + pythonTestDeps = append(pythonTestDeps, deps...) +} + +// UnitTest executes the unit tests (Go and Python). +func UnitTest() { + mg.SerialDeps(GoUnitTest, PythonUnitTest) +} + +// GoUnitTest executes the Go unit tests. +// Use TEST_COVERAGE=true to enable code coverage profiling. +// Use RACE_DETECTOR=true to enable the race detector. +func GoUnitTest(ctx context.Context) error { + mg.SerialCtxDeps(ctx, goTestDeps...) + return mage.GoTest(ctx, mage.DefaultGoTestUnitArgs()) +} + +// PythonUnitTest executes the python system tests. +func PythonUnitTest() error { + mg.SerialDeps(pythonTestDeps...) + mg.Deps(mage.BuildSystemTestBinary) + return mage.PythonNoseTest(mage.DefaultPythonTestUnitArgs()) +} diff --git a/dev-tools/make/xpack.mk b/dev-tools/make/xpack.mk index cb49f48c40f0..2930d27c0af8 100644 --- a/dev-tools/make/xpack.mk +++ b/dev-tools/make/xpack.mk @@ -43,7 +43,6 @@ testsuite: mage -rm build/TEST-go-integration.out mage update build unitTest integTest || ( cat build/TEST-go-integration.out && false ) - .PHONY: update update: mage mage update diff --git a/winlogbeat/Makefile b/winlogbeat/Makefile index 234ca977df61..83b5f86dcadc 100644 --- a/winlogbeat/Makefile +++ b/winlogbeat/Makefile @@ -3,13 +3,14 @@ BEAT_TITLE=Winlogbeat SYSTEM_TESTS=true TEST_ENVIRONMENT=false GOX_OS=windows +EXCLUDE_COMMON_UPDATE_TARGET=true include ../libbeat/scripts/Makefile +.PHONY: update +update: mage + mage update + .PHONY: gen gen: GOOS=windows GOARCH=386 go generate -v -x ./... - -# Collects all dependencies and then calls update -.PHONY: collect -collect: diff --git a/winlogbeat/_meta/beat.yml.tmpl b/winlogbeat/_meta/beat.yml.tmpl new file mode 100644 index 000000000000..2fe244d55129 --- /dev/null +++ b/winlogbeat/_meta/beat.yml.tmpl @@ -0,0 +1,10 @@ +{{ template "header" . }} +winlogbeat.event_logs: + - name: Application + ignore_older: 72h + + - name: System + + - name: Security + +{{if not .Reference}}{{ template "elasticsearch_settings" . }}{{end}} diff --git a/winlogbeat/_meta/beat.yml b/winlogbeat/_meta/common.yml.tmpl similarity index 59% rename from winlogbeat/_meta/beat.yml rename to winlogbeat/_meta/common.yml.tmpl index ba8f85214ed8..7a7feaddf5a0 100644 --- a/winlogbeat/_meta/beat.yml +++ b/winlogbeat/_meta/common.yml.tmpl @@ -1,14 +1,22 @@ -###################### Winlogbeat Configuration Example ########################## +{{define "header" -}} +###################### Winlogbeat Configuration Example ######################## # This file is an example configuration file highlighting only the most common -# options. The winlogbeat.reference.yml file from the same directory contains all the -# supported options with more comments. You can use it as a reference. +# options. The winlogbeat.reference.yml file from the same directory contains +# all the supported options with more comments. You can use it as a reference. # # You can find the full configuration reference here: # https://www.elastic.co/guide/en/beats/winlogbeat/index.html -#======================= Winlogbeat specific options ========================== +#======================= Winlogbeat specific options =========================== +{{if .Reference -}} +# The registry file is where Winlogbeat persists its state so that the beat can +# resume after shutdown or an outage. The default is .winlogbeat.yml in the +# directory in which it was started. +#winlogbeat.registry_file: .winlogbeat.yml + +{{end -}} # event_logs specifies a list of event logs to monitor as well as any # accompanying options. The YAML data type of event_logs is a list of # dictionaries. @@ -16,16 +24,13 @@ # The supported keys are name (required), tags, fields, fields_under_root, # forwarded, ignore_older, level, event_id, provider, and include_xml. Please # visit the documentation for the complete details of each option. -# https://go.es.io/WinlogbeatConfig -winlogbeat.event_logs: - - name: Application - ignore_older: 72h - - name: Security - - name: System +# https://go.es.io/WinlogbeatConfig{{end -}} -#==================== Elasticsearch template setting ========================== +{{define "elasticsearch_settings" -}} +#==================== Elasticsearch template settings ========================== setup.template.settings: index.number_of_shards: 1 #index.codec: best_compression #_source.enabled: false +{{end -}} diff --git a/winlogbeat/cmd/root.go b/winlogbeat/cmd/root.go index 437726166e4b..8947d0bb9b18 100644 --- a/winlogbeat/cmd/root.go +++ b/winlogbeat/cmd/root.go @@ -22,7 +22,10 @@ import ( "github.com/elastic/beats/libbeat/cmd/instance" "github.com/elastic/beats/winlogbeat/beater" - // Import the script processor. + // Register fields. + _ "github.com/elastic/beats/winlogbeat/include" + + // Import the script processor and supporting modules. _ "github.com/elastic/beats/libbeat/processors/script" ) diff --git a/winlogbeat/include/fields.go b/winlogbeat/include/fields.go index eb90ac57e71d..e372994d1d66 100644 --- a/winlogbeat/include/fields.go +++ b/winlogbeat/include/fields.go @@ -24,13 +24,13 @@ import ( ) func init() { - if err := asset.SetFields("winlogbeat", "fields.yml", asset.BeatFieldsPri, AssetFieldsYml); err != nil { + if err := asset.SetFields("winlogbeat", "build/fields/fields.common.yml", asset.BeatFieldsPri, AssetBuildFieldsFieldsCommonYml); err != nil { panic(err) } } -// AssetFieldsYml returns asset data. -// This is the base64 encoded gzipped contents of fields.yml. -func AssetFieldsYml() string { +// AssetBuildFieldsFieldsCommonYml returns asset data. +// This is the base64 encoded gzipped contents of build/fields/fields.common.yml. +func AssetBuildFieldsFieldsCommonYml() string { return "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" } diff --git a/winlogbeat/magefile.go b/winlogbeat/magefile.go index 0ca1411d2a7b..5f5c68ec1e29 100644 --- a/winlogbeat/magefile.go +++ b/winlogbeat/magefile.go @@ -20,97 +20,44 @@ package main import ( - "context" - "fmt" - "time" - "github.com/magefile/mage/mg" - "github.com/magefile/mage/sh" "github.com/elastic/beats/dev-tools/mage" + + // mage:import + _ "github.com/elastic/beats/dev-tools/mage/target/common" + // mage:import + _ "github.com/elastic/beats/dev-tools/mage/target/build" + // mage:import + _ "github.com/elastic/beats/dev-tools/mage/target/pkg" + // mage:import + _ "github.com/elastic/beats/dev-tools/mage/target/dashboards" + // mage:import + _ "github.com/elastic/beats/dev-tools/mage/target/docs" + // mage:import + _ "github.com/elastic/beats/dev-tools/mage/target/test" + // mage:import + "github.com/elastic/beats/dev-tools/mage/target/unittest" + // mage:import + winlogbeat "github.com/elastic/beats/winlogbeat/scripts/mage" ) func init() { - mage.BeatDescription = "Winlogbeat ships Windows event logs to Elasticsearch or Logstash." - - mage.Platforms = mage.Platforms.Filter("windows") -} - -// Build builds the Beat binary. -func Build() error { - return mage.Build(mage.DefaultBuildArgs()) -} - -// GolangCrossBuild build the Beat binary inside of the golang-builder. -// Do not use directly, use crossBuild instead. -func GolangCrossBuild() error { - return mage.GolangCrossBuild(mage.DefaultGolangCrossBuildArgs()) + winlogbeat.SelectLogic = mage.OSSProject } -// BuildGoDaemon builds the go-daemon binary (use crossBuildGoDaemon). -func BuildGoDaemon() error { - return mage.BuildGoDaemon() -} +// Update is an alias for update:all. This is a workaround for +// https://github.com/magefile/mage/issues/217. +func Update() { mg.Deps(winlogbeat.Update.All) } -// CrossBuild cross-builds the beat for all target platforms. -func CrossBuild() error { - return mage.CrossBuild() -} - -// CrossBuildXPack cross-builds the beat with XPack for all target platforms. -func CrossBuildXPack() error { - return mage.CrossBuildXPack() -} - -// CrossBuildGoDaemon cross-builds the go-daemon binary using Docker. -func CrossBuildGoDaemon() error { - return mage.CrossBuildGoDaemon() -} - -// Clean cleans all generated files and build artifacts. -func Clean() error { - return mage.Clean() -} - -// Package packages the Beat for distribution. -// Use SNAPSHOT=true to build snapshots. -// Use PLATFORMS to control the target platforms. -// Use VERSION_QUALIFIER to control the version qualifier. -func Package() { - start := time.Now() - defer func() { fmt.Println("package ran for", time.Since(start)) }() - - mage.UseElasticBeatPackaging() - mg.Deps(Update) - mg.Deps(CrossBuild, CrossBuildXPack, CrossBuildGoDaemon) - mg.SerialDeps(mage.Package, TestPackages) -} - -// TestPackages tests the generated packages (i.e. file modes, owners, groups). -func TestPackages() error { - return mage.TestPackages() -} - -// Update updates the generated files (aka make update). -func Update() error { - return sh.Run("make", "update") -} - -// Fields generates a fields.yml for the Beat. -func Fields() error { - return mage.GenerateFieldsYAML() -} - -// GoTestUnit executes the Go unit tests. -// Use TEST_COVERAGE=true to enable code coverage profiling. -// Use RACE_DETECTOR=true to enable the race detector. -func GoTestUnit(ctx context.Context) error { - return mage.GoTest(ctx, mage.DefaultGoTestUnitArgs()) -} +// Fields is an alias for update:fields. +// +// TODO: dev-tools/jenkins_ci.ps1 uses this. This should be removed when all +// projects have update to use goUnitTest. +func Fields() { mg.Deps(winlogbeat.Update.Fields) } -// GoTestIntegration executes the Go integration tests. -// Use TEST_COVERAGE=true to enable code coverage profiling. -// Use RACE_DETECTOR=true to enable the race detector. -func GoTestIntegration(ctx context.Context) error { - return mage.GoTest(ctx, mage.DefaultGoTestIntegrationArgs()) -} +// GoTestUnit is an alias for goUnitTest. +// +// TODO: dev-tools/jenkins_ci.ps1 uses this. This should be removed when all +// projects have update to use goUnitTest. +func GoTestUnit() { mg.Deps(unittest.GoUnitTest) } diff --git a/winlogbeat/main.go b/winlogbeat/main.go index fff4708a9fb7..c561fdb98096 100644 --- a/winlogbeat/main.go +++ b/winlogbeat/main.go @@ -28,7 +28,6 @@ import ( "os" "github.com/elastic/beats/winlogbeat/cmd" - _ "github.com/elastic/beats/winlogbeat/include" ) func main() { diff --git a/winlogbeat/scripts/mage/config.go b/winlogbeat/scripts/mage/config.go new file mode 100644 index 000000000000..5d43c1e60ed1 --- /dev/null +++ b/winlogbeat/scripts/mage/config.go @@ -0,0 +1,60 @@ +// Licensed to Elasticsearch B.V. under one or more contributor +// license agreements. See the NOTICE file distributed with +// this work for additional information regarding copyright +// ownership. Elasticsearch B.V. licenses this file to you under +// the Apache License, Version 2.0 (the "License"); you may +// not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, +// software distributed under the License is distributed on an +// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +// KIND, either express or implied. See the License for the +// specific language governing permissions and limitations +// under the License. + +package mage + +import ( + "github.com/elastic/beats/dev-tools/mage" +) + +// config generates short/reference configs. +func config() error { + // NOTE: No Docker config. + return mage.Config(mage.ShortConfigType|mage.ReferenceConfigType, configFileParams(), ".") +} + +func configFileParams() mage.ConfigFileParams { + beatDir := mage.OSSBeatDir + switch SelectLogic { + case mage.OSSProject: + beatDir = mage.OSSBeatDir + case mage.XPackProject: + beatDir = mage.XPackBeatDir + default: + panic(mage.ErrUnknownProjectType) + } + + return mage.ConfigFileParams{ + ShortParts: []string{ + mage.OSSBeatDir("_meta/common.yml.tmpl"), + beatDir("_meta/beat.yml.tmpl"), + mage.LibbeatDir("_meta/config.yml"), + }, + ReferenceParts: []string{ + mage.OSSBeatDir("_meta/common.yml.tmpl"), + beatDir("_meta/beat.yml.tmpl"), + mage.LibbeatDir("_meta/config.reference.yml"), + }, + DockerParts: []string{ + mage.OSSBeatDir("_meta/beat.docker.yml"), + mage.LibbeatDir("_meta/config.docker.yml"), + }, + ExtraVars: map[string]interface{}{ + "GOOS": "windows", + }, + } +} diff --git a/winlogbeat/scripts/mage/fields.go b/winlogbeat/scripts/mage/fields.go new file mode 100644 index 000000000000..bf40c644a4e2 --- /dev/null +++ b/winlogbeat/scripts/mage/fields.go @@ -0,0 +1,75 @@ +// Licensed to Elasticsearch B.V. under one or more contributor +// license agreements. See the NOTICE file distributed with +// this work for additional information regarding copyright +// ownership. Elasticsearch B.V. licenses this file to you under +// the Apache License, Version 2.0 (the "License"); you may +// not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, +// software distributed under the License is distributed on an +// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +// KIND, either express or implied. See the License for the +// specific language governing permissions and limitations +// under the License. + +package mage + +import ( + "os" + + "github.com/magefile/mage/mg" + + "github.com/elastic/beats/dev-tools/mage" +) + +var fb fieldsBuilder + +var _ mage.FieldsBuilder = fb + +type fieldsBuilder struct{} + +func (b fieldsBuilder) All() { + mg.Deps(b.FieldsGo, b.FieldsYML, b.FieldsAllYML) +} + +func (b fieldsBuilder) FieldsGo() error { + switch SelectLogic { + case mage.OSSProject: + return b.commonFieldsGo() + case mage.XPackProject: + return nil + default: + panic(mage.ErrUnknownProjectType) + } +} + +func (fieldsBuilder) FieldsYML() error { + var modules []string + switch SelectLogic { + case mage.OSSProject, mage.XPackProject: + // No modules. + default: + panic(mage.ErrUnknownProjectType) + } + + if err := mage.GenerateFieldsYAMLTo(mage.FieldsYML, modules...); err != nil { + return err + } + return mage.Copy(mage.FieldsYML, mage.FieldsYMLRoot) +} + +func (fieldsBuilder) FieldsAllYML() error { + return mage.GenerateFieldsYAMLTo(mage.FieldsAllYML) +} + +func (b fieldsBuilder) commonFieldsGo() error { + const file = "build/fields/fields.common.yml" + if err := mage.GenerateFieldsYAMLTo(file); err != nil { + return err + } + defer os.Remove(file) + return mage.GenerateFieldsGo(file, "include/fields.go") +} diff --git a/winlogbeat/scripts/mage/package.go b/winlogbeat/scripts/mage/package.go new file mode 100644 index 000000000000..37537041d6f7 --- /dev/null +++ b/winlogbeat/scripts/mage/package.go @@ -0,0 +1,113 @@ +// Licensed to Elasticsearch B.V. under one or more contributor +// license agreements. See the NOTICE file distributed with +// this work for additional information regarding copyright +// ownership. Elasticsearch B.V. licenses this file to you under +// the Apache License, Version 2.0 (the "License"); you may +// not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, +// software distributed under the License is distributed on an +// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +// KIND, either express or implied. See the License for the +// specific language governing permissions and limitations +// under the License. + +package mage + +import ( + "fmt" + "os" + "time" + + "github.com/magefile/mage/mg" + "github.com/pkg/errors" + + "github.com/elastic/beats/dev-tools/mage" + "github.com/elastic/beats/dev-tools/mage/target/build" + "github.com/elastic/beats/dev-tools/mage/target/pkg" +) + +const ( + dirModuleGenerated = "build/package/module" +) + +func init() { + mage.BeatDescription = "Winlogbeat ships Windows event logs to Elasticsearch or Logstash." + + mage.Platforms = mage.Platforms.Filter("windows") +} + +// Package packages the Beat for distribution. +// Use SNAPSHOT=true to build snapshots. +// Use PLATFORMS to control the target platforms. +// Use VERSION_QUALIFIER to control the version qualifier. +func Package() { + start := time.Now() + defer func() { fmt.Println("package ran for", time.Since(start)) }() + + switch SelectLogic { + case mage.OSSProject: + mage.UseElasticBeatOSSPackaging() + case mage.XPackProject: + mage.UseElasticBeatXPackPackaging() + customizePackaging() + } + mage.PackageKibanaDashboardsFromBuildDir() + + mg.Deps(Update.All) + mg.Deps(build.CrossBuild, build.CrossBuildGoDaemon) + mg.SerialDeps(mage.Package, pkg.PackageTest) +} + +func customizePackaging() { + // Skip if the module dir does not exist. + // TODO: Remove this after the module dir is added. + if _, err := os.Stat(mage.XPackBeatDir("module")); err != nil { + return + } + + mg.Deps(prepareModulePackaging) + + moduleDir := mage.PackageFile{ + Mode: 0644, + Source: dirModuleGenerated, + Config: true, + Modules: true, + } + + for _, args := range mage.Packages { + for _, pkgType := range args.Types { + switch pkgType { + case mage.TarGz, mage.Zip, mage.Docker: + args.Spec.Files["module"] = moduleDir + case mage.Deb, mage.RPM, mage.DMG: + args.Spec.Files["/etc/{{.BeatName}}/module"] = moduleDir + default: + panic(errors.Errorf("unhandled package type: %v", pkgType)) + } + } + } +} + +// prepareModulePackaging generates build/package/module. +func prepareModulePackaging() error { + // Clean any existing generated directories. + if err := mage.Clean([]string{dirModuleGenerated}); err != nil { + return err + } + + return (&mage.CopyTask{ + Source: mage.XPackBeatDir("module"), + Dest: dirModuleGenerated, + Mode: 0644, + DirMode: 0755, + Exclude: []string{ + "/_meta", + "/test", + `\.go$`, + }, + }).Execute() +} diff --git a/winlogbeat/scripts/mage/update.go b/winlogbeat/scripts/mage/update.go new file mode 100644 index 000000000000..876402dd85af --- /dev/null +++ b/winlogbeat/scripts/mage/update.go @@ -0,0 +1,71 @@ +// Licensed to Elasticsearch B.V. under one or more contributor +// license agreements. See the NOTICE file distributed with +// this work for additional information regarding copyright +// ownership. Elasticsearch B.V. licenses this file to you under +// the Apache License, Version 2.0 (the "License"); you may +// not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, +// software distributed under the License is distributed on an +// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +// KIND, either express or implied. See the License for the +// specific language governing permissions and limitations +// under the License. + +package mage + +import ( + "github.com/magefile/mage/mg" + + "github.com/elastic/beats/dev-tools/mage" + "github.com/elastic/beats/dev-tools/mage/target/build" + "github.com/elastic/beats/dev-tools/mage/target/common" + "github.com/elastic/beats/dev-tools/mage/target/dashboards" + "github.com/elastic/beats/dev-tools/mage/target/docs" +) + +func init() { + common.RegisterCheckDeps(Update.All) + + dashboards.RegisterImportDeps(build.Build, Update.Dashboards) + + docs.RegisterDeps(Update.FieldDocs) +} + +var ( + // SelectLogic configures the types of project logic to use (OSS vs X-Pack). + SelectLogic mage.ProjectType +) + +// Update target namespace. +type Update mg.Namespace + +// All updates all generated content. +func (Update) All() { + mg.Deps(Update.Fields, Update.Dashboards, Update.Config, Update.FieldDocs) +} + +// Config updates the Beat's config files. +func (Update) Config() error { + return config() +} + +// Dashboards collects all the dashboards and generates index patterns. +func (Update) Dashboards() error { + mg.Deps(fb.FieldsYML) + return mage.KibanaDashboards() +} + +// Fields updates all fields files (.go, .yml). +func (Update) Fields() { + mg.Deps(fb.All) +} + +// FieldDocs updates the field documentation. +func (Update) FieldDocs() error { + mg.Deps(fb.FieldsAllYML) + return mage.Docs.FieldDocs(mage.FieldsAllYML) +} diff --git a/winlogbeat/winlogbeat.reference.yml b/winlogbeat/winlogbeat.reference.yml index c0108672a11a..dfbde5cfd0e4 100644 --- a/winlogbeat/winlogbeat.reference.yml +++ b/winlogbeat/winlogbeat.reference.yml @@ -1,38 +1,37 @@ -########################## Winlogbeat Configuration ########################### +###################### Winlogbeat Configuration Example ######################## -# This file is a full configuration example documenting all non-deprecated -# options in comments. For a shorter configuration example, that contains only -# the most common options, please see winlogbeat.yml in the same directory. +# This file is an example configuration file highlighting only the most common +# options. The winlogbeat.reference.yml file from the same directory contains +# all the supported options with more comments. You can use it as a reference. # # You can find the full configuration reference here: # https://www.elastic.co/guide/en/beats/winlogbeat/index.html -#======================= Winlogbeat specific options ========================== +#======================= Winlogbeat specific options =========================== -# The registry file is where Winlogbeat persists its state so that the beat -# can resume after shutdown or an outage. The default is .winlogbeat.yml -# in the directory in which it was started. +# The registry file is where Winlogbeat persists its state so that the beat can +# resume after shutdown or an outage. The default is .winlogbeat.yml in the +# directory in which it was started. #winlogbeat.registry_file: .winlogbeat.yml -# The maximum amount of time Winlogbeat should wait for events to finish -# publishing when shutting down. -#winlogbeat.shutdown_timeout: 0s - # event_logs specifies a list of event logs to monitor as well as any # accompanying options. The YAML data type of event_logs is a list of # dictionaries. # # The supported keys are name (required), tags, fields, fields_under_root, -# forwarded, ignore_older, level, no_more_events, event_id, provider, and -# include_xml. Please visit the documentation for the complete details of each -# option. +# forwarded, ignore_older, level, event_id, provider, and include_xml. Please +# visit the documentation for the complete details of each option. # https://go.es.io/WinlogbeatConfig winlogbeat.event_logs: - name: Application ignore_older: 72h - - name: Security + - name: System + - name: Security + + + #================================ General ====================================== # The name of the shipper that publishes the network data. It can be used to group diff --git a/winlogbeat/winlogbeat.yml b/winlogbeat/winlogbeat.yml index 9b06e91dcafb..b4cd439d4e94 100644 --- a/winlogbeat/winlogbeat.yml +++ b/winlogbeat/winlogbeat.yml @@ -1,13 +1,13 @@ -###################### Winlogbeat Configuration Example ########################## +###################### Winlogbeat Configuration Example ######################## # This file is an example configuration file highlighting only the most common -# options. The winlogbeat.reference.yml file from the same directory contains all the -# supported options with more comments. You can use it as a reference. +# options. The winlogbeat.reference.yml file from the same directory contains +# all the supported options with more comments. You can use it as a reference. # # You can find the full configuration reference here: # https://www.elastic.co/guide/en/beats/winlogbeat/index.html -#======================= Winlogbeat specific options ========================== +#======================= Winlogbeat specific options =========================== # event_logs specifies a list of event logs to monitor as well as any # accompanying options. The YAML data type of event_logs is a list of @@ -20,16 +20,19 @@ winlogbeat.event_logs: - name: Application ignore_older: 72h - - name: Security + - name: System -#==================== Elasticsearch template setting ========================== + - name: Security + +#==================== Elasticsearch template settings ========================== setup.template.settings: index.number_of_shards: 1 #index.codec: best_compression #_source.enabled: false + #================================ General ===================================== # The name of the shipper that publishes the network data. It can be used to group diff --git a/x-pack/winlogbeat/Makefile b/x-pack/winlogbeat/Makefile new file mode 100644 index 000000000000..5da45563104a --- /dev/null +++ b/x-pack/winlogbeat/Makefile @@ -0,0 +1,10 @@ +# +# Variables +# +ES_BEATS ?= ../.. +GOX_OS := windows + +# +# Includes +# +include ../../dev-tools/make/xpack.mk diff --git a/x-pack/winlogbeat/_meta/beat.yml.tmpl b/x-pack/winlogbeat/_meta/beat.yml.tmpl new file mode 100644 index 000000000000..5c2878664e41 --- /dev/null +++ b/x-pack/winlogbeat/_meta/beat.yml.tmpl @@ -0,0 +1,9 @@ +{{ template "header" . }} +winlogbeat.event_logs: + - name: Application + ignore_older: 72h + + - name: System + + - name: Security +{{if not .Reference}}{{ template "elasticsearch_settings" . }}{{end}} diff --git a/x-pack/winlogbeat/magefile.go b/x-pack/winlogbeat/magefile.go new file mode 100644 index 000000000000..14459300a3f2 --- /dev/null +++ b/x-pack/winlogbeat/magefile.go @@ -0,0 +1,49 @@ +// Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one +// or more contributor license agreements. Licensed under the Elastic License; +// you may not use this file except in compliance with the Elastic License. + +// +build mage + +package main + +import ( + "github.com/magefile/mage/mg" + + "github.com/elastic/beats/dev-tools/mage" + + // mage:import + _ "github.com/elastic/beats/dev-tools/mage/target/common" + // mage:import + _ "github.com/elastic/beats/dev-tools/mage/target/build" + // mage:import + _ "github.com/elastic/beats/dev-tools/mage/target/pkg" + // mage:import + _ "github.com/elastic/beats/dev-tools/mage/target/dashboards" + // mage:import + _ "github.com/elastic/beats/dev-tools/mage/target/test" + // mage:import + "github.com/elastic/beats/dev-tools/mage/target/unittest" + // mage:import + winlogbeat "github.com/elastic/beats/winlogbeat/scripts/mage" +) + +func init() { + winlogbeat.SelectLogic = mage.XPackProject + mage.BeatLicense = "Elastic License" +} + +// Update is an alias for update:all. This is a workaround for +// https://github.com/magefile/mage/issues/217. +func Update() { mg.Deps(winlogbeat.Update.All) } + +// Fields is an alias for update:fields. +// +// TODO: dev-tools/jenkins_ci.ps1 uses this. This should be removed when all +// projects have update to use goUnitTest. +func Fields() { mg.Deps(winlogbeat.Update.Fields) } + +// GoTestUnit is an alias for goUnitTest. +// +// TODO: dev-tools/jenkins_ci.ps1 uses this. This should be removed when all +// projects have update to use goUnitTest. +func GoTestUnit() { mg.Deps(unittest.GoUnitTest) } diff --git a/x-pack/winlogbeat/main.go b/x-pack/winlogbeat/main.go index 54e3654bf330..56e4e0aab224 100644 --- a/x-pack/winlogbeat/main.go +++ b/x-pack/winlogbeat/main.go @@ -2,13 +2,6 @@ // or more contributor license agreements. Licensed under the Elastic License; // you may not use this file except in compliance with the Elastic License. -/* -Package winlogbeat contains the entrypoint to Winlogbeat which is a lightweight -data shipper for Windows event logs. It ships events directly to Elasticsearch -or Logstash. The data can then be visualized in Kibana. - -Downloads: https://www.elastic.co/downloads/beats/winlogbeat -*/ package main import ( diff --git a/x-pack/winlogbeat/make.bat b/x-pack/winlogbeat/make.bat new file mode 100644 index 000000000000..81de1ba946f9 --- /dev/null +++ b/x-pack/winlogbeat/make.bat @@ -0,0 +1,11 @@ +@echo off + +REM Windows wrapper for Mage (https://magefile.org/) that installs it +REM to %GOPATH%\bin from the Beats vendor directory. +REM +REM After running this once you may invoke mage.exe directly. + +WHERE mage +IF %ERRORLEVEL% NEQ 0 go install github.com/elastic/beats/vendor/github.com/magefile/mage + +mage %* diff --git a/x-pack/winlogbeat/winlogbeat.reference.yml b/x-pack/winlogbeat/winlogbeat.reference.yml new file mode 100644 index 000000000000..4c27b256d72f --- /dev/null +++ b/x-pack/winlogbeat/winlogbeat.reference.yml @@ -0,0 +1,1228 @@ +###################### Winlogbeat Configuration Example ######################## + +# This file is an example configuration file highlighting only the most common +# options. The winlogbeat.reference.yml file from the same directory contains +# all the supported options with more comments. You can use it as a reference. +# +# You can find the full configuration reference here: +# https://www.elastic.co/guide/en/beats/winlogbeat/index.html + +#======================= Winlogbeat specific options =========================== + +# The registry file is where Winlogbeat persists its state so that the beat can +# resume after shutdown or an outage. The default is .winlogbeat.yml in the +# directory in which it was started. +#winlogbeat.registry_file: .winlogbeat.yml + +# event_logs specifies a list of event logs to monitor as well as any +# accompanying options. The YAML data type of event_logs is a list of +# dictionaries. +# +# The supported keys are name (required), tags, fields, fields_under_root, +# forwarded, ignore_older, level, event_id, provider, and include_xml. Please +# visit the documentation for the complete details of each option. +# https://go.es.io/WinlogbeatConfig +winlogbeat.event_logs: + - name: Application + ignore_older: 72h + + - name: System + + - name: Security + + +#================================ General ====================================== + +# The name of the shipper that publishes the network data. It can be used to group +# all the transactions sent by a single shipper in the web interface. +# If this options is not defined, the hostname is used. +#name: + +# The tags of the shipper are included in their own field with each +# transaction published. Tags make it easy to group servers by different +# logical properties. +#tags: ["service-X", "web-tier"] + +# Optional fields that you can specify to add additional information to the +# output. Fields can be scalar values, arrays, dictionaries, or any nested +# combination of these. +#fields: +# env: staging + +# If this option is set to true, the custom fields are stored as top-level +# fields in the output document instead of being grouped under a fields +# sub-dictionary. Default is false. +#fields_under_root: false + +# Internal queue configuration for buffering events to be published. +#queue: + # Queue type by name (default 'mem') + # The memory queue will present all available events (up to the outputs + # bulk_max_size) to the output, the moment the output is ready to server + # another batch of events. + #mem: + # Max number of events the queue can buffer. + #events: 4096 + + # Hints the minimum number of events stored in the queue, + # before providing a batch of events to the outputs. + # The default value is set to 2048. + # A value of 0 ensures events are immediately available + # to be sent to the outputs. + #flush.min_events: 2048 + + # Maximum duration after which events are available to the outputs, + # if the number of events stored in the queue is < min_flush_events. + #flush.timeout: 1s + + # The spool queue will store events in a local spool file, before + # forwarding the events to the outputs. + # + # Beta: spooling to disk is currently a beta feature. Use with care. + # + # The spool file is a circular buffer, which blocks once the file/buffer is full. + # Events are put into a write buffer and flushed once the write buffer + # is full or the flush_timeout is triggered. + # Once ACKed by the output, events are removed immediately from the queue, + # making space for new events to be persisted. + #spool: + # The file namespace configures the file path and the file creation settings. + # Once the file exists, the `size`, `page_size` and `prealloc` settings + # will have no more effect. + #file: + # Location of spool file. The default value is ${path.data}/spool.dat. + #path: "${path.data}/spool.dat" + + # Configure file permissions if file is created. The default value is 0600. + #permissions: 0600 + + # File size hint. The spool blocks, once this limit is reached. The default value is 100 MiB. + #size: 100MiB + + # The files page size. A file is split into multiple pages of the same size. The default value is 4KiB. + #page_size: 4KiB + + # If prealloc is set, the required space for the file is reserved using + # truncate. The default value is true. + #prealloc: true + + # Spool writer settings + # Events are serialized into a write buffer. The write buffer is flushed if: + # - The buffer limit has been reached. + # - The configured limit of buffered events is reached. + # - The flush timeout is triggered. + #write: + # Sets the write buffer size. + #buffer_size: 1MiB + + # Maximum duration after which events are flushed if the write buffer + # is not full yet. The default value is 1s. + #flush.timeout: 1s + + # Number of maximum buffered events. The write buffer is flushed once the + # limit is reached. + #flush.events: 16384 + + # Configure the on-disk event encoding. The encoding can be changed + # between restarts. + # Valid encodings are: json, ubjson, and cbor. + #codec: cbor + #read: + # Reader flush timeout, waiting for more events to become available, so + # to fill a complete batch as required by the outputs. + # If flush_timeout is 0, all available events are forwarded to the + # outputs immediately. + # The default value is 0s. + #flush.timeout: 0s + +# Sets the maximum number of CPUs that can be executing simultaneously. The +# default is the number of logical CPUs available in the system. +#max_procs: + +#================================ Processors =================================== + +# Processors are used to reduce the number of fields in the exported event or to +# enhance the event with external metadata. This section defines a list of +# processors that are applied one by one and the first one receives the initial +# event: +# +# event -> filter1 -> event1 -> filter2 ->event2 ... +# +# The supported processors are drop_fields, drop_event, include_fields, +# decode_json_fields, and add_cloud_metadata. +# +# For example, you can use the following processors to keep the fields that +# contain CPU load percentages, but remove the fields that contain CPU ticks +# values: +# +#processors: +#- include_fields: +# fields: ["cpu"] +#- drop_fields: +# fields: ["cpu.user", "cpu.system"] +# +# The following example drops the events that have the HTTP response code 200: +# +#processors: +#- drop_event: +# when: +# equals: +# http.code: 200 +# +# The following example renames the field a to b: +# +#processors: +#- rename: +# fields: +# - from: "a" +# to: "b" +# +# The following example tokenizes the string into fields: +# +#processors: +#- dissect: +# tokenizer: "%{key1} - %{key2}" +# field: "message" +# target_prefix: "dissect" +# +# The following example enriches each event with metadata from the cloud +# provider about the host machine. It works on EC2, GCE, DigitalOcean, +# Tencent Cloud, and Alibaba Cloud. +# +#processors: +#- add_cloud_metadata: ~ +# +# The following example enriches each event with the machine's local time zone +# offset from UTC. +# +#processors: +#- add_locale: +# format: offset +# +# The following example enriches each event with docker metadata, it matches +# given fields to an existing container id and adds info from that container: +# +#processors: +#- add_docker_metadata: +# host: "unix:///var/run/docker.sock" +# match_fields: ["system.process.cgroup.id"] +# match_pids: ["process.pid", "process.ppid"] +# match_source: true +# match_source_index: 4 +# match_short_id: false +# cleanup_timeout: 60 +# labels.dedot: false +# # To connect to Docker over TLS you must specify a client and CA certificate. +# #ssl: +# # certificate_authority: "/etc/pki/root/ca.pem" +# # certificate: "/etc/pki/client/cert.pem" +# # key: "/etc/pki/client/cert.key" +# +# The following example enriches each event with docker metadata, it matches +# container id from log path available in `source` field (by default it expects +# it to be /var/lib/docker/containers/*/*.log). +# +#processors: +#- add_docker_metadata: ~ +# +# The following example enriches each event with host metadata. +# +#processors: +#- add_host_metadata: +# netinfo.enabled: false +# +# The following example enriches each event with process metadata using +# process IDs included in the event. +# +#processors: +#- add_process_metadata: +# match_pids: ["system.process.ppid"] +# target: system.process.parent +# +# The following example decodes fields containing JSON strings +# and replaces the strings with valid JSON objects. +# +#processors: +#- decode_json_fields: +# fields: ["field1", "field2", ...] +# process_array: false +# max_depth: 1 +# target: "" +# overwrite_keys: false +# +# The following example copies the value of message to message_copied +# +#processors: +#- copy_fields: +# fields: +# - from: message +# to: message_copied +# fail_on_error: true +# ignore_missing: false +# +# The following example truncates the value of message to 1024 bytes +# +#processors: +#- truncate_fields: +# fields: +# - message +# max_bytes: 1024 +# fail_on_error: false +# ignore_missing: true +# +# The following example preserves the raw message under event.original +# +#processors: +#- copy_fields: +# fields: +# - from: message +# to: event.original +# fail_on_error: false +# ignore_missing: true +#- truncate_fields: +# fields: +# - event.original +# max_bytes: 1024 +# fail_on_error: false +# ignore_missing: true + +#============================= Elastic Cloud ================================== + +# These settings simplify using winlogbeat with the Elastic Cloud (https://cloud.elastic.co/). + +# The cloud.id setting overwrites the `output.elasticsearch.hosts` and +# `setup.kibana.host` options. +# You can find the `cloud.id` in the Elastic Cloud web UI. +#cloud.id: + +# The cloud.auth setting overwrites the `output.elasticsearch.username` and +# `output.elasticsearch.password` settings. The format is `:`. +#cloud.auth: + +#================================ Outputs ====================================== + +# Configure what output to use when sending the data collected by the beat. + +#-------------------------- Elasticsearch output ------------------------------- +output.elasticsearch: + # Boolean flag to enable or disable the output module. + #enabled: true + + # Array of hosts to connect to. + # Scheme and port can be left out and will be set to the default (http and 9200) + # In case you specify and additional path, the scheme is required: http://localhost:9200/path + # IPv6 addresses should always be defined as: https://[2001:db8::1]:9200 + hosts: ["localhost:9200"] + + # Set gzip compression level. + #compression_level: 0 + + # Configure escaping HTML symbols in strings. + #escape_html: false + + # Optional protocol and basic auth credentials. + #protocol: "https" + #username: "elastic" + #password: "changeme" + + # Dictionary of HTTP parameters to pass within the URL with index operations. + #parameters: + #param1: value1 + #param2: value2 + + # Number of workers per Elasticsearch host. + #worker: 1 + + # Optional index name. The default is "winlogbeat" plus date + # and generates [winlogbeat-]YYYY.MM.DD keys. + # In case you modify this pattern you must update setup.template.name and setup.template.pattern accordingly. + #index: "winlogbeat-%{[agent.version]}-%{+yyyy.MM.dd}" + + # Optional ingest node pipeline. By default no pipeline will be used. + #pipeline: "" + + # Optional HTTP path + #path: "/elasticsearch" + + # Custom HTTP headers to add to each request + #headers: + # X-My-Header: Contents of the header + + # Proxy server URL + #proxy_url: http://proxy:3128 + + # The number of times a particular Elasticsearch index operation is attempted. If + # the indexing operation doesn't succeed after this many retries, the events are + # dropped. The default is 3. + #max_retries: 3 + + # The maximum number of events to bulk in a single Elasticsearch bulk API index request. + # The default is 50. + #bulk_max_size: 50 + + # The number of seconds to wait before trying to reconnect to Elasticsearch + # after a network error. After waiting backoff.init seconds, the Beat + # tries to reconnect. If the attempt fails, the backoff timer is increased + # exponentially up to backoff.max. After a successful connection, the backoff + # timer is reset. The default is 1s. + #backoff.init: 1s + + # The maximum number of seconds to wait before attempting to connect to + # Elasticsearch after a network error. The default is 60s. + #backoff.max: 60s + + # Configure HTTP request timeout before failing a request to Elasticsearch. + #timeout: 90 + + # Use SSL settings for HTTPS. + #ssl.enabled: true + + # Configure SSL verification mode. If `none` is configured, all server hosts + # and certificates will be accepted. In this mode, SSL-based connections are + # susceptible to man-in-the-middle attacks. Use only for testing. Default is + # `full`. + #ssl.verification_mode: full + + # List of supported/valid TLS versions. By default all TLS versions from 1.0 up to + # 1.2 are enabled. + #ssl.supported_protocols: [TLSv1.0, TLSv1.1, TLSv1.2] + + # List of root certificates for HTTPS server verifications + #ssl.certificate_authorities: ["/etc/pki/root/ca.pem"] + + # Certificate for SSL client authentication + #ssl.certificate: "/etc/pki/client/cert.pem" + + # Client certificate key + #ssl.key: "/etc/pki/client/cert.key" + + # Optional passphrase for decrypting the certificate key. + #ssl.key_passphrase: '' + + # Configure cipher suites to be used for SSL connections + #ssl.cipher_suites: [] + + # Configure curve types for ECDHE-based cipher suites + #ssl.curve_types: [] + + # Configure what types of renegotiation are supported. Valid options are + # never, once, and freely. Default is never. + #ssl.renegotiation: never + + +#----------------------------- Logstash output --------------------------------- +#output.logstash: + # Boolean flag to enable or disable the output module. + #enabled: true + + # The Logstash hosts + #hosts: ["localhost:5044"] + + # Number of workers per Logstash host. + #worker: 1 + + # Set gzip compression level. + #compression_level: 3 + + # Configure escaping HTML symbols in strings. + #escape_html: false + + # Optional maximum time to live for a connection to Logstash, after which the + # connection will be re-established. A value of `0s` (the default) will + # disable this feature. + # + # Not yet supported for async connections (i.e. with the "pipelining" option set) + #ttl: 30s + + # Optionally load-balance events between Logstash hosts. Default is false. + #loadbalance: false + + # Number of batches to be sent asynchronously to Logstash while processing + # new batches. + #pipelining: 2 + + # If enabled only a subset of events in a batch of events is transferred per + # transaction. The number of events to be sent increases up to `bulk_max_size` + # if no error is encountered. + #slow_start: false + + # The number of seconds to wait before trying to reconnect to Logstash + # after a network error. After waiting backoff.init seconds, the Beat + # tries to reconnect. If the attempt fails, the backoff timer is increased + # exponentially up to backoff.max. After a successful connection, the backoff + # timer is reset. The default is 1s. + #backoff.init: 1s + + # The maximum number of seconds to wait before attempting to connect to + # Logstash after a network error. The default is 60s. + #backoff.max: 60s + + # Optional index name. The default index name is set to winlogbeat + # in all lowercase. + #index: 'winlogbeat' + + # SOCKS5 proxy server URL + #proxy_url: socks5://user:password@socks5-server:2233 + + # Resolve names locally when using a proxy server. Defaults to false. + #proxy_use_local_resolver: false + + # Enable SSL support. SSL is automatically enabled if any SSL setting is set. + #ssl.enabled: true + + # Configure SSL verification mode. If `none` is configured, all server hosts + # and certificates will be accepted. In this mode, SSL based connections are + # susceptible to man-in-the-middle attacks. Use only for testing. Default is + # `full`. + #ssl.verification_mode: full + + # List of supported/valid TLS versions. By default all TLS versions from 1.0 up to + # 1.2 are enabled. + #ssl.supported_protocols: [TLSv1.0, TLSv1.1, TLSv1.2] + + # Optional SSL configuration options. SSL is off by default. + # List of root certificates for HTTPS server verifications + #ssl.certificate_authorities: ["/etc/pki/root/ca.pem"] + + # Certificate for SSL client authentication + #ssl.certificate: "/etc/pki/client/cert.pem" + + # Client certificate key + #ssl.key: "/etc/pki/client/cert.key" + + # Optional passphrase for decrypting the Certificate Key. + #ssl.key_passphrase: '' + + # Configure cipher suites to be used for SSL connections + #ssl.cipher_suites: [] + + # Configure curve types for ECDHE-based cipher suites + #ssl.curve_types: [] + + # Configure what types of renegotiation are supported. Valid options are + # never, once, and freely. Default is never. + #ssl.renegotiation: never + + # The number of times to retry publishing an event after a publishing failure. + # After the specified number of retries, the events are typically dropped. + # Some Beats, such as Filebeat and Winlogbeat, ignore the max_retries setting + # and retry until all events are published. Set max_retries to a value less + # than 0 to retry until all events are published. The default is 3. + #max_retries: 3 + + # The maximum number of events to bulk in a single Logstash request. The + # default is 2048. + #bulk_max_size: 2048 + + # The number of seconds to wait for responses from the Logstash server before + # timing out. The default is 30s. + #timeout: 30s + +#------------------------------- Kafka output ---------------------------------- +#output.kafka: + # Boolean flag to enable or disable the output module. + #enabled: true + + # The list of Kafka broker addresses from which to fetch the cluster metadata. + # The cluster metadata contain the actual Kafka brokers events are published + # to. + #hosts: ["localhost:9092"] + + # The Kafka topic used for produced events. The setting can be a format string + # using any event field. To set the topic from document type use `%{[type]}`. + #topic: beats + + # The Kafka event key setting. Use format string to create a unique event key. + # By default no event key will be generated. + #key: '' + + # The Kafka event partitioning strategy. Default hashing strategy is `hash` + # using the `output.kafka.key` setting or randomly distributes events if + # `output.kafka.key` is not configured. + #partition.hash: + # If enabled, events will only be published to partitions with reachable + # leaders. Default is false. + #reachable_only: false + + # Configure alternative event field names used to compute the hash value. + # If empty `output.kafka.key` setting will be used. + # Default value is empty list. + #hash: [] + + # Authentication details. Password is required if username is set. + #username: '' + #password: '' + + # Kafka version winlogbeat is assumed to run against. Defaults to the "1.0.0". + #version: '1.0.0' + + # Configure JSON encoding + #codec.json: + # Pretty-print JSON event + #pretty: false + + # Configure escaping HTML symbols in strings. + #escape_html: false + + # Metadata update configuration. Metadata contains leader information + # used to decide which broker to use when publishing. + #metadata: + # Max metadata request retry attempts when cluster is in middle of leader + # election. Defaults to 3 retries. + #retry.max: 3 + + # Wait time between retries during leader elections. Default is 250ms. + #retry.backoff: 250ms + + # Refresh metadata interval. Defaults to every 10 minutes. + #refresh_frequency: 10m + + # Strategy for fetching the topics metadata from the broker. Default is true. + #full: true + + # The number of concurrent load-balanced Kafka output workers. + #worker: 1 + + # The number of times to retry publishing an event after a publishing failure. + # After the specified number of retries, events are typically dropped. + # Some Beats, such as Filebeat, ignore the max_retries setting and retry until + # all events are published. Set max_retries to a value less than 0 to retry + # until all events are published. The default is 3. + #max_retries: 3 + + # The maximum number of events to bulk in a single Kafka request. The default + # is 2048. + #bulk_max_size: 2048 + + # The number of seconds to wait for responses from the Kafka brokers before + # timing out. The default is 30s. + #timeout: 30s + + # The maximum duration a broker will wait for number of required ACKs. The + # default is 10s. + #broker_timeout: 10s + + # The number of messages buffered for each Kafka broker. The default is 256. + #channel_buffer_size: 256 + + # The keep-alive period for an active network connection. If 0s, keep-alives + # are disabled. The default is 0 seconds. + #keep_alive: 0 + + # Sets the output compression codec. Must be one of none, snappy and gzip. The + # default is gzip. + #compression: gzip + + # Set the compression level. Currently only gzip provides a compression level + # between 0 and 9. The default value is chosen by the compression algorithm. + #compression_level: 4 + + # The maximum permitted size of JSON-encoded messages. Bigger messages will be + # dropped. The default value is 1000000 (bytes). This value should be equal to + # or less than the broker's message.max.bytes. + #max_message_bytes: 1000000 + + # The ACK reliability level required from broker. 0=no response, 1=wait for + # local commit, -1=wait for all replicas to commit. The default is 1. Note: + # If set to 0, no ACKs are returned by Kafka. Messages might be lost silently + # on error. + #required_acks: 1 + + # The configurable ClientID used for logging, debugging, and auditing + # purposes. The default is "beats". + #client_id: beats + + # Enable SSL support. SSL is automatically enabled if any SSL setting is set. + #ssl.enabled: true + + # Optional SSL configuration options. SSL is off by default. + # List of root certificates for HTTPS server verifications + #ssl.certificate_authorities: ["/etc/pki/root/ca.pem"] + + # Configure SSL verification mode. If `none` is configured, all server hosts + # and certificates will be accepted. In this mode, SSL based connections are + # susceptible to man-in-the-middle attacks. Use only for testing. Default is + # `full`. + #ssl.verification_mode: full + + # List of supported/valid TLS versions. By default all TLS versions from 1.0 up to + # 1.2 are enabled. + #ssl.supported_protocols: [TLSv1.0, TLSv1.1, TLSv1.2] + + # Certificate for SSL client authentication + #ssl.certificate: "/etc/pki/client/cert.pem" + + # Client Certificate Key + #ssl.key: "/etc/pki/client/cert.key" + + # Optional passphrase for decrypting the Certificate Key. + #ssl.key_passphrase: '' + + # Configure cipher suites to be used for SSL connections + #ssl.cipher_suites: [] + + # Configure curve types for ECDHE-based cipher suites + #ssl.curve_types: [] + + # Configure what types of renegotiation are supported. Valid options are + # never, once, and freely. Default is never. + #ssl.renegotiation: never + +#------------------------------- Redis output ---------------------------------- +#output.redis: + # Boolean flag to enable or disable the output module. + #enabled: true + + # Configure JSON encoding + #codec.json: + # Pretty print json event + #pretty: false + + # Configure escaping HTML symbols in strings. + #escape_html: false + + # The list of Redis servers to connect to. If load-balancing is enabled, the + # events are distributed to the servers in the list. If one server becomes + # unreachable, the events are distributed to the reachable servers only. + #hosts: ["localhost:6379"] + + # The name of the Redis list or channel the events are published to. The + # default is winlogbeat. + #key: winlogbeat + + # The password to authenticate to Redis with. The default is no authentication. + #password: + + # The Redis database number where the events are published. The default is 0. + #db: 0 + + # The Redis data type to use for publishing events. If the data type is list, + # the Redis RPUSH command is used. If the data type is channel, the Redis + # PUBLISH command is used. The default value is list. + #datatype: list + + # The number of workers to use for each host configured to publish events to + # Redis. Use this setting along with the loadbalance option. For example, if + # you have 2 hosts and 3 workers, in total 6 workers are started (3 for each + # host). + #worker: 1 + + # If set to true and multiple hosts or workers are configured, the output + # plugin load balances published events onto all Redis hosts. If set to false, + # the output plugin sends all events to only one host (determined at random) + # and will switch to another host if the currently selected one becomes + # unreachable. The default value is true. + #loadbalance: true + + # The Redis connection timeout in seconds. The default is 5 seconds. + #timeout: 5s + + # The number of times to retry publishing an event after a publishing failure. + # After the specified number of retries, the events are typically dropped. + # Some Beats, such as Filebeat, ignore the max_retries setting and retry until + # all events are published. Set max_retries to a value less than 0 to retry + # until all events are published. The default is 3. + #max_retries: 3 + + # The number of seconds to wait before trying to reconnect to Redis + # after a network error. After waiting backoff.init seconds, the Beat + # tries to reconnect. If the attempt fails, the backoff timer is increased + # exponentially up to backoff.max. After a successful connection, the backoff + # timer is reset. The default is 1s. + #backoff.init: 1s + + # The maximum number of seconds to wait before attempting to connect to + # Redis after a network error. The default is 60s. + #backoff.max: 60s + + # The maximum number of events to bulk in a single Redis request or pipeline. + # The default is 2048. + #bulk_max_size: 2048 + + # The URL of the SOCKS5 proxy to use when connecting to the Redis servers. The + # value must be a URL with a scheme of socks5://. + #proxy_url: + + # This option determines whether Redis hostnames are resolved locally when + # using a proxy. The default value is false, which means that name resolution + # occurs on the proxy server. + #proxy_use_local_resolver: false + + # Enable SSL support. SSL is automatically enabled, if any SSL setting is set. + #ssl.enabled: true + + # Configure SSL verification mode. If `none` is configured, all server hosts + # and certificates will be accepted. In this mode, SSL based connections are + # susceptible to man-in-the-middle attacks. Use only for testing. Default is + # `full`. + #ssl.verification_mode: full + + # List of supported/valid TLS versions. By default all TLS versions 1.0 up to + # 1.2 are enabled. + #ssl.supported_protocols: [TLSv1.0, TLSv1.1, TLSv1.2] + + # Optional SSL configuration options. SSL is off by default. + # List of root certificates for HTTPS server verifications + #ssl.certificate_authorities: ["/etc/pki/root/ca.pem"] + + # Certificate for SSL client authentication + #ssl.certificate: "/etc/pki/client/cert.pem" + + # Client Certificate Key + #ssl.key: "/etc/pki/client/cert.key" + + # Optional passphrase for decrypting the Certificate Key. + #ssl.key_passphrase: '' + + # Configure cipher suites to be used for SSL connections + #ssl.cipher_suites: [] + + # Configure curve types for ECDHE based cipher suites + #ssl.curve_types: [] + + # Configure what types of renegotiation are supported. Valid options are + # never, once, and freely. Default is never. + #ssl.renegotiation: never + +#------------------------------- File output ----------------------------------- +#output.file: + # Boolean flag to enable or disable the output module. + #enabled: true + + # Configure JSON encoding + #codec.json: + # Pretty-print JSON event + #pretty: false + + # Configure escaping HTML symbols in strings. + #escape_html: false + + # Path to the directory where to save the generated files. The option is + # mandatory. + #path: "/tmp/winlogbeat" + + # Name of the generated files. The default is `winlogbeat` and it generates + # files: `winlogbeat`, `winlogbeat.1`, `winlogbeat.2`, etc. + #filename: winlogbeat + + # Maximum size in kilobytes of each file. When this size is reached, and on + # every winlogbeat restart, the files are rotated. The default value is 10240 + # kB. + #rotate_every_kb: 10000 + + # Maximum number of files under path. When this number of files is reached, + # the oldest file is deleted and the rest are shifted from last to first. The + # default is 7 files. + #number_of_files: 7 + + # Permissions to use for file creation. The default is 0600. + #permissions: 0600 + + +#----------------------------- Console output --------------------------------- +#output.console: + # Boolean flag to enable or disable the output module. + #enabled: true + + # Configure JSON encoding + #codec.json: + # Pretty-print JSON event + #pretty: false + + # Configure escaping HTML symbols in strings. + #escape_html: false + +#================================= Paths ====================================== + +# The home path for the winlogbeat installation. This is the default base path +# for all other path settings and for miscellaneous files that come with the +# distribution (for example, the sample dashboards). +# If not set by a CLI flag or in the configuration file, the default for the +# home path is the location of the binary. +#path.home: + +# The configuration path for the winlogbeat installation. This is the default +# base path for configuration files, including the main YAML configuration file +# and the Elasticsearch template file. If not set by a CLI flag or in the +# configuration file, the default for the configuration path is the home path. +#path.config: ${path.home} + +# The data path for the winlogbeat installation. This is the default base path +# for all the files in which winlogbeat needs to store its data. If not set by a +# CLI flag or in the configuration file, the default for the data path is a data +# subdirectory inside the home path. +#path.data: ${path.home}/data + +# The logs path for a winlogbeat installation. This is the default location for +# the Beat's log files. If not set by a CLI flag or in the configuration file, +# the default for the logs path is a logs subdirectory inside the home path. +#path.logs: ${path.home}/logs + +#================================ Keystore ========================================== +# Location of the Keystore containing the keys and their sensitive values. +#keystore.path: "${path.config}/beats.keystore" + +#============================== Dashboards ===================================== +# These settings control loading the sample dashboards to the Kibana index. Loading +# the dashboards are disabled by default and can be enabled either by setting the +# options here, or by using the `-setup` CLI flag or the `setup` command. +#setup.dashboards.enabled: false + +# The directory from where to read the dashboards. The default is the `kibana` +# folder in the home path. +#setup.dashboards.directory: ${path.home}/kibana + +# The URL from where to download the dashboards archive. It is used instead of +# the directory if it has a value. +#setup.dashboards.url: + +# The file archive (zip file) from where to read the dashboards. It is used instead +# of the directory when it has a value. +#setup.dashboards.file: + +# In case the archive contains the dashboards from multiple Beats, this lets you +# select which one to load. You can load all the dashboards in the archive by +# setting this to the empty string. +#setup.dashboards.beat: winlogbeat + +# The name of the Kibana index to use for setting the configuration. Default is ".kibana" +#setup.dashboards.kibana_index: .kibana + +# The Elasticsearch index name. This overwrites the index name defined in the +# dashboards and index pattern. Example: testbeat-* +#setup.dashboards.index: + +# Always use the Kibana API for loading the dashboards instead of autodetecting +# how to install the dashboards by first querying Elasticsearch. +#setup.dashboards.always_kibana: false + +# If true and Kibana is not reachable at the time when dashboards are loaded, +# it will retry to reconnect to Kibana instead of exiting with an error. +#setup.dashboards.retry.enabled: false + +# Duration interval between Kibana connection retries. +#setup.dashboards.retry.interval: 1s + +# Maximum number of retries before exiting with an error, 0 for unlimited retrying. +#setup.dashboards.retry.maximum: 0 + + +#============================== Template ===================================== + +# A template is used to set the mapping in Elasticsearch +# By default template loading is enabled and the template is loaded. +# These settings can be adjusted to load your own template or overwrite existing ones. + +# Set to false to disable template loading. +#setup.template.enabled: true + +# Template name. By default the template name is "winlogbeat-%{[agent.version]}" +# The template name and pattern has to be set in case the Elasticsearch index pattern is modified. +#setup.template.name: "winlogbeat-%{[agent.version]}" + +# Template pattern. By default the template pattern is "-%{[agent.version]}-*" to apply to the default index settings. +# The first part is the version of the beat and then -* is used to match all daily indices. +# The template name and pattern has to be set in case the Elasticsearch index pattern is modified. +#setup.template.pattern: "winlogbeat-%{[agent.version]}-*" + +# Path to fields.yml file to generate the template +#setup.template.fields: "${path.config}/fields.yml" + +# A list of fields to be added to the template and Kibana index pattern. Also +# specify setup.template.overwrite: true to overwrite the existing template. +# This setting is experimental. +#setup.template.append_fields: +#- name: field_name +# type: field_type + +# Enable JSON template loading. If this is enabled, the fields.yml is ignored. +#setup.template.json.enabled: false + +# Path to the JSON template file +#setup.template.json.path: "${path.config}/template.json" + +# Name under which the template is stored in Elasticsearch +#setup.template.json.name: "" + +# Overwrite existing template +#setup.template.overwrite: false + +# Elasticsearch template settings +setup.template.settings: + + # A dictionary of settings to place into the settings.index dictionary + # of the Elasticsearch template. For more details, please check + # https://www.elastic.co/guide/en/elasticsearch/reference/current/mapping.html + #index: + #number_of_shards: 1 + #codec: best_compression + #number_of_routing_shards: 30 + + # A dictionary of settings for the _source field. For more details, please check + # https://www.elastic.co/guide/en/elasticsearch/reference/current/mapping-source-field.html + #_source: + #enabled: false + +#============================== Setup ILM ===================================== + +# Configure Index Lifecycle Management Index Lifecycle Management creates a +# write alias and adds additional settings to the template. +# The elasticsearch.output.index setting will be replaced with the write alias +# if ILM is enabled. + +# Enabled ILM support. Valid values are true, false, and auto. The beat will +# detect availabilty of Index Lifecycle Management in Elasticsearch and enable +# or disable ILM support. +#setup.ilm.enabled: auto + +# Configure the ILM write alias name. +#setup.ilm.rollover_alias: "winlogbeat" + +# Configure rollover index pattern. +#setup.ilm.pattern: "{now/d}-000001" + + +#============================== Kibana ===================================== + +# Starting with Beats version 6.0.0, the dashboards are loaded via the Kibana API. +# This requires a Kibana endpoint configuration. +setup.kibana: + + # Kibana Host + # Scheme and port can be left out and will be set to the default (http and 5601) + # In case you specify and additional path, the scheme is required: http://localhost:5601/path + # IPv6 addresses should always be defined as: https://[2001:db8::1]:5601 + #host: "localhost:5601" + + # Optional protocol and basic auth credentials. + #protocol: "https" + #username: "elastic" + #password: "changeme" + + # Optional HTTP path + #path: "" + + # Use SSL settings for HTTPS. Default is true. + #ssl.enabled: true + + # Configure SSL verification mode. If `none` is configured, all server hosts + # and certificates will be accepted. In this mode, SSL based connections are + # susceptible to man-in-the-middle attacks. Use only for testing. Default is + # `full`. + #ssl.verification_mode: full + + # List of supported/valid TLS versions. By default all TLS versions from 1.0 up to + # 1.2 are enabled. + #ssl.supported_protocols: [TLSv1.0, TLSv1.1, TLSv1.2] + + # SSL configuration. The default is off. + # List of root certificates for HTTPS server verifications + #ssl.certificate_authorities: ["/etc/pki/root/ca.pem"] + + # Certificate for SSL client authentication + #ssl.certificate: "/etc/pki/client/cert.pem" + + # Client certificate key + #ssl.key: "/etc/pki/client/cert.key" + + # Optional passphrase for decrypting the certificate key. + #ssl.key_passphrase: '' + + # Configure cipher suites to be used for SSL connections + #ssl.cipher_suites: [] + + # Configure curve types for ECDHE-based cipher suites + #ssl.curve_types: [] + + + +#================================ Logging ====================================== +# There are four options for the log output: file, stderr, syslog, eventlog +# The file output is the default. + +# Sets log level. The default log level is info. +# Available log levels are: error, warning, info, debug +#logging.level: info + +# Enable debug output for selected components. To enable all selectors use ["*"] +# Other available selectors are "beat", "publish", "service" +# Multiple selectors can be chained. +#logging.selectors: [ ] + +# Send all logging output to syslog. The default is false. +#logging.to_syslog: false + +# Send all logging output to Windows Event Logs. The default is false. +#logging.to_eventlog: false + +# If enabled, winlogbeat periodically logs its internal metrics that have changed +# in the last period. For each metric that changed, the delta from the value at +# the beginning of the period is logged. Also, the total values for +# all non-zero internal metrics are logged on shutdown. The default is true. +#logging.metrics.enabled: true + +# The period after which to log the internal metrics. The default is 30s. +#logging.metrics.period: 30s + +# Logging to rotating files. Set logging.to_files to false to disable logging to +# files. +logging.to_files: true +logging.files: + # Configure the path where the logs are written. The default is the logs directory + # under the home path (the binary location). + #path: /var/log/winlogbeat + + # The name of the files where the logs are written to. + #name: winlogbeat + + # Configure log file size limit. If limit is reached, log file will be + # automatically rotated + #rotateeverybytes: 10485760 # = 10MB + + # Number of rotated log files to keep. Oldest files will be deleted first. + #keepfiles: 7 + + # The permissions mask to apply when rotating log files. The default value is 0600. + # Must be a valid Unix-style file permissions mask expressed in octal notation. + #permissions: 0600 + + # Enable log file rotation on time intervals in addition to size-based rotation. + # Intervals must be at least 1s. Values of 1m, 1h, 24h, 7*24h, 30*24h, and 365*24h + # are boundary-aligned with minutes, hours, days, weeks, months, and years as + # reported by the local system clock. All other intervals are calculated from the + # Unix epoch. Defaults to disabled. + #interval: 0 + +# Set to true to log messages in JSON format. +#logging.json: false + + +#============================== Xpack Monitoring =============================== +# winlogbeat can export internal metrics to a central Elasticsearch monitoring +# cluster. This requires xpack monitoring to be enabled in Elasticsearch. The +# reporting is disabled by default. + +# Set to true to enable the monitoring reporter. +#monitoring.enabled: false + +# Uncomment to send the metrics to Elasticsearch. Most settings from the +# Elasticsearch output are accepted here as well. +# Note that the settings should point to your Elasticsearch *monitoring* cluster. +# Any setting that is not set is automatically inherited from the Elasticsearch +# output configuration, so if you have the Elasticsearch output configured such +# that it is pointing to your Elasticsearch monitoring cluster, you can simply +# uncomment the following line. +#monitoring.elasticsearch: + + # Array of hosts to connect to. + # Scheme and port can be left out and will be set to the default (http and 9200) + # In case you specify and additional path, the scheme is required: http://localhost:9200/path + # IPv6 addresses should always be defined as: https://[2001:db8::1]:9200 + #hosts: ["localhost:9200"] + + # Set gzip compression level. + #compression_level: 0 + + # Optional protocol and basic auth credentials. + #protocol: "https" + #username: "beats_system" + #password: "changeme" + + # Dictionary of HTTP parameters to pass within the URL with index operations. + #parameters: + #param1: value1 + #param2: value2 + + # Custom HTTP headers to add to each request + #headers: + # X-My-Header: Contents of the header + + # Proxy server url + #proxy_url: http://proxy:3128 + + # The number of times a particular Elasticsearch index operation is attempted. If + # the indexing operation doesn't succeed after this many retries, the events are + # dropped. The default is 3. + #max_retries: 3 + + # The maximum number of events to bulk in a single Elasticsearch bulk API index request. + # The default is 50. + #bulk_max_size: 50 + + # The number of seconds to wait before trying to reconnect to Elasticsearch + # after a network error. After waiting backoff.init seconds, the Beat + # tries to reconnect. If the attempt fails, the backoff timer is increased + # exponentially up to backoff.max. After a successful connection, the backoff + # timer is reset. The default is 1s. + #backoff.init: 1s + + # The maximum number of seconds to wait before attempting to connect to + # Elasticsearch after a network error. The default is 60s. + #backoff.max: 60s + + # Configure HTTP request timeout before failing an request to Elasticsearch. + #timeout: 90 + + # Use SSL settings for HTTPS. + #ssl.enabled: true + + # Configure SSL verification mode. If `none` is configured, all server hosts + # and certificates will be accepted. In this mode, SSL based connections are + # susceptible to man-in-the-middle attacks. Use only for testing. Default is + # `full`. + #ssl.verification_mode: full + + # List of supported/valid TLS versions. By default all TLS versions from 1.0 up to + # 1.2 are enabled. + #ssl.supported_protocols: [TLSv1.0, TLSv1.1, TLSv1.2] + + # SSL configuration. The default is off. + # List of root certificates for HTTPS server verifications + #ssl.certificate_authorities: ["/etc/pki/root/ca.pem"] + + # Certificate for SSL client authentication + #ssl.certificate: "/etc/pki/client/cert.pem" + + # Client certificate key + #ssl.key: "/etc/pki/client/cert.key" + + # Optional passphrase for decrypting the certificate key. + #ssl.key_passphrase: '' + + # Configure cipher suites to be used for SSL connections + #ssl.cipher_suites: [] + + # Configure curve types for ECDHE-based cipher suites + #ssl.curve_types: [] + + # Configure what types of renegotiation are supported. Valid options are + # never, once, and freely. Default is never. + #ssl.renegotiation: never + + #metrics.period: 10s + #state.period: 1m + +#================================ HTTP Endpoint ====================================== +# Each beat can expose internal metrics through a HTTP endpoint. For security +# reasons the endpoint is disabled by default. This feature is currently experimental. +# Stats can be access through http://localhost:5066/stats . For pretty JSON output +# append ?pretty to the URL. + +# Defines if the HTTP endpoint is enabled. +#http.enabled: false + +# The HTTP endpoint will bind to this hostname or IP address. It is recommended to use only localhost. +#http.host: localhost + +# Port on which the HTTP endpoint will bind. Default is 5066. +#http.port: 5066 + +#============================= Process Security ================================ + +# Enable or disable seccomp system call filtering on Linux. Default is enabled. +#seccomp.enabled: true + +#================================= Migration ================================== + +# This allows to enable 6.7 migration aliases +#migration.6_to_7.enabled: false diff --git a/x-pack/winlogbeat/winlogbeat.yml b/x-pack/winlogbeat/winlogbeat.yml new file mode 100644 index 000000000000..30e628838812 --- /dev/null +++ b/x-pack/winlogbeat/winlogbeat.yml @@ -0,0 +1,161 @@ +###################### Winlogbeat Configuration Example ######################## + +# This file is an example configuration file highlighting only the most common +# options. The winlogbeat.reference.yml file from the same directory contains +# all the supported options with more comments. You can use it as a reference. +# +# You can find the full configuration reference here: +# https://www.elastic.co/guide/en/beats/winlogbeat/index.html + +#======================= Winlogbeat specific options =========================== + +# event_logs specifies a list of event logs to monitor as well as any +# accompanying options. The YAML data type of event_logs is a list of +# dictionaries. +# +# The supported keys are name (required), tags, fields, fields_under_root, +# forwarded, ignore_older, level, event_id, provider, and include_xml. Please +# visit the documentation for the complete details of each option. +# https://go.es.io/WinlogbeatConfig +winlogbeat.event_logs: + - name: Application + ignore_older: 72h + + - name: System + + - name: Security +#==================== Elasticsearch template settings ========================== + +setup.template.settings: + index.number_of_shards: 1 + #index.codec: best_compression + #_source.enabled: false + + +#================================ General ===================================== + +# The name of the shipper that publishes the network data. It can be used to group +# all the transactions sent by a single shipper in the web interface. +#name: + +# The tags of the shipper are included in their own field with each +# transaction published. +#tags: ["service-X", "web-tier"] + +# Optional fields that you can specify to add additional information to the +# output. +#fields: +# env: staging + + +#============================== Dashboards ===================================== +# These settings control loading the sample dashboards to the Kibana index. Loading +# the dashboards is disabled by default and can be enabled either by setting the +# options here or by using the `setup` command. +#setup.dashboards.enabled: false + +# The URL from where to download the dashboards archive. By default this URL +# has a value which is computed based on the Beat name and version. For released +# versions, this URL points to the dashboard archive on the artifacts.elastic.co +# website. +#setup.dashboards.url: + +#============================== Kibana ===================================== + +# Starting with Beats version 6.0.0, the dashboards are loaded via the Kibana API. +# This requires a Kibana endpoint configuration. +setup.kibana: + + # Kibana Host + # Scheme and port can be left out and will be set to the default (http and 5601) + # In case you specify and additional path, the scheme is required: http://localhost:5601/path + # IPv6 addresses should always be defined as: https://[2001:db8::1]:5601 + #host: "localhost:5601" + + # Kibana Space ID + # ID of the Kibana Space into which the dashboards should be loaded. By default, + # the Default Space will be used. + #space.id: + +#============================= Elastic Cloud ================================== + +# These settings simplify using winlogbeat with the Elastic Cloud (https://cloud.elastic.co/). + +# The cloud.id setting overwrites the `output.elasticsearch.hosts` and +# `setup.kibana.host` options. +# You can find the `cloud.id` in the Elastic Cloud web UI. +#cloud.id: + +# The cloud.auth setting overwrites the `output.elasticsearch.username` and +# `output.elasticsearch.password` settings. The format is `:`. +#cloud.auth: + +#================================ Outputs ===================================== + +# Configure what output to use when sending the data collected by the beat. + +#-------------------------- Elasticsearch output ------------------------------ +output.elasticsearch: + # Array of hosts to connect to. + hosts: ["localhost:9200"] + + # Optional protocol and basic auth credentials. + #protocol: "https" + #username: "elastic" + #password: "changeme" + +#----------------------------- Logstash output -------------------------------- +#output.logstash: + # The Logstash hosts + #hosts: ["localhost:5044"] + + # Optional SSL. By default is off. + # List of root certificates for HTTPS server verifications + #ssl.certificate_authorities: ["/etc/pki/root/ca.pem"] + + # Certificate for SSL client authentication + #ssl.certificate: "/etc/pki/client/cert.pem" + + # Client Certificate Key + #ssl.key: "/etc/pki/client/cert.key" + +#================================ Processors ===================================== + +# Configure processors to enhance or manipulate events generated by the beat. + +processors: + - add_host_metadata: ~ + - add_cloud_metadata: ~ + +#================================ Logging ===================================== + +# Sets log level. The default log level is info. +# Available log levels are: error, warning, info, debug +#logging.level: debug + +# At debug level, you can selectively enable logging only for some components. +# To enable all selectors use ["*"]. Examples of other selectors are "beat", +# "publish", "service". +#logging.selectors: ["*"] + +#============================== Xpack Monitoring =============================== +# winlogbeat can export internal metrics to a central Elasticsearch monitoring +# cluster. This requires xpack monitoring to be enabled in Elasticsearch. The +# reporting is disabled by default. + +# Set to true to enable the monitoring reporter. +#monitoring.enabled: false + +# Uncomment to send the metrics to Elasticsearch. Most settings from the +# Elasticsearch output are accepted here as well. +# Note that the settings should point to your Elasticsearch *monitoring* cluster. +# Any setting that is not set is automatically inherited from the Elasticsearch +# output configuration, so if you have the Elasticsearch output configured such +# that it is pointing to your Elasticsearch monitoring cluster, you can simply +# uncomment the following line. +#monitoring.elasticsearch: + +#================================= Migration ================================== + +# This allows to enable 6.7 migration aliases +#migration.6_to_7.enabled: true