Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/typescript/9.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Reactjs 如何测试异步void函数中的潜在空值,而不在TypeScript中使用@ts ignore_Reactjs_Typescript_Jestjs_React Testing Library - Fatal编程技术网

Reactjs 如何测试异步void函数中的潜在空值,而不在TypeScript中使用@ts ignore

Reactjs 如何测试异步void函数中的潜在空值,而不在TypeScript中使用@ts ignore,reactjs,typescript,jestjs,react-testing-library,Reactjs,Typescript,Jestjs,React Testing Library,这可能更像是一个JavaScript/TypeScript问题,而不是关于反应/测试 但我会给出完整的故事。所以我有一个带有基本路由功能的测试应用程序,并通过测试来验证路由是否有效 App.tsx App.test.tsx 一切都很顺利。然后我添加了一个useEffect钩子来初始化我的国际化库: useEffect(() => { async function initMessages() { await intl.init({ cur

这可能更像是一个JavaScript/TypeScript问题,而不是关于反应/测试

但我会给出完整的故事。所以我有一个带有基本路由功能的测试应用程序,并通过测试来验证路由是否有效

App.tsx

App.test.tsx

一切都很顺利。然后我添加了一个useEffect钩子来初始化我的国际化库:

useEffect(() => {
    async function initMessages() {
        await intl.init({
            currentLocale: "en-US",
            locales
        });
    }

    initMessages().then(() => setLoading(false));
}, [loading]);
这将加载我所有的英文文本资源。这工作正常,但由于以下错误消息而中断了所有测试:
警告:测试中的应用程序更新未包装在act(…)中。

经过一些阅读,我通过添加此“act”函数修复了测试,下面是一个示例:

import React from 'react';
import {act, render, fireEvent, waitForElement} from '@testing-library/react';
import "@testing-library/jest-dom/extend-expect";
import App from './App';

test('Verify home page header', async() => {
    let app: HTMLElement;
    await act(async () => {
        const {container} = render(<App/>);
        app = container;
    });
    // @ts-ignore
    if (app) {
        const pageHeaderContent = app.querySelector("#pageHeader")?.firstChild?.textContent;
        expect(pageHeaderContent).toMatch('Home page');
    } else {
        fail("The app should have been initialized.");
    }
});
从“React”导入React;
从'@testing library/react'导入{act,render,firevent,waitForElement};
导入“@测试库/jest dom/extend expect”;
从“./App”导入应用程序;
测试('Verify home page header',async()=>{
let-app:HTMLElement;
等待动作(异步()=>{
常量{container}=render(

指向上次提交的链接:

Typescript抱怨当您在if语句中访问应用程序变量时,该变量尚未初始化。您只需将
null
赋值给它即可解决此问题

let app: HTMLElement = null;
如果使用严格的null检查,则必须允许类型为null:

let app: HTMLElement | null = null;

经过深思熟虑,这就是我的结果

test('Verify home page header', async() => {
    let app: HTMLElement | undefined = undefined;
    await act(async () => {
        const {container} = render(<App/>);
        app = container;
    });
    let appAsHtmlElement = (app as unknown as HTMLElement);
    const pageHeaderContent = appAsHtmlElement.querySelector("#pageHeader")?.firstChild?.textContent;
    expect(pageHeaderContent).toMatch('Home page');
});
test('Verify home page header',async()=>{
let app:HTMLElement |未定义=未定义;
等待动作(异步()=>{
const{container}=render();
app=容器;
});
让appAsHtmlElement=(应用程序与HTMLElement一样未知);
const pageHeaderContent=appashtmlement.querySelector(“#pageHeader”)?.firstChild?.textContent;
expect(pageHeaderContent.toMatch('homepage');
});

更好的建议(如果有某种方式不必使用“act”功能)仍然受欢迎。

它可以是未定义的,但您声明它仅为HTMLElement?TypeScript无法判断
act
是否将调用回调,并且无法保证将定义
app
。您可以尝试在另一个承诺中包装
act
,该承诺将在回调内部通过
app
解决。您可能还需要等待
act
解决后才能继续。正如@alexey所说的。您可以将测试代码移到回调中。这会让TS闭嘴,因为这将保证应用程序被定义。@colefner他尝试过这样做,但这违背了
act
的目的,即允许React完成所有li在使用
expect
进行断言之前,fecycle钩子。啊,是的,我错过了那一部分。这很好,@AlexeyLebedev