-
Notifications
You must be signed in to change notification settings - Fork 8.3k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[Ingest] Support yaml variables in datasource #64459
[Ingest] Support yaml variables in datasource #64459
Conversation
Pinging @elastic/ingest-management (Team:Ingest Management) |
Can you elaborate on what you exactly mean by "traverse the generated yaml and replace placeholders by yaml values." |
@ruflin Yes let's say we have the following template
and the following values {
host: { value: "http://127.0.0.1"},
"key.patterns": { value: "\n- limit: 20\n pattern: .*\n", type: "yaml"}
}
load this yaml as json
|
…t-datasource-support-yaml-values
@nchaulet I'm still missing on why in step 1 not all of the handlebar parts are replaced? Is the second step because of the |
@nchaulet We chose Handlebars to avoid all the safety/performance/etc issues with rolling our own templating. I'd like to find a way to work within Handlebars if possible. I think we can change either/both a) the object/keys we supply to handlebars b) adding/registering a |
export function createStream(vars: StreamVars, streamTemplate: string) { | ||
const template = Handlebars.compile(streamTemplate); | ||
return template(vars); | ||
export function createStream(variables: DatasourceConfigRecord, streamTemplate: string) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This function went from returning a YAML string out to returning JS object. I'd like to keep some function that accepts a template string & variables and returns YAML. It doesn't need to this createStream
function, but I'd like to keep a function which accepts the template string & variables and outputs the YAML. That way we don't lose the YAML output step and can do safeLoad
if/when we want to convert it to JS.
processors: | ||
- add_locale: ~ | ||
`); | ||
it('should support yaml values', () => { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If we changed createStream
to accept a map of string
-> any
or unknown
(vs current string
-> string
) I believe we could do this test like
test('Test nested', () => {
const streamTemplate = `
host: {{host}}
{{#if key.patterns}}
key.patterns:{{key.patterns}}
{{/if}}
`;
const vars = {
host: 'http://127.0.0.1',
key: {
patterns: '\n - limit: 20\n pattern: .*',
},
};
const output = createStream(vars, streamTemplate);
expect(output).toBe(`
host: http://127.0.0.1
key.patterns:
- limit: 20
pattern: .*
`);
});
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I could retranslate to a yaml after, but it's going to be stored as a JSON and send to the agent as a JSON, so if we can avoid one other round of conversion to yaml -> to json
@ruflin @nchaulet agreed on iterating. I think the example I posted works and will allow us to keep progressing without the safety/other issues. If we adopt this we really need to test and/or get feedback from security before releasing. We're processing user input into JS. That's a risky operation and something I'd like to run through a system which has guards and tests instead of rolling our own. |
@jfsiii Yes I would like to avoid to write logic that looks like a template engine too, but I think handlebar is very limited here and replacing a yaml value is more complex than just a string interpolation, you need to have the right indentation, (for some value we could consider escaping them too) I now it's frequent to do it this way in Helm charts for example but I think this make template really hard to write.
|
@nchaulet handlebars is intentionally limited but extensible and iiuc still suitable for what we're doing here. If you can supply some more examples/tests of inputs/outputs I am happy to look into it. To @ruflin's request I guess we can merge this as-is, but I would like to open a ticket for security to review before any release. |
@jfsiii My hope is that we have a follow up PR directly after this one fixing it. |
@jfsiii for the security perspective, we are already loading yaml coming from user using |
@ruflin @jfsiii if we stay with a solution that is purely handlebar the template will change from
to
and we need to introduce a custom handlebar helper something like to |
@nchaulet did you see #64459 (comment)? Doesn't that keep the same template and use handlebars w/o a custom helper? |
@jfsiii in you example you need to know the place where the variable is going to use to already have the indentation in the variable |
Couldn't it also be:
And now it is purely up to the package to make sure the variable in |
@nchaulet I took that from the example you posted
If you have other examples, I can adapt. Let's try to get together soon and talk about this. |
@ruflin in you example this mean the variable can be used only one time as the variable will contains the indentation, and we need to add new config to the yaml variable to have the indentation inside |
Not sure I follow the part that it can be used only one time. But yes, as the user will provide some input here, he would also have to use the correct indentation in the editor. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🚀 Thanks for the token changes and restoring the escaping. That addresses my biggest concerns.
Any changes I can think of wouldn't affect the templates or ability to move the input to arbitrary positions in the map. We can do that in a later PR if it comes up.
Thanks again
Co-Authored-By: John Schulz <john.schulz@elastic.co>
Co-Authored-By: John Schulz <john.schulz@elastic.co>
…t-datasource-support-yaml-values
💚 Build SucceededHistory
To update your PR or re-run it, just comment with: |
|
||
interface StreamVars { | ||
[k: string]: string | string[]; | ||
function isValidKey(key: string) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Not a blocker for this PR but future improvement: I think these services belong in /services/datasources.ts
too rather than EPM as EPM services are registry & asset interactions. Might be good to make a separate directory for data source services as that single file is getting rather long.
Trying to resume discussions we had offline: One confusion was coming from the fact that even if we dispaly a YAML to the user, we do not store in saved object or send the agent configuration to the agent as a YAML but as a JSON. This solution allow to have this template working, and we do not need to change existing templates, and because we load yaml using
|
* master: (60 commits) [SIEM] Create template timeline (elastic#63136) load react component lazily in so management section (elastic#64285) Cleanup .eslingignore and add target (elastic#64617) [Ingest] Support yaml variables in datasource (elastic#64459) typescript-ify portions of src/optimize (elastic#64688) [ngSanitize] add explicit dependencies to all uses of `ngSanitize` angular module (elastic#64546) Consolidate downloading plugin bundles to bootstrap script (elastic#64685) [Maps] disable edit layer button when flyout is open for add layer or map settings (elastic#64230) chore(NA): add async import into infra plugin to reduce apm bundle size (elastic#63292) [Maps] fix edit filter (elastic#64586) [SIEM][Detections] Adds large list support using REST endpoints Replace a number of any-ed styled(eui*) with accurate types (elastic#64555) [Endpoint] Recursive resolver children (elastic#61914) [ML] Fix new job wizard with multiple indices (elastic#64567) Use short URLs for legacy plugin deprecation warning (elastic#64540) [Uptime] Update uptime ml job id to limit to 64 char (elastic#64394) [Ingest] Fix GET /enrollment-api-keys/null error (elastic#64595) Consolidate cross-cutting concerns between region & coordinate maps in new maps_legacy plugin (elastic#64123) ES UI new platform cleanup (elastic#64332) [Event Log] use @timestamp field for queries (elastic#64391) ...
* alerting/np-migration: (64 commits) [ML] Changes Machine learning overview UI text (elastic#64625) [Uptime] Migrate client to New Platform (elastic#55086) Slim vis type timeseries (elastic#64631) [Telemetry] Fix inconsistent search behaviour in Advanced Settings (elastic#64510) removed unneeded dep and file [SIEM] Create template timeline (elastic#63136) load react component lazily in so management section (elastic#64285) Cleanup .eslingignore and add target (elastic#64617) [Ingest] Support yaml variables in datasource (elastic#64459) typescript-ify portions of src/optimize (elastic#64688) [ngSanitize] add explicit dependencies to all uses of `ngSanitize` angular module (elastic#64546) Consolidate downloading plugin bundles to bootstrap script (elastic#64685) [Maps] disable edit layer button when flyout is open for add layer or map settings (elastic#64230) chore(NA): add async import into infra plugin to reduce apm bundle size (elastic#63292) [Maps] fix edit filter (elastic#64586) [SIEM][Detections] Adds large list support using REST endpoints Replace a number of any-ed styled(eui*) with accurate types (elastic#64555) [Endpoint] Recursive resolver children (elastic#61914) [ML] Fix new job wizard with multiple indices (elastic#64567) Use short URLs for legacy plugin deprecation warning (elastic#64540) ...
Summary
Resolve #64152
Support yaml value in stream template. (Needed for redis package for example)
This PR allow agent stream to contain yaml variables, and variables to contains
.
.Added more tests to cover these scenarios.
The way yaml variables are processed is done in two step:
Example redis key metrics