/admin/
This commit is contained in:
parent
28ae8beb2d
commit
f373b208f6
@ -102,6 +102,19 @@ body {
|
||||
.boxedcontent .bc_data {
|
||||
padding: 8px; }
|
||||
|
||||
.button {
|
||||
color: #DDD;
|
||||
text-decoration: none;
|
||||
background-color: #222;
|
||||
font-size: 1rem;
|
||||
border: 1px solid black;
|
||||
height: 36px;
|
||||
line-height: 36px;
|
||||
padding: 2px 2rem; }
|
||||
|
||||
.button:hover {
|
||||
background-color: #555; }
|
||||
|
||||
/* 400px */
|
||||
#headerdiv {
|
||||
z-index: 999;
|
||||
@ -887,6 +900,41 @@ html, body {
|
||||
text-decoration: none;
|
||||
color: #22F; }
|
||||
|
||||
/* 400px */
|
||||
.admincontent {
|
||||
display: block;
|
||||
width: 100%; }
|
||||
|
||||
.admincontent .boxedcontent {
|
||||
margin-bottom: 20px; }
|
||||
|
||||
.egh_ajaxOutput {
|
||||
display: flex;
|
||||
box-sizing: border-box;
|
||||
width: 100%;
|
||||
align-self: center;
|
||||
justify-self: center;
|
||||
margin-left: auto;
|
||||
margin-right: auto;
|
||||
resize: none;
|
||||
height: 300px; }
|
||||
|
||||
/* 400px */
|
||||
#loginform div {
|
||||
display: flex;
|
||||
flex-direction: column; }
|
||||
|
||||
#loginform div button {
|
||||
margin: 10px 0;
|
||||
padding: 0; }
|
||||
|
||||
.loginerror {
|
||||
display: flex;
|
||||
background: #FF4444;
|
||||
font-weight: bold;
|
||||
padding: 0 5px;
|
||||
margin: 5px 0 20px 0; }
|
||||
|
||||
/* 400px */
|
||||
.euler_pnl_base {
|
||||
display: inline-flex;
|
||||
|
8
www/data/css/styles.min.css
vendored
8
www/data/css/styles.min.css
vendored
@ -21,6 +21,8 @@ body{background-color:#EEE;color:#CCC;font-family:serif}
|
||||
.boxedcontent{color:#333;border:1px solid black;background-color:#e0e0e0;width:100%;margin-left:auto;margin-right:auto}
|
||||
.boxedcontent .bc_header{background-color:#BBB;padding:0 4px}
|
||||
.boxedcontent .bc_data{padding:8px}
|
||||
.button{color:#DDD;text-decoration:none;background-color:#222;font-size:1rem;border:1px solid black;height:36px;line-height:36px;padding:2px 2rem}
|
||||
.button:hover{background-color:#555}
|
||||
#headerdiv{z-index:999;background-color:#333;display:flex;border-bottom:1px solid #111;box-shadow:0 0 8px #000;position:fixed;width:100%}
|
||||
#headerdiv .logowrapper{flex:initial;margin:0;padding:0;height:42px}
|
||||
#headerdiv .logowrapper .logo{height:30px;margin:4px 0 8px 6px;flex:initial}
|
||||
@ -221,6 +223,12 @@ html,body{margin:0;padding:0;height:100%}
|
||||
.egg_footer{margin-top:5px;text-align:right;margin-right:5px;margin-bottom:5px;color:#888}
|
||||
.egg_footer>a{text-decoration:none;color:inherit}
|
||||
.egg_footer>a:hover{text-decoration:none;color:#22F}
|
||||
.admincontent{display:block;width:100%}
|
||||
.admincontent .boxedcontent{margin-bottom:20px}
|
||||
.egh_ajaxOutput{display:flex;box-sizing:border-box;width:100%;align-self:center;justify-self:center;margin-left:auto;margin-right:auto;resize:none;height:300px}
|
||||
#loginform div{display:flex;flex-direction:column}
|
||||
#loginform div button{margin:10px 0;padding:0}
|
||||
.loginerror{display:flex;background:#f44;font-weight:bold;padding:0 5px;margin:5px 0 20px 0}
|
||||
.euler_pnl_base{display:inline-flex;flex-direction:column;border:1px solid #AAA;border-radius:5px 5px 0 0;margin:15px}
|
||||
.euler_pnl_header{display:flex;align-items:center;justify-content:center;padding:4px;background:#AAA}
|
||||
.euler_pnl_header a{color:#222;text-decoration:none;font-family:Lato,"Helvetica Neue",Helvetica,Arial,sans-serif;font-size:22px;font-weight:900}
|
||||
|
@ -10,6 +10,8 @@
|
||||
@import 'styles_programslist';
|
||||
@import 'styles_programsview';
|
||||
@import 'styles_about';
|
||||
@import 'styles_admin';
|
||||
@import 'styles_login';
|
||||
|
||||
@import 'styles_eulerpanel';
|
||||
@import 'styles_programspanel';
|
||||
|
23
www/data/css/styles_admin.scss
Normal file
23
www/data/css/styles_admin.scss
Normal file
@ -0,0 +1,23 @@
|
||||
@import 'styles_config';
|
||||
|
||||
.admincontent {
|
||||
display: block;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
.admincontent .boxedcontent{
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.egh_ajaxOutput {
|
||||
display: flex;
|
||||
box-sizing: border-box;
|
||||
|
||||
width: 100%;
|
||||
align-self: center;
|
||||
justify-self: center;
|
||||
margin-left: auto;
|
||||
margin-right: auto;
|
||||
resize: none;
|
||||
height: 300px;
|
||||
}
|
@ -104,3 +104,19 @@ body {
|
||||
padding: 8px;
|
||||
}
|
||||
}
|
||||
|
||||
.button {
|
||||
|
||||
color: #DDD;
|
||||
text-decoration: none;
|
||||
background-color: #222;
|
||||
font-size: 1rem;
|
||||
border: 1px solid black;
|
||||
height: 36px;
|
||||
line-height: 36px;
|
||||
padding: 2px 2rem;
|
||||
}
|
||||
|
||||
.button:hover {
|
||||
background-color: #555;
|
||||
}
|
19
www/data/css/styles_login.scss
Normal file
19
www/data/css/styles_login.scss
Normal file
@ -0,0 +1,19 @@
|
||||
@import 'styles_config';
|
||||
|
||||
#loginform div {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
#loginform div button {
|
||||
margin: 10px 0;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
.loginerror {
|
||||
display: flex;
|
||||
background: #FF4444;
|
||||
font-weight: bold;
|
||||
padding: 0 5px;
|
||||
margin: 5px 0 20px 0;
|
||||
}
|
55
www/data/javascript/admin.js
Normal file
55
www/data/javascript/admin.js
Normal file
@ -0,0 +1,55 @@
|
||||
function queryStatus(appendix, secret)
|
||||
{
|
||||
jQuery.ajax({
|
||||
url: '/admin/egh/status?secret='+secret,
|
||||
success: function(result)
|
||||
{
|
||||
let ajaxOutput = $('#egh_ajaxOutput');
|
||||
ajaxOutput.val(result + '\r\n' + appendix);
|
||||
ajaxOutput.scrollTop(ajaxOutput[0].scrollHeight);
|
||||
},
|
||||
async: true
|
||||
});
|
||||
}
|
||||
|
||||
function startAjaxRefresh(secret)
|
||||
{
|
||||
$('#egh_ajaxOutput').val("Started.");
|
||||
val = setInterval(function(){ queryStatus('', secret); }, 500);
|
||||
|
||||
jQuery.ajax({
|
||||
url: '/admin/egh/reload?secret='+secret,
|
||||
success: function(result)
|
||||
{
|
||||
clearInterval(val);
|
||||
queryStatus('Finished.', secret);
|
||||
},
|
||||
error: function( jqXHR, textStatus, errorThrown)
|
||||
{
|
||||
clearInterval(val);
|
||||
queryStatus('AN ERROR OCCURED:' + '\r\n' + textStatus, secret);
|
||||
},
|
||||
async: true
|
||||
});
|
||||
}
|
||||
|
||||
function startAjaxRedraw(secret)
|
||||
{
|
||||
$('#egh_ajaxOutput').val("Started.");
|
||||
val = setInterval(function(){ queryStatus('', secret); }, 500);
|
||||
|
||||
jQuery.ajax({
|
||||
url: '/admin/egh/redraw?secret='+secret,
|
||||
success: function(result)
|
||||
{
|
||||
clearInterval(val);
|
||||
queryStatus('Finished.', secret);
|
||||
},
|
||||
error: function( jqXHR, textStatus, errorThrown)
|
||||
{
|
||||
clearInterval(val);
|
||||
queryStatus('AN ERROR OCCURED:' + '\r\n' + textStatus, secret);
|
||||
},
|
||||
async: true
|
||||
});
|
||||
}
|
11
www/extern/egh/ExtendedGitGraph.php
vendored
11
www/extern/egh/ExtendedGitGraph.php
vendored
@ -66,11 +66,9 @@ class ExtendedGitGraph
|
||||
$_SESSION[self::PROGRESS_SESSION_COOKIE] .= $txt . "\r\n";
|
||||
session_commit();
|
||||
}
|
||||
else if ($this->outputMode === self::OUT_STDOUT)
|
||||
{
|
||||
|
||||
print $txt;
|
||||
print "\r\n";
|
||||
}
|
||||
|
||||
$logfile = Utils::sharpFormat($this->logFilePath, ['num'=>'']);
|
||||
file_put_contents($logfile, $txt.PHP_EOL , FILE_APPEND | LOCK_EX);
|
||||
@ -181,4 +179,11 @@ class ExtendedGitGraph
|
||||
{
|
||||
return $this->renderedHTML;
|
||||
}
|
||||
|
||||
public function getAll()
|
||||
{
|
||||
$all = '';
|
||||
foreach ($this->get() as $year => $html) $all .= $html . "\n";
|
||||
return $all;
|
||||
}
|
||||
}
|
@ -10,6 +10,7 @@ $URL_RULES =
|
||||
[ 'url' => ['msmain', 'index'], 'target' => 'pages/main.php', 'options' => [], ],
|
||||
[ 'url' => ['about'], 'target' => 'pages/about.php', 'options' => [], ],
|
||||
[ 'url' => ['msmain', 'about'], 'target' => 'pages/about.php', 'options' => [], ],
|
||||
[ 'url' => ['login'], 'target' => 'pages/login.php', 'options' => [ 'login_target' => '/' ], ],
|
||||
|
||||
[ 'url' => ['programs'], 'target' => 'pages/programs_list.php', 'options' => [ 'categoryfilter' => '' ], ],
|
||||
[ 'url' => ['programs', 'index'], 'target' => 'pages/programs_list.php', 'options' => [ 'categoryfilter' => '%GET%' ], ],
|
||||
@ -34,8 +35,8 @@ $URL_RULES =
|
||||
[ 'url' => ['api', 'setselfadress'], 'target' => 'pages/api_setselfadress.php', 'options' => [], ],
|
||||
[ 'url' => ['api', 'statsping'], 'target' => 'pages/api_stats.php', 'options' => [ 'Name' => '%GET%', 'ClientID' => '%GET%', 'Version' => '%GET%', 'ProviderStr' => '%GET%', 'ProviderID' => '%GET%', 'NoteCount' => '%GET%', ], ],
|
||||
|
||||
[ 'url' => ['msmain', 'admin', 'egh', '?{commandcode}'], 'target' => 'pages/admin_egh.php', 'options' => [ 'commandcode' => '%URL%' ], ],
|
||||
[ 'url' => ['msmain', 'adminEGH'], 'target' => 'pages/admin_egh.php', 'options' => [ 'commandcode' => '%GET%' ], ],
|
||||
[ 'url' => ['admin'], 'target' => 'pages/admin.php', 'options' => [ '_opt' => 'password'], ],
|
||||
[ 'url' => ['admin', 'egh', '?{cmd}'], 'target' => 'pages/admin_egh.php', 'options' => [ 'cmd' => '%URL%', 'secret' => '%GET%' ], ],
|
||||
|
||||
[ 'url' => ['blog'], 'target' => 'pages/blog_list.php', 'options' => [], ],
|
||||
[ 'url' => ['log'], 'target' => 'pages/blog_list.php', 'options' => [], ],
|
||||
@ -94,6 +95,8 @@ try {
|
||||
if ($partcount !== count($rule['url'])) continue;
|
||||
|
||||
$urlparams = [];
|
||||
$opt = key_exists('_opt', $rule['options']) ? explode($rule['options']['_opt'], '|') : [];
|
||||
$target = $rule['target'];
|
||||
|
||||
$match = true;
|
||||
for($i = 0; $i < $partcount; $i++)
|
||||
@ -136,8 +139,26 @@ try {
|
||||
}
|
||||
if (!$match) continue;
|
||||
|
||||
if (in_array('disabled', $opt)) continue;
|
||||
|
||||
if (in_array('password', $opt))
|
||||
{
|
||||
$auth = hash('sha256', $CONFIG['admin_username'] . ';' . $CONFIG['admin_password']);
|
||||
|
||||
if (!key_exists('mikescher_auth', $_COOKIE))
|
||||
{
|
||||
$opt['login_target'] = $path;
|
||||
$target = 'pages/login.php';
|
||||
}
|
||||
else if ($auth !== $_COOKIE['mikescher_auth'])
|
||||
{
|
||||
$opt['login_target'] = $path;
|
||||
$target = 'pages/login.php';
|
||||
}
|
||||
}
|
||||
|
||||
$OPTIONS = $opt;
|
||||
include $rule['target'];
|
||||
include $target;
|
||||
return;
|
||||
|
||||
}
|
||||
@ -174,5 +195,4 @@ try {
|
||||
//TODO optimize image sizes for display/download (? - auto?)
|
||||
//TODO send cache header (?)
|
||||
//TODO programs add [license]
|
||||
//TODO admin
|
||||
//TODO last 3 blog entries on /index/ (?)
|
@ -1,5 +1,9 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<?php
|
||||
require_once (__DIR__ . '/../internals/base.php');
|
||||
global $OPTIONS;
|
||||
?>
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<title>Mikescher.com - About</title>
|
||||
|
59
www/pages/admin.php
Normal file
59
www/pages/admin.php
Normal file
@ -0,0 +1,59 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<?php
|
||||
require_once (__DIR__ . '/../internals/base.php');
|
||||
?>
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<title>Mikescher.com - About</title>
|
||||
<link rel="icon" type="image/png" href="/data/images/favicon.png"/>
|
||||
<link rel="canonical" href="https://www.mikescher.com/about"/>
|
||||
<?php printCSS(); ?>
|
||||
<?php includeScriptOnce("http://code.jquery.com/jquery-latest.min.js", true, '') ?>
|
||||
<?php includeScriptOnce("/data/javascript/admin.js", true, 'defer') ?>
|
||||
</head>
|
||||
<body>
|
||||
<div id="mastercontainer">
|
||||
|
||||
<?php $HEADER_ACTIVE = 'admin'; include (__DIR__ . '/../fragments/header.php'); ?>
|
||||
|
||||
<div id="content" class="content-responsive">
|
||||
|
||||
<div class="admincontent">
|
||||
|
||||
<div class="contentheader"><h1>Admin</h1><hr/></div>
|
||||
|
||||
<div class="boxedcontent">
|
||||
<div class="bc_header">Version</div>
|
||||
|
||||
<div class="bc_data">
|
||||
<div><b style="display:inline-block; min-width: 100px">Branch: </b><span><?php echo exec('git rev-parse --abbrev-ref HEAD'); ?></span></div>
|
||||
<div><b style="display:inline-block; min-width: 100px">Commit: </b><span><?php echo exec('git rev-parse HEAD'); ?></span></div>
|
||||
<div><b style="display:inline-block; min-width: 100px">Date: </b><span><?php echo exec('git log -1 --format=%cd'); ?></span></div>
|
||||
<div><b style="display:inline-block; min-width: 100px">Message: </b><span><?php echo nl2br(exec('git log -1')); ?></span></div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
<div class="boxedcontent">
|
||||
<div class="bc_header">ExtendedGitGraph</div>
|
||||
|
||||
<div class="bc_data">
|
||||
|
||||
<textarea class="egh_ajaxOutput" id="egh_ajaxOutput" readonly="readonly"></textarea>
|
||||
<a class="button" href="javascript:startAjaxRefresh('<?php echo $CONFIG['ajax_secret'] ?>')">Update</a>
|
||||
<a class="button" href="javascript:startAjaxRedraw('<?php echo $CONFIG['ajax_secret'] ?>')">Redraw</a>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
<?php include (__DIR__ . '/../fragments/footer.php'); ?>
|
||||
|
||||
</div>
|
||||
</body>
|
||||
</html>
|
70
www/pages/admin_egh.php
Normal file
70
www/pages/admin_egh.php
Normal file
@ -0,0 +1,70 @@
|
||||
<?php
|
||||
|
||||
require_once (__DIR__ . '/../internals/base.php');
|
||||
require_once (__DIR__ . '/../extern/egh/ExtendedGitGraph.php');
|
||||
|
||||
$cmd = $OPTIONS['cmd'];
|
||||
$secret = $OPTIONS['secret'];
|
||||
|
||||
if ($secret !== $CONFIG['ajax_secret'])
|
||||
die('Unauthorized.');
|
||||
|
||||
function create()
|
||||
{
|
||||
global $CONFIG;
|
||||
|
||||
$v = new ExtendedGitGraph(__DIR__ . '/../temp/egh_cache.bin', ExtendedGitGraph::OUT_SESSION, __DIR__ . '/../temp/egh_log{num}.log');
|
||||
|
||||
$v->addRemote('github-user', null, 'Mikescher', 'Mikescher');
|
||||
//$v->addRemote('github-user', null, 'Mikescher', 'Sam-Development');
|
||||
//$v->addRemote('github-repository', null, 'Mikescher', 'Anastron/ColorRunner');
|
||||
$v->addRemote('gitea-repository', null, 'Mikescher', 'Mikescher/server-scripts');
|
||||
$v->addRemote('gitea-repository', null, 'Mikescher', 'Mikescher/apache-sites');
|
||||
$v->addRemote('gitea-repository', null, 'Mikescher', 'Mikescher/MVU_API');
|
||||
|
||||
$v->setColorScheme($CONFIG['egh_theme']);
|
||||
|
||||
$v->ConnectionGithub->setAPIToken($CONFIG['egh_token']);
|
||||
|
||||
$v->ConnectionGitea->setURL('https://gogs.mikescher.com');
|
||||
|
||||
return $v;
|
||||
}
|
||||
|
||||
if ($cmd === 'status')
|
||||
{
|
||||
if (session_status() !== PHP_SESSION_ACTIVE) session_start();
|
||||
|
||||
if (key_exists('ajax_progress_egh_refresh', $_SESSION))
|
||||
echo $_SESSION['ajax_progress_egh_refresh'];
|
||||
else
|
||||
echo '[[ NO SESSION STARTED ]]';
|
||||
|
||||
return;
|
||||
}
|
||||
else if ($cmd === 'refresh')
|
||||
{
|
||||
set_time_limit(900); // 15min
|
||||
|
||||
$v = create();
|
||||
$v->init();
|
||||
$v->updateFromRemotes();
|
||||
$v->generate();
|
||||
|
||||
file_put_contents(__DIR__ . '/../dynamic/egh.html', $v->getAll());
|
||||
}
|
||||
else if ($cmd === 'redraw')
|
||||
{
|
||||
set_time_limit(900); // 15min
|
||||
|
||||
$v = create();
|
||||
$v->init();
|
||||
$v->updateFromCache();
|
||||
$v->generate();
|
||||
|
||||
file_put_contents(__DIR__ . '/../dynamic/egh.html', $v->getAll());
|
||||
}
|
||||
else
|
||||
{
|
||||
die('Wrong command.');
|
||||
}
|
92
www/pages/login.php
Normal file
92
www/pages/login.php
Normal file
@ -0,0 +1,92 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<?php
|
||||
require_once (__DIR__ . '/../internals/base.php');
|
||||
global $OPTIONS;
|
||||
|
||||
$err = false;
|
||||
|
||||
if (key_exists('username', $_GET) && key_exists('password', $_GET) && key_exists('redirect', $_GET))
|
||||
{
|
||||
if ($_GET['username'] === $CONFIG['admin_username'] && $_GET['password'] === $CONFIG['admin_password'])
|
||||
{
|
||||
$expires = time() + (24*60*60); // 24h
|
||||
$hash = hash('sha256', $_GET['username'] . ';' . $_GET['password']);
|
||||
setcookie('mikescher_auth', $hash, $expires);
|
||||
|
||||
header('Location: ' . $_GET['redirect']);
|
||||
die();
|
||||
}
|
||||
else
|
||||
{
|
||||
$err = true;
|
||||
}
|
||||
}
|
||||
|
||||
$redirect = $OPTIONS['login_target'];
|
||||
|
||||
?>
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<title>Mikescher.com - Login</title>
|
||||
<link rel="icon" type="image/png" href="/data/images/favicon.png"/>
|
||||
<link rel="canonical" href="https://www.mikescher.com/login"/>
|
||||
<?php printCSS(); ?>
|
||||
</head>
|
||||
<body>
|
||||
<div id="mastercontainer">
|
||||
|
||||
<?php $HEADER_ACTIVE = 'login'; include (__DIR__ . '/../fragments/header.php'); ?>
|
||||
|
||||
<div id="content" class="content-responsive">
|
||||
|
||||
<div class="aboutcontent">
|
||||
|
||||
<div class="boxedcontent">
|
||||
<div class="bc_header">Mikescher.com - Login</div>
|
||||
|
||||
<div class="bc_data">
|
||||
|
||||
<div class="form">
|
||||
<form id="loginform" action="/login" method="GET">
|
||||
|
||||
<?php if ($err): ?>
|
||||
<span class="loginerror">Wrong username or password</span>
|
||||
<?php endif; ?>
|
||||
|
||||
<div>
|
||||
<label for="username" class="required">Username</label>
|
||||
<input name="username" id="username" type="text">
|
||||
</div>
|
||||
|
||||
<div>
|
||||
<label for="password">Password</label>
|
||||
<input name="password" id="password" type="password">
|
||||
</div>
|
||||
|
||||
<div style="display: none; visibility: hidden">
|
||||
<label for="redirect">Redirect</label>
|
||||
<input name="redirect" id="redirect" type="text" value="<?php echo $redirect ?>">
|
||||
</div>
|
||||
|
||||
<div>
|
||||
<button class="button" type="submit" name="yt0">Login</button>
|
||||
</div>
|
||||
|
||||
</form>
|
||||
</div>
|
||||
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
<?php include (__DIR__ . '/../fragments/footer.php'); ?>
|
||||
|
||||
</div>
|
||||
</body>
|
||||
</html>
|
3
www/temp/.gitignore
vendored
Normal file
3
www/temp/.gitignore
vendored
Normal file
@ -0,0 +1,3 @@
|
||||
*
|
||||
!.gitignore
|
||||
!.gitkeep
|
0
www/temp/.gitkeep
Normal file
0
www/temp/.gitkeep
Normal file
Loading…
Reference in New Issue
Block a user