I have the following yaml
file:
trainingPhrases:
- help me
- what to do
- how to play
- help
I readi it from disk using readFile
from node and parse it using load
from js-yaml
:
import { load } from "js-yaml";
import { readFile } from "fs/promises";
const phrases = load(await readFile(filepath, "utf8")).trainingPhrases as string[];
I get the following eslint
warning:
ESLint: Unsafe member access .trainingPhrases on an any value.(@typescript-eslint/no-unsafe-member-access)
Instead of suppressing the warning, I would like to map it into a concrete type for the YAML file (as it happens in axios for example: axios.get<MyResponseInterface>(...)
- performs a GET
and MyResponseInterface
defines the structure of the HTTP response).
Is there a dedicated library for that?
I have the following yaml
file:
trainingPhrases:
- help me
- what to do
- how to play
- help
I readi it from disk using readFile
from node and parse it using load
from js-yaml
:
import { load } from "js-yaml";
import { readFile } from "fs/promises";
const phrases = load(await readFile(filepath, "utf8")).trainingPhrases as string[];
I get the following eslint
warning:
ESLint: Unsafe member access .trainingPhrases on an any value.(@typescript-eslint/no-unsafe-member-access)
Instead of suppressing the warning, I would like to map it into a concrete type for the YAML file (as it happens in axios for example: axios.get<MyResponseInterface>(...)
- performs a GET
and MyResponseInterface
defines the structure of the HTTP response).
Is there a dedicated library for that?
Share Improve this question edited Jun 28, 2021 at 9:52 pixel asked Jun 23, 2021 at 14:03 pixelpixel 26.5k39 gold badges167 silver badges283 bronze badges 4- What do you mean by "concrete type for the YAML file (as it happens in axios for example)."? – Yoshi Commented Jun 28, 2021 at 8:19
-
@Yoshi that I define structure as interfaces in TS - in axios it looks like:
axios.get<MyResponseInterface>(...)
whereMyResponseInterface
is interface defined by me and it reflects structure of the response – pixel Commented Jun 28, 2021 at 9:06 -
I'm not used to the node functions, so I can't say if say accept a type parameter. But you could simply declare phrases to be of the correct type. Have you tried that? E.g.
const phrases: YourType = ...
. (At least I'm assuming it's node, otherwise, you'd need to explain whereload
andreadFile
are from). – Yoshi Commented Jun 28, 2021 at 9:07 - @yoshi I added imports – pixel Commented Jun 28, 2021 at 9:37
1 Answer
Reset to default 11From what I can see when using @types/js-yaml
is that load
is not generic, meaning it does not accept a type parameter.
So the only way to get a type here is to use an assertion, for example:
const yaml = load(await readFile(filepath, "utf8")) as YourType;
const phrases = yaml.trainingPhrases;
Or in short:
const phrases = (load(await readFile(filepath, "utf8")) as YourType).trainingPhrases;
If you absolutely want a generic function, you can easily wrap the original, like:
import {load as original} from 'js-yaml';
export const load = <T = ReturnType<typeof original>>(...args: Parameters<typeof original>): T => load(...args);
And then you can use it as:
const phrases = load<YourType>('....').trainingPhrases;