StockLending.tsx 2.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990
  1. 'use client';
  2. import '@/app/styles/data-table.scss';
  3. import DataTable, { DataTableColumn } from '@/components/table/DataTable';
  4. import Sparkline from '../../../market/_components/Sparkline';
  5. import { LendingHistoryRow } from '@/types/seibro';
  6. import { formatShares, formatRatePercent } from '@/lib/utils/market';
  7. function buildColumns(): DataTableColumn<LendingHistoryRow>[] {
  8. return [
  9. {
  10. key: 'stdDt',
  11. header: '기준일',
  12. align: 'left',
  13. priority: 'high',
  14. cell: (row) => row.stdDt
  15. },
  16. {
  17. key: 'lendingBalanceQty',
  18. header: '대차잔고',
  19. align: 'right',
  20. priority: 'high',
  21. cell: (row) => formatShares(row.lendingBalanceQty)
  22. },
  23. {
  24. key: 'matchedQty',
  25. header: '체결량',
  26. align: 'right',
  27. priority: 'medium',
  28. cell: (row) => formatShares(row.matchedQty)
  29. },
  30. {
  31. key: 'redeemedQty',
  32. header: '상환량',
  33. align: 'right',
  34. priority: 'low',
  35. cell: (row) => formatShares(row.redeemedQty)
  36. },
  37. {
  38. key: 'foreignLendRatio',
  39. header: '외국인 대여비율',
  40. align: 'right',
  41. priority: 'high',
  42. cell: (row) => formatRatePercent(row.foreignLendRatio)
  43. },
  44. {
  45. key: 'foreignBorrowRatio',
  46. header: '외국인 차입비율',
  47. align: 'right',
  48. priority: 'low',
  49. cell: (row) => formatRatePercent(row.foreignBorrowRatio)
  50. }
  51. ];
  52. }
  53. interface Props {
  54. rows: LendingHistoryRow[];
  55. }
  56. // 대차 시계열 — 외국인 대여비율 추이(스파크라인, 오래된→최신) + 상세 테이블(최신순).
  57. export default function StockLending({ rows }: Props)
  58. {
  59. if (rows.length === 0) {
  60. return <p className='stock-detail__empty'>수집된 대차 시계열이 없습니다.</p>;
  61. }
  62. // rows 는 최신순 → 스파크라인은 오래된→최신 순서로 뒤집어 표시
  63. const trend = [...rows].reverse().map(c => c.foreignLendRatio);
  64. const latest = rows[0];
  65. return (
  66. <div className='stock-lending'>
  67. <div className='stock-lending__trend'>
  68. <div className='stock-lending__trend-head'>
  69. <span className='stock-lending__trend-label'>외국인 대여잔고비율 추이</span>
  70. <span className='stock-lending__trend-latest'>{formatRatePercent(latest.foreignLendRatio)}</span>
  71. </div>
  72. <Sparkline values={trend} label='외국인 대여잔고비율 추이' />
  73. </div>
  74. <DataTable<LendingHistoryRow>
  75. caption='대차 시계열 — 기준일, 대차잔고, 체결량, 상환량, 외국인 대여비율, 외국인 차입비율'
  76. columns={buildColumns()}
  77. rows={rows}
  78. rowKey={(row) => row.stdDt}
  79. emptyMessage='수집된 대차 시계열이 없습니다.'
  80. />
  81. </div>
  82. );
  83. }