Browse Source

[CHORE] Specs and Test env improvements (#198)

* [CHORE] Update dependencies

* [CHORE] Configure Test env. Add enzyme-to-json snapshot serializer

* [CHORE] Specs for Topic Messages component

* [CHORE] Mock Date-fns

* [CHORE] Refactor keys

* Run related tests on commit

* [CHORE] Stub date

Co-authored-by: Azat Mutigullin <mehemaul@gmail.com>
Oleg Shur 4 years ago
parent
commit
6fb1d12355

+ 6 - 2
kafka-ui-react-app/.eslintrc.json

@@ -15,7 +15,10 @@
     },
     "ecmaVersion": 2018,
     "sourceType": "module",
-    "project": ["./tsconfig.json", "./src/setupTests.ts"]
+    "project": [
+        "./tsconfig.json",
+         "./src/setupTests.ts"
+      ]
   },
   "plugins": ["@typescript-eslint", "prettier"],
   "extends": [
@@ -30,7 +33,8 @@
     "@typescript-eslint/explicit-module-boundary-types": "off",
     "jsx-a11y/label-has-associated-control": "off",
     "import/prefer-default-export": "off",
-    "@typescript-eslint/no-explicit-any": "error"
+    "@typescript-eslint/no-explicit-any": "error",
+    "import/no-extraneous-dependencies": ["error", { "devDependencies": true }]
   },
   "overrides": [
     {

+ 0 - 8
kafka-ui-react-app/jest.config.js

@@ -1,8 +0,0 @@
-module.exports = {
-  roots: ['<rootDir>/src'],
-  transform: {
-    '^.+\\.tsx?$': 'ts-jest',
-  },
-  testRegex: '(/__tests__/.*|(\\.|/)(test|spec))\\.tsx?$',
-  moduleFileExtensions: ['ts', 'tsx', 'js', 'jsx', 'json', 'node'],
-};

File diff suppressed because it is too large
+ 339 - 351
kafka-ui-react-app/package-lock.json


+ 12 - 5
kafka-ui-react-app/package.json

@@ -3,8 +3,6 @@
   "version": "0.1.0",
   "private": true,
   "dependencies": {
-    "@types/react-datepicker": "^3.1.1",
-    "@types/uuid": "^8.3.0",
     "bulma": "^0.8.2",
     "bulma-switch": "^2.0.0",
     "classnames": "^2.2.6",
@@ -33,7 +31,7 @@
     "*.{js,ts,jsx,tsx}": [
       "eslint -c .eslintrc.json --fix",
       "git add",
-      "jest --bail --findRelatedTests"
+      "npm test -- --bail --findRelatedTests --watchAll=false"
     ]
   },
   "scripts": {
@@ -42,6 +40,7 @@
     "lint": "eslint --ext .tsx,.ts src/",
     "lint:fix": "eslint --ext .tsx,.ts src/ --fix",
     "test": "react-scripts test",
+    "test:CI": "CI=true npm test --watchAll=false",
     "eject": "react-scripts eject",
     "tsc": "tsc"
   },
@@ -66,6 +65,7 @@
     ]
   },
   "devDependencies": {
+    "@jest/types": "^26.6.2",
     "@testing-library/jest-dom": "^5.11.9",
     "@testing-library/react": "^9.5.0",
     "@testing-library/user-event": "^7.1.2",
@@ -75,16 +75,19 @@
     "@types/lodash": "^4.14.165",
     "@types/node": "^12.19.8",
     "@types/react": "^17.0.0",
+    "@types/react-datepicker": "^3.1.1",
     "@types/react-dom": "^17.0.0",
     "@types/react-redux": "^7.1.11",
     "@types/react-router-dom": "^5.1.6",
     "@types/redux": "^3.6.0",
     "@types/redux-thunk": "^2.1.0",
+    "@types/uuid": "^8.3.0",
     "@typescript-eslint/eslint-plugin": "^4.9.0",
     "@typescript-eslint/parser": "^4.9.0",
     "@wojtekmaj/enzyme-adapter-react-17": "^0.4.1",
     "dotenv": "^8.2.0",
     "enzyme": "^3.11.0",
+    "enzyme-to-json": "^3.6.1",
     "eslint": "^7.14.0",
     "eslint-config-airbnb": "^18.2.1",
     "eslint-config-airbnb-typescript": "^12.0.0",
@@ -99,12 +102,16 @@
     "lint-staged": "^10.5.2",
     "node-sass": "^4.14.1",
     "prettier": "^2.2.1",
-    "react-scripts": "4.0.1",
+    "react-scripts": "4.0.2",
     "ts-jest": "^26.4.4",
+    "ts-node": "^9.1.1",
     "typescript": "~4.1.2"
   },
   "engines": {
     "node": ">=14.15.4"
   },
-  "proxy": "http://localhost:8080"
+  "proxy": "http://localhost:8080",
+  "jest": {
+    "snapshotSerializers": ["enzyme-to-json/serializer"]
+  }
 }

+ 5 - 7
kafka-ui-react-app/src/components/Topics/Details/Messages/MessageItem.tsx

@@ -3,11 +3,11 @@ import { format } from 'date-fns';
 import JSONTree from 'react-json-tree';
 import { TopicMessage } from 'generated-sources';
 
-interface MessageItemProp {
+export interface MessageItemProp {
   partition: TopicMessage['partition'];
   offset: TopicMessage['offset'];
   timestamp: TopicMessage['timestamp'];
-  content: TopicMessage['content'];
+  content?: TopicMessage['content'];
 }
 
 const MessageItem: React.FC<MessageItemProp> = ({
@@ -16,13 +16,11 @@ const MessageItem: React.FC<MessageItemProp> = ({
   timestamp,
   content,
 }) => (
-  <tr key="{timestamp}">
-    <td style={{ width: 200 }}>
-      {timestamp ? format(timestamp, 'yyyy-MM-dd HH:mm:ss') : null}
-    </td>
+  <tr>
+    <td style={{ width: 200 }}>{format(timestamp, 'yyyy-MM-dd HH:mm:ss')}</td>
     <td style={{ width: 150 }}>{offset}</td>
     <td style={{ width: 100 }}>{partition}</td>
-    <td key="{content}" style={{ wordBreak: 'break-word' }}>
+    <td style={{ wordBreak: 'break-word' }}>
       {content && (
         <JSONTree
           data={content}

+ 11 - 13
kafka-ui-react-app/src/components/Topics/Details/Messages/Messages.tsx

@@ -1,4 +1,9 @@
+import 'react-datepicker/dist/react-datepicker.css';
 import React, { useCallback, useEffect, useRef } from 'react';
+import { groupBy, map, concat, maxBy } from 'lodash';
+import MultiSelect from 'react-multi-select-component';
+import { Option } from 'react-multi-select-component/dist/lib/interfaces';
+import { useDebouncedCallback } from 'use-debounce';
 import {
   ClusterName,
   TopicMessageQueryParams,
@@ -7,13 +12,6 @@ import {
 import { TopicMessage, Partition, SeekType } from 'generated-sources';
 import PageLoader from 'components/common/PageLoader/PageLoader';
 import DatePicker from 'react-datepicker';
-import 'react-datepicker/dist/react-datepicker.css';
-
-import MultiSelect from 'react-multi-select-component';
-
-import * as _ from 'lodash';
-import { useDebouncedCallback } from 'use-debounce';
-import { Option } from 'react-multi-select-component/dist/lib/interfaces';
 import MessagesTable from './MessagesTable';
 
 export interface Props {
@@ -81,17 +79,17 @@ const Messages: React.FC<Props> = ({
       offset: 0,
       partition: p.partition,
     }));
-    const messageUniqs: FilterProps[] = _.map(
-      _.groupBy(messages, 'partition'),
-      (v) => _.maxBy(v, 'offset')
+    const messageUniqs: FilterProps[] = map(
+      groupBy(messages, 'partition'),
+      (v) => maxBy(v, 'offset')
     ).map((v) => ({
       offset: v ? v.offset : 0,
       partition: v ? v.partition : 0,
     }));
 
-    return _.map(
-      _.groupBy(_.concat(partitionUniqs, messageUniqs), 'partition'),
-      (v) => _.maxBy(v, 'offset') as FilterProps
+    return map(
+      groupBy(concat(partitionUniqs, messageUniqs), 'partition'),
+      (v) => maxBy(v, 'offset') as FilterProps
     );
   }, [messages, partitions]);
 

+ 2 - 11
kafka-ui-react-app/src/components/Topics/Details/Messages/MessagesContainer.ts

@@ -1,10 +1,5 @@
 import { connect } from 'react-redux';
-import {
-  ClusterName,
-  RootState,
-  TopicMessageQueryParams,
-  TopicName,
-} from 'redux/interfaces';
+import { ClusterName, RootState, TopicName } from 'redux/interfaces';
 import { RouteComponentProps, withRouter } from 'react-router-dom';
 import { fetchTopicMessages } from 'redux/actions';
 import {
@@ -38,11 +33,7 @@ const mapStateToProps = (
 });
 
 const mapDispatchToProps = {
-  fetchTopicMessages: (
-    clusterName: ClusterName,
-    topicName: TopicName,
-    queryParams: Partial<TopicMessageQueryParams>
-  ) => fetchTopicMessages(clusterName, topicName, queryParams),
+  fetchTopicMessages,
 };
 
 export default withRouter(

+ 4 - 4
kafka-ui-react-app/src/components/Topics/Details/Messages/MessagesTable.tsx

@@ -3,7 +3,7 @@ import { TopicMessage } from 'generated-sources';
 import CustomParamButton from 'components/Topics/shared/Form/CustomParams/CustomParamButton';
 import MessageItem from './MessageItem';
 
-interface MessagesTableProp {
+export interface MessagesTableProp {
   messages: TopicMessage[];
   onNext(event: React.MouseEvent<HTMLButtonElement>): void;
 }
@@ -14,7 +14,7 @@ const MessagesTable: React.FC<MessagesTableProp> = ({ messages, onNext }) => {
   }
 
   return (
-    <div>
+    <>
       <table className="table is-striped is-fullwidth">
         <thead>
           <tr>
@@ -28,7 +28,7 @@ const MessagesTable: React.FC<MessagesTableProp> = ({ messages, onNext }) => {
           {messages.map(
             ({ partition, offset, timestamp, content }: TopicMessage) => (
               <MessageItem
-                key={timestamp.toString()}
+                key={`message-${timestamp.getTime()}`}
                 partition={partition}
                 offset={offset}
                 timestamp={timestamp}
@@ -48,7 +48,7 @@ const MessagesTable: React.FC<MessagesTableProp> = ({ messages, onNext }) => {
           />
         </div>
       </div>
-    </div>
+    </>
   );
 };
 

+ 38 - 0
kafka-ui-react-app/src/components/Topics/Details/Messages/__test__/MessageItem.spec.tsx

@@ -0,0 +1,38 @@
+import React from 'react';
+import { shallow } from 'enzyme';
+import MessageItem from 'components/Topics/Details/Messages/MessageItem';
+import { messages } from './fixtures';
+
+jest.mock('date-fns', () => ({
+  format: () => `mocked date`,
+}));
+
+describe('MessageItem', () => {
+  describe('when content is defined', () => {
+    it('renders table row with JSONTree', () => {
+      const wrapper = shallow(<MessageItem {...messages[0]} />);
+
+      expect(wrapper.find('tr').length).toEqual(1);
+      expect(wrapper.find('td').length).toEqual(4);
+      expect(wrapper.find('JSONTree').length).toEqual(1);
+    });
+
+    it('matches snapshot', () => {
+      expect(shallow(<MessageItem {...messages[0]} />)).toMatchSnapshot();
+    });
+  });
+
+  describe('when content is undefined', () => {
+    it('renders table row without JSONTree', () => {
+      const wrapper = shallow(<MessageItem {...messages[1]} />);
+
+      expect(wrapper.find('tr').length).toEqual(1);
+      expect(wrapper.find('td').length).toEqual(4);
+      expect(wrapper.find('JSONTree').length).toEqual(0);
+    });
+
+    it('matches snapshot', () => {
+      expect(shallow(<MessageItem {...messages[1]} />)).toMatchSnapshot();
+    });
+  });
+});

+ 178 - 0
kafka-ui-react-app/src/components/Topics/Details/Messages/__test__/Messages.spec.tsx

@@ -0,0 +1,178 @@
+import React from 'react';
+import { Provider } from 'react-redux';
+import { mount, shallow } from 'enzyme';
+import * as useDebounce from 'use-debounce';
+import DatePicker from 'react-datepicker';
+import Messages, { Props } from 'components/Topics/Details/Messages/Messages';
+import MessagesContainer from 'components/Topics/Details/Messages/MessagesContainer';
+import PageLoader from 'components/common/PageLoader/PageLoader';
+import configureStore from 'redux/store/configureStore';
+
+describe('Messages', () => {
+  describe('Container', () => {
+    const store = configureStore();
+
+    it('renders view', () => {
+      const component = shallow(
+        <Provider store={store}>
+          <MessagesContainer />
+        </Provider>
+      );
+
+      expect(component.exists()).toBeTruthy();
+    });
+  });
+
+  describe('View', () => {
+    beforeEach(() => {
+      jest.restoreAllMocks();
+    });
+
+    const setupWrapper = (props: Partial<Props> = {}) => (
+      <Messages
+        clusterName="Test cluster"
+        topicName="Cluster topic"
+        isFetched
+        fetchTopicMessages={jest.fn()}
+        messages={[]}
+        partitions={[]}
+        {...props}
+      />
+    );
+
+    describe('Initial state', () => {
+      it('renders PageLoader', () => {
+        expect(
+          shallow(setupWrapper({ isFetched: false })).exists(PageLoader)
+        ).toBeTruthy();
+      });
+    });
+
+    describe('Table', () => {
+      describe('With messages', () => {
+        const messagesWrapper = mount(
+          setupWrapper({
+            messages: [
+              {
+                partition: 1,
+                offset: 2,
+                timestamp: new Date('05-05-1994'),
+                content: [1, 2, 3],
+              },
+            ],
+          })
+        );
+        it('renders table', () => {
+          expect(
+            messagesWrapper.exists(
+              '[className="table is-striped is-fullwidth"]'
+            )
+          ).toBeTruthy();
+        });
+        it('renders JSONTree', () => {
+          expect(messagesWrapper.find('JSONTree').length).toEqual(1);
+        });
+        it('parses message content correctly', () => {
+          const messages = [
+            {
+              partition: 1,
+              offset: 2,
+              timestamp: new Date('05-05-1994'),
+              content: [1, 2, 3],
+            },
+          ];
+          const content = JSON.stringify(messages[0].content);
+          expect(JSON.parse(content)).toEqual(messages[0].content);
+        });
+      });
+      describe('Without messages', () => {
+        it('renders string', () => {
+          const wrapper = mount(setupWrapper());
+          expect(wrapper.text()).toContain('No messages at selected topic');
+        });
+      });
+    });
+
+    describe('Offset field', () => {
+      describe('Seek Type dependency', () => {
+        const wrapper = mount(setupWrapper());
+
+        it('renders DatePicker', () => {
+          wrapper
+            .find('[id="selectSeekType"]')
+            .simulate('change', { target: { value: 'TIMESTAMP' } });
+
+          expect(
+            wrapper.find('[id="selectSeekType"]').first().props().value
+          ).toEqual('TIMESTAMP');
+
+          expect(wrapper.exists(DatePicker)).toBeTruthy();
+        });
+      });
+
+      describe('With defined offset value', () => {
+        const wrapper = shallow(setupWrapper());
+
+        it('shows offset value in input', () => {
+          const offset = '10';
+
+          wrapper
+            .find('#searchOffset')
+            .simulate('change', { target: { value: offset } });
+
+          expect(wrapper.find('#searchOffset').first().props().value).toEqual(
+            offset
+          );
+        });
+      });
+      describe('With invalid offset value', () => {
+        const wrapper = shallow(setupWrapper());
+
+        it('shows 0 in input', () => {
+          wrapper
+            .find('#searchOffset')
+            .simulate('change', { target: { value: null } });
+
+          expect(wrapper.find('#searchOffset').first().props().value).toBe('0');
+        });
+      });
+    });
+
+    describe('Search field', () => {
+      it('renders input correctly', () => {
+        const query = 20;
+        const mockedUseDebouncedCallback = jest.fn();
+        jest
+          .spyOn(useDebounce, 'useDebouncedCallback')
+          .mockImplementationOnce(() => [
+            mockedUseDebouncedCallback,
+            jest.fn(),
+            jest.fn(),
+          ]);
+
+        const wrapper = shallow(setupWrapper());
+
+        wrapper
+          .find('#searchText')
+          .simulate('change', { target: { value: query } });
+
+        expect(wrapper.find('#searchText').first().props().value).toEqual(
+          query
+        );
+        expect(mockedUseDebouncedCallback).toHaveBeenCalledWith({ q: query });
+      });
+    });
+
+    describe('Submit button', () => {
+      it('fetches topic messages', () => {
+        const mockedfetchTopicMessages = jest.fn();
+        const wrapper = mount(
+          setupWrapper({ fetchTopicMessages: mockedfetchTopicMessages })
+        );
+
+        wrapper.find('[type="submit"]').simulate('click');
+        expect(mockedfetchTopicMessages).toHaveBeenCalled();
+      });
+    });
+  });
+});

+ 49 - 0
kafka-ui-react-app/src/components/Topics/Details/Messages/__test__/MessagesTable.spec.tsx

@@ -0,0 +1,49 @@
+import React from 'react';
+import { shallow } from 'enzyme';
+import MessagesTable, {
+  MessagesTableProp,
+} from 'components/Topics/Details/Messages/MessagesTable';
+import { messages } from './fixtures';
+
+jest.mock('date-fns', () => ({
+  format: () => `mocked date`,
+}));
+
+describe('MessagesTable', () => {
+  const setupWrapper = (props: Partial<MessagesTableProp> = {}) => (
+    <MessagesTable messages={[]} onNext={jest.fn()} {...props} />
+  );
+
+  describe('when topic is empty', () => {
+    it('renders table row with JSONTree', () => {
+      const wrapper = shallow(setupWrapper());
+      expect(wrapper.exists('table')).toBeFalsy();
+      expect(wrapper.exists('CustomParamButton')).toBeFalsy();
+      expect(wrapper.text()).toEqual('No messages at selected topic');
+    });
+
+    it('matches snapshot', () => {
+      expect(shallow(setupWrapper())).toMatchSnapshot();
+    });
+  });
+
+  describe('when topic contains messages', () => {
+    const onNext = jest.fn();
+    const wrapper = shallow(setupWrapper({ messages, onNext }));
+
+    it('renders table row without JSONTree', () => {
+      expect(wrapper.exists('table')).toBeTruthy();
+      expect(wrapper.exists('CustomParamButton')).toBeTruthy();
+      expect(wrapper.find('MessageItem').length).toEqual(2);
+    });
+
+    it('handles CustomParamButton click', () => {
+      wrapper.find('CustomParamButton').simulate('click');
+      expect(onNext).toHaveBeenCalled();
+    });
+
+    it('matches snapshot', () => {
+      expect(shallow(setupWrapper({ messages, onNext }))).toMatchSnapshot();
+    });
+  });
+});

+ 110 - 0
kafka-ui-react-app/src/components/Topics/Details/Messages/__test__/__snapshots__/MessageItem.spec.tsx.snap

@@ -0,0 +1,110 @@
+// Jest Snapshot v1, https://goo.gl/fbAQLP
+
+exports[`MessageItem when content is defined matches snapshot 1`] = `
+<tr>
+  <td
+    style={
+      Object {
+        "width": 200,
+      }
+    }
+  >
+    mocked date
+  </td>
+  <td
+    style={
+      Object {
+        "width": 150,
+      }
+    }
+  >
+    2
+  </td>
+  <td
+    style={
+      Object {
+        "width": 100,
+      }
+    }
+  >
+    1
+  </td>
+  <td
+    style={
+      Object {
+        "wordBreak": "break-word",
+      }
+    }
+  >
+    <JSONTree
+      collectionLimit={50}
+      data={
+        Object {
+          "foo": "bar",
+          "key": "val",
+        }
+      }
+      getItemString={[Function]}
+      hideRoot={true}
+      invertTheme={false}
+      isCustomNode={[Function]}
+      keyPath={
+        Array [
+          "root",
+        ]
+      }
+      labelRenderer={[Function]}
+      postprocessValue={[Function]}
+      shouldExpandNode={[Function]}
+      theme={
+        Object {
+          "base0B": "#363636",
+          "base0D": "#3273dc",
+          "tree": [Function],
+          "value": [Function],
+        }
+      }
+      valueRenderer={[Function]}
+    />
+  </td>
+</tr>
+`;
+
+exports[`MessageItem when content is undefined matches snapshot 1`] = `
+<tr>
+  <td
+    style={
+      Object {
+        "width": 200,
+      }
+    }
+  >
+    mocked date
+  </td>
+  <td
+    style={
+      Object {
+        "width": 150,
+      }
+    }
+  >
+    20
+  </td>
+  <td
+    style={
+      Object {
+        "width": 100,
+      }
+    }
+  >
+    2
+  </td>
+  <td
+    style={
+      Object {
+        "wordBreak": "break-word",
+      }
+    }
+  />
+</tr>
+`;

+ 66 - 0
kafka-ui-react-app/src/components/Topics/Details/Messages/__test__/__snapshots__/MessagesTable.spec.tsx.snap

@@ -0,0 +1,66 @@
+// Jest Snapshot v1, https://goo.gl/fbAQLP
+
+exports[`MessagesTable when topic contains messages matches snapshot 1`] = `
+<Fragment>
+  <table
+    className="table is-striped is-fullwidth"
+  >
+    <thead>
+      <tr>
+        <th>
+          Timestamp
+        </th>
+        <th>
+          Offset
+        </th>
+        <th>
+          Partition
+        </th>
+        <th>
+          Content
+        </th>
+      </tr>
+    </thead>
+    <tbody>
+      <MessageItem
+        content={
+          Object {
+            "foo": "bar",
+            "key": "val",
+          }
+        }
+        key="message-802310400000"
+        offset={2}
+        partition={1}
+        timestamp={1995-06-05T00:00:00.000Z}
+      />
+      <MessageItem
+        key="message-1596585600000"
+        offset={20}
+        partition={2}
+        timestamp={2020-08-05T00:00:00.000Z}
+      />
+    </tbody>
+  </table>
+  <div
+    className="columns"
+  >
+    <div
+      className="column is-full"
+    >
+      <CustomParamButton
+        btnText="Next"
+        className="is-link is-pulled-right"
+        onClick={[MockFunction]}
+        type="fa-chevron-right"
+      />
+    </div>
+  </div>
+</Fragment>
+`;
+
+exports[`MessagesTable when topic is empty matches snapshot 1`] = `
+<div>
+  No messages at selected topic
+</div>
+`;

+ 19 - 0
kafka-ui-react-app/src/components/Topics/Details/Messages/__test__/fixtures.ts

@@ -0,0 +1,19 @@
+import { TopicMessage } from 'generated-sources';
+
+export const messages: TopicMessage[] = [
+  {
+    partition: 1,
+    offset: 2,
+    timestamp: new Date(Date.UTC(1995, 5, 5)),
+    content: {
+      foo: 'bar',
+      key: 'val',
+    },
+  },
+  {
+    partition: 2,
+    offset: 20,
+    timestamp: new Date(Date.UTC(2020, 7, 5)),
+    content: undefined,
+  },
+];

+ 1 - 1
kafka-ui-react-app/src/components/Topics/shared/Form/CustomParams/CustomParams.tsx

@@ -88,7 +88,7 @@ const CustomParams: React.FC<Props> = ({ isSubmitting, config }) => {
 
       {formCustomParams.allIndexes.map((index) => (
         <CustomParamField
-          key={index}
+          key={formCustomParams.byIndex[index].name}
           index={index}
           isDisabled={isSubmitting}
           name={formCustomParams.byIndex[index].name}

+ 2 - 3
kafka-ui-react-app/src/setupTests.ts

@@ -1,6 +1,5 @@
-/* eslint-disable */
-import * as Enzyme from 'enzyme';
+import { configure } from 'enzyme';
 import Adapter from '@wojtekmaj/enzyme-adapter-react-17';
 import '@testing-library/jest-dom/extend-expect';
 
-Enzyme.configure({ adapter: new Adapter() });
+configure({ adapter: new Adapter() });

+ 0 - 156
kafka-ui-react-app/src/tests/Topics/Details/Messages/Messages.spec.tsx

@@ -1,156 +0,0 @@
-import React from 'react';
-import { mount, shallow } from 'enzyme';
-import JSONTree from 'react-json-tree';
-import * as useDebounce from 'use-debounce';
-import DatePicker from 'react-datepicker';
-import Messages, { Props } from 'components/Topics/Details/Messages/Messages';
-import PageLoader from 'components/common/PageLoader/PageLoader';
-
-describe('Messages component', () => {
-  beforeEach(() => {
-    jest.restoreAllMocks();
-  });
-
-  const setupWrapper = (props: Partial<Props> = {}) => (
-    <Messages
-      clusterName="Test cluster"
-      topicName="Cluster topic"
-      isFetched
-      fetchTopicMessages={jest.fn()}
-      messages={[]}
-      partitions={[]}
-      {...props}
-    />
-  );
-
-  describe('Initial state', () => {
-    it('renders PageLoader', () => {
-      expect(
-        shallow(setupWrapper({ isFetched: false })).exists(PageLoader)
-      ).toBeTruthy();
-    });
-  });
-
-  describe('Messages table', () => {
-    describe('With messages', () => {
-      const messagesWrapper = mount(
-        setupWrapper({
-          messages: [
-            {
-              partition: 1,
-              offset: 2,
-              timestamp: new Date('05-05-1994'),
-              content: [1, 2, 3],
-            },
-          ],
-        })
-      );
-      it('renders table', () => {
-        expect(
-          messagesWrapper.exists('[className="table is-striped is-fullwidth"]')
-        ).toBeTruthy();
-      });
-      it('renders JSONTree', () => {
-        expect(messagesWrapper.find(JSONTree).length).toEqual(1);
-      });
-      it('parses message content correctly', () => {
-        const messages = [
-          {
-            partition: 1,
-            offset: 2,
-            timestamp: new Date('05-05-1994'),
-            content: [1, 2, 3],
-          },
-        ];
-        const content = JSON.stringify(messages[0].content);
-        expect(JSON.parse(content)).toEqual(messages[0].content);
-      });
-    });
-    describe('Without messages', () => {
-      it('renders string', () => {
-        const wrapper = mount(setupWrapper());
-        expect(wrapper.text()).toContain('No messages at selected topic');
-      });
-    });
-  });
-
-  describe('Offset field', () => {
-    describe('Seek Type dependency', () => {
-      const wrapper = mount(setupWrapper());
-
-      it('renders DatePicker', () => {
-        wrapper
-          .find('[id="selectSeekType"]')
-          .simulate('change', { target: { value: 'TIMESTAMP' } });
-
-        expect(
-          wrapper.find('[id="selectSeekType"]').first().props().value
-        ).toEqual('TIMESTAMP');
-
-        expect(wrapper.exists(DatePicker)).toBeTruthy();
-      });
-    });
-
-    describe('With defined offset value', () => {
-      const wrapper = shallow(setupWrapper());
-
-      it('shows offset value in input', () => {
-        const offset = '10';
-
-        wrapper
-          .find('#searchOffset')
-          .simulate('change', { target: { value: offset } });
-
-        expect(wrapper.find('#searchOffset').first().props().value).toEqual(
-          offset
-        );
-      });
-    });
-    describe('With invalid offset value', () => {
-      const wrapper = shallow(setupWrapper());
-
-      it('shows 0 in input', () => {
-        wrapper
-          .find('#searchOffset')
-          .simulate('change', { target: { value: null } });
-
-        expect(wrapper.find('#searchOffset').first().props().value).toBe('0');
-      });
-    });
-  });
-
-  describe('Search field', () => {
-    it('renders input correctly', () => {
-      const query = 20;
-      const mockedUseDebouncedCallback = jest.fn();
-      jest
-        .spyOn(useDebounce, 'useDebouncedCallback')
-        .mockImplementationOnce(() => [
-          mockedUseDebouncedCallback,
-          jest.fn(),
-          jest.fn(),
-        ]);
-
-      const wrapper = shallow(setupWrapper());
-
-      wrapper
-        .find('#searchText')
-        .simulate('change', { target: { value: query } });
-
-      expect(wrapper.find('#searchText').first().props().value).toEqual(query);
-      expect(mockedUseDebouncedCallback).toHaveBeenCalledWith({ q: query });
-    });
-  });
-
-  describe('Submit button', () => {
-    it('fetches topic messages', () => {
-      const mockedfetchTopicMessages = jest.fn();
-      const wrapper = mount(
-        setupWrapper({ fetchTopicMessages: mockedfetchTopicMessages })
-      );
-
-      wrapper.find('[type="submit"]').simulate('click');
-      expect(mockedfetchTopicMessages).toHaveBeenCalled();
-    });
-  });
-});

+ 1 - 1
kafka-ui-react-app/tsconfig.json

@@ -22,6 +22,6 @@
     "noFallthroughCasesInSwitch": true
   },
   "include": [
-    "src"
+    "src",
   ]
 }

Some files were not shown because too many files changed in this diff