Update Web Dependencies (#7011)

* update gulp

* update web dependencies

* update typescript

* update testing-library

* update esbuild

* update react

* [autofix.ci] apply automated fixes

---------

Co-authored-by: autofix-ci[bot] <114827586+autofix-ci[bot]@users.noreply.github.com>
This commit is contained in:
Maximilian Hils 2024-07-13 01:20:15 +02:00 committed by GitHub
parent f77327634c
commit 30ecc2dfbc
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
20 changed files with 4736 additions and 3868 deletions

View File

@ -78,7 +78,7 @@ const copy_src = [
function copy() {
return gulp
.src(copy_src, { base: "src/" })
.src(copy_src, { base: "src/", encoding: false })
.pipe(gulp.dest("../mitmproxy/tools/web/static"));
}

7999
web/package-lock.json generated

File diff suppressed because it is too large Load Diff

View File

@ -17,26 +17,26 @@
"lodash": "^4.17.21",
"prop-types": "^15.7.2",
"qrcode": "^1.5.1",
"react": "^17.0.2",
"react-dom": "^17.0.2",
"react": "^18.3.1",
"react-dom": "^18.3.1",
"react-popper": "^2.2.5",
"react-redux": "^8.1.3",
"react-redux": "^9.1.2",
"stable": "^0.1.8"
},
"devDependencies": {
"@eslint/js": "^9.6.0",
"@testing-library/dom": "^8.1.0",
"@testing-library/jest-dom": "^5.14.1",
"@testing-library/react": "^12.0.0",
"@testing-library/user-event": "^13.2.1",
"@testing-library/dom": "^10.3.1",
"@testing-library/jest-dom": "^6.4.6",
"@testing-library/react": "^16.0.0",
"@testing-library/user-event": "^14.5.2",
"@types/jest": "^29.5.12",
"@types/redux-mock-store": "^1.0.3",
"esbuild": "^0.12.29",
"esbuild": "^0.23.0",
"esbuild-jest": "^0.5.0",
"eslint": "^8.57.0",
"eslint-plugin-react": "^7.34.3",
"globals": "^15.8.0",
"gulp": "^4.0.2",
"gulp": "^5.0.0",
"gulp-clean-css": "^4.3.0",
"gulp-esbuild": "^0.12.0",
"gulp-less": "^5.0.0",
@ -50,10 +50,10 @@
"jest-environment-jsdom": "^29.7.0",
"jest-fetch-mock": "^3.0.3",
"prettier": "3.3.2",
"react-test-renderer": "^17.0.2",
"react-test-renderer": "^18.3.1",
"redux-mock-store": "^1.5.4",
"through2": "^4.0.2",
"typescript": "^4.3.5",
"typescript": "^5.5.3",
"typescript-eslint": "^7.15.0"
}
}

View File

@ -70,29 +70,29 @@ test("CommandBar", async () => {
const input = screen.getByPlaceholderText("Enter command");
userEvent.type(input, "x");
await userEvent.type(input, "x");
expect(screen.getByText("[]")).toBeInTheDocument();
userEvent.type(input, "{backspace}");
await userEvent.type(input, "{backspace}");
userEvent.type(input, "fl");
userEvent.tab();
await userEvent.type(input, "fl");
await userEvent.tab();
expect(input).toHaveValue("flow.decode");
userEvent.tab();
await userEvent.tab();
expect(input).toHaveValue("flow.encode");
fetchMock.mockOnce(JSON.stringify({ value: null }));
userEvent.type(input, "{enter}");
await userEvent.type(input, "{enter}");
await waitFor(() => screen.getByText("Command Result"));
userEvent.type(input, "{arrowdown}");
await userEvent.type(input, "{arrowdown}");
expect(input).toHaveValue("");
userEvent.type(input, "{arrowup}");
await userEvent.type(input, "{arrowup}");
expect(input).toHaveValue("flow.encode");
userEvent.type(input, "{arrowup}");
await userEvent.type(input, "{arrowup}");
expect(input).toHaveValue("foo");
userEvent.type(input, "{arrowdown}");
await userEvent.type(input, "{arrowdown}");
expect(input).toHaveValue("flow.encode");
userEvent.type(input, "{arrowdown}");
await userEvent.type(input, "{arrowdown}");
expect(input).toHaveValue("");
});

View File

@ -1,28 +1,19 @@
import * as React from "react";
import EventLogList from "../../../components/EventLog/EventList";
import TestUtils from "react-dom/test-utils";
import { EventLogItem, LogLevel } from "../../../ducks/eventLog";
import { render } from "../../test-utils";
describe("EventList Component", () => {
const mockEventList: EventLogItem[] = [
{ id: "1", level: LogLevel.info, message: "foo" },
{ id: "2", level: LogLevel.error, message: "bar" },
];
const eventLogList = TestUtils.renderIntoDocument(
<EventLogList events={mockEventList} />,
);
it("should render correctly", () => {
expect(eventLogList.state).toMatchSnapshot();
expect(eventLogList.props).toMatchSnapshot();
});
it("should handle componentWillUnmount", () => {
window.removeEventListener = jest.fn();
eventLogList.componentWillUnmount();
expect(window.removeEventListener).toBeCalledWith(
"resize",
eventLogList.onViewportUpdate,
const { asFragment, unmount } = render(
<EventLogList events={mockEventList} />,
);
expect(asFragment()).toMatchSnapshot();
unmount(); // no errors
});
});

View File

@ -1,30 +1,20 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP
exports[`EventList Component should render correctly 1`] = `
{
"vScroll": {
"end": 1,
"paddingBottom": 18,
"paddingTop": 0,
"start": 0,
},
}
`;
exports[`EventList Component should render correctly 2`] = `
{
"events": [
{
"id": "1",
"level": "info",
"message": "foo",
},
{
"id": "2",
"level": "error",
"message": "bar",
},
],
"rowHeight": 18,
}
<DocumentFragment>
<pre>
<div
style="height: 0px;"
/>
<div>
<i
class="fa fa-fw fa-info"
/>
foo
</div>
<div
style="height: 18px;"
/>
</pre>
</DocumentFragment>
`;

View File

@ -133,9 +133,7 @@ exports[`Flowcolumns Components should render pathColumn 1`] = `
/>
<span
className="marker pull-right"
>
</span>
/>
http://address:22/path
</td>
`;
@ -152,9 +150,7 @@ exports[`Flowcolumns Components should render pathColumn 2`] = `
/>
<span
className="marker pull-right"
>
</span>
/>
http://address:22/path
</td>
`;

View File

@ -1,7 +1,7 @@
import * as React from "react";
import FlowTable, { PureFlowTable } from "../../components/FlowTable";
import { render } from "../test-utils";
import { act, render } from "../test-utils";
import { select } from "../../ducks/flows";
window.addEventListener = jest.fn();
@ -21,7 +21,7 @@ describe("FlowTable Component", () => {
);
expect(asFragment()).toMatchSnapshot();
store.dispatch(select(store.getState().flows.view[3].id));
act(() => store.dispatch(select(store.getState().flows.view[3].id)));
expect(asFragment()).toMatchSnapshot();
});
});

View File

@ -1,9 +1,8 @@
import * as React from "react";
import { render, screen } from "../test-utils";
import { act, fireEvent, render, screen } from "../test-utils";
import FlowView from "../../components/FlowView";
import * as flowActions from "../../ducks/flows";
import fetchMock, { enableFetchMocks } from "jest-fetch-mock";
import { fireEvent } from "@testing-library/react";
enableFetchMocks();
@ -31,7 +30,9 @@ test("FlowView", async () => {
fireEvent.click(screen.getByText("Error"));
expect(asFragment()).toMatchSnapshot();
store.dispatch(flowActions.select(store.getState().flows.list[2].id));
act(() =>
store.dispatch(flowActions.select(store.getState().flows.list[2].id)),
);
fireEvent.click(screen.getByText("Stream Data"));
expect(asFragment()).toMatchSnapshot();
@ -39,7 +40,9 @@ test("FlowView", async () => {
fireEvent.click(screen.getByText("Error"));
expect(asFragment()).toMatchSnapshot();
store.dispatch(flowActions.select(store.getState().flows.list[3].id));
act(() =>
store.dispatch(flowActions.select(store.getState().flows.list[3].id)),
);
fireEvent.click(screen.getByText("Request"));
expect(asFragment()).toMatchSnapshot();
@ -50,7 +53,9 @@ test("FlowView", async () => {
fireEvent.click(screen.getByText("Error"));
expect(asFragment()).toMatchSnapshot();
store.dispatch(flowActions.select(store.getState().flows.list[4].id));
act(() =>
store.dispatch(flowActions.select(store.getState().flows.list[4].id)),
);
fireEvent.click(screen.getByText("Datagrams"));
expect(asFragment()).toMatchSnapshot();

View File

@ -1,21 +1,21 @@
import * as React from "react";
import ConnectionIndicator from "../../../components/Header/ConnectionIndicator";
import * as connectionActions from "../../../ducks/connection";
import { render } from "../../test-utils";
import { act, render } from "../../test-utils";
test("ConnectionIndicator", async () => {
const { asFragment, store } = render(<ConnectionIndicator />);
expect(asFragment()).toMatchSnapshot();
store.dispatch(connectionActions.startFetching());
act(() => store.dispatch(connectionActions.startFetching()));
expect(asFragment()).toMatchSnapshot();
store.dispatch(connectionActions.connectionEstablished());
act(() => store.dispatch(connectionActions.connectionEstablished()));
expect(asFragment()).toMatchSnapshot();
store.dispatch(connectionActions.connectionError("wat"));
act(() => store.dispatch(connectionActions.connectionError("wat")));
expect(asFragment()).toMatchSnapshot();
store.dispatch(connectionActions.setOffline());
act(() => store.dispatch(connectionActions.setOffline()));
expect(asFragment()).toMatchSnapshot();
});

View File

@ -2,7 +2,7 @@ import * as React from "react";
import renderer from "react-test-renderer";
import FilterInput from "../../../components/Header/FilterInput";
import FilterDocs from "../../../components/Header/FilterDocs";
import TestUtil from "react-dom/test-utils";
import { act, render } from "../../test-utils";
describe("FilterInput Component", () => {
it("should render correctly", () => {
@ -19,90 +19,125 @@ describe("FilterInput Component", () => {
expect(tree).toMatchSnapshot();
});
const filterInput = TestUtil.renderIntoDocument(
<FilterInput
type="foo"
color="red"
placeholder="bar"
value=""
onChange={jest.fn()}
/>,
);
function dummyInput(): FilterInput {
const ref = React.createRef<FilterInput>();
render(
<FilterInput
type="foo"
color="red"
placeholder="bar"
value="wat"
onChange={jest.fn()}
ref={ref}
/>,
);
return ref.current!;
}
it("should handle componentWillReceiveProps", () => {
filterInput.UNSAFE_componentWillReceiveProps({ value: "foo" });
expect(filterInput.state.value).toEqual("foo");
const { rerender, getByDisplayValue } = render(
<FilterInput
type="typ"
color="red"
value="foo"
placeholder=""
onChange={() => null}
/>,
);
rerender(
<FilterInput
type="typ"
color="red"
value="bar"
placeholder=""
onChange={() => null}
/>,
);
expect(getByDisplayValue("bar")).toBeInTheDocument();
});
it("should handle isValid", () => {
const filterInput = dummyInput();
// valid
expect(filterInput.isValid("~u foo")).toBeTruthy();
expect(filterInput.isValid("~foo bar")).toBeFalsy();
});
it("should handle getDesc", () => {
filterInput.state.value = "";
const filterInput = dummyInput();
act(() => filterInput.setState({ value: "" }));
expect(filterInput.getDesc().type).toEqual(FilterDocs);
filterInput.state.value = "~u foo";
act(() => filterInput.setState({ value: "~u foo" }));
expect(filterInput.getDesc()).toEqual("url matches /foo/i");
filterInput.state.value = "~foo bar";
act(() => filterInput.setState({ value: "~foo bar" }));
expect(filterInput.getDesc()).toEqual(
'SyntaxError: Expected filter expression but "~" found.',
);
});
it("should handle change", () => {
const filterInput = dummyInput();
const mockEvent = { target: { value: "~a bar" } };
filterInput.onChange(mockEvent);
act(() => filterInput.onChange(mockEvent));
expect(filterInput.state.value).toEqual("~a bar");
expect(filterInput.props.onChange).toBeCalledWith("~a bar");
});
it("should handle focus", () => {
filterInput.onFocus();
const filterInput = dummyInput();
act(() => filterInput.onFocus());
expect(filterInput.state.focus).toBeTruthy();
});
it("should handle blur", () => {
filterInput.onBlur();
const filterInput = dummyInput();
act(() => filterInput.onBlur());
expect(filterInput.state.focus).toBeFalsy();
});
it("should handle mouseEnter", () => {
filterInput.onMouseEnter();
const filterInput = dummyInput();
act(() => filterInput.onMouseEnter());
expect(filterInput.state.mousefocus).toBeTruthy();
});
it("should handle mouseLeave", () => {
filterInput.onMouseLeave();
const filterInput = dummyInput();
act(() => filterInput.onMouseLeave());
expect(filterInput.state.mousefocus).toBeFalsy();
});
const input = filterInput.inputRef.current!;
it("should handle keyDown", () => {
const filterInput = dummyInput();
const input = filterInput.inputRef.current!;
input.blur = jest.fn();
const mockEvent = {
key: "Escape",
stopPropagation: jest.fn(),
};
filterInput.onKeyDown(mockEvent);
act(() => filterInput.onKeyDown(mockEvent));
expect(input.blur).toBeCalled();
expect(filterInput.state.mousefocus).toBeFalsy();
expect(mockEvent.stopPropagation).toBeCalled();
});
it("should handle selectFilter", () => {
const filterInput = dummyInput();
const input = filterInput.inputRef.current!;
input.focus = jest.fn();
filterInput.selectFilter("bar");
act(() => filterInput.selectFilter("bar"));
expect(filterInput.state.value).toEqual("bar");
expect(input.focus).toBeCalled();
});
it("should handle select", () => {
const filterInput = dummyInput();
const input = filterInput.inputRef.current!;
input.select = jest.fn();
filterInput.select();
act(() => filterInput.select());
expect(input.select).toBeCalled();
});
});

View File

@ -1,12 +1,12 @@
import * as React from "react";
import Modal from "../../../components/Modal/Modal";
import { render } from "../../test-utils";
import { render, act } from "../../test-utils";
import { setActiveModal } from "../../../ducks/ui/modal";
test("Modal Component", async () => {
const { asFragment, store } = render(<Modal />);
expect(asFragment()).toMatchSnapshot();
store.dispatch(setActiveModal("OptionModal"));
act(() => store.dispatch(setActiveModal("OptionModal")));
expect(asFragment()).toMatchSnapshot();
});

View File

@ -1,5 +1,5 @@
import * as React from "react";
import { render } from "../../test-utils";
import { act, render } from "../../test-utils";
import { TStore } from "../../ducks/tutils";
import Regular from "../../../components/Modes/Regular";
import * as backendState from "../../../ducks/backendState";
@ -10,19 +10,21 @@ test("RegularSpec", async () => {
expect(asFragment()).toMatchSnapshot();
store.dispatch(
backendState.mockUpdate({
servers: [
{
description: "Regular Mode",
full_spec: "regular",
is_running: false,
last_exception: "port already in use",
listen_addrs: [],
type: "regular",
},
],
}),
act(() =>
store.dispatch(
backendState.mockUpdate({
servers: [
{
description: "Regular Mode",
full_spec: "regular",
is_running: false,
last_exception: "port already in use",
listen_addrs: [],
type: "regular",
},
],
}),
),
);
expect(asFragment()).toMatchSnapshot();

View File

@ -1,172 +1,51 @@
import * as React from "react";
import renderer from "react-test-renderer";
import Splitter from "../../../components/common/Splitter";
import TestUtils from "react-dom/test-utils";
import { act, render } from "../../test-utils";
describe.each([
["", ""],
["x", "X"],
["y", "Y"],
])("Splitter Component", (axisLower, axisUpper) => {
if (axisLower === "") {
it("should render correctly with default (x) axis", () => {
const splitter = renderer.create(<Splitter />);
const tree = splitter.toJSON();
expect(tree).toMatchInlineSnapshot(`
<div
className="splitter splitter-x"
>
<div
onLostPointerCapture={[Function]}
onPointerDown={[Function]}
onPointerMove={[Function]}
/>
</div>
`);
});
return;
}
it("should render correctly with specified axis", () => {
const splitter = renderer.create(<Splitter axis={axisLower} />);
const tree = splitter.toJSON();
expect(tree).toMatchInlineSnapshot(`
<div
className="splitter splitter-${axisLower}"
>
<div
onLostPointerCapture={[Function]}
onPointerDown={[Function]}
onPointerMove={[Function]}
/>
</div>
`);
});
const splitter = TestUtils.renderIntoDocument(
<Splitter axis={axisLower} />,
);
const dom = splitter.node.current;
const previousElementSibling = document.createElement("div");
const nextElementSibling = document.createElement("div");
Object.defineProperties(previousElementSibling, {
offsetWidth: { value: 300 },
offsetHeight: { value: 500 },
});
previousElementSibling.style.flex = "";
nextElementSibling.style.flex = "";
Object.defineProperties(dom, {
previousElementSibling: { value: previousElementSibling },
nextElementSibling: { value: nextElementSibling },
});
dom.firstElementChild.setPointerCapture = jest.fn();
it("should handle pointerdown", () => {
const e = {
pageX: 13,
pageY: 22,
pointerId: -4618,
target: dom.firstElementChild,
};
expect(splitter.state.dragPointer).toEqual(0.1);
splitter.onPointerDown(e);
expect(e.target.setPointerCapture).toBeCalledWith(-4618);
expect(splitter.state.dragPointer).toEqual(-4618);
expect(splitter.state.startPos).toEqual(e[`page${axisUpper}`]);
});
it("should handle pointermove", () => {
const e = {
pageX: 62,
pageY: 21,
pointerId: -4618,
target: dom.firstElementChild,
};
splitter.onPointerMove(e);
expect(dom.style.transform).toEqual(
axisLower === "x"
? `translateX(${62 - 13}px)`
: `translateY(${21 - 22}px)`,
describe.each([["x"], ["y"]])("Splitter Component", (axis) => {
it(`should render correctly (${axis} axis)`, () => {
const ref = React.createRef<Splitter>();
const { asFragment, unmount } = render(
<>
<div></div>
<Splitter axis={axis} ref={ref} />
<div></div>
</>,
);
});
const splitter = ref.current!;
it("should handle lostpointercapture", () => {
const e = {
pageX: 56,
pageY: 82,
pointerId: -4618,
target: dom.firstElementChild,
};
splitter.onLostPointerCapture(e);
expect(splitter.state.dragPointer).toEqual(0.1);
expect(dom.style.transform).toEqual("");
expect(previousElementSibling.style.flex).toEqual(
`0 0 ${axisLower === "x" ? 300 + 56 - 13 : 500 + 82 - 22}px`,
);
expect(nextElementSibling.style.flex).toEqual("1 1 auto");
});
expect(asFragment()).toMatchSnapshot();
it("should not resize previousElementSibling negative", () => {
const e = {
pageX: 56,
pageY: 82,
pointerId: 47,
target: dom.firstElementChild,
};
splitter.onPointerDown(e);
e[`page${axisUpper}`] = -1234;
splitter.onLostPointerCapture(e);
expect(previousElementSibling.style.flex).toEqual("0 0 0px");
});
it("should ignore other pointers", () => {
splitter.onPointerDown({
pageX: 70,
pageY: 60,
pointerId: 47,
target: dom.firstElementChild,
act(() => {
splitter.onPointerDown({
target: {
setPointerCapture: () => 0,
} as unknown,
pageX: 100,
pageY: 200,
pointerId: 42,
} as React.PointerEvent<HTMLDivElement>);
});
splitter.onPointerDown({
pageX: 70,
pageY: 60,
pointerId: 46,
target: dom.firstElementChild,
expect(splitter.state.startPos).toBe(axis === "x" ? 100 : 200);
act(() => {
splitter.onPointerMove({
pageX: 300,
pageY: 300,
pointerId: 42,
} as React.PointerEvent<HTMLDivElement>);
});
expect(splitter.state.dragPointer).toEqual(47);
splitter.onPointerMove({ pageX: 75, pageY: 55, pointerId: 46 });
expect(dom.style.transform).toEqual("");
splitter.onPointerMove({
pageX: 74,
pageY: 54,
pointerId: 47,
target: dom.firstElementChild,
expect(splitter.node.current!.style.transform).toBeTruthy();
act(() => {
splitter.onLostPointerCapture({
pageX: 400,
pageY: 400,
pointerId: 42,
} as React.PointerEvent<HTMLDivElement>);
});
splitter.onLostPointerCapture({ pageX: 76, pageY: 56, pointerId: 46 });
expect(dom.style.transform).toEqual(
axisLower === "x"
? `translateX(${74 - 70}px)`
: `translateY(${54 - 60}px)`,
);
});
expect(asFragment()).toMatchSnapshot();
it("should handle resize", () => {
const x = jest.spyOn(window, "setTimeout");
splitter.onResize();
expect(x).toHaveBeenCalled();
});
it("should handle componentWillUnmount", () => {
splitter.componentWillUnmount();
expect(previousElementSibling.style.flex).toEqual("");
expect(nextElementSibling.style.flex).toEqual("");
expect(splitter.state.applied).toBeTruthy();
});
it("should handle reset", () => {
splitter.reset(false);
expect(splitter.state.applied).toBeFalsy();
expect(splitter.reset(true)).toEqual(undefined);
unmount();
});
});

View File

@ -0,0 +1,59 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP
exports[`Splitter Component should render correctly (x axis) 1`] = `
<DocumentFragment>
<div />
<div
class="splitter splitter-x"
>
<div />
</div>
<div />
</DocumentFragment>
`;
exports[`Splitter Component should render correctly (x axis) 2`] = `
<DocumentFragment>
<div
style="flex: 0 0 300px;"
/>
<div
class="splitter splitter-x"
style=""
>
<div />
</div>
<div
style="flex: 1 1 auto;"
/>
</DocumentFragment>
`;
exports[`Splitter Component should render correctly (y axis) 1`] = `
<DocumentFragment>
<div />
<div
class="splitter splitter-y"
>
<div />
</div>
<div />
</DocumentFragment>
`;
exports[`Splitter Component should render correctly (y axis) 2`] = `
<DocumentFragment>
<div
style="flex: 0 0 200px;"
/>
<div
class="splitter splitter-y"
style=""
>
<div />
</div>
<div
style="flex: 1 1 auto;"
/>
</DocumentFragment>
`;

View File

@ -1,46 +1,56 @@
import * as React from "react";
import * as autoscroll from "../../../components/helpers/AutoScroll";
import TestUtils from "react-dom/test-utils";
import { fireEvent, render } from "../../test-utils";
describe("Autoscroll", () => {
class TComponent extends React.Component {
interface TComponentProps {
height: number;
}
class TComponent extends React.Component<TComponentProps> {
private viewport = React.createRef<HTMLDivElement>();
getSnapshotBeforeUpdate() {
getSnapshotBeforeUpdate(prevProps) {
this.fixupJsDom(prevProps.height);
return autoscroll.isAtBottom(this.viewport);
}
componentDidUpdate(prevProps, prevState, snapshot) {
this.fixupJsDom(this.props.height);
if (snapshot) {
autoscroll.adjustScrollTop(this.viewport);
}
}
fixupJsDom(scrollHeight: number) {
// work around jsdom limitations
Object.defineProperty(this.viewport.current!, "clientHeight", {
value: 100,
writable: true,
});
Object.defineProperty(this.viewport.current!, "scrollHeight", {
value: scrollHeight,
writable: true,
});
}
render() {
return <div ref={this.viewport}>foo</div>;
return <div ref={this.viewport} />;
}
}
it("should update component", () => {
const autoScroll = TestUtils.renderIntoDocument(
<TComponent></TComponent>,
);
const viewport = autoScroll.viewport.current;
const { rerender, container } = render(<TComponent height={120} />);
const viewport = container.firstElementChild!;
expect(autoScroll.getSnapshotBeforeUpdate()).toBe(false);
fireEvent.scroll(viewport, { target: { scrollTop: 10 } });
rerender(<TComponent height={140} />);
viewport.scrollTop = 10;
Object.defineProperty(viewport, "scrollHeight", {
value: 10,
writable: true,
});
expect(autoScroll.getSnapshotBeforeUpdate()).toBe(true);
expect(viewport.scrollTop).toBe(10);
Object.defineProperty(viewport, "scrollHeight", {
value: 42,
writable: true,
});
autoScroll.componentDidUpdate({}, {}, true);
expect(viewport.scrollTop).toBe(42);
fireEvent.scroll(viewport, { target: { scrollTop: 40 } });
rerender(<TComponent height={160} />);
expect(viewport.scrollTop).toBeGreaterThanOrEqual(60);
});
});

View File

@ -1,5 +1,5 @@
import * as React from "react";
import { render } from "react-dom";
import { createRoot } from "react-dom/client";
import { Provider } from "react-redux";
import ProxyApp from "./components/ProxyApp";
@ -24,10 +24,11 @@ window.addEventListener("error", (e: ErrorEvent) => {
});
document.addEventListener("DOMContentLoaded", () => {
render(
const container = document.getElementById("mitmproxy");
const root = createRoot(container!);
root.render(
<Provider store={store}>
<ProxyApp />
</Provider>,
document.getElementById("mitmproxy"),
);
});

View File

@ -8,9 +8,7 @@ type FilterInputProps = {
color: any;
placeholder: string;
value: string;
onChange: (
value,
) => { type: string; filter?: string; highlight?: string } | void;
onChange: (value) => void;
};
type FilterInputState = {
@ -23,7 +21,7 @@ export default class FilterInput extends Component<
FilterInputProps,
FilterInputState
> {
private inputRef = React.createRef<HTMLInputElement>();
inputRef = React.createRef<HTMLInputElement>();
constructor(props, context) {
super(props, context);

View File

@ -25,23 +25,24 @@ export default class Splitter extends Component<SplitterProps, SplitterState> {
this.onPointerMove = this.onPointerMove.bind(this);
}
onPointerDown(e) {
onPointerDown(e: React.PointerEvent<HTMLDivElement>) {
if (this.state.dragPointer !== 0.1) {
return;
}
e.target.setPointerCapture(e.pointerId);
(e.target as HTMLDivElement).setPointerCapture(e.pointerId);
this.setState({
startPos: this.props.axis === "x" ? e.pageX : e.pageY,
dragPointer: e.pointerId,
});
}
onLostPointerCapture(e) {
onLostPointerCapture(e: React.PointerEvent<HTMLDivElement>) {
if (this.state.dragPointer !== e.pointerId) {
return;
}
const node = e.target.parentNode;
const prev = node.previousElementSibling;
const node = this.node.current!;
const prev = node.previousElementSibling! as HTMLElement;
const next = node.nextElementSibling! as HTMLElement;
node.style.transform = "";
prev.style.flex = `0 0 ${Math.max(
@ -50,17 +51,17 @@ export default class Splitter extends Component<SplitterProps, SplitterState> {
? prev.offsetWidth + e.pageX
: prev.offsetHeight + e.pageY) - this.state.startPos,
)}px`;
node.nextElementSibling.style.flex = "1 1 auto";
next.style.flex = "1 1 auto";
this.setState({ applied: true, dragPointer: 0.1 });
this.onResize();
}
onPointerMove(e) {
onPointerMove(e: React.PointerEvent<HTMLDivElement>) {
if (this.state.dragPointer !== e.pointerId) {
return;
}
e.target.parentNode.style.transform =
this.node.current!.style.transform =
this.props.axis === "x"
? `translateX(${e.pageX - this.state.startPos}px)`
: `translateY(${e.pageY - this.state.startPos}px)`;

View File

@ -31,7 +31,7 @@ export default class ValueEditor extends Component<ValueEditorProps> {
ref={this.input}
tabIndex={0}
className={className}
// @ts-expect-error spans can have placeholders
// @ts-expect-error placeholder works here.
placeholder={this.props.placeholder}
onFocus={this.onFocus}
onBlur={this.onBlur}