.idea + minor bugfixes

This commit is contained in:
Roman 2021-03-30 00:27:15 +02:00
parent dd3c18cf78
commit 89badafbb1
12 changed files with 104 additions and 15 deletions

5
adminPanel/.idea/.gitignore vendored Normal file

@ -0,0 +1,5 @@
# Default ignored files
/shelf/
/workspace.xml
# Editor-based HTTP Client requests
/httpRequests/

@ -0,0 +1,12 @@
<?xml version="1.0" encoding="UTF-8"?>
<module type="WEB_MODULE" version="4">
<component name="NewModuleRootManager">
<content url="file://$MODULE_DIR$">
<excludeFolder url="file://$MODULE_DIR$/temp" />
<excludeFolder url="file://$MODULE_DIR$/.tmp" />
<excludeFolder url="file://$MODULE_DIR$/tmp" />
</content>
<orderEntry type="inheritedJdk" />
<orderEntry type="sourceFolder" forTests="false" />
</component>
</module>

@ -0,0 +1,6 @@
<component name="InspectionProjectProfileManager">
<profile version="1.0">
<option name="myName" value="Project Default" />
<inspection_tool class="Eslint" enabled="true" level="WARNING" enabled_by_default="true" />
</profile>
</component>

@ -0,0 +1,8 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="ProjectModuleManager">
<modules>
<module fileurl="file://$PROJECT_DIR$/.idea/adminPanel.iml" filepath="$PROJECT_DIR$/.idea/adminPanel.iml" />
</modules>
</component>
</project>

6
adminPanel/.idea/vcs.xml Normal file

@ -0,0 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="VcsDirectoryMappings">
<mapping directory="$PROJECT_DIR$/.." vcs="Git" />
</component>
</project>

@ -30,7 +30,8 @@ class AdminDashboard extends React.Component {
this.state = { this.state = {
loaded: false, loaded: false,
dialog: { onClose: () => this.hideDialog() }, dialog: { onClose: () => this.hideDialog() },
notifications: [ ] notifications: [ ],
filesPath: null
}; };
} }
@ -57,12 +58,35 @@ class AdminDashboard extends React.Component {
}); });
} }
fetchFilesPath() {
this.api.getRoutes().then((res) => {
if (!res.success) {
this.showDialog("Error fetching routes: " + res.msg, "Error fetching routes");
} else {
for (const route of res.routes) {
if (route.target === "\\Documents\\Files") {
// prepare the path patterns, e.g. '/files(/.*)?' => '/files'
let path = route.request;
path = path.replace(/\(.*\)([?*])/g, ''); // remove optional and 0-n groups
path = path.replace(/.\*/g, ''); // remove .*
path = path.replace(/\[.*]\*/g, ''); // remove []*
path = path.replace(/(.*)\+/g, "$1"); // replace 1-n groups with one match
// todo: add some more rules, but we should have most of the cases now
this.setState({...this.state, filesPath: path });
break;
}
}
}
});
}
componentDidMount() { componentDidMount() {
this.api.fetchUser().then(Success => { this.api.fetchUser().then(Success => {
if (!Success) { if (!Success) {
document.location = "/admin"; document.location = "/admin";
} else { } else {
this.fetchNotifications(); this.fetchNotifications();
this.fetchFilesPath();
setInterval(this.onUpdate.bind(this), 60*1000); setInterval(this.onUpdate.bind(this), 60*1000);
this.setState({...this.state, loaded: true}); this.setState({...this.state, loaded: true});
} }
@ -83,7 +107,7 @@ class AdminDashboard extends React.Component {
return <Router> return <Router>
<Header {...this.controlObj} notifications={this.state.notifications} /> <Header {...this.controlObj} notifications={this.state.notifications} />
<Sidebar {...this.controlObj} notifications={this.state.notifications} /> <Sidebar {...this.controlObj} notifications={this.state.notifications} filesPath={this.state.filesPath} />
<div className={"content-wrapper p-2"}> <div className={"content-wrapper p-2"}>
<section className={"content"}> <section className={"content"}>
<Switch> <Switch>

@ -7,7 +7,8 @@ export default function Sidebar(props) {
let parent = { let parent = {
showDialog: props.showDialog || function() {}, showDialog: props.showDialog || function() {},
api: props.api, api: props.api,
notifications: props.notifications || [ ] notifications: props.notifications || [ ],
filesPath: props.filesPath || null
}; };
function onLogout() { function onLogout() {
@ -71,6 +72,16 @@ export default function Sidebar(props) {
); );
} }
let filePath = parent.filesPath;
if (filePath) {
li.push(<li className={"nav-item"} key={"files"}>
<a href={filePath} className={"nav-link"} target={"_blank"} rel={"noopener noreferrer"}>
<Icon icon={"folder"} className={"nav-icon"} />
<p>Files</p>
</a>
</li>);
}
li.push(<li className={"nav-item"} key={"logout"}> li.push(<li className={"nav-item"} key={"logout"}>
<a href={"#"} onClick={() => onLogout()} className={"nav-link"}> <a href={"#"} onClick={() => onLogout()} className={"nav-link"}>
<Icon icon={"arrow-left"} className={"nav-icon"} /> <Icon icon={"arrow-left"} className={"nav-icon"} />

@ -0,0 +1,6 @@
<component name="InspectionProjectProfileManager">
<profile version="1.0">
<option name="myName" value="Project Default" />
<inspection_tool class="Eslint" enabled="true" level="WARNING" enabled_by_default="true" />
</profile>
</component>

@ -4,6 +4,7 @@ import API from "./api";
import Icon from "./elements/icon"; import Icon from "./elements/icon";
import {FileBrowser} from "./elements/file-browser"; import {FileBrowser} from "./elements/file-browser";
import {TokenList} from "./elements/token-list"; import {TokenList} from "./elements/token-list";
import {Link} from "react-router-dom";
class FileControlPanel extends React.Component { class FileControlPanel extends React.Component {
@ -134,6 +135,7 @@ class FileControlPanel extends React.Component {
const self = this; const self = this;
const errorMessageShown = !!this.state.errorMessage; const errorMessageShown = !!this.state.errorMessage;
// still loading
if (!this.state.loaded) { if (!this.state.loaded) {
let checkUser = true; let checkUser = true;
@ -165,7 +167,9 @@ class FileControlPanel extends React.Component {
} }
return <>Loading <Icon icon={"spinner"} /></>; return <>Loading <Icon icon={"spinner"} /></>;
} else if (this.api.loggedIn || this.state.token.valid) { }
// access granted
else if (this.api.loggedIn || this.state.token.valid) {
let selectedIds = this.getSelectedIds(); let selectedIds = this.getSelectedIds();
let directories = this.getDirectories(); let directories = this.getDirectories();
let tokenList = (this.api.loggedIn) ? let tokenList = (this.api.loggedIn) ?
@ -205,6 +209,9 @@ class FileControlPanel extends React.Component {
<div className={"alert alert-danger mt-2"} hidden={!errorMessageShown}> <div className={"alert alert-danger mt-2"} hidden={!errorMessageShown}>
{ this.state.errorMessage } { this.state.errorMessage }
</div> </div>
<div className={"mt-3"}>
Or either <a href={"/admin"}>login</a> to access the file control panel.
</div>
</div> </div>
</div> </div>
</div>; </div>;

@ -1,5 +1,9 @@
$(document).ready(function () { $(document).ready(function () {
function isRecaptchaEnabled() {
return (typeof grecaptcha !== 'undefined');
}
function showAlert(type, msg) { function showAlert(type, msg) {
let alert = $("#alertMessage"); let alert = $("#alertMessage");
alert.text(msg); alert.text(msg);
@ -61,7 +65,6 @@ $(document).ready(function () {
let email = $("#email").val().trim(); let email = $("#email").val().trim();
let password = $("#password").val(); let password = $("#password").val();
let confirmPassword = $("#confirmPassword").val(); let confirmPassword = $("#confirmPassword").val();
let siteKey = $("#siteKey").val().trim();
if (username === '' || email === '' || password === '' || confirmPassword === '') { if (username === '' || email === '' || password === '' || confirmPassword === '') {
showAlert("danger", "Please fill out every field."); showAlert("danger", "Please fill out every field.");
@ -69,7 +72,8 @@ $(document).ready(function () {
showAlert("danger", "Your passwords did not match."); showAlert("danger", "Your passwords did not match.");
} else { } else {
let params = { username: username, email: email, password: password, confirmPassword: confirmPassword }; let params = { username: username, email: email, password: password, confirmPassword: confirmPassword };
if (typeof grecaptcha !== 'undefined') { if (isRecaptchaEnabled()) {
let siteKey = $("#siteKey").val().trim();
grecaptcha.ready(function() { grecaptcha.ready(function() {
grecaptcha.execute(siteKey, {action: 'register'}).then(function(captcha) { grecaptcha.execute(siteKey, {action: 'register'}).then(function(captcha) {
params["captcha"] = captcha; params["captcha"] = captcha;
@ -124,10 +128,10 @@ $(document).ready(function () {
let btn = $(this); let btn = $(this);
let email = $("#email").val(); let email = $("#email").val();
let siteKey = $("#siteKey").val().trim();
let params = { email: email }; let params = { email: email };
if (typeof grecaptcha !== 'undefined') { if (isRecaptchaEnabled()) {
let siteKey = $("#siteKey").val().trim();
grecaptcha.ready(function() { grecaptcha.ready(function() {
grecaptcha.execute(siteKey, {action: 'resetPassword'}).then(function(captcha) { grecaptcha.execute(siteKey, {action: 'resetPassword'}).then(function(captcha) {
params["captcha"] = captcha; params["captcha"] = captcha;

2
js/admin.min.js vendored

File diff suppressed because one or more lines are too long

12
js/files.min.js vendored

File diff suppressed because one or more lines are too long