@deephaven/file-explorer 0.43.0 → 0.44.0

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.
Files changed (41) hide show
  1. package/dist/FileExistsError.js +14 -0
  2. package/dist/FileExistsError.js.map +1 -0
  3. package/dist/FileExplorer.css +26 -0
  4. package/dist/FileExplorer.css.map +1 -0
  5. package/dist/FileExplorer.js +153 -0
  6. package/dist/FileExplorer.js.map +1 -0
  7. package/dist/FileExplorerShortcuts.js +20 -0
  8. package/dist/FileExplorerShortcuts.js.map +1 -0
  9. package/dist/FileExplorerToolbar.css +37 -0
  10. package/dist/FileExplorerToolbar.css.map +1 -0
  11. package/dist/FileExplorerToolbar.js +37 -0
  12. package/dist/FileExplorerToolbar.js.map +1 -0
  13. package/dist/FileList.css +93 -0
  14. package/dist/FileList.css.map +1 -0
  15. package/dist/FileList.js +309 -0
  16. package/dist/FileList.js.map +1 -0
  17. package/dist/FileListContainer.js +167 -0
  18. package/dist/FileListContainer.js.map +1 -0
  19. package/dist/FileListItem.js +118 -0
  20. package/dist/FileListItem.js.map +1 -0
  21. package/dist/FileListItemEditor.css +33 -0
  22. package/dist/FileListItemEditor.css.map +1 -0
  23. package/dist/FileListItemEditor.js +92 -0
  24. package/dist/FileListItemEditor.js.map +1 -0
  25. package/dist/FileListUtils.js +34 -0
  26. package/dist/FileListUtils.js.map +1 -0
  27. package/dist/FileNotFoundError.js +11 -0
  28. package/dist/FileNotFoundError.js.map +1 -0
  29. package/dist/FileStorage.js +12 -0
  30. package/dist/FileStorage.js.map +1 -0
  31. package/dist/FileTestUtils.js +103 -0
  32. package/dist/FileTestUtils.js.map +1 -0
  33. package/dist/FileUtils.js +243 -0
  34. package/dist/FileUtils.js.map +1 -0
  35. package/dist/NewItemModal.css +17 -0
  36. package/dist/NewItemModal.css.map +1 -0
  37. package/dist/NewItemModal.js +467 -0
  38. package/dist/NewItemModal.js.map +1 -0
  39. package/dist/index.js +15 -0
  40. package/dist/index.js.map +1 -0
  41. package/package.json +8 -8
@@ -0,0 +1,467 @@
1
+ function asyncGeneratorStep(gen, resolve, reject, _next, _throw, key, arg) { try { var info = gen[key](arg); var value = info.value; } catch (error) { reject(error); return; } if (info.done) { resolve(value); } else { Promise.resolve(value).then(_next, _throw); } }
2
+ function _asyncToGenerator(fn) { return function () { var self = this, args = arguments; return new Promise(function (resolve, reject) { var gen = fn.apply(self, args); function _next(value) { asyncGeneratorStep(gen, resolve, reject, _next, _throw, "next", value); } function _throw(err) { asyncGeneratorStep(gen, resolve, reject, _next, _throw, "throw", err); } _next(undefined); }); }; }
3
+ 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; }
4
+ function _toPropertyKey(arg) { var key = _toPrimitive(arg, "string"); return typeof key === "symbol" ? key : String(key); }
5
+ function _toPrimitive(input, hint) { if (typeof input !== "object" || input === null) return input; var prim = input[Symbol.toPrimitive]; if (prim !== undefined) { var res = prim.call(input, hint || "default"); if (typeof res !== "object") return res; throw new TypeError("@@toPrimitive must return a primitive value."); } return (hint === "string" ? String : Number)(input); }
6
+ import React, { PureComponent } from 'react';
7
+ import PropTypes from 'prop-types';
8
+ import classNames from 'classnames';
9
+ import { Modal, ModalBody, ModalFooter, ModalHeader, BasicModal, Button } from '@deephaven/components';
10
+ import { Pending, PromiseUtils, ValidationError } from '@deephaven/utils';
11
+ import Log from '@deephaven/log';
12
+ import { vsHome } from '@deephaven/icons';
13
+ import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
14
+ import FileExplorer from "./FileExplorer.js";
15
+ import FileUtils from "./FileUtils.js";
16
+ import "./NewItemModal.css";
17
+ import FileExistsError from "./FileExistsError.js";
18
+ import FileNotFoundError from "./FileNotFoundError.js";
19
+ var log = Log.module('NewItemModal');
20
+ class NewItemModal extends PureComponent {
21
+ static getValidationMessage(err) {
22
+ if (err instanceof FileExistsError && err.info.type === 'directory') {
23
+ return 'Error: Cannot overwrite existing directory';
24
+ }
25
+ return "".concat(err);
26
+ }
27
+ static handleError(err) {
28
+ if (!PromiseUtils.isCanceled(err)) {
29
+ log.error(err);
30
+ }
31
+ }
32
+ constructor(props) {
33
+ super(props);
34
+ _defineProperty(this, "inputRef", /*#__PURE__*/React.createRef());
35
+ _defineProperty(this, "cancelableValidatePromise", void 0);
36
+ _defineProperty(this, "cancelableExistingItemPromise", void 0);
37
+ _defineProperty(this, "pending", new Pending());
38
+ _defineProperty(this, "pathMap", new Map());
39
+ _defineProperty(this, "isInitialLoad", true);
40
+ this.handleModalSubmit = this.handleModalSubmit.bind(this);
41
+ this.handleModalOpened = this.handleModalOpened.bind(this);
42
+ this.handleSelect = this.handleSelect.bind(this);
43
+ this.handleChange = this.handleChange.bind(this);
44
+ this.handleKeyDown = this.handleKeyDown.bind(this);
45
+ this.handleValidationError = this.handleValidationError.bind(this);
46
+ this.handleOverwriteCancel = this.handleOverwriteCancel.bind(this);
47
+ this.handleOverwriteConfirm = this.handleOverwriteConfirm.bind(this);
48
+ this.handleExtensionChangeCancel = this.handleExtensionChangeCancel.bind(this);
49
+ this.handleExtensionChangeConfirm = this.handleExtensionChangeConfirm.bind(this);
50
+ this.handleBreadcrumbSelect = this.handleBreadcrumbSelect.bind(this);
51
+ var {
52
+ defaultValue
53
+ } = props;
54
+ var path = FileUtils.hasPath(defaultValue) ? FileUtils.getPath(defaultValue) : '/';
55
+ this.state = {
56
+ isSubmitting: false,
57
+ path,
58
+ prevExtension: FileUtils.getExtension(defaultValue),
59
+ showExtensionChangeModal: false,
60
+ showOverwriteModal: false,
61
+ value: FileUtils.getBaseName(defaultValue)
62
+ };
63
+ }
64
+ componentDidUpdate(prevProps, prevState) {
65
+ var {
66
+ isOpen
67
+ } = this.props;
68
+ var {
69
+ isOpen: prevIsOpen
70
+ } = prevProps;
71
+ var {
72
+ value,
73
+ path
74
+ } = this.state;
75
+ if (!prevIsOpen && isOpen) {
76
+ this.resetValue();
77
+ this.isInitialLoad = true;
78
+ }
79
+ if (prevIsOpen && isOpen) {
80
+ if (!this.isInitialLoad && (path !== prevState.path || value !== prevState.value)) {
81
+ this.updateValidationStatus(path, value);
82
+ }
83
+ this.isInitialLoad = false;
84
+ }
85
+ }
86
+ componentWillUnmount() {
87
+ this.pending.cancel();
88
+ if (this.cancelableValidatePromise) {
89
+ this.cancelableValidatePromise.cancel();
90
+ }
91
+ if (this.cancelableExistingItemPromise) {
92
+ this.cancelableExistingItemPromise.cancel();
93
+ }
94
+ }
95
+ resetValue() {
96
+ var {
97
+ defaultValue
98
+ } = this.props;
99
+ var path = FileUtils.hasPath(defaultValue) ? FileUtils.getPath(defaultValue) : '/';
100
+ this.setState({
101
+ path,
102
+ value: FileUtils.getBaseName(defaultValue),
103
+ validationError: undefined,
104
+ prevExtension: FileUtils.getExtension(defaultValue),
105
+ isSubmitting: false
106
+ });
107
+ }
108
+ getValidationPromise(path, name) {
109
+ var checkExisting = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : false;
110
+ if (this.cancelableValidatePromise) {
111
+ this.cancelableValidatePromise.cancel();
112
+ }
113
+ this.cancelableValidatePromise = PromiseUtils.makeCancelable(this.validateName(path, name, checkExisting));
114
+ return this.cancelableValidatePromise;
115
+ }
116
+ validateName(path, name, checkExisting) {
117
+ var _this = this;
118
+ return _asyncToGenerator(function* () {
119
+ FileUtils.validateName(name);
120
+ var {
121
+ defaultValue,
122
+ storage
123
+ } = _this.props;
124
+ if (checkExisting) {
125
+ var value = "".concat(path).concat(name);
126
+ if (value !== defaultValue) {
127
+ try {
128
+ var existingFile = yield storage.info(value);
129
+ throw new FileExistsError(existingFile);
130
+ } catch (e) {
131
+ if (!(e instanceof FileNotFoundError)) {
132
+ throw e;
133
+ }
134
+ // There is no existing file, ignore
135
+ }
136
+ }
137
+ }
138
+
139
+ return name;
140
+ })();
141
+ }
142
+ updateValidationStatus(path, newName) {
143
+ this.getValidationPromise(path, newName).then(() => {
144
+ this.setState({
145
+ validationError: undefined
146
+ });
147
+ }).catch(this.handleValidationError).catch(NewItemModal.handleError);
148
+ }
149
+ handleModalOpened() {
150
+ this.focusRenameInput();
151
+ }
152
+ handleModalSubmit() {
153
+ this.submitModal();
154
+ }
155
+ handleChange(event) {
156
+ var {
157
+ value
158
+ } = event.target;
159
+ this.setState({
160
+ value
161
+ });
162
+ }
163
+ handleSelect(item) {
164
+ log.debug('handleSelect', item);
165
+ if (item.type === 'directory') {
166
+ this.setState({
167
+ path: FileUtils.makePath(item.filename)
168
+ });
169
+ } else {
170
+ // Use selected item name and folder and focus the input
171
+ var value = item.basename;
172
+ var path = FileUtils.getPath(item.filename);
173
+ this.setState({
174
+ value,
175
+ path
176
+ }, () => {
177
+ this.focusRenameInput();
178
+ });
179
+ }
180
+ }
181
+
182
+ // eslint-disable-next-line class-methods-use-this
183
+ handleKeyDown(e) {
184
+ var {
185
+ key
186
+ } = e;
187
+ e.stopPropagation();
188
+ switch (key) {
189
+ case 'Enter':
190
+ {
191
+ // Prevent form submit event
192
+ e.preventDefault();
193
+ this.submitModal();
194
+ break;
195
+ }
196
+ case 'Escape':
197
+ {
198
+ e.preventDefault();
199
+ var {
200
+ onCancel
201
+ } = this.props;
202
+ onCancel();
203
+ break;
204
+ }
205
+ default:
206
+ }
207
+ }
208
+ handleValidationError(err) {
209
+ if (!(err instanceof ValidationError)) {
210
+ throw err;
211
+ }
212
+ log.debug('Validation error', err);
213
+ this.setState({
214
+ validationError: err
215
+ });
216
+ }
217
+ handleOverwriteCancel() {
218
+ this.setState({
219
+ showOverwriteModal: false,
220
+ isSubmitting: false
221
+ });
222
+ }
223
+ handleOverwriteConfirm() {
224
+ this.setState({
225
+ showOverwriteModal: false
226
+ });
227
+ var {
228
+ onSubmit
229
+ } = this.props;
230
+ var {
231
+ path,
232
+ value
233
+ } = this.state;
234
+ log.debug('handleOverwriteConfirm', path, value);
235
+ onSubmit("".concat(path).concat(value), true);
236
+ }
237
+ handleExtensionChangeCancel() {
238
+ log.debug('handleExtensionChangeCancel');
239
+ this.setState(_ref => {
240
+ var {
241
+ value,
242
+ prevExtension
243
+ } = _ref;
244
+ var newValue = FileUtils.replaceExtension(value, prevExtension);
245
+ return {
246
+ showExtensionChangeModal: false,
247
+ value: newValue
248
+ };
249
+ });
250
+ this.submitModal(true);
251
+ }
252
+ handleExtensionChangeConfirm() {
253
+ log.debug('handleExtensionChangeConfirm');
254
+ this.setState({
255
+ showExtensionChangeModal: false
256
+ });
257
+ this.submitModal(true);
258
+ }
259
+
260
+ /**
261
+ * Focus rename input and select name part for files, select all text for folders
262
+ */
263
+ focusRenameInput() {
264
+ var input = this.inputRef.current;
265
+ if (input) {
266
+ var {
267
+ type
268
+ } = this.props;
269
+ var {
270
+ value
271
+ } = input;
272
+ var selectionEnd = type === 'directory' ? value.length : value.lastIndexOf('.');
273
+ input.focus();
274
+ input.setSelectionRange(0, selectionEnd > 0 ? selectionEnd : value.length);
275
+ }
276
+ }
277
+ submitModal() {
278
+ var skipExtensionCheck = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : false;
279
+ this.setState(_ref2 => {
280
+ var {
281
+ prevExtension,
282
+ value,
283
+ path
284
+ } = _ref2;
285
+ var {
286
+ notifyOnExtensionChange,
287
+ type
288
+ } = this.props;
289
+ log.debug('submitModal', prevExtension, value);
290
+ var newExtension = FileUtils.getExtension(value);
291
+ if (notifyOnExtensionChange && !skipExtensionCheck && prevExtension !== null && prevExtension !== newExtension) {
292
+ return {
293
+ isSubmitting: false,
294
+ showExtensionChangeModal: true,
295
+ newExtension
296
+ };
297
+ }
298
+ this.getValidationPromise(path, value, true).then(newItemName => {
299
+ var {
300
+ onSubmit
301
+ } = this.props;
302
+ onSubmit("".concat(path).concat(value));
303
+ }).catch(e => {
304
+ // Don't allow using existing names for folders
305
+ // For files, prompt if they want to overwrite existing file
306
+ if (e instanceof FileExistsError) {
307
+ if (type !== 'directory' && e.info.type !== 'directory') {
308
+ this.setState({
309
+ showOverwriteModal: true
310
+ });
311
+ return;
312
+ }
313
+ }
314
+ throw e;
315
+ }).catch(e => {
316
+ if (PromiseUtils.isCanceled(e)) {
317
+ this.setState({
318
+ isSubmitting: false
319
+ });
320
+ }
321
+ throw e;
322
+ }).catch(this.handleValidationError).catch(NewItemModal.handleError);
323
+ return {
324
+ isSubmitting: true,
325
+ showExtensionChangeModal: false,
326
+ newExtension: undefined
327
+ };
328
+ });
329
+ }
330
+ handleBreadcrumbSelect(directoryPath) {
331
+ this.setState({
332
+ path: directoryPath
333
+ });
334
+ }
335
+ renderPathButtons(path) {
336
+ var pathAsList = path.split('/');
337
+ pathAsList.pop();
338
+ return pathAsList.map((basename, index) => {
339
+ var directoryPath = '';
340
+ for (var i = 0; i < index; i += 1) {
341
+ directoryPath += "".concat(pathAsList[i], "/");
342
+ }
343
+ directoryPath += "".concat(basename, "/");
344
+ return /*#__PURE__*/React.createElement(React.Fragment, {
345
+ key: directoryPath
346
+ }, /*#__PURE__*/React.createElement(Button, {
347
+ kind: "ghost",
348
+ className: "directory-breadcrumbs",
349
+ onClick: () => this.handleBreadcrumbSelect(directoryPath),
350
+ "aria-label": index === 0 ? 'Home' : undefined,
351
+ icon: index === 0 ? /*#__PURE__*/React.createElement(FontAwesomeIcon, {
352
+ icon: vsHome,
353
+ transform: "right-1.6"
354
+ }) : undefined,
355
+ tooltip: index === 0 ? 'Home' : undefined
356
+ }, basename), "/");
357
+ });
358
+ }
359
+ render() {
360
+ var {
361
+ storage,
362
+ isOpen,
363
+ onCancel,
364
+ placeholder,
365
+ title,
366
+ type
367
+ } = this.props;
368
+ var {
369
+ isSubmitting,
370
+ path,
371
+ showExtensionChangeModal,
372
+ showOverwriteModal,
373
+ validationError,
374
+ value,
375
+ prevExtension,
376
+ newExtension
377
+ } = this.state;
378
+ var isDirectory = type === 'directory';
379
+ var prevExtensionText = FileUtils.fileExtensionToString(prevExtension);
380
+ var newExtensionText = FileUtils.fileExtensionToString(newExtension);
381
+ var submitBtnLabel = isDirectory ? 'Create' : 'Save';
382
+ var nameInputLabel = isDirectory ? 'New folder name' : 'Save file as';
383
+ return /*#__PURE__*/React.createElement(React.Fragment, null, /*#__PURE__*/React.createElement(Modal, {
384
+ isOpen: isOpen,
385
+ toggle: onCancel,
386
+ onOpened: this.handleModalOpened,
387
+ className: "modal-dialog-centered new-file-modal theme-bg-dark"
388
+ }, /*#__PURE__*/React.createElement(ModalHeader, {
389
+ toggle: onCancel
390
+ }, title), /*#__PURE__*/React.createElement(ModalBody, null, /*#__PURE__*/React.createElement("form", null, /*#__PURE__*/React.createElement("div", {
391
+ className: "d-flex flex-column new-file-modal-content"
392
+ }, /*#__PURE__*/React.createElement("div", {
393
+ className: "flex-grow-0 mb-4"
394
+ }, /*#__PURE__*/React.createElement("label", {
395
+ htmlFor: "file-name-input"
396
+ }, nameInputLabel), /*#__PURE__*/React.createElement("input", {
397
+ id: "file-name-input",
398
+ type: "text",
399
+ autoComplete: "off",
400
+ autoCapitalize: "none",
401
+ autoCorrect: "off",
402
+ spellCheck: "false",
403
+ className: classNames('form-control', {
404
+ 'is-invalid': validationError
405
+ }),
406
+ value: value,
407
+ placeholder: placeholder,
408
+ ref: this.inputRef,
409
+ onKeyDown: this.handleKeyDown,
410
+ onChange: this.handleChange
411
+ }), validationError && /*#__PURE__*/React.createElement("div", {
412
+ className: "invalid-feedback"
413
+ }, NewItemModal.getValidationMessage(validationError))), /*#__PURE__*/React.createElement("div", {
414
+ className: "flex-grow-0"
415
+ }, /*#__PURE__*/React.createElement("label", null, "Directory: /"), this.renderPathButtons(path)), /*#__PURE__*/React.createElement("div", {
416
+ className: "flex-grow-1 file-explorer-container"
417
+ }, /*#__PURE__*/React.createElement(FileExplorer, {
418
+ onSelect: this.handleSelect,
419
+ storage: storage,
420
+ focusedPath: path
421
+ }))))), /*#__PURE__*/React.createElement(ModalFooter, null, /*#__PURE__*/React.createElement(Button, {
422
+ kind: "secondary",
423
+ onClick: onCancel
424
+ }, "Cancel"), /*#__PURE__*/React.createElement(Button, {
425
+ kind: "primary",
426
+ disabled: isSubmitting,
427
+ onClick: this.handleModalSubmit
428
+ }, submitBtnLabel))), /*#__PURE__*/React.createElement(BasicModal, {
429
+ isOpen: showOverwriteModal,
430
+ headerText: "Confirm overwrite",
431
+ bodyText: "File with this name already exists, are you sure you want to overwrite it?",
432
+ onCancel: this.handleOverwriteCancel,
433
+ onConfirm: this.handleOverwriteConfirm,
434
+ cancelButtonText: "Cancel",
435
+ confirmButtonText: "Overwrite"
436
+ }), /*#__PURE__*/React.createElement(BasicModal, {
437
+ isOpen: showExtensionChangeModal,
438
+ headerText: "Confirm extension change",
439
+ bodyText: "Are you sure you want to change extension from \"".concat(prevExtensionText, "\" to \"").concat(newExtensionText, "\"?"),
440
+ onCancel: this.handleExtensionChangeCancel,
441
+ onConfirm: this.handleExtensionChangeConfirm,
442
+ cancelButtonText: "Keep \"".concat(prevExtensionText, "\""),
443
+ confirmButtonText: "Use \"".concat(newExtensionText, "\"")
444
+ }));
445
+ }
446
+ }
447
+ _defineProperty(NewItemModal, "propTypes", {
448
+ isOpen: PropTypes.bool,
449
+ title: PropTypes.string.isRequired,
450
+ defaultValue: PropTypes.string,
451
+ type: PropTypes.oneOf(['file', 'directory']).isRequired,
452
+ onSubmit: PropTypes.func,
453
+ onCancel: PropTypes.func,
454
+ placeholder: PropTypes.string,
455
+ storage: PropTypes.shape({}).isRequired,
456
+ notifyOnExtensionChange: PropTypes.bool
457
+ });
458
+ _defineProperty(NewItemModal, "defaultProps", {
459
+ isOpen: false,
460
+ defaultValue: '/',
461
+ notifyOnExtensionChange: false,
462
+ placeholder: '',
463
+ onSubmit: (name, isOverwrite) => undefined,
464
+ onCancel: () => undefined
465
+ });
466
+ export default NewItemModal;
467
+ //# sourceMappingURL=NewItemModal.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"NewItemModal.js","names":["React","PureComponent","PropTypes","classNames","Modal","ModalBody","ModalFooter","ModalHeader","BasicModal","Button","Pending","PromiseUtils","ValidationError","Log","vsHome","FontAwesomeIcon","FileExplorer","FileUtils","FileExistsError","FileNotFoundError","log","module","NewItemModal","getValidationMessage","err","info","type","handleError","isCanceled","error","constructor","props","createRef","Map","handleModalSubmit","bind","handleModalOpened","handleSelect","handleChange","handleKeyDown","handleValidationError","handleOverwriteCancel","handleOverwriteConfirm","handleExtensionChangeCancel","handleExtensionChangeConfirm","handleBreadcrumbSelect","defaultValue","path","hasPath","getPath","state","isSubmitting","prevExtension","getExtension","showExtensionChangeModal","showOverwriteModal","value","getBaseName","componentDidUpdate","prevProps","prevState","isOpen","prevIsOpen","resetValue","isInitialLoad","updateValidationStatus","componentWillUnmount","pending","cancel","cancelableValidatePromise","cancelableExistingItemPromise","setState","validationError","undefined","getValidationPromise","name","checkExisting","makeCancelable","validateName","storage","existingFile","e","newName","then","catch","focusRenameInput","submitModal","event","target","item","debug","makePath","filename","basename","key","stopPropagation","preventDefault","onCancel","onSubmit","newValue","replaceExtension","input","inputRef","current","selectionEnd","length","lastIndexOf","focus","setSelectionRange","skipExtensionCheck","notifyOnExtensionChange","newExtension","newItemName","directoryPath","renderPathButtons","pathAsList","split","pop","map","index","i","render","placeholder","title","isDirectory","prevExtensionText","fileExtensionToString","newExtensionText","submitBtnLabel","nameInputLabel","bool","string","isRequired","oneOf","func","shape","isOverwrite"],"sources":["../src/NewItemModal.tsx"],"sourcesContent":["import React, { ChangeEvent, KeyboardEvent, PureComponent } from 'react';\nimport PropTypes from 'prop-types';\nimport classNames from 'classnames';\nimport {\n Modal,\n ModalBody,\n ModalFooter,\n ModalHeader,\n BasicModal,\n Button,\n} from '@deephaven/components';\nimport {\n CancelablePromise,\n Pending,\n PromiseUtils,\n ValidationError,\n} from '@deephaven/utils';\nimport Log from '@deephaven/log';\nimport { vsHome } from '@deephaven/icons';\nimport { FontAwesomeIcon } from '@fortawesome/react-fontawesome';\nimport FileExplorer from './FileExplorer';\nimport FileStorage, { FileStorageItem, FileType } from './FileStorage';\nimport FileUtils from './FileUtils';\n\nimport './NewItemModal.scss';\nimport FileExistsError from './FileExistsError';\nimport FileNotFoundError from './FileNotFoundError';\n\nconst log = Log.module('NewItemModal');\n\nexport type NewItemModalProps = typeof NewItemModal.defaultProps & {\n isOpen: boolean;\n title: string;\n defaultValue: string;\n type: FileType;\n onSubmit: (name: string, isOverwrite?: boolean) => void;\n onCancel: () => void;\n placeholder: string;\n storage: FileStorage;\n notifyOnExtensionChange?: boolean;\n};\n\nexport type NewItemModalState = {\n path: string;\n isSubmitting: boolean;\n showExtensionChangeModal: boolean;\n showOverwriteModal: boolean;\n validationError?: ValidationError;\n value: string;\n prevExtension?: string;\n newExtension?: string;\n};\n\nclass NewItemModal extends PureComponent<NewItemModalProps, NewItemModalState> {\n static propTypes = {\n isOpen: PropTypes.bool,\n title: PropTypes.string.isRequired,\n defaultValue: PropTypes.string,\n type: PropTypes.oneOf(['file', 'directory']).isRequired,\n onSubmit: PropTypes.func,\n onCancel: PropTypes.func,\n placeholder: PropTypes.string,\n storage: PropTypes.shape({}).isRequired,\n notifyOnExtensionChange: PropTypes.bool,\n };\n\n static defaultProps = {\n isOpen: false,\n defaultValue: '/',\n notifyOnExtensionChange: false,\n placeholder: '',\n onSubmit: (name: string, isOverwrite?: boolean): void => undefined,\n onCancel: (): void => undefined,\n };\n\n static getValidationMessage(err: Error): string {\n if (err instanceof FileExistsError && err.info.type === 'directory') {\n return 'Error: Cannot overwrite existing directory';\n }\n return `${err}`;\n }\n\n static handleError(err: Error): void {\n if (!PromiseUtils.isCanceled(err)) {\n log.error(err);\n }\n }\n\n constructor(props: NewItemModalProps) {\n super(props);\n this.handleModalSubmit = this.handleModalSubmit.bind(this);\n this.handleModalOpened = this.handleModalOpened.bind(this);\n this.handleSelect = this.handleSelect.bind(this);\n this.handleChange = this.handleChange.bind(this);\n this.handleKeyDown = this.handleKeyDown.bind(this);\n this.handleValidationError = this.handleValidationError.bind(this);\n this.handleOverwriteCancel = this.handleOverwriteCancel.bind(this);\n this.handleOverwriteConfirm = this.handleOverwriteConfirm.bind(this);\n this.handleExtensionChangeCancel = this.handleExtensionChangeCancel.bind(\n this\n );\n this.handleExtensionChangeConfirm = this.handleExtensionChangeConfirm.bind(\n this\n );\n this.handleBreadcrumbSelect = this.handleBreadcrumbSelect.bind(this);\n\n const { defaultValue } = props;\n\n const path = FileUtils.hasPath(defaultValue)\n ? FileUtils.getPath(defaultValue)\n : '/';\n\n this.state = {\n isSubmitting: false,\n path,\n prevExtension: FileUtils.getExtension(defaultValue),\n showExtensionChangeModal: false,\n showOverwriteModal: false,\n value: FileUtils.getBaseName(defaultValue),\n };\n }\n\n componentDidUpdate(\n prevProps: NewItemModalProps,\n prevState: NewItemModalState\n ): void {\n const { isOpen } = this.props;\n const { isOpen: prevIsOpen } = prevProps;\n const { value, path } = this.state;\n if (!prevIsOpen && isOpen) {\n this.resetValue();\n this.isInitialLoad = true;\n }\n\n if (prevIsOpen && isOpen) {\n if (\n !this.isInitialLoad &&\n (path !== prevState.path || value !== prevState.value)\n ) {\n this.updateValidationStatus(path, value);\n }\n this.isInitialLoad = false;\n }\n }\n\n componentWillUnmount(): void {\n this.pending.cancel();\n if (this.cancelableValidatePromise) {\n this.cancelableValidatePromise.cancel();\n }\n if (this.cancelableExistingItemPromise) {\n this.cancelableExistingItemPromise.cancel();\n }\n }\n\n private inputRef = React.createRef<HTMLInputElement>();\n\n private cancelableValidatePromise?: CancelablePromise<string>;\n\n private cancelableExistingItemPromise?: CancelablePromise<FileStorageItem | null>;\n\n private pending = new Pending();\n\n private pathMap = new Map();\n\n private isInitialLoad = true;\n\n resetValue(): void {\n const { defaultValue } = this.props as NewItemModalProps;\n const path = FileUtils.hasPath(defaultValue)\n ? FileUtils.getPath(defaultValue)\n : '/';\n this.setState({\n path,\n value: FileUtils.getBaseName(defaultValue),\n validationError: undefined,\n prevExtension: FileUtils.getExtension(defaultValue),\n isSubmitting: false,\n });\n }\n\n getValidationPromise(\n path: string,\n name: string,\n checkExisting = false\n ): CancelablePromise<string> {\n if (this.cancelableValidatePromise) {\n this.cancelableValidatePromise.cancel();\n }\n this.cancelableValidatePromise = PromiseUtils.makeCancelable(\n this.validateName(path, name, checkExisting)\n );\n return this.cancelableValidatePromise;\n }\n\n async validateName(\n path: string,\n name: string,\n checkExisting: boolean\n ): Promise<string> {\n FileUtils.validateName(name);\n\n const { defaultValue, storage } = this.props;\n if (checkExisting) {\n const value = `${path}${name}`;\n if (value !== defaultValue) {\n try {\n const existingFile = await storage.info(value);\n throw new FileExistsError(existingFile);\n } catch (e) {\n if (!(e instanceof FileNotFoundError)) {\n throw e;\n }\n // There is no existing file, ignore\n }\n }\n }\n\n return name;\n }\n\n updateValidationStatus(path: string, newName: string): void {\n this.getValidationPromise(path, newName)\n .then(() => {\n this.setState({ validationError: undefined });\n })\n .catch(this.handleValidationError)\n .catch(NewItemModal.handleError);\n }\n\n handleModalOpened(): void {\n this.focusRenameInput();\n }\n\n handleModalSubmit(): void {\n this.submitModal();\n }\n\n handleChange(event: ChangeEvent<HTMLInputElement>): void {\n const { value } = event.target;\n this.setState({ value });\n }\n\n handleSelect(item: FileStorageItem): void {\n log.debug('handleSelect', item);\n if (item.type === 'directory') {\n this.setState({ path: FileUtils.makePath(item.filename) });\n } else {\n // Use selected item name and folder and focus the input\n const value = item.basename;\n const path = FileUtils.getPath(item.filename);\n this.setState({ value, path }, () => {\n this.focusRenameInput();\n });\n }\n }\n\n // eslint-disable-next-line class-methods-use-this\n handleKeyDown(e: KeyboardEvent): void {\n const { key } = e;\n e.stopPropagation();\n\n switch (key) {\n case 'Enter': {\n // Prevent form submit event\n e.preventDefault();\n this.submitModal();\n break;\n }\n case 'Escape': {\n e.preventDefault();\n const { onCancel } = this.props;\n onCancel();\n break;\n }\n default:\n }\n }\n\n handleValidationError(err: Error): void {\n if (!(err instanceof ValidationError)) {\n throw err;\n }\n log.debug('Validation error', err);\n this.setState({ validationError: err });\n }\n\n handleOverwriteCancel(): void {\n this.setState({\n showOverwriteModal: false,\n isSubmitting: false,\n });\n }\n\n handleOverwriteConfirm(): void {\n this.setState({ showOverwriteModal: false });\n const { onSubmit } = this.props;\n const { path, value } = this.state;\n log.debug('handleOverwriteConfirm', path, value);\n\n onSubmit(`${path}${value}`, true);\n }\n\n handleExtensionChangeCancel(): void {\n log.debug('handleExtensionChangeCancel');\n this.setState(({ value, prevExtension }) => {\n const newValue = FileUtils.replaceExtension(value, prevExtension);\n return {\n showExtensionChangeModal: false,\n value: newValue,\n };\n });\n\n this.submitModal(true);\n }\n\n handleExtensionChangeConfirm(): void {\n log.debug('handleExtensionChangeConfirm');\n this.setState({ showExtensionChangeModal: false });\n this.submitModal(true);\n }\n\n /**\n * Focus rename input and select name part for files, select all text for folders\n */\n focusRenameInput(): void {\n const input = this.inputRef.current;\n if (input) {\n const { type } = this.props;\n const { value } = input;\n const selectionEnd =\n type === 'directory' ? value.length : value.lastIndexOf('.');\n input.focus();\n input.setSelectionRange(\n 0,\n selectionEnd > 0 ? selectionEnd : value.length\n );\n }\n }\n\n submitModal(skipExtensionCheck = false): void {\n this.setState(({ prevExtension, value, path }) => {\n const { notifyOnExtensionChange, type } = this.props;\n log.debug('submitModal', prevExtension, value);\n const newExtension = FileUtils.getExtension(value);\n if (\n notifyOnExtensionChange &&\n !skipExtensionCheck &&\n prevExtension !== null &&\n prevExtension !== newExtension\n ) {\n return {\n isSubmitting: false,\n showExtensionChangeModal: true,\n newExtension,\n };\n }\n\n this.getValidationPromise(path, value, true)\n .then((newItemName: string) => {\n const { onSubmit } = this.props;\n onSubmit(`${path}${value}`);\n })\n .catch(e => {\n // Don't allow using existing names for folders\n // For files, prompt if they want to overwrite existing file\n if (e instanceof FileExistsError) {\n if (type !== 'directory' && e.info.type !== 'directory') {\n this.setState({ showOverwriteModal: true });\n return;\n }\n }\n throw e;\n })\n .catch(e => {\n if (PromiseUtils.isCanceled(e)) {\n this.setState({ isSubmitting: false });\n }\n throw e;\n })\n .catch(this.handleValidationError)\n .catch(NewItemModal.handleError);\n\n return {\n isSubmitting: true,\n showExtensionChangeModal: false,\n newExtension: undefined,\n };\n });\n }\n\n handleBreadcrumbSelect(directoryPath: string): void {\n this.setState({ path: directoryPath });\n }\n\n renderPathButtons(path: string): React.ReactNode {\n const pathAsList = path.split('/');\n pathAsList.pop();\n return pathAsList.map((basename, index) => {\n let directoryPath = '';\n for (let i = 0; i < index; i += 1) {\n directoryPath += `${pathAsList[i]}/`;\n }\n directoryPath += `${basename}/`;\n\n return (\n <React.Fragment key={directoryPath}>\n <Button\n kind=\"ghost\"\n className=\"directory-breadcrumbs\"\n onClick={() => this.handleBreadcrumbSelect(directoryPath)}\n aria-label={index === 0 ? 'Home' : undefined}\n icon={\n index === 0 ? (\n <FontAwesomeIcon icon={vsHome} transform=\"right-1.6\" />\n ) : undefined\n }\n tooltip={index === 0 ? 'Home' : undefined}\n >\n {basename}\n </Button>\n /\n </React.Fragment>\n );\n });\n }\n\n render(): React.ReactNode {\n const { storage, isOpen, onCancel, placeholder, title, type } = this.props;\n const {\n isSubmitting,\n path,\n showExtensionChangeModal,\n showOverwriteModal,\n validationError,\n value,\n prevExtension,\n newExtension,\n } = this.state;\n\n const isDirectory = type === 'directory';\n const prevExtensionText = FileUtils.fileExtensionToString(prevExtension);\n const newExtensionText = FileUtils.fileExtensionToString(newExtension);\n const submitBtnLabel = isDirectory ? 'Create' : 'Save';\n const nameInputLabel = isDirectory ? 'New folder name' : 'Save file as';\n\n return (\n <>\n <Modal\n isOpen={isOpen}\n toggle={onCancel}\n onOpened={this.handleModalOpened}\n className=\"modal-dialog-centered new-file-modal theme-bg-dark\"\n >\n <ModalHeader toggle={onCancel}>{title}</ModalHeader>\n <ModalBody>\n <form>\n <div className=\"d-flex flex-column new-file-modal-content\">\n <div className=\"flex-grow-0 mb-4\">\n <label htmlFor=\"file-name-input\">{nameInputLabel}</label>\n <input\n id=\"file-name-input\"\n type=\"text\"\n autoComplete=\"off\"\n autoCapitalize=\"none\"\n autoCorrect=\"off\"\n spellCheck=\"false\"\n className={classNames('form-control', {\n 'is-invalid': validationError,\n })}\n value={value}\n placeholder={placeholder}\n ref={this.inputRef}\n onKeyDown={this.handleKeyDown}\n onChange={this.handleChange}\n />\n {validationError && (\n <div className=\"invalid-feedback\">\n {NewItemModal.getValidationMessage(validationError)}\n </div>\n )}\n </div>\n <div className=\"flex-grow-0\">\n <label>Directory: /</label>\n {this.renderPathButtons(path)}\n </div>\n <div className=\"flex-grow-1 file-explorer-container\">\n <FileExplorer\n onSelect={this.handleSelect}\n storage={storage}\n focusedPath={path}\n />\n </div>\n </div>\n </form>\n </ModalBody>\n\n <ModalFooter>\n <Button kind=\"secondary\" onClick={onCancel}>\n Cancel\n </Button>\n <Button\n kind=\"primary\"\n disabled={isSubmitting}\n onClick={this.handleModalSubmit}\n >\n {submitBtnLabel}\n </Button>\n </ModalFooter>\n </Modal>\n <BasicModal\n isOpen={showOverwriteModal}\n headerText=\"Confirm overwrite\"\n bodyText=\"File with this name already exists, are you sure you want to overwrite it?\"\n onCancel={this.handleOverwriteCancel}\n onConfirm={this.handleOverwriteConfirm}\n cancelButtonText=\"Cancel\"\n confirmButtonText=\"Overwrite\"\n />\n <BasicModal\n isOpen={showExtensionChangeModal}\n headerText=\"Confirm extension change\"\n bodyText={`Are you sure you want to change extension from \"${prevExtensionText}\" to \"${newExtensionText}\"?`}\n onCancel={this.handleExtensionChangeCancel}\n onConfirm={this.handleExtensionChangeConfirm}\n cancelButtonText={`Keep \"${prevExtensionText}\"`}\n confirmButtonText={`Use \"${newExtensionText}\"`}\n />\n </>\n );\n }\n}\n\nexport default NewItemModal;\n"],"mappings":"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"}
package/dist/index.js ADDED
@@ -0,0 +1,15 @@
1
+ import FileExplorer from "./FileExplorer.js";
2
+ export * from "./FileExplorer.js";
3
+ export * from "./FileListContainer.js";
4
+ export * from "./FileList.js";
5
+ export * from "./FileListItem.js";
6
+ export * from "./FileListUtils.js";
7
+ export * from "./FileStorage.js";
8
+ export { default as FileExistsError } from "./FileExistsError.js";
9
+ export { default as FileNotFoundError } from "./FileNotFoundError.js";
10
+ export { default as SHORTCUTS } from "./FileExplorerShortcuts.js";
11
+ export { default as NewItemModal } from "./NewItemModal.js";
12
+ export { default as FileExplorerToolbar } from "./FileExplorerToolbar.js";
13
+ export { default as FileUtils } from "./FileUtils.js";
14
+ export default FileExplorer;
15
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","names":["FileExplorer","default","FileExistsError","FileNotFoundError","SHORTCUTS","NewItemModal","FileExplorerToolbar","FileUtils"],"sources":["../src/index.ts"],"sourcesContent":["import FileExplorer from './FileExplorer';\n\nexport * from './FileExplorer';\nexport * from './FileListContainer';\nexport * from './FileList';\nexport * from './FileListItem';\nexport * from './FileListUtils';\nexport * from './FileStorage';\nexport { default as FileExistsError } from './FileExistsError';\nexport { default as FileNotFoundError } from './FileNotFoundError';\nexport { default as SHORTCUTS } from './FileExplorerShortcuts';\nexport { default as NewItemModal } from './NewItemModal';\nexport { default as FileExplorerToolbar } from './FileExplorerToolbar';\nexport { default as FileUtils } from './FileUtils';\n\nexport default FileExplorer;\n"],"mappings":"OAAOA,YAAY;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,SAQVC,OAAO,IAAIC,eAAe;AAAA,SAC1BD,OAAO,IAAIE,iBAAiB;AAAA,SAC5BF,OAAO,IAAIG,SAAS;AAAA,SACpBH,OAAO,IAAII,YAAY;AAAA,SACvBJ,OAAO,IAAIK,mBAAmB;AAAA,SAC9BL,OAAO,IAAIM,SAAS;AAE7B,eAAeP,YAAY"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@deephaven/file-explorer",
3
- "version": "0.43.0",
3
+ "version": "0.44.0",
4
4
  "description": "Deephaven File Explorer React component",
5
5
  "author": "Deephaven Data Labs LLC",
6
6
  "license": "Apache-2.0",
@@ -22,11 +22,11 @@
22
22
  "build:sass": "sass --embed-sources --load-path=../../node_modules ./src:./dist"
23
23
  },
24
24
  "dependencies": {
25
- "@deephaven/components": "^0.43.0",
26
- "@deephaven/icons": "^0.43.0",
27
- "@deephaven/log": "^0.43.0",
28
- "@deephaven/storage": "^0.43.0",
29
- "@deephaven/utils": "^0.43.0",
25
+ "@deephaven/components": "^0.44.0",
26
+ "@deephaven/icons": "^0.44.0",
27
+ "@deephaven/log": "^0.44.0",
28
+ "@deephaven/storage": "^0.44.0",
29
+ "@deephaven/utils": "^0.44.0",
30
30
  "@fortawesome/fontawesome-svg-core": "^6.2.1",
31
31
  "@fortawesome/react-fontawesome": "^0.2.0",
32
32
  "classnames": "^2.3.1",
@@ -37,7 +37,7 @@
37
37
  "react": "^17.0.0"
38
38
  },
39
39
  "devDependencies": {
40
- "@deephaven/mocks": "^0.43.0"
40
+ "@deephaven/mocks": "^0.44.0"
41
41
  },
42
42
  "files": [
43
43
  "dist"
@@ -48,5 +48,5 @@
48
48
  "publishConfig": {
49
49
  "access": "public"
50
50
  },
51
- "gitHead": "b16776b5bdc15a02cd2897cd79d562ea38c60ed8"
51
+ "gitHead": "ba13c9139b3b7a5f5d64d79069f1de9d4727eeb6"
52
52
  }