react-terminal-viewer-cicd 2.0.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +181 -0
- package/dist/esm/Addon/EventEmiter.d.ts +18 -0
- package/dist/esm/Addon/EventEmiter.js +64 -0
- package/dist/esm/Addon/HighlightAddon.d.ts +26 -0
- package/dist/esm/Addon/HighlightAddon.js +188 -0
- package/dist/esm/Addon/SearchAddon.d.ts +140 -0
- package/dist/esm/Addon/SearchAddon.js +797 -0
- package/dist/esm/Addon/WorkerLog/GlobalContext.d.ts +10 -0
- package/dist/esm/Addon/WorkerLog/GlobalContext.js +37 -0
- package/dist/esm/Addon/WorkerLog/LimitMap.d.ts +14 -0
- package/dist/esm/Addon/WorkerLog/LimitMap.js +54 -0
- package/dist/esm/Addon/WorkerLog/LogWorker.d.ts +2 -0
- package/dist/esm/Addon/WorkerLog/LogWorker.js +13 -0
- package/dist/esm/Addon/WorkerLog/Logs.d.ts +21 -0
- package/dist/esm/Addon/WorkerLog/Logs.js +60 -0
- package/dist/esm/Addon/WorkerLog/Mark.d.ts +36 -0
- package/dist/esm/Addon/WorkerLog/Mark.js +155 -0
- package/dist/esm/Addon/WorkerLog/Searcher.d.ts +16 -0
- package/dist/esm/Addon/WorkerLog/Searcher.js +88 -0
- package/dist/esm/Addon/WorkerLog/WebWokerServer.d.ts +10 -0
- package/dist/esm/Addon/WorkerLog/WebWokerServer.js +57 -0
- package/dist/esm/Addon/WorkerLog/WebWorkerClient.d.ts +13 -0
- package/dist/esm/Addon/WorkerLog/WebWorkerClient.js +83 -0
- package/dist/esm/Addon/WorkerLog/log.worker.d.ts +1 -0
- package/dist/esm/Addon/WorkerLog/log.worker.js +63 -0
- package/dist/esm/Addon/WorkerLog/types.d.ts +18 -0
- package/dist/esm/Addon/WorkerLog/types.js +1 -0
- package/dist/esm/Addon/useAddon.d.ts +9 -0
- package/dist/esm/Addon/useAddon.js +33 -0
- package/dist/esm/Hooks/useBatchProcess.d.ts +2 -0
- package/dist/esm/Hooks/useBatchProcess.js +47 -0
- package/dist/esm/Hooks/useCache.d.ts +31 -0
- package/dist/esm/Hooks/useCache.js +206 -0
- package/dist/esm/Hooks/useDebounceInput.d.ts +3 -0
- package/dist/esm/Hooks/useDebounceInput.js +26 -0
- package/dist/esm/Hooks/useLocalStore.d.ts +2 -0
- package/dist/esm/Hooks/useLocalStore.js +9 -0
- package/dist/esm/Hooks/useRemote.d.ts +30 -0
- package/dist/esm/Hooks/useRemote.js +398 -0
- package/dist/esm/Hooks/useThrottle.d.ts +2 -0
- package/dist/esm/Hooks/useThrottle.js +13 -0
- package/dist/esm/Hooks/useWorkerLogs.d.ts +9 -0
- package/dist/esm/Hooks/useWorkerLogs.js +162 -0
- package/dist/esm/TerminalViewer/index.d.ts +185 -0
- package/dist/esm/TerminalViewer/index.js +292 -0
- package/dist/esm/TerminalViewer/index.less +17 -0
- package/dist/esm/TerminalViewerBody/index.d.ts +87 -0
- package/dist/esm/TerminalViewerBody/index.js +248 -0
- package/dist/esm/TerminalViewerBody/index.less +51 -0
- package/dist/esm/TerminalViewerHeader/index.d.ts +88 -0
- package/dist/esm/TerminalViewerHeader/index.js +129 -0
- package/dist/esm/TerminalViewerHeader/index.less +143 -0
- package/dist/esm/TerminalViewerToolBar/index.d.ts +46 -0
- package/dist/esm/TerminalViewerToolBar/index.js +28 -0
- package/dist/esm/TerminalViewerToolBar/index.less +32 -0
- package/dist/esm/TerminalViewerVirtualDom/index.d.ts +71 -0
- package/dist/esm/TerminalViewerVirtualDom/index.js +309 -0
- package/dist/esm/TerminalViewerVirtualDom/index.less +68 -0
- package/dist/esm/index.d.ts +9 -0
- package/dist/esm/index.js +9 -0
- package/dist/esm/mock/index.d.ts +12 -0
- package/dist/esm/mock/index.js +98 -0
- package/dist/esm/types.d.ts +30 -0
- package/dist/esm/types.js +1 -0
- package/dist/worker/Addon/EventEmiter.d.ts +18 -0
- package/dist/worker/Addon/HighlightAddon.d.ts +26 -0
- package/dist/worker/Addon/SearchAddon.d.ts +140 -0
- package/dist/worker/Addon/WorkerLog/GlobalContext.d.ts +10 -0
- package/dist/worker/Addon/WorkerLog/LimitMap.d.ts +14 -0
- package/dist/worker/Addon/WorkerLog/LogWorker.d.ts +2 -0
- package/dist/worker/Addon/WorkerLog/Logs.d.ts +21 -0
- package/dist/worker/Addon/WorkerLog/Mark.d.ts +36 -0
- package/dist/worker/Addon/WorkerLog/Searcher.d.ts +16 -0
- package/dist/worker/Addon/WorkerLog/WebWokerServer.d.ts +10 -0
- package/dist/worker/Addon/WorkerLog/WebWorkerClient.d.ts +13 -0
- package/dist/worker/Addon/WorkerLog/log.worker.d.ts +1 -0
- package/dist/worker/Addon/WorkerLog/types.d.ts +18 -0
- package/dist/worker/Addon/useAddon.d.ts +9 -0
- package/dist/worker/Hooks/useBatchProcess.d.ts +2 -0
- package/dist/worker/Hooks/useCache.d.ts +31 -0
- package/dist/worker/Hooks/useDebounceInput.d.ts +3 -0
- package/dist/worker/Hooks/useLocalStore.d.ts +2 -0
- package/dist/worker/Hooks/useRemote.d.ts +30 -0
- package/dist/worker/Hooks/useRemote.test.d.ts +1 -0
- package/dist/worker/Hooks/useThrottle.d.ts +2 -0
- package/dist/worker/Hooks/useWorkerLogs.d.ts +9 -0
- package/dist/worker/TerminalViewer/index.d.ts +185 -0
- package/dist/worker/TerminalViewer/index.test.d.ts +1 -0
- package/dist/worker/TerminalViewerBody/index.d.ts +87 -0
- package/dist/worker/TerminalViewerBody/index.test.d.ts +1 -0
- package/dist/worker/TerminalViewerHeader/index.d.ts +88 -0
- package/dist/worker/TerminalViewerToolBar/index.d.ts +46 -0
- package/dist/worker/TerminalViewerVirtualDom/index.d.ts +71 -0
- package/dist/worker/index.d.ts +9 -0
- package/dist/worker/log.worker.js +2 -0
- package/dist/worker/log.worker.js.map +1 -0
- package/dist/worker/mock/index.d.ts +12 -0
- package/dist/worker/types.d.ts +30 -0
- package/package.json +97 -0
|
@@ -0,0 +1,185 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { ITerminalOptions } from 'xterm';
|
|
3
|
+
import type { ISearchOptions } from '../Addon/SearchAddon';
|
|
4
|
+
import type { IRemoteOptions } from '../Hooks/useRemote';
|
|
5
|
+
import type { ICacheOptions } from '../Hooks/useCache';
|
|
6
|
+
import type { IHighlightOptions } from '../Addon/HighlightAddon';
|
|
7
|
+
import { ExtraOptions, TerminalRef, LogAfterProps } from '../types';
|
|
8
|
+
import './index.less';
|
|
9
|
+
export interface TerminalViewerProps {
|
|
10
|
+
/**
|
|
11
|
+
* @description.zh-CN 指定 TerminalViewer 挂载的节点,并在容器内展现,false 为挂载在当前位置
|
|
12
|
+
* @default 当前位置
|
|
13
|
+
*/
|
|
14
|
+
ref?: TerminalRef;
|
|
15
|
+
/**
|
|
16
|
+
* @description.zh-CN 是否自动拉伸填充容器宽高
|
|
17
|
+
* @default true
|
|
18
|
+
*/
|
|
19
|
+
fit?: boolean;
|
|
20
|
+
/**
|
|
21
|
+
*@description.zh-CN 是否开启自动滚动到底部
|
|
22
|
+
*@default true
|
|
23
|
+
*/
|
|
24
|
+
autoScroll?: boolean;
|
|
25
|
+
/**
|
|
26
|
+
* @description.zh-CN 自动滚动到某一行,开启后自动滚动到底部失效
|
|
27
|
+
*/
|
|
28
|
+
scrollToRow?: number;
|
|
29
|
+
/**
|
|
30
|
+
* @description.zh-CN 是否支持刷新
|
|
31
|
+
* @default true
|
|
32
|
+
*/
|
|
33
|
+
refreshable?: boolean;
|
|
34
|
+
/**
|
|
35
|
+
* @description.zh-CN 搜索框 placeholder
|
|
36
|
+
*/
|
|
37
|
+
searchPlaceholder?: string;
|
|
38
|
+
/**
|
|
39
|
+
* @description.zh-CN 默认全屏显示
|
|
40
|
+
* @default false
|
|
41
|
+
*/
|
|
42
|
+
defaultFullScreen?: boolean;
|
|
43
|
+
/**
|
|
44
|
+
* @description.zh-CN 自定义日志头部, null 为不显示默认头部
|
|
45
|
+
*/
|
|
46
|
+
header?: React.ReactNode;
|
|
47
|
+
/**
|
|
48
|
+
* @description.zh-CN 搜索框前的内容
|
|
49
|
+
*/
|
|
50
|
+
inputAddonBefore?: React.ReactNode;
|
|
51
|
+
/**
|
|
52
|
+
* @description.zh-CN 搜索框后的内容
|
|
53
|
+
*/
|
|
54
|
+
inputAddonAfter?: React.ReactNode;
|
|
55
|
+
/**
|
|
56
|
+
* @description.zh-CN toolbar 自定义工具栏
|
|
57
|
+
*/
|
|
58
|
+
toolbar?: React.ReactNode;
|
|
59
|
+
/**
|
|
60
|
+
* @description.zh-CN 是否显示全屏图标
|
|
61
|
+
* @default true
|
|
62
|
+
*/
|
|
63
|
+
showFullScreen?: boolean;
|
|
64
|
+
/**
|
|
65
|
+
* @description.zh-CN 自定义空文本显示
|
|
66
|
+
*/
|
|
67
|
+
empty?: React.ReactNode;
|
|
68
|
+
/**
|
|
69
|
+
* @description.zh-CN 外层样式类名
|
|
70
|
+
*/
|
|
71
|
+
className?: string;
|
|
72
|
+
/**
|
|
73
|
+
* @description.zh-CN 可用于设置外层容器样式
|
|
74
|
+
*/
|
|
75
|
+
style?: object;
|
|
76
|
+
/**
|
|
77
|
+
* @description.zh-CN 用于渲染日志的默认数据,如 "echo 1\r\necho2"
|
|
78
|
+
* @default ''
|
|
79
|
+
*/
|
|
80
|
+
defaultData?: string;
|
|
81
|
+
/**
|
|
82
|
+
* @description.zh-CN 默认打开的标签
|
|
83
|
+
* @default 0
|
|
84
|
+
*/
|
|
85
|
+
defaultTabIndex?: number;
|
|
86
|
+
/**
|
|
87
|
+
* @description.zh-CN 激活的标签, 如果同时设置了 defaultTabIndex 则以此属性为准
|
|
88
|
+
* @default 0
|
|
89
|
+
*/
|
|
90
|
+
activeTabIndex?: number;
|
|
91
|
+
/**
|
|
92
|
+
* @description.zh-CN 设置日志后置标签,仅在开启虚拟 DOM 生效
|
|
93
|
+
*/
|
|
94
|
+
logAfter?: React.FunctionComponent<LogAfterProps> | React.ComponentClass<LogAfterProps>;
|
|
95
|
+
/**
|
|
96
|
+
* @description.zh-CN 多标签配置选项
|
|
97
|
+
*/
|
|
98
|
+
tabs?: {
|
|
99
|
+
key: string | number;
|
|
100
|
+
title?: React.ReactNode;
|
|
101
|
+
defaultData?: string;
|
|
102
|
+
remoteOptions?: IRemoteOptions;
|
|
103
|
+
cacheOptions?: ICacheOptions;
|
|
104
|
+
}[];
|
|
105
|
+
/**
|
|
106
|
+
*@description.zh-CN 自定义图标
|
|
107
|
+
*/
|
|
108
|
+
icons?: {
|
|
109
|
+
search?: React.ReactNode;
|
|
110
|
+
up?: React.ReactNode;
|
|
111
|
+
down?: React.ReactNode;
|
|
112
|
+
clear?: React.ReactNode;
|
|
113
|
+
top?: React.ReactNode;
|
|
114
|
+
bottom?: React.ReactNode;
|
|
115
|
+
fullScreen?: React.ReactNode;
|
|
116
|
+
fullScreenExit?: React.ReactNode;
|
|
117
|
+
refresh?: React.ReactNode;
|
|
118
|
+
loading?: React.ReactNode;
|
|
119
|
+
};
|
|
120
|
+
/**
|
|
121
|
+
* @description.zh-CN 是否支持渲染超链接
|
|
122
|
+
* @default true
|
|
123
|
+
*/
|
|
124
|
+
webLinksSupport?: boolean;
|
|
125
|
+
/**
|
|
126
|
+
* @description.zh-CN 是否使用 canvas 渲染, 开启 canvas 会有更好的性能但可能会遇到更多的问题
|
|
127
|
+
* @default false
|
|
128
|
+
*/
|
|
129
|
+
canvasSupport?: boolean;
|
|
130
|
+
/**
|
|
131
|
+
* @description.zh-CN 是否使用自研虚拟 DOM 内核,开启后 terminalOptions, canvasSupport, webLinksSupport 不可用
|
|
132
|
+
* @default false
|
|
133
|
+
*/
|
|
134
|
+
virtualDomSupport?: boolean;
|
|
135
|
+
/**
|
|
136
|
+
* @description.zh-CN 日志 web worker 路径, 需配合 CopyPlugin 使用且仅在开启 virtualDomSupport 为 true 时有效
|
|
137
|
+
|
|
138
|
+
* @default "/worker"
|
|
139
|
+
*/
|
|
140
|
+
workerPath?: string;
|
|
141
|
+
/**
|
|
142
|
+
* @description.zh-CN 远程加载配置
|
|
143
|
+
*
|
|
144
|
+
*/
|
|
145
|
+
remoteOptions?: IRemoteOptions;
|
|
146
|
+
/**
|
|
147
|
+
* @description.zh-CN 缓存全局配置,仅在配置远程加载后有效,如 `expires: 60 * 1000` 表示自动清理已过期一分钟的缓存
|
|
148
|
+
*/
|
|
149
|
+
cacheOptions?: ICacheOptions;
|
|
150
|
+
/**
|
|
151
|
+
* @description.zh-CN xterm 搜索选项
|
|
152
|
+
*/
|
|
153
|
+
searchOptions?: ISearchOptions;
|
|
154
|
+
/**
|
|
155
|
+
* @description.zh-CN 高亮选项
|
|
156
|
+
*/
|
|
157
|
+
highlightOptions?: IHighlightOptions[];
|
|
158
|
+
/**
|
|
159
|
+
* @description.zh-CN xtem.js 配置, https://github.com/xtermjs/xterm.js
|
|
160
|
+
*/
|
|
161
|
+
terminalOptions?: ITerminalOptions;
|
|
162
|
+
/**
|
|
163
|
+
* @description.zh-CN 额外的功能选项 { showLineNumber 仅 虚拟 DOM 模式支持}
|
|
164
|
+
*/
|
|
165
|
+
extraOptions?: ExtraOptions;
|
|
166
|
+
/**
|
|
167
|
+
* @description.zh-CN 指定 TerminalViewer 挂载的节点,并在容器内展现,开启全屏后无效, false 为挂载在当前位置
|
|
168
|
+
* @default 当前节点
|
|
169
|
+
*/
|
|
170
|
+
getContainer?: string | HTMLElement | (() => HTMLElement | null);
|
|
171
|
+
/**
|
|
172
|
+
* @description.zh-CN 点击 tab 标题后回调函数
|
|
173
|
+
*/
|
|
174
|
+
onTitleChange?: (index: number) => void;
|
|
175
|
+
/**
|
|
176
|
+
* @description.zh-CN 加载状态变更回调函数
|
|
177
|
+
*/
|
|
178
|
+
onLoading?: (bool: boolean) => void;
|
|
179
|
+
/**
|
|
180
|
+
* @description.zh-CN 刷新后的回调函数
|
|
181
|
+
*/
|
|
182
|
+
onRefresh?: () => void;
|
|
183
|
+
}
|
|
184
|
+
declare const TerminalViewer: React.ForwardRefExoticComponent<Omit<TerminalViewerProps, "ref"> & React.RefAttributes<TerminalRef | undefined>>;
|
|
185
|
+
export default TerminalViewer;
|
|
@@ -0,0 +1,292 @@
|
|
|
1
|
+
function _typeof(o) { "@babel/helpers - typeof"; return _typeof = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function (o) { return typeof o; } : function (o) { return o && "function" == typeof Symbol && o.constructor === Symbol && o !== Symbol.prototype ? "symbol" : typeof o; }, _typeof(o); }
|
|
2
|
+
function ownKeys(e, r) { var t = Object.keys(e); if (Object.getOwnPropertySymbols) { var o = Object.getOwnPropertySymbols(e); r && (o = o.filter(function (r) { return Object.getOwnPropertyDescriptor(e, r).enumerable; })), t.push.apply(t, o); } return t; }
|
|
3
|
+
function _objectSpread(e) { for (var r = 1; r < arguments.length; r++) { var t = null != arguments[r] ? arguments[r] : {}; r % 2 ? ownKeys(Object(t), !0).forEach(function (r) { _defineProperty(e, r, t[r]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(e, Object.getOwnPropertyDescriptors(t)) : ownKeys(Object(t)).forEach(function (r) { Object.defineProperty(e, r, Object.getOwnPropertyDescriptor(t, r)); }); } return e; }
|
|
4
|
+
function _defineProperty(obj, key, value) { key = _toPropertyKey(key); if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
|
|
5
|
+
function _toPropertyKey(t) { var i = _toPrimitive(t, "string"); return "symbol" == _typeof(i) ? i : String(i); }
|
|
6
|
+
function _toPrimitive(t, r) { if ("object" != _typeof(t) || !t) return t; var e = t[Symbol.toPrimitive]; if (void 0 !== e) { var i = e.call(t, r || "default"); if ("object" != _typeof(i)) return i; throw new TypeError("@@toPrimitive must return a primitive value."); } return ("string" === r ? String : Number)(t); }
|
|
7
|
+
function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
|
|
8
|
+
function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
|
|
9
|
+
function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
|
|
10
|
+
function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) arr2[i] = arr[i]; return arr2; }
|
|
11
|
+
function _iterableToArrayLimit(r, l) { var t = null == r ? null : "undefined" != typeof Symbol && r[Symbol.iterator] || r["@@iterator"]; if (null != t) { var e, n, i, u, a = [], f = !0, o = !1; try { if (i = (t = t.call(r)).next, 0 === l) { if (Object(t) !== t) return; f = !1; } else for (; !(f = (e = i.call(t)).done) && (a.push(e.value), a.length !== l); f = !0); } catch (r) { o = !0, n = r; } finally { try { if (!f && null != t.return && (u = t.return(), Object(u) !== u)) return; } finally { if (o) throw n; } } return a; } }
|
|
12
|
+
function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
|
|
13
|
+
import React, { forwardRef, useCallback, useState, useImperativeHandle, useRef, useEffect, useMemo } from 'react';
|
|
14
|
+
import { createPortal } from 'react-dom';
|
|
15
|
+
import useDebounceInput from "../Hooks/useDebounceInput";
|
|
16
|
+
import TerminalViewerHeader from "../TerminalViewerHeader";
|
|
17
|
+
import TerminalViewerBody from "../TerminalViewerBody";
|
|
18
|
+
import TerminalViewerVirtualDom from "../TerminalViewerVirtualDom";
|
|
19
|
+
import TerminalViewerToolBar from "../TerminalViewerToolBar";
|
|
20
|
+
import globalContext from "../Addon/WorkerLog/GlobalContext";
|
|
21
|
+
import "./index.less";
|
|
22
|
+
var defaultSearchOptions = {
|
|
23
|
+
regex: false,
|
|
24
|
+
wholeWord: false,
|
|
25
|
+
caseSensitive: false,
|
|
26
|
+
incremental: false,
|
|
27
|
+
decorations: {
|
|
28
|
+
matchForegroundColor: '#000000',
|
|
29
|
+
matchBackground: '#ffff54',
|
|
30
|
+
matchBorder: 'none',
|
|
31
|
+
matchOverviewRuler: 'none',
|
|
32
|
+
activeMatchBackground: '#ff9540',
|
|
33
|
+
activeMatchBorder: 'none',
|
|
34
|
+
activeMatchColorOverviewRuler: 'none'
|
|
35
|
+
}
|
|
36
|
+
};
|
|
37
|
+
|
|
38
|
+
// eslint-disable-next-line react/display-name
|
|
39
|
+
var TerminalViewer = /*#__PURE__*/forwardRef(function (_ref, ref) {
|
|
40
|
+
var fit = _ref.fit,
|
|
41
|
+
autoScroll = _ref.autoScroll,
|
|
42
|
+
scrollToRow = _ref.scrollToRow,
|
|
43
|
+
refreshable = _ref.refreshable,
|
|
44
|
+
searchPlaceholder = _ref.searchPlaceholder,
|
|
45
|
+
header = _ref.header,
|
|
46
|
+
inputAddonBefore = _ref.inputAddonBefore,
|
|
47
|
+
inputAddonAfter = _ref.inputAddonAfter,
|
|
48
|
+
empty = _ref.empty,
|
|
49
|
+
icons = _ref.icons,
|
|
50
|
+
toolbar = _ref.toolbar,
|
|
51
|
+
showFullScreen = _ref.showFullScreen,
|
|
52
|
+
className = _ref.className,
|
|
53
|
+
style = _ref.style,
|
|
54
|
+
defaultFullScreen = _ref.defaultFullScreen,
|
|
55
|
+
defaultData = _ref.defaultData,
|
|
56
|
+
defaultTabIndex = _ref.defaultTabIndex,
|
|
57
|
+
activeTabIndexProp = _ref.activeTabIndex,
|
|
58
|
+
logAfter = _ref.logAfter,
|
|
59
|
+
tabs = _ref.tabs,
|
|
60
|
+
webLinksSupport = _ref.webLinksSupport,
|
|
61
|
+
canvasSupport = _ref.canvasSupport,
|
|
62
|
+
virtualDomSupport = _ref.virtualDomSupport,
|
|
63
|
+
workerPath = _ref.workerPath,
|
|
64
|
+
remoteOptions = _ref.remoteOptions,
|
|
65
|
+
cacheOptions = _ref.cacheOptions,
|
|
66
|
+
searchOptions = _ref.searchOptions,
|
|
67
|
+
highlightOptions = _ref.highlightOptions,
|
|
68
|
+
terminalOptions = _ref.terminalOptions,
|
|
69
|
+
extraOptions = _ref.extraOptions,
|
|
70
|
+
getContainer = _ref.getContainer,
|
|
71
|
+
onTitleChange = _ref.onTitleChange,
|
|
72
|
+
onLoading = _ref.onLoading,
|
|
73
|
+
onRefresh = _ref.onRefresh;
|
|
74
|
+
var localSearchOptions = searchOptions !== null && searchOptions !== void 0 ? searchOptions : {};
|
|
75
|
+
var instanceRef = useRef();
|
|
76
|
+
var searchValueRef = useRef('');
|
|
77
|
+
var _useState = useState(false),
|
|
78
|
+
_useState2 = _slicedToArray(_useState, 2),
|
|
79
|
+
loading = _useState2[0],
|
|
80
|
+
setLoading = _useState2[1];
|
|
81
|
+
var _useState3 = useState(defaultFullScreen),
|
|
82
|
+
_useState4 = _slicedToArray(_useState3, 2),
|
|
83
|
+
fullScreen = _useState4[0],
|
|
84
|
+
setFullScreen = _useState4[1];
|
|
85
|
+
var _useState5 = useState(activeTabIndexProp || defaultTabIndex || 0),
|
|
86
|
+
_useState6 = _slicedToArray(_useState5, 2),
|
|
87
|
+
activeTabIndex = _useState6[0],
|
|
88
|
+
setActiveTabIndex = _useState6[1];
|
|
89
|
+
var _useState7 = useState({
|
|
90
|
+
resultIndex: -1,
|
|
91
|
+
resultCount: 0
|
|
92
|
+
}),
|
|
93
|
+
_useState8 = _slicedToArray(_useState7, 2),
|
|
94
|
+
searchResult = _useState8[0],
|
|
95
|
+
setSearchResult = _useState8[1];
|
|
96
|
+
var searchOptionsRef = useRef(_objectSpread(_objectSpread({}, defaultSearchOptions), localSearchOptions));
|
|
97
|
+
useEffect(function () {
|
|
98
|
+
searchOptionsRef.current = _objectSpread(_objectSpread({}, defaultSearchOptions), localSearchOptions);
|
|
99
|
+
});
|
|
100
|
+
var cln = ['terminal-viewer', fullScreen && 'terminal-viewer--fullscreen', className].filter(Boolean).join(' ');
|
|
101
|
+
var ViewerBody = virtualDomSupport ? TerminalViewerVirtualDom : TerminalViewerBody;
|
|
102
|
+
var titles = useMemo(function () {
|
|
103
|
+
if (!Array.isArray(tabs)) {
|
|
104
|
+
return [];
|
|
105
|
+
}
|
|
106
|
+
return tabs.map(function (tab, index) {
|
|
107
|
+
return tab.title || index;
|
|
108
|
+
});
|
|
109
|
+
}, [tabs]);
|
|
110
|
+
var getQueryElement = useCallback(function (query) {
|
|
111
|
+
if (typeof query === 'string') {
|
|
112
|
+
return document.querySelector(query);
|
|
113
|
+
}
|
|
114
|
+
if (typeof query === 'function') {
|
|
115
|
+
return query();
|
|
116
|
+
}
|
|
117
|
+
return query;
|
|
118
|
+
}, []);
|
|
119
|
+
var mountElement = fullScreen ? document.body : getQueryElement(getContainer);
|
|
120
|
+
var handleLoading = useCallback(function (bool) {
|
|
121
|
+
setLoading(bool);
|
|
122
|
+
if (typeof onLoading === 'function') {
|
|
123
|
+
onLoading(bool);
|
|
124
|
+
}
|
|
125
|
+
}, [onLoading]);
|
|
126
|
+
var handleTitleChange = useCallback(function (index) {
|
|
127
|
+
setActiveTabIndex(index);
|
|
128
|
+
setSearchResult({
|
|
129
|
+
resultIndex: -1,
|
|
130
|
+
resultCount: 0
|
|
131
|
+
});
|
|
132
|
+
if (typeof onTitleChange === 'function') {
|
|
133
|
+
onTitleChange(index);
|
|
134
|
+
}
|
|
135
|
+
}, [onTitleChange]);
|
|
136
|
+
var handleSearchChange = useDebounceInput(function (value) {
|
|
137
|
+
var _instanceRef$current;
|
|
138
|
+
searchValueRef.current = value;
|
|
139
|
+
if ((_instanceRef$current = instanceRef.current) !== null && _instanceRef$current !== void 0 && (_instanceRef$current = _instanceRef$current.addons) !== null && _instanceRef$current !== void 0 && _instanceRef$current.search) {
|
|
140
|
+
var _instanceRef$current$;
|
|
141
|
+
(_instanceRef$current$ = instanceRef.current.addons.search()) === null || _instanceRef$current$ === void 0 || _instanceRef$current$.findNext(value, searchOptionsRef.current);
|
|
142
|
+
}
|
|
143
|
+
});
|
|
144
|
+
var handleSearchClear = useCallback(function () {
|
|
145
|
+
var _instanceRef$current2;
|
|
146
|
+
if ((_instanceRef$current2 = instanceRef.current) !== null && _instanceRef$current2 !== void 0 && (_instanceRef$current2 = _instanceRef$current2.addons) !== null && _instanceRef$current2 !== void 0 && _instanceRef$current2.search) {
|
|
147
|
+
var _instanceRef$current$2;
|
|
148
|
+
(_instanceRef$current$2 = instanceRef.current.addons.search()) === null || _instanceRef$current$2 === void 0 || _instanceRef$current$2.findNext('', searchOptionsRef.current);
|
|
149
|
+
}
|
|
150
|
+
}, []);
|
|
151
|
+
var handleSearchPrev = useCallback(function (value) {
|
|
152
|
+
var _instanceRef$current3;
|
|
153
|
+
if ((_instanceRef$current3 = instanceRef.current) !== null && _instanceRef$current3 !== void 0 && (_instanceRef$current3 = _instanceRef$current3.addons) !== null && _instanceRef$current3 !== void 0 && _instanceRef$current3.search) {
|
|
154
|
+
var _instanceRef$current4;
|
|
155
|
+
(_instanceRef$current4 = instanceRef.current) === null || _instanceRef$current4 === void 0 || (_instanceRef$current4 = _instanceRef$current4.addons.search()) === null || _instanceRef$current4 === void 0 || _instanceRef$current4.findPrevious(value, searchOptionsRef.current);
|
|
156
|
+
}
|
|
157
|
+
}, []);
|
|
158
|
+
var handleSearchNext = useCallback(function (value) {
|
|
159
|
+
var _instanceRef$current5;
|
|
160
|
+
if ((_instanceRef$current5 = instanceRef.current) !== null && _instanceRef$current5 !== void 0 && (_instanceRef$current5 = _instanceRef$current5.addons) !== null && _instanceRef$current5 !== void 0 && _instanceRef$current5.search) {
|
|
161
|
+
var _instanceRef$current$3;
|
|
162
|
+
(_instanceRef$current$3 = instanceRef.current.addons.search()) === null || _instanceRef$current$3 === void 0 || _instanceRef$current$3.findNext(value, searchOptionsRef.current);
|
|
163
|
+
}
|
|
164
|
+
}, []);
|
|
165
|
+
var handleAddonReady = useCallback(function (terminal, addon) {
|
|
166
|
+
var searchAddon = addon;
|
|
167
|
+
// 注意需配置 decorations 才会触发
|
|
168
|
+
if (searchAddon !== null && searchAddon !== void 0 && searchAddon.onDidChangeResults) {
|
|
169
|
+
searchAddon.onDidChangeResults(function (e) {
|
|
170
|
+
setSearchResult(e || {
|
|
171
|
+
resultIndex: -1,
|
|
172
|
+
resultCount: 0
|
|
173
|
+
});
|
|
174
|
+
});
|
|
175
|
+
}
|
|
176
|
+
}, []);
|
|
177
|
+
var handleScrollTop = useCallback(function () {
|
|
178
|
+
var _instanceRef$current6;
|
|
179
|
+
if ((_instanceRef$current6 = instanceRef.current) !== null && _instanceRef$current6 !== void 0 && _instanceRef$current6.terminal) {
|
|
180
|
+
var _instanceRef$current$4;
|
|
181
|
+
(_instanceRef$current$4 = instanceRef.current.terminal()) === null || _instanceRef$current$4 === void 0 || _instanceRef$current$4.scrollToTop();
|
|
182
|
+
}
|
|
183
|
+
}, []);
|
|
184
|
+
var handleScrollBottom = useCallback(function () {
|
|
185
|
+
var _instanceRef$current7;
|
|
186
|
+
if ((_instanceRef$current7 = instanceRef.current) !== null && _instanceRef$current7 !== void 0 && _instanceRef$current7.terminal) {
|
|
187
|
+
var _instanceRef$current$5;
|
|
188
|
+
(_instanceRef$current$5 = instanceRef.current.terminal()) === null || _instanceRef$current$5 === void 0 || _instanceRef$current$5.scrollToBottom();
|
|
189
|
+
}
|
|
190
|
+
}, []);
|
|
191
|
+
var handleFullScreen = useCallback(function () {
|
|
192
|
+
setFullScreen(function (p) {
|
|
193
|
+
return !p;
|
|
194
|
+
});
|
|
195
|
+
}, []);
|
|
196
|
+
var handleRefresh = useCallback(function () {
|
|
197
|
+
var _instanceRef$current8;
|
|
198
|
+
if (typeof onRefresh === 'function') {
|
|
199
|
+
onRefresh();
|
|
200
|
+
}
|
|
201
|
+
(_instanceRef$current8 = instanceRef.current) === null || _instanceRef$current8 === void 0 || _instanceRef$current8.refresh();
|
|
202
|
+
}, [onRefresh]);
|
|
203
|
+
useEffect(function () {
|
|
204
|
+
setActiveTabIndex(activeTabIndexProp || 0);
|
|
205
|
+
}, [activeTabIndexProp]);
|
|
206
|
+
useImperativeHandle(ref, function () {
|
|
207
|
+
return instanceRef.current;
|
|
208
|
+
});
|
|
209
|
+
if (virtualDomSupport) {
|
|
210
|
+
globalContext.setWorkerPath(workerPath || "" || '/worker');
|
|
211
|
+
}
|
|
212
|
+
useEffect(function () {
|
|
213
|
+
var worker = globalContext.getWorker();
|
|
214
|
+
return function () {
|
|
215
|
+
worker === null || worker === void 0 || worker.terminate();
|
|
216
|
+
globalContext.setWorker(undefined);
|
|
217
|
+
};
|
|
218
|
+
}, [virtualDomSupport]);
|
|
219
|
+
var render = /*#__PURE__*/React.createElement("div", {
|
|
220
|
+
className: cln,
|
|
221
|
+
style: style
|
|
222
|
+
}, header || /*#__PURE__*/React.createElement(TerminalViewerHeader, {
|
|
223
|
+
defaultValue: searchValueRef.current,
|
|
224
|
+
refreshable: refreshable,
|
|
225
|
+
icons: icons,
|
|
226
|
+
loading: loading,
|
|
227
|
+
activeTitleIndex: activeTabIndex,
|
|
228
|
+
titles: titles,
|
|
229
|
+
placeholder: searchPlaceholder,
|
|
230
|
+
searchResult: searchResult,
|
|
231
|
+
inputAddonBefore: inputAddonBefore,
|
|
232
|
+
inputAddonAfter: inputAddonAfter,
|
|
233
|
+
onSearchChange: handleSearchChange,
|
|
234
|
+
onSearchClear: handleSearchClear,
|
|
235
|
+
onSearchPrev: handleSearchPrev,
|
|
236
|
+
onSearchNext: handleSearchNext,
|
|
237
|
+
onTitleChange: handleTitleChange,
|
|
238
|
+
onRefresh: handleRefresh
|
|
239
|
+
}), Array.isArray(tabs) && tabs.map(function (tab, index) {
|
|
240
|
+
if (activeTabIndex === index) {
|
|
241
|
+
return /*#__PURE__*/React.createElement(ViewerBody, {
|
|
242
|
+
key: tab.key || index,
|
|
243
|
+
fit: fit,
|
|
244
|
+
empty: empty,
|
|
245
|
+
autoScroll: autoScroll,
|
|
246
|
+
scrollToRow: scrollToRow,
|
|
247
|
+
logAfter: logAfter,
|
|
248
|
+
webLinksSupport: webLinksSupport,
|
|
249
|
+
canvasSupport: canvasSupport,
|
|
250
|
+
ref: instanceRef,
|
|
251
|
+
defaultData: tab.defaultData,
|
|
252
|
+
cacheOptions: tab.cacheOptions || cacheOptions,
|
|
253
|
+
remoteOptions: tab.remoteOptions,
|
|
254
|
+
highlightOptions: highlightOptions,
|
|
255
|
+
terminalOptions: terminalOptions,
|
|
256
|
+
extraOptions: extraOptions,
|
|
257
|
+
onAddonReady: handleAddonReady,
|
|
258
|
+
onLoading: handleLoading
|
|
259
|
+
});
|
|
260
|
+
}
|
|
261
|
+
return null;
|
|
262
|
+
}).filter(Boolean), !Array.isArray(tabs) && /*#__PURE__*/React.createElement(ViewerBody, {
|
|
263
|
+
fit: fit,
|
|
264
|
+
empty: empty,
|
|
265
|
+
autoScroll: autoScroll,
|
|
266
|
+
scrollToRow: scrollToRow,
|
|
267
|
+
logAfter: logAfter,
|
|
268
|
+
webLinksSupport: webLinksSupport,
|
|
269
|
+
canvasSupport: canvasSupport,
|
|
270
|
+
ref: instanceRef,
|
|
271
|
+
defaultData: defaultData,
|
|
272
|
+
remoteOptions: remoteOptions,
|
|
273
|
+
cacheOptions: cacheOptions,
|
|
274
|
+
highlightOptions: highlightOptions,
|
|
275
|
+
terminalOptions: terminalOptions,
|
|
276
|
+
extraOptions: extraOptions,
|
|
277
|
+
onAddonReady: handleAddonReady,
|
|
278
|
+
onLoading: handleLoading
|
|
279
|
+
}), toolbar || /*#__PURE__*/React.createElement(TerminalViewerToolBar, {
|
|
280
|
+
icons: icons,
|
|
281
|
+
fullScreen: fullScreen,
|
|
282
|
+
showFullScreen: showFullScreen,
|
|
283
|
+
onScrollTop: handleScrollTop,
|
|
284
|
+
onScrollBottom: handleScrollBottom,
|
|
285
|
+
onFullScreen: handleFullScreen
|
|
286
|
+
}));
|
|
287
|
+
if (mountElement) {
|
|
288
|
+
return /*#__PURE__*/createPortal(render, mountElement);
|
|
289
|
+
}
|
|
290
|
+
return render;
|
|
291
|
+
});
|
|
292
|
+
export default TerminalViewer;
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
.terminal-viewer {
|
|
2
|
+
position: relative;
|
|
3
|
+
display: flex;
|
|
4
|
+
flex-direction: column;
|
|
5
|
+
width: 100%;
|
|
6
|
+
height: 100%;
|
|
7
|
+
overflow: hidden;
|
|
8
|
+
}
|
|
9
|
+
|
|
10
|
+
.terminal-viewer--fullscreen {
|
|
11
|
+
position: fixed;
|
|
12
|
+
top: 0;
|
|
13
|
+
left: 0;
|
|
14
|
+
z-index: 1800;
|
|
15
|
+
width: 100%;
|
|
16
|
+
height: 100%;
|
|
17
|
+
}
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { Terminal, ITerminalOptions } from 'xterm';
|
|
3
|
+
import 'xterm/css/xterm.css';
|
|
4
|
+
import { FitAddon } from 'xterm-addon-fit';
|
|
5
|
+
import { WebLinksAddon } from 'xterm-addon-web-links';
|
|
6
|
+
import { CanvasAddon } from 'xterm-addon-canvas';
|
|
7
|
+
import { SearchAddon } from '../Addon/SearchAddon';
|
|
8
|
+
import { HighlightAddon } from '../Addon/HighlightAddon';
|
|
9
|
+
import type { AddonType } from '../Addon/useAddon';
|
|
10
|
+
import type { IRemoteOptions } from '../Hooks/useRemote';
|
|
11
|
+
import type { ICacheOptions } from '../Hooks/useCache';
|
|
12
|
+
import type { IHighlightOptions } from '../Addon/HighlightAddon';
|
|
13
|
+
import { TerminalRef } from '../types';
|
|
14
|
+
import './index.less';
|
|
15
|
+
export interface TerminalExposedRef {
|
|
16
|
+
terminal?: Terminal | undefined;
|
|
17
|
+
addons?: {
|
|
18
|
+
search?: SearchAddon | undefined;
|
|
19
|
+
fit?: FitAddon | undefined;
|
|
20
|
+
webLinks?: WebLinksAddon | undefined;
|
|
21
|
+
highlight?: HighlightAddon | undefined;
|
|
22
|
+
canvas?: CanvasAddon | undefined;
|
|
23
|
+
};
|
|
24
|
+
refresh?: (() => void) | undefined;
|
|
25
|
+
}
|
|
26
|
+
export interface TerminalViewerBodyProps {
|
|
27
|
+
/**
|
|
28
|
+
* @description.zh-CN 是否自动拉伸填充容器宽高
|
|
29
|
+
* @default true
|
|
30
|
+
*/
|
|
31
|
+
fit?: boolean;
|
|
32
|
+
/**
|
|
33
|
+
*@description.zh-CN 是否开启自动滚动到底部
|
|
34
|
+
*@default true
|
|
35
|
+
*/
|
|
36
|
+
autoScroll?: boolean;
|
|
37
|
+
/**
|
|
38
|
+
* @description.zh-CN 外层样式类名
|
|
39
|
+
*/
|
|
40
|
+
className?: string;
|
|
41
|
+
/**
|
|
42
|
+
* @description.zh-CN 自定义空文本显示
|
|
43
|
+
*/
|
|
44
|
+
empty?: React.ReactNode;
|
|
45
|
+
/**
|
|
46
|
+
* @description.zh-CN 是否支持渲染超链接
|
|
47
|
+
* @default true
|
|
48
|
+
*/
|
|
49
|
+
webLinksSupport?: boolean;
|
|
50
|
+
/**
|
|
51
|
+
* @description.zh-CN 是否使用 canvas 渲染
|
|
52
|
+
* @default false
|
|
53
|
+
*/
|
|
54
|
+
canvasSupport?: boolean;
|
|
55
|
+
/**
|
|
56
|
+
* @description.zh-CN 远程搜索选配置
|
|
57
|
+
*
|
|
58
|
+
*/
|
|
59
|
+
remoteOptions?: IRemoteOptions;
|
|
60
|
+
/**
|
|
61
|
+
* @description.zh-CN 缓存配置,仅在配置远程加载后有效,如 `expires: 60 * 1000` 表示自动清理已过期一分钟的缓存
|
|
62
|
+
*/
|
|
63
|
+
cacheOptions?: ICacheOptions;
|
|
64
|
+
/**
|
|
65
|
+
* @description.zh-CN 高亮选项
|
|
66
|
+
*/
|
|
67
|
+
highlightOptions?: IHighlightOptions[];
|
|
68
|
+
/**
|
|
69
|
+
* @description.zh-CN xtem.js 配置, https://github.com/xtermjs/xterm.js
|
|
70
|
+
*/
|
|
71
|
+
terminalOptions?: ITerminalOptions;
|
|
72
|
+
/**
|
|
73
|
+
* @description.zh-CN 用于渲染日志的默认数据,如 "echo 1\r\necho2"
|
|
74
|
+
* @default '''
|
|
75
|
+
*/
|
|
76
|
+
defaultData?: string;
|
|
77
|
+
/**
|
|
78
|
+
* @description.zh-CN 插件加载成功后的回调
|
|
79
|
+
*/
|
|
80
|
+
onAddonReady?: (instance: Terminal, addon: AddonType) => void;
|
|
81
|
+
/**
|
|
82
|
+
* @description.zh-CN 加载状态变更后的回调
|
|
83
|
+
*/
|
|
84
|
+
onLoading?: (loading: boolean) => void;
|
|
85
|
+
}
|
|
86
|
+
declare const TerminalViewerBody: React.ForwardRefExoticComponent<TerminalViewerBodyProps & React.RefAttributes<TerminalRef | undefined>>;
|
|
87
|
+
export default TerminalViewerBody;
|