Интеграционное тестирование в контексте Hyperapp направлено на проверку взаимодействия компонентов приложения и корректности работы их совместной логики. В отличие от модульного тестирования, где проверяется отдельная функция или компонент, интеграционные тесты оценивают сценарии, охватывающие несколько элементов приложения и их связь с состоянием, эффектами и действиями.
Hyperapp строится вокруг централизованного состояния
(state) и действий (actions).
Все изменения UI проходят через эти структуры, что упрощает создание
интеграционных тестов. Основные элементы, на которые ориентируются при
интеграционном тестировании:
Такой подход позволяет тестировать сценарии без необходимости монтировать реальный DOM, используя виртуальный DOM Hyperapp.
Для интеграционных тестов Hyperapp используют следующие библиотеки:
Комбинация этих инструментов позволяет создавать тесты, охватывающие как внутреннюю логику приложения, так и отображение UI.
import { app } from "hyperapp";
const initState = {
counter: 0
};
const increment = state => ({ counter: state.counter + 1 });
const view = state => (
<div>
<p id="count">{state.counter}</p>
<button oncl ick={increment}>+</button>
</div>
);
const mainApp = app({ init: initState, view, node: document.body, actions: { increment } });
test("increment button increases counter", () => {
const button = document.querySelector("button");
const countDisplay = document.getElementById("count");
button.click();
expect(countDisplay.textContent).toBe("1");
});
Эффекты в Hyperapp — это асинхронные операции, такие как API-запросы. Их интеграционные тесты включают мокирование:
const fetchData = () => async (state, actions) => {
const response = await fetch("/data");
const data = await response.json();
return { ...state, data };
};
// Тест с мокированием fetch
global.fetch = jest.fn(() =>
Promise.resolve({
json: () => Promise.resolve({ items: [1, 2, 3] })
})
);
test("fetchData effect updates state", async () => {
let state = { data: [] };
const actions = { fetchData };
state = await actions.fetchData()(state, actions);
expect(state.data.items.length).toBe(3);
});
Интеграционное тестирование в Hyperapp часто требует проверки цепочек действий:
Пример цепочки:
const addItem = (state, actions, item) => ({ items: [...state.items, item] });
const view = state => (
<div>
<ul>
{state.items.map(i => <li>{i}</li>)}
</ul>
<button oncl ick={() => addItem(state, null, "Task 1")}>Add</button>
</div>
);
Тест проверяет добавление элемента в список и рендер нового
<li>:
test("adding item updates list", () => {
const button = document.querySelector("button");
button.click();
const listItems = document.querySelectorAll("li");
expect(listItems.length).toBe(1);
expect(listItems[0].textContent).toBe("Task 1");
});
Интеграционное тестирование в Hyperapp становится мощным инструментом для проверки сложных взаимодействий компонентов, асинхронных эффектов и корректного рендера пользовательского интерфейса. Оно обеспечивает уверенность в том, что приложение работает целостно, а не только по отдельным блокам кода.