\ [실무 React.Js] Tabulater로 Grid 활용하기 :: Something New
728x90
반응형

abulator는 JavaScript로 작성된 고성능 그리드 테이블 라이브러리로, 다양한 기능과 유연성을 제공하여 복잡한 데이터 테이블을 쉽게 만들 수 있습니다. 이 블로그에서는 React Query와 Tabulator를 함께 사용하여 조회 및 저장 기능을 구현하는 방법을 설명하겠습니다.

Tabulator 사용 이유

  • 고성능: 대량의 데이터를 빠르게 처리하고 렌더링할 수 있습니다.
  • 유연성: 다양한 데이터 소스와 쉽게 통합할 수 있습니다.
  • 사용 편의성: 간단한 API와 다양한 설정 옵션을 제공하여 개발 시간을 절약할 수 있습니다.
  • 풍부한 기능: 정렬, 필터링, 페이지네이션, 편집 등의 다양한 기능을 기본적으로 제공합니다.

Tabulator 설치 및 설정

npm install tabulator-tables

설치 후, Tabulator 스타일시트를 추가해야 합니다. 이를 위해 index.html 파일에 다음을 추가합니다:

<link href="https://unpkg.com/tabulator-tables@4.9.3/dist/css/tabulator.min.css" rel="stylesheet">

이제 React 컴포넌트에서 Tabulator를 사용할 준비가 되었습니다.

import React, { useEffect, useRef } from 'react';
import Tabulator from 'tabulator-tables';
import 'tabulator-tables/dist/css/tabulator.min.css';

const SimpleGrid = ({ data, onAddRow, onDeleteRow }) => {
  const tableRef = useRef(null);

  useEffect(() => {
    const table = new Tabulator(tableRef.current, {
      columns: [
        { title: 'Name', 
          field: 'name', 
          editor: 'input'   
        },
        { title: 'Age', 
          field: 'age', 
          editor: 'input' 
        },
        // 필요한 다른 컬럼들을 추가합니다
      ],
    });

    // 데이터가 변경될 때마다 테이블을 업데이트합니다
    if (data) {
      table.setData(data);
    }
    
    // Cleanup function to destroy the table when the component unmounts
    return () => table.destroy();
  }, [data]);

  const handleAddRow = () => {
    onAddRow({ name: '', age: '' }); // 기본값을 가진 새 행 추가
  };

  const handleDeleteRow = () => {
    const table = tableRef.current.tabulator;
    const selectedRows = table.getSelectedRows();
    selectedRows.forEach(row => row.delete());
    onDeleteRow(selectedRows.map(row => row.getData())); // 삭제된 행 데이터 반환
  };

  return (
    <div>
      <button onClick={handleAddRow}>행 추가</button>
      <button onClick={handleDeleteRow}>행 삭제</button>
      <div ref={tableRef}></div>
    </div>
  );
};

export default SimpleGrid;
import React, { useState } from 'react';
import { useQuery } from 'react-query';
import SimpleGrid from './SimpleGrid';

// 데이터 조회 함수
const fetchData = async (params) => {
  const response = await fetch(`https://api.example.com/data?${new URLSearchParams(params)}`);
  if (!response.ok) {
    throw new Error('네트워크 응답에 문제가 있습니다');
  }
  return response.json();
};

const DataView = () => {
  const [searchParams, setSearchParams] = useState({});
  const [gridData, setGridData] = useState([]);
  
  // useQuery 훅을 사용하여 데이터를 조회합니다
  const { refetch, isFetching } = useQuery(
    ['fetchData', searchParams],
    () => fetchData(searchParams),
    {
      enabled: false,
      onSuccess: (data) => setGridData(data), // 데이터 조회 후 상태 업데이트
    }
  );

  // 검색 버튼 클릭 시 호출되는 함수
  const handleSearch = () => {
    const params = {
      key1: 'value1',
      key2: 'value2',
    };
    setSearchParams(params);
    refetch();
  };

  const handleAddRow = (newRow) => {
    setGridData([...gridData, newRow]);
  };

  const handleDeleteRow = (deletedRows) => {
    setGridData(gridData.filter(row => !deletedRows.includes(row)));
  };

  return (
    <div>
      <button onClick={handleSearch}>검색</button>
      {isFetching ? (
        <p>로딩 중...</p>
      ) : (
        <SimpleGrid 
        	data={gridData} 
        	onAddRow={handleAddRow} 
            onDeleteRow={handleDeleteRow} />
      )}
    </div>
  );
};

export default DataView;

 

728x90

+ Recent posts