| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  | import React, { Component, Fragment } from 'react'; | 
					
						
							| 
									
										
										
										
											2023-09-13 08:40:50 +08:00
										 |  |  | import PropTypes from 'prop-types'; | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  | import { Button } from 'reactstrap'; | 
					
						
							| 
									
										
										
										
											2022-12-21 13:30:29 +08:00
										 |  |  | import axios from 'axios'; | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  | import { Utils } from '../../../utils/utils'; | 
					
						
							|  |  |  | import { seafileAPI } from '../../../utils/seafile-api'; | 
					
						
							| 
									
										
										
										
											2019-12-05 15:45:16 +08:00
										 |  |  | import { siteRoot, gettext } from '../../../utils/constants'; | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  | import toaster from '../../../components/toast'; | 
					
						
							|  |  |  | import CreateFolderDialog from '../../../components/dialog/create-folder-dialog'; | 
					
						
							|  |  |  | import Dirent from '../../../models/system-admin/dirent'; | 
					
						
							|  |  |  | import MainPanelTopbar from '../main-panel-topbar'; | 
					
						
							|  |  |  | import DirPathBar from './dir-path-bar'; | 
					
						
							|  |  |  | import DirContent from './dir-content'; | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | class DirView extends Component { | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   constructor(props) { | 
					
						
							|  |  |  |     super(props); | 
					
						
							|  |  |  |     this.state = { | 
					
						
							|  |  |  |       loading: true, | 
					
						
							|  |  |  |       errorMsg: '', | 
					
						
							|  |  |  |       isSystemRepo: false, | 
					
						
							|  |  |  |       repoName: '', | 
					
						
							|  |  |  |       path: '', | 
					
						
							|  |  |  |       direntList: [], | 
					
						
							|  |  |  |       isNewFolderDialogOpen: false | 
					
						
							|  |  |  |     }; | 
					
						
							| 
									
										
										
										
											2022-12-24 10:41:34 +08:00
										 |  |  |     this.fileInput = React.createRef(); | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-07-18 11:58:42 +08:00
										 |  |  |   componentDidMount() { | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  |     this.loadDirentList('/'); | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   onPathClick = (path) => { | 
					
						
							|  |  |  |     this.loadDirentList(path); | 
					
						
							| 
									
										
										
										
											2023-09-13 08:40:50 +08:00
										 |  |  |   }; | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  | 
 | 
					
						
							|  |  |  |   toggleNewFolderDialog = () => { | 
					
						
							| 
									
										
										
										
											2024-07-18 11:58:42 +08:00
										 |  |  |     this.setState({ isNewFolderDialogOpen: !this.state.isNewFolderDialogOpen }); | 
					
						
							| 
									
										
										
										
											2023-09-13 08:40:50 +08:00
										 |  |  |   }; | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  | 
 | 
					
						
							|  |  |  |   createNewFolder = (path) => { | 
					
						
							|  |  |  |     let folderName = Utils.getFileName(path); | 
					
						
							|  |  |  |     seafileAPI.sysAdminCreateSysRepoFolder(this.props.repoID, this.state.path, folderName).then(res => { | 
					
						
							|  |  |  |       let new_dirent = new Dirent(res.data); | 
					
						
							|  |  |  |       let direntList = this.state.direntList; | 
					
						
							|  |  |  |       direntList.unshift(new_dirent); | 
					
						
							|  |  |  |       this.setState({ | 
					
						
							|  |  |  |         direntList: direntList | 
					
						
							|  |  |  |       }); | 
					
						
							|  |  |  |       this.toggleNewFolderDialog(); | 
					
						
							|  |  |  |     }).catch((err) => { | 
					
						
							|  |  |  |       let errMessage = Utils.getErrorMsg(err); | 
					
						
							|  |  |  |       toaster.danger(errMessage); | 
					
						
							|  |  |  |     }); | 
					
						
							| 
									
										
										
										
											2023-09-13 08:40:50 +08:00
										 |  |  |   }; | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  | 
 | 
					
						
							|  |  |  |   openFolder = (dirent) => { | 
					
						
							|  |  |  |     let direntPath = Utils.joinPath(this.state.path, dirent.name); | 
					
						
							|  |  |  |     if (!dirent.is_file) { | 
					
						
							|  |  |  |       this.loadDirentList(direntPath); | 
					
						
							|  |  |  |     } | 
					
						
							| 
									
										
										
										
											2023-09-13 08:40:50 +08:00
										 |  |  |   }; | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  | 
 | 
					
						
							|  |  |  |   loadDirentList = (path) => { | 
					
						
							|  |  |  |     const repoID = this.props.repoID; | 
					
						
							|  |  |  |     seafileAPI.sysAdminListRepoDirents(repoID, path).then(res => { | 
					
						
							|  |  |  |       const { is_system_library: isSystemRepo, repo_name: repoName, dirent_list } = res.data; | 
					
						
							|  |  |  |       let direntList = []; | 
					
						
							|  |  |  |       dirent_list.forEach(item => { | 
					
						
							|  |  |  |         let dirent = new Dirent(item); | 
					
						
							|  |  |  |         direntList.push(dirent); | 
					
						
							|  |  |  |       }); | 
					
						
							|  |  |  |       this.setState({ | 
					
						
							|  |  |  |         loading: false, | 
					
						
							|  |  |  |         repoName: repoName, | 
					
						
							| 
									
										
										
										
											2020-11-02 13:56:35 +08:00
										 |  |  |         isSystemRepo: isSystemRepo, | 
					
						
							|  |  |  |         direntList: direntList, | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  |         path: path, | 
					
						
							|  |  |  |       }, () => { | 
					
						
							|  |  |  |         let url = siteRoot + 'sys/libraries/' + repoID + '/' + encodeURIComponent(this.state.repoName) + Utils.encodePath(path); | 
					
						
							| 
									
										
										
										
											2024-07-18 11:58:42 +08:00
										 |  |  |         window.history.replaceState({ url: url, path: path }, path, url); | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  |       }); | 
					
						
							|  |  |  |     }).catch((error) => { | 
					
						
							| 
									
										
										
										
											2019-12-05 15:45:16 +08:00
										 |  |  |       this.setState({ | 
					
						
							|  |  |  |         loading: false, | 
					
						
							|  |  |  |         errorMsg: Utils.getErrorMsg(error, true) // true: show login tip if 403
 | 
					
						
							|  |  |  |       }); | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  |     }); | 
					
						
							| 
									
										
										
										
											2023-09-13 08:40:50 +08:00
										 |  |  |   }; | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  | 
 | 
					
						
							|  |  |  |   deleteDirent = (dirent) => { | 
					
						
							|  |  |  |     let path = Utils.joinPath(this.state.path, dirent.name); | 
					
						
							|  |  |  |     seafileAPI.sysAdminDeleteRepoDirent(this.props.repoID, path).then(res => { | 
					
						
							|  |  |  |       toaster.success(gettext('Successfully deleted 1 item.')); | 
					
						
							|  |  |  |       let direntList = this.state.direntList.filter(item => { | 
					
						
							|  |  |  |         return item.name != dirent.name; | 
					
						
							|  |  |  |       }); | 
					
						
							|  |  |  |       this.setState({ | 
					
						
							|  |  |  |         direntList: direntList | 
					
						
							|  |  |  |       }); | 
					
						
							|  |  |  |     }).catch((err) => { | 
					
						
							|  |  |  |       let errMessage = Utils.getErrorMsg(err); | 
					
						
							|  |  |  |       toaster.danger(errMessage); | 
					
						
							|  |  |  |     }); | 
					
						
							| 
									
										
										
										
											2023-09-13 08:40:50 +08:00
										 |  |  |   }; | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  | 
 | 
					
						
							|  |  |  |   downloadDirent = (dirent) => { | 
					
						
							|  |  |  |     let path = Utils.joinPath(this.state.path, dirent.name); | 
					
						
							|  |  |  |     seafileAPI.sysAdminGetRepoFileDownloadURL(this.props.repoID, path).then(res => { | 
					
						
							|  |  |  |       location.href = res.data.download_url; | 
					
						
							|  |  |  |     }).catch((err) => { | 
					
						
							|  |  |  |       let errMessage = Utils.getErrorMsg(err); | 
					
						
							|  |  |  |       toaster.danger(errMessage); | 
					
						
							|  |  |  |     }); | 
					
						
							| 
									
										
										
										
											2023-09-13 08:40:50 +08:00
										 |  |  |   }; | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  | 
 | 
					
						
							|  |  |  |   openFileInput = () => { | 
					
						
							|  |  |  |     this.fileInput.current.click(); | 
					
						
							| 
									
										
										
										
											2023-09-13 08:40:50 +08:00
										 |  |  |   }; | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  | 
 | 
					
						
							|  |  |  |   onFileInputChange = () => { | 
					
						
							|  |  |  |     if (!this.fileInput.current.files.length) { | 
					
						
							|  |  |  |       return; | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |     const file = this.fileInput.current.files[0]; | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     let { path } = this.state; | 
					
						
							|  |  |  |     seafileAPI.sydAdminGetSysRepoItemUploadURL(path).then(res => { | 
					
						
							|  |  |  |       let formData = new FormData(); | 
					
						
							|  |  |  |       formData.append('parent_dir', path); | 
					
						
							|  |  |  |       formData.append('file', file); | 
					
						
							| 
									
										
										
										
											2022-12-21 13:30:29 +08:00
										 |  |  |       axios.post(res.data.upload_link, formData).then(res => { | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  |         const fileObj = res.data[0]; | 
					
						
							|  |  |  |         let newDirent = new Dirent({ | 
					
						
							|  |  |  |           'is_file': true, | 
					
						
							|  |  |  |           'obj_name': fileObj.name, | 
					
						
							|  |  |  |           'file_size': Utils.bytesToSize(fileObj.size), | 
					
						
							|  |  |  |           'last_update': (new Date()).getTime() | 
					
						
							|  |  |  |         }); | 
					
						
							|  |  |  |         let direntList = this.state.direntList; | 
					
						
							|  |  |  |         const dirs = direntList.filter(item => { return !item.is_file; }); | 
					
						
							|  |  |  |         direntList.splice(dirs.length, 0, newDirent); | 
					
						
							|  |  |  |         this.setState({ | 
					
						
							|  |  |  |           direntList: direntList | 
					
						
							|  |  |  |         }); | 
					
						
							|  |  |  |       }); | 
					
						
							|  |  |  |     }).catch((err) => { | 
					
						
							|  |  |  |       let errMessage = Utils.getErrorMsg(err); | 
					
						
							|  |  |  |       toaster.danger(errMessage); | 
					
						
							|  |  |  |     }); | 
					
						
							| 
									
										
										
										
											2023-09-13 08:40:50 +08:00
										 |  |  |   }; | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  | 
 | 
					
						
							|  |  |  |   checkDuplicatedName = (newName) => { | 
					
						
							|  |  |  |     let direntList = this.state.direntList; | 
					
						
							|  |  |  |     let isDuplicated = direntList.some(object => { | 
					
						
							|  |  |  |       return object.name === newName; | 
					
						
							|  |  |  |     }); | 
					
						
							|  |  |  |     return isDuplicated; | 
					
						
							| 
									
										
										
										
											2023-09-13 08:40:50 +08:00
										 |  |  |   }; | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  | 
 | 
					
						
							|  |  |  |   render() { | 
					
						
							| 
									
										
										
										
											2020-11-02 13:56:35 +08:00
										 |  |  |     const { loading, errorMsg, | 
					
						
							|  |  |  |       repoName, direntList, isSystemRepo, path, | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  |       isNewFolderDialogOpen } = this.state; | 
					
						
							|  |  |  |     const { repoID } = this.props; | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     return ( | 
					
						
							|  |  |  |       <Fragment> | 
					
						
							|  |  |  |         {isSystemRepo ? | 
					
						
							| 
									
										
										
										
											2023-01-29 18:16:00 +08:00
										 |  |  |           <MainPanelTopbar {...this.props}> | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  |             <Fragment> | 
					
						
							|  |  |  |               <input className="d-none" type="file" onChange={this.onFileInputChange} ref={this.fileInput} /> | 
					
						
							|  |  |  |               <Button className="operation-item" onClick={this.openFileInput}>{gettext('Upload')}</Button> | 
					
						
							|  |  |  |               <Button className="operation-item" onClick={this.toggleNewFolderDialog}>{gettext('New Folder')}</Button> | 
					
						
							|  |  |  |             </Fragment> | 
					
						
							| 
									
										
										
										
											2023-01-29 18:16:00 +08:00
										 |  |  |           </MainPanelTopbar> : <MainPanelTopbar {...this.props} /> | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  |         } | 
					
						
							|  |  |  |         <div className="main-panel-center flex-row"> | 
					
						
							|  |  |  |           <div className="cur-view-container"> | 
					
						
							|  |  |  |             <div className="cur-view-path align-items-center"> | 
					
						
							| 
									
										
										
										
											2020-11-02 13:56:35 +08:00
										 |  |  |               <DirPathBar | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  |                 isSystemRepo={isSystemRepo} | 
					
						
							|  |  |  |                 repoID={repoID} | 
					
						
							|  |  |  |                 repoName={repoName} | 
					
						
							|  |  |  |                 currentPath={path} | 
					
						
							|  |  |  |                 onPathClick={this.onPathClick} | 
					
						
							|  |  |  |               /> | 
					
						
							|  |  |  |             </div> | 
					
						
							|  |  |  |             <div className="cur-view-content"> | 
					
						
							|  |  |  |               <DirContent | 
					
						
							|  |  |  |                 loading={loading} | 
					
						
							|  |  |  |                 errorMsg={errorMsg} | 
					
						
							|  |  |  |                 fromSystemRepo={isSystemRepo} | 
					
						
							|  |  |  |                 direntList={direntList} | 
					
						
							|  |  |  |                 openFolder={this.openFolder} | 
					
						
							|  |  |  |                 deleteDirent={this.deleteDirent} | 
					
						
							|  |  |  |                 downloadDirent={this.downloadDirent} | 
					
						
							|  |  |  |               /> | 
					
						
							|  |  |  |             </div> | 
					
						
							|  |  |  |           </div> | 
					
						
							|  |  |  |         </div> | 
					
						
							|  |  |  |         {isNewFolderDialogOpen && | 
					
						
							|  |  |  |           <CreateFolderDialog | 
					
						
							|  |  |  |             parentPath={path} | 
					
						
							|  |  |  |             checkDuplicatedName={this.checkDuplicatedName} | 
					
						
							|  |  |  |             onAddFolder={this.createNewFolder} | 
					
						
							| 
									
										
										
										
											2020-11-02 13:56:35 +08:00
										 |  |  |             addFolderCancel={this.toggleNewFolderDialog} | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  |           /> | 
					
						
							|  |  |  |         } | 
					
						
							|  |  |  |       </Fragment> | 
					
						
							|  |  |  |     ); | 
					
						
							|  |  |  |   } | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2023-09-13 08:40:50 +08:00
										 |  |  | DirView.propTypes = { | 
					
						
							|  |  |  |   repoID: PropTypes.string, | 
					
						
							|  |  |  | }; | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2019-09-24 12:18:53 +08:00
										 |  |  | export default DirView; |