Skip to content

Commit d5c804b

Browse files
authored
[Docs] Update "Alert and action settings" docs to be generated from YAML source (#191787)
This PR: - Updates the Kibana [Alert and action settings](https://www.elastic.co/guide/en/kibana/current/alert-action-settings-kb.html) page to be based off of a YAML source file (`/docs/settings-gen/source/kibana-alert-action-settings.yml`) that is manually converted to Asciidoc format (`kibana-alert-action-settings.asciidoc`) by means of a Perl script (`docs/settings-gen/parse-settings.pl`). A preview of the new, generated page is [here](https://kibana_bk_191787.docs-preview.app.elstc.co/guide/en/kibana/master/alert-action-settings-kb.html). - Adds the `docs/settings-gen/parse-settings.pl` script which does the YAML → Asciidoc conversion. All new files are added to the `/docs/source-gen` folder. This is a trial run updating only one page of settings in the docs. Later, in separate PRs, we plan to convert other pages. After all Kibana settings pages have been converted, we would ask that the Perl script be run automatically as part of the CI whenever the YAML files in `/docs/source-gen` are added or updated. **Notes:** - The Docs team is happy to own and maintain the Perl script (sorry to use Perl - it's the only scripting language that I know). - In time we also plan to convert all of these files from Asciidoc to Markdown. - When we eventually/hopefully get the rest of the Kibana settings files converted, we will announce the settings doc process to the Kibana team by email and/or in the Kibana newsletter. Big thanks to the amazing @lukeelmers and @KOTungseth for guiding this! --- Why are we doing this? We aim to: - Create a more consistent appearance for settings across all of the docs. - Make it easier for people to contribute, since all Asciidoc/Markdown formatting is handled by a script. - Make it more apparent which settings may be missing info, such as the default values, available options, etc. --- P.S. I haven't worked in the Kibana repo very much and would appreciate any help navigating the CI checks. Rel: elastic/docs-projects#239
1 parent c4371e9 commit d5c804b

File tree

7 files changed

+3870
-623
lines changed

7 files changed

+3870
-623
lines changed

.github/CODEOWNERS

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2640,6 +2640,9 @@ oas_docs/.spectral.yaml @elastic/platform-docs
26402640
oas_docs/kibana.info.serverless.yaml @elastic/platform-docs
26412641
oas_docs/kibana.info.yaml @elastic/platform-docs
26422642

2643+
# Documentation settings files
2644+
docs/settings-gen @elastic/platform-docs
2645+
26432646
# Plugin manifests
26442647
/src/plugins/**/kibana.jsonc @elastic/kibana-core
26452648
/src/platform/plugins/shared/**/kibana.jsonc @elastic/kibana-core
Lines changed: 227 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,227 @@
1+
#!/usr/bin/perl
2+
3+
# This script takes all .yml files in the /source directory and, for each, generates an asciidoc file of the same name.
4+
# Run the script: perl parse-settings.pl
5+
6+
use strict;
7+
use warnings;
8+
use YAML::Tiny;
9+
use File::Find;
10+
use File::Copy;
11+
12+
my $file;
13+
# I'm hardcoding these directories just temporarily for testing
14+
my $sourcedir = './source';
15+
my $asciidocdir = 'source/';
16+
my $count;
17+
18+
find(\&iteratefiles, $sourcedir);
19+
print "\n\nProcessed ".$count. " files.\n";
20+
exit;
21+
22+
sub iteratefiles {
23+
$file = $_;
24+
# ignore any non-yaml files
25+
if (!($file =~ /\.yml$/)) {return;}
26+
print "\nParsed file: ".$file;
27+
my $testslice = parsefile($file);
28+
return;
29+
}
30+
31+
sub parsefile {
32+
# Create an output file based on yaml filename
33+
my $outputfile = my $outputfileorig = $file;
34+
$outputfile =~ s/.yml/.asciidoc/g;
35+
# We'll use this to store the contents of the generated asciidoc file
36+
37+
# Read in the yaml file
38+
my $yaml = YAML::Tiny->read( $file );
39+
40+
# Get a reference to the first document
41+
#my $config = $yaml->[0];
42+
43+
my $collection = $yaml->[0]->{collection};
44+
my $product = $yaml->[0]->{product};
45+
46+
# This variable is used to capture all the content that will become our output asciidoc file
47+
my $asciidocoutput = "\n".'// '."This is a generated file; please don't update it directly.\n".'//'." Instead, the updatable source for these settings can be found in ".$outputfileorig;
48+
$asciidocoutput .= "\n".'// '."Collection: ".$collection;
49+
$asciidocoutput .= "\n".'// '."Product: ".$product."\n\n";
50+
51+
# build the page preamble paragraphs
52+
my $page_description = $yaml->[0]->{page_description};
53+
if ($page_description) {
54+
# preserve newlines
55+
$page_description =~ s/\n/\n\n/g;
56+
$asciidocoutput .= $page_description;
57+
}
58+
59+
my $groups = $yaml->[0]{groups};
60+
for my $group (@$groups) {
61+
62+
# Grab the group name, description, and other properties
63+
my $group_id = $group->{id};
64+
my $group_name = $group->{group};
65+
my $group_description = $group->{description};
66+
my $group_example = $group->{example};
67+
68+
# Add the group info to the asciidoc file contents
69+
$asciidocoutput .= "\n\n";
70+
if ($group_id) {
71+
$asciidocoutput .= "[float]\n[[".$group_id."]]\n=== ".$group_name."\n\n";
72+
}
73+
else {
74+
$asciidocoutput .= "[float]\n=== ".$group_name."\n\n";
75+
}
76+
if ($group_description) {
77+
# preserve newlines
78+
$group_description =~ s/\n/\n\n/g;
79+
$asciidocoutput .= "\n$group_description\n";
80+
}
81+
82+
83+
# Add an example if there is one, like this: include::../examples/example-logging-root-level.asciidoc[]
84+
if ($group_example) {
85+
$asciidocoutput .= "\n\n$group_example\n\n";
86+
}
87+
88+
my $settings = $group->{settings};
89+
for my $setting (@$settings) {
90+
91+
# Grab the setting name, description, and other properties
92+
my $setting_name = $setting->{setting};
93+
my $setting_id = $setting->{id};
94+
my $setting_description = $setting->{description};
95+
my $setting_note = $setting->{note};
96+
my $setting_warning = $setting->{warning};
97+
my $setting_important = $setting->{important};
98+
my $setting_tip = $setting->{tip};
99+
my $setting_datatype = $setting->{datatype};
100+
my $setting_default = $setting->{default};
101+
my $setting_type = $setting->{type};
102+
my $setting_options = $setting->{options};
103+
my $setting_platforms = $setting->{platforms};
104+
my $setting_example = $setting->{example};
105+
my $setting_state = $setting->{state};
106+
my $deprecation_details = $setting->{deprecation_details};
107+
108+
# skip settings that are flagged as "hidden"
109+
if (($setting_state) && ($setting_state =~ /hidden/i)) {next;}
110+
111+
# Get the setting options and option descriptions and build the string
112+
my $options = $setting->{options};
113+
my $setting_options_string = "";
114+
if ($options) {
115+
for my $option (@$options) {
116+
my $option_name = $option->{option};
117+
# if ($option_name) {print "\nOPTION = ".$option_name;}
118+
if ($option_name) {$setting_options_string .= '* `'.$option_name.'`';}
119+
my $option_description = $option->{description};
120+
# if ($option_description) {print "\nDESCRIPTION = ".$option_description;}
121+
if ($option_description) {$setting_options_string .= ' - '.$option_description;}
122+
$setting_options_string .= "\n";
123+
}
124+
}
125+
126+
# check if supported on Cloud (these settings are marked with a Cloud icon)
127+
my $supported_cloud = 0;
128+
for my $platform (@$setting_platforms) {
129+
if ($platform =~ /cloud/) {$supported_cloud = 1;}
130+
}
131+
132+
# Add the settings info to the asciidoc file contents
133+
$asciidocoutput .= "\n";
134+
if ($setting_id) {
135+
$asciidocoutput .= "\n".'[['.$setting_id.']]'."\n";
136+
}
137+
$asciidocoutput .= '`'.$setting_name.'`';
138+
if ($supported_cloud) {
139+
$asciidocoutput .= ' {ess-icon}';
140+
}
141+
$asciidocoutput .= "::\n+\n====\n";
142+
143+
if ($setting_state) {
144+
# Add a standard disclaimer for technical preview settings
145+
if ($setting_state =~ /technical-preview/i)
146+
{
147+
$asciidocoutput .= "\n\npreview::[]\n\n";
148+
}
149+
150+
# Mark deprecated settings and add guidance (such as when it was deprecated) if there is any
151+
elsif ($setting_state =~ /deprecated/i)
152+
{
153+
$asciidocoutput .= "**Deprecated:** ";
154+
if ($deprecation_details) {
155+
$asciidocoutput .= $deprecation_details."\n\n";
156+
}
157+
}
158+
# known setting_states are 'technical-preview', 'deprecated' and 'hidden'. Anything else is ignored.
159+
else {
160+
print "\nUnknown setting state: ".$setting_state."\n";
161+
}
162+
}
163+
164+
#if ($setting_description_string) {
165+
# $asciidocoutput .= $setting_description_string;
166+
#}
167+
if ($setting_description) {
168+
# preserve newlines
169+
$setting_description =~ s/\n/\n\n/g;
170+
$asciidocoutput .= "$setting_description";
171+
}
172+
173+
if ($setting_note) {
174+
$asciidocoutput .= "\nNOTE: ".$setting_note."\n";
175+
}
176+
if ($setting_warning) {
177+
$asciidocoutput .= "\nWARNING: ".$setting_warning."\n";
178+
}
179+
if ($setting_important) {
180+
$asciidocoutput .= "\nIMPORTANT: ".$setting_important."\n";
181+
}
182+
if ($setting_tip) {
183+
$asciidocoutput .= "\nTIP: ".$setting_tip."\n";
184+
}
185+
186+
# If any of these are defined (setting options, setting default value, settting type...) add those inside a box.
187+
# We put a " +" at the end of each line to to achieve single spacing inside the box.
188+
189+
if (($setting_options_string) || ($setting_datatype) || ($setting_default) || ($setting_type)) {
190+
if ($setting_datatype) {
191+
$asciidocoutput .= "Data type: ".'`'.$setting_datatype.'`'.' +'."\n";
192+
}
193+
if ($setting_options_string) {
194+
$asciidocoutput .= "\nOptions:\n\n".$setting_options_string."\n";
195+
}
196+
if ($setting_default) {
197+
$asciidocoutput .= "Default: ".'`'.$setting_default.'`'.' +'."\n";
198+
}
199+
if ($setting_type) {
200+
$asciidocoutput .= 'Type: `'.$setting_type.'` +'."\n";
201+
}
202+
}
203+
204+
# Add an example if there is one, like this: include::../examples/example-logging-root-level.asciidoc[]
205+
if ($setting_example) {
206+
$asciidocoutput .= "\n\n$setting_example\n\n";
207+
}
208+
209+
$asciidocoutput .= "====\n";
210+
}
211+
}
212+
213+
# Just in case we need to grab all of the keys, this is how:
214+
# foreach my $key (keys %hash) { ... }
215+
216+
$asciidocoutput .= "\n\n";
217+
218+
# write the contents into the generated asciidoc file
219+
open (WRITE, "> $outputfile") or die("$!");
220+
print WRITE $asciidocoutput;
221+
close WRITE;
222+
print "\nGenerated file: ".$outputfile;
223+
++$count;
224+
225+
return;
226+
}
227+

docs/settings-gen/readme.md

Lines changed: 57 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,57 @@
1+
# YAML-based settings documentation
2+
3+
We're aiming to update the Kibana configuration settings pages to be based off of YAML-formatted source files. The approach has the advantages that:
4+
- The YAML format makes it easier to add new settings and update existing ones. The setting data is separate from almost all formatting, whether Asciidoc or (future) Markdown.
5+
- The HTML files will have a more consistent and user-friendly appearance.
6+
- The YAML format makes it easier for teams to identify missing settings or settings that are lacking details that should be made available in the docs.
7+
8+
The YAML settings files in the `settings-gen/source` folder are converted to Asciidoc source, located in the same directory, by means of the `parse-settings.pl` Perl script. Please do not update the generated Asciidoc files directly as your changes will be overwritten. Please make any required docs changes in the `<name>-settings.yml` files.
9+
10+
Following is a schema for all available properties in a YAML settings file.
11+
12+
## Schema
13+
14+
```
15+
product: REQUIRED e.g. Elasticsearch, Kibana, Enterprise Search
16+
collection: REQUIRED e.g. Alerting and action settings in Kibana
17+
page_description: |
18+
OPTIONAL
19+
Multiline string. Can include tables, lists, code examples, etc.
20+
21+
groups:
22+
- group: REQUIRED e.g. Preconfigured connector settings
23+
id: REQUIRED The ID used for documentation links, e.g., general-alert-action-settings
24+
# description: |
25+
OPTIONAL
26+
Multiline string. Can include tables, lists, code examples, etc.
27+
# example: |
28+
OPTIONAL
29+
Multiline string.
30+
Can include tables, lists, code examples, etc.
31+
32+
settings:
33+
- setting: REQUIRED e.g. xpack.encryptedSavedObjects.encryptionKey
34+
# id: OPTIONAL ID used for documentation links, e.g., xpack-encryptedsavedobjects-encryptionkey
35+
description: |
36+
REQUIRED
37+
Multiline string. Can include tables, lists, code examples, etc.
38+
# state: OPTIONAL One of deprecated/hidden/tech-preview
39+
# deprecation_details: "" OPTIONAL
40+
# note: "" OPTIONAL
41+
# tip: "" OPTIONAL
42+
# warning: "" OPTIONAL
43+
# important: "" OPTIONAL
44+
# datatype: REQUIRED One of string/bool/int/float/enum. For enum include the supported 'options', below.
45+
# default: OPTIONAL
46+
# options:
47+
# - option: OPTIONAL
48+
# description: "" OPTIONAL
49+
# type: OPTIONAL ONe of static/dynamic
50+
# platforms: OPTIONAL, list each supported platform
51+
# - cloud
52+
# - serverless
53+
# - self-managed
54+
# example: |
55+
OPTIONAL
56+
Multiline string. Can include tables, lists, code examples, etc.
57+
```

0 commit comments

Comments
 (0)