Kaydet (Commit) 46048a08 authored tarafından mertcelen's avatar mertcelen

Extension detailed log support added.

üst fb812fa6
...@@ -7,6 +7,7 @@ APP_NOTIFICATION_EMAIL=admin@liman.dev ...@@ -7,6 +7,7 @@ APP_NOTIFICATION_EMAIL=admin@liman.dev
LOG_LEVEL=debug LOG_LEVEL=debug
LOG_PATH=/liman/logs/liman.log LOG_PATH=/liman/logs/liman.log
LOG_EXTENSION_PATH=/liman/logs/extension.log
EXTENSION_DEVELOPER_MODE=false EXTENSION_DEVELOPER_MODE=false
QUEUE_DRIVER=database QUEUE_DRIVER=database
NAV_EXTENSION_HIDE_COUNT=10 NAV_EXTENSION_HIDE_COUNT=10
......
...@@ -11,7 +11,7 @@ class PHPSandbox implements Sandbox ...@@ -11,7 +11,7 @@ class PHPSandbox implements Sandbox
{ {
private $path = "/liman/sandbox/php/index.php"; private $path = "/liman/sandbox/php/index.php";
private $fileExtension = ".blade.php"; private $fileExtension = ".blade.php";
private $server,$extension,$user,$request; private $server,$extension,$user,$request,$logId;
public function __construct($server = null, $extension = null, $user = null,$request = null) public function __construct($server = null, $extension = null, $user = null,$request = null)
{ {
...@@ -32,6 +32,10 @@ class PHPSandbox implements Sandbox ...@@ -32,6 +32,10 @@ class PHPSandbox implements Sandbox
return $this->path; return $this->path;
} }
public function setLogId($logId){
$this->logId = $logId;
}
public function getFileExtension() public function getFileExtension()
{ {
return $this->fileExtension; return $this->fileExtension;
...@@ -145,6 +149,7 @@ class PHPSandbox implements Sandbox ...@@ -145,6 +149,7 @@ class PHPSandbox implements Sandbox
json_encode($userData), json_encode($userData),
$publicPath, $publicPath,
$isAjax, $isAjax,
$this->logId
]; ];
$encrypted = openssl_encrypt( $encrypted = openssl_encrypt(
......
...@@ -11,7 +11,7 @@ class PythonSandbox implements Sandbox ...@@ -11,7 +11,7 @@ class PythonSandbox implements Sandbox
{ {
private $path = "/liman/sandbox/python/index.py"; private $path = "/liman/sandbox/python/index.py";
private $fileExtension = ".html.ninja"; private $fileExtension = ".html.ninja";
private $server,$extension,$user,$request; private $server,$extension,$user,$request,$logId;
public function __construct($server = null, $extension = null, $user = null,$request = null) public function __construct($server = null, $extension = null, $user = null,$request = null)
{ {
...@@ -32,6 +32,10 @@ class PythonSandbox implements Sandbox ...@@ -32,6 +32,10 @@ class PythonSandbox implements Sandbox
return $this->path; return $this->path;
} }
public function setLogId($logId){
$this->logId = $logId;
}
public function getFileExtension() public function getFileExtension()
{ {
return $this->fileExtension; return $this->fileExtension;
...@@ -136,6 +140,7 @@ class PythonSandbox implements Sandbox ...@@ -136,6 +140,7 @@ class PythonSandbox implements Sandbox
json_encode($userData), json_encode($userData),
$publicPath, $publicPath,
$isAjax, $isAjax,
$this->logId
]; ];
$keyPath = '/liman/keys' . DIRECTORY_SEPARATOR . $this->extension->id; $keyPath = '/liman/keys' . DIRECTORY_SEPARATOR . $this->extension->id;
......
...@@ -13,4 +13,6 @@ interface Sandbox ...@@ -13,4 +13,6 @@ interface Sandbox
public function command($function, $extensiondb = null); public function command($function, $extensiondb = null);
public function getInitialFiles(); public function getInitialFiles();
public function setLogId($logId);
} }
<?php
namespace App;
use Illuminate\Database\Eloquent\Model;
class ExtensionLog extends Model
{
use UsesUuid;
protected $fillable = [
"log_id", "title", "message"
];
}
...@@ -4,6 +4,7 @@ namespace App\Http\Controllers\Extension\Sandbox; ...@@ -4,6 +4,7 @@ namespace App\Http\Controllers\Extension\Sandbox;
use App\Classes\Connector\SSHTunnelConnector; use App\Classes\Connector\SSHTunnelConnector;
use App\Extension; use App\Extension;
use App\ExtensionLog;
use App\Http\Controllers\Controller; use App\Http\Controllers\Controller;
use App\JobHistory; use App\JobHistory;
use App\Jobs\ExtensionJob; use App\Jobs\ExtensionJob;
...@@ -13,6 +14,7 @@ use App\Server; ...@@ -13,6 +14,7 @@ use App\Server;
use App\ServerLog; use App\ServerLog;
use App\Token; use App\Token;
use Illuminate\Contracts\Bus\Dispatcher; use Illuminate\Contracts\Bus\Dispatcher;
use Illuminate\Support\Facades\Log;
use Illuminate\Http\Request; use Illuminate\Http\Request;
use Illuminate\Support\Str; use Illuminate\Support\Str;
...@@ -312,6 +314,18 @@ class InternalController extends Controller ...@@ -312,6 +314,18 @@ class InternalController extends Controller
); );
} }
public function sendLog()
{
$log = new ExtensionLog([
"log_id" => request('log_id'),
"message" => request('message'),
"title" => request('title')
]);
$log->save();
Log::channel('extension')->info(json_encode($log->toArray()));
}
/** /**
* @api {post} /lmn/private/reverseProxyRequest Add Vnc Proxy Config * @api {post} /lmn/private/reverseProxyRequest Add Vnc Proxy Config
* @apiName SandboxAddVncProxyConfig * @apiName SandboxAddVncProxyConfig
......
...@@ -51,7 +51,9 @@ class MainController extends Controller ...@@ -51,7 +51,9 @@ class MainController extends Controller
? request('target_function') ? request('target_function')
: 'index'; : 'index';
ServerLog::new(extension()->name, $page); $logObject = ServerLog::new(extension()->name, $page);
$this->sandbox->setLogId($logObject->id);
list($output, $timestamp) = $this->executeSandbox($page); list($output, $timestamp) = $this->executeSandbox($page);
...@@ -59,6 +61,7 @@ class MainController extends Controller ...@@ -59,6 +61,7 @@ class MainController extends Controller
"extension_id" => extension()->id, "extension_id" => extension()->id,
"server_id" => server()->id, "server_id" => server()->id,
"view" => $page, "view" => $page,
"log_id" => $logObject->id
]); ]);
if (trim($output) == "") { if (trim($output) == "") {
abort(504, "İstek zaman aşımına uğradı!"); abort(504, "İstek zaman aşımına uğradı!");
......
...@@ -20,6 +20,11 @@ Route::post( ...@@ -20,6 +20,11 @@ Route::post(
'Extension\Sandbox\InternalController@sendNotification' 'Extension\Sandbox\InternalController@sendNotification'
)->name('SandboxSendNotification'); )->name('SandboxSendNotification');
Route::post(
'/lmn/private/sendLog',
'Extension\Sandbox\InternalController@sendLog'
)->name('SandboxSendLog');
Route::post( Route::post(
'/lmn/private/runCommandApi', '/lmn/private/runCommandApi',
'Extension\Sandbox\InternalController@runCommand' 'Extension\Sandbox\InternalController@runCommand'
......
...@@ -9,6 +9,7 @@ use App\Extension; ...@@ -9,6 +9,7 @@ use App\Extension;
use App\Http\Controllers\Controller; use App\Http\Controllers\Controller;
use App\Notification; use App\Notification;
use App\ServerLog; use App\ServerLog;
use App\ExtensionLog;
use App\Permission; use App\Permission;
use Carbon\Carbon; use Carbon\Carbon;
use Exception; use Exception;
...@@ -647,13 +648,36 @@ class OneController extends Controller ...@@ -647,13 +648,36 @@ class OneController extends Controller
if(!Permission::can(user()->id,'liman','id','view_logs')){ if(!Permission::can(user()->id,'liman','id','view_logs')){
return respond("Sunucu Günlük Kayıtlarını görüntülemek için yetkiniz yok",201); return respond("Sunucu Günlük Kayıtlarını görüntülemek için yetkiniz yok",201);
} }
return view('l.table', [ list($logs,$count) = ServerLog::retrieve(true,request('query'));
"value" => ServerLog::retrieve(true),
"title" => ["Başlık", "Açıklama", "Kullanıcı","İşlem Tarihi"], $table = view('table',[
"display" => ["command", "output", "username","created_at"], "value" => $logs,
"startingNumber" => request('page') ? (intval(request('page'))-1) * request('size') : 0,
"title" => ["Eklenti", "Fonksiyon", "Kullanıcı","İşlem Tarihi", "*hidden*"],
"display" => ["command", "output", "username","created_at","id:id"],
"onclick" => "getLogDetails"
])->render();
$pagination = view('pagination',[
"current" => request('page') ? intval(request('page')) : 1,
"count" => floor($count / 10) + 1,
"onclick" => "getLogs"
])->render();
return respond([
"table" => $table . "<br>" . $pagination
]); ]);
} }
public function getLogDetails()
{
$logs = ExtensionLog::where('log_id',request('log_id'))->get();
if($logs->count() == 0){
return respond("Bu loga ait detay bulunamadı",201);
}
return respond($logs->toArray());
}
public function installPackage() public function installPackage()
{ {
if ( if (
......
...@@ -169,6 +169,12 @@ Route::group(['middleware' => ['server']], function () { ...@@ -169,6 +169,12 @@ Route::group(['middleware' => ['server']], function () {
'Server\OneController@getLogs' 'Server\OneController@getLogs'
)->name('server_get_logs'); )->name('server_get_logs');
Route::post(
'/sunucu/gunluk_kayitlari_detay',
'Server\OneController@getLogDetails'
)->name('server_get_log_details');
Route::post('/sunucu/paketler', 'Server\OneController@packageList')->name( Route::post('/sunucu/paketler', 'Server\OneController@packageList')->name(
'server_package_list' 'server_package_list'
); );
......
...@@ -31,5 +31,6 @@ class VerifyCsrfToken extends Middleware ...@@ -31,5 +31,6 @@ class VerifyCsrfToken extends Middleware
"/lmn/private/openTunnel", "/lmn/private/openTunnel",
"/lmn/private/stopTunnel", "/lmn/private/stopTunnel",
"/lmn/private/sendNotification", "/lmn/private/sendNotification",
"/lmn/private/sendLog",
]; ];
} }
...@@ -24,19 +24,23 @@ class ServerLog extends Model ...@@ -24,19 +24,23 @@ class ServerLog extends Model
]); ]);
} }
public static function retrieve($readable = false, $server_id = null) public static function retrieve($readable = false, $searchQuery = null,$server_id = null)
{ {
// First, Retrieve Logs. // First, Retrieve Logs.
$logs = ServerLog::where([ $query = ServerLog::where([
"server_id" => $server_id == null ? server()->id : $server_id, "server_id" => $server_id == null ? server()->id : $server_id,
]) ]);
->orderBy('updated_at', 'DESC') if($searchQuery != null){
->get(); $query = $query->where('command', 'LIKE', '%'.$searchQuery.'%')->orWhere('output', 'LIKE', '%'.$searchQuery.'%');
}
$query2 = clone $query;
$logs = $query->orderBy('updated_at', 'DESC')->paginate(10);
// If it's not requested as readable, which means id's only without logic. // If it's not requested as readable, which means id's only without logic.
if (!$readable) { if (!$readable) {
return $logs; return $logs;
} }
$count = $query2->count();
// First, convert user_id's into the user names. // First, convert user_id's into the user names.
$users = User::all(); $users = User::all();
...@@ -49,6 +53,6 @@ class ServerLog extends Model ...@@ -49,6 +53,6 @@ class ServerLog extends Model
$log->username = $user->name; $log->username = $user->name;
$log->output = substr($log->output,0,100); $log->output = substr($log->output,0,100);
} }
return $logs; return [$logs,$count];
} }
} }
...@@ -20,7 +20,7 @@ ...@@ -20,7 +20,7 @@
"guzzlehttp/guzzle": "^6.3", "guzzlehttp/guzzle": "^6.3",
"icewind/smb": "^3.1", "icewind/smb": "^3.1",
"jenssegers/blade": "^1.3", "jenssegers/blade": "^1.3",
"laravel/framework": "^6.5", "laravel/framework": "^6.0",
"laravel/helpers": "*", "laravel/helpers": "*",
"phpseclib/phpseclib": "^2.0", "phpseclib/phpseclib": "^2.0",
"pusher/pusher-php-server": "~3.0" "pusher/pusher-php-server": "~3.0"
......
This diff is collapsed.
...@@ -51,6 +51,12 @@ return [ ...@@ -51,6 +51,12 @@ return [
'days' => 14, 'days' => 14,
], ],
'extension' => [
'driver' => 'single',
'path' => env('LOG_EXTENSION_PATH','/liman/logs/extension.log'),
'level' => 'info',
],
'slack' => [ 'slack' => [
'driver' => 'slack', 'driver' => 'slack',
'url' => env('LOG_SLACK_WEBHOOK_URL'), 'url' => env('LOG_SLACK_WEBHOOK_URL'),
......
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
class CreateExtensionLogsTable extends Migration
{
/**
* Run the migrations.
*
* @return void
*/
public function up()
{
Schema::create('extension_logs', function (Blueprint $table) {
$table->uuid('id')->primary();
$table->uuid('log_id');
$table
->foreign('log_id')
->references('id')
->on('server_logs')
->onDelete('cascade');
$table->string('title')->nullable();
$table->string('message');
$table->timestamps();
});
}
/**
* Reverse the migrations.
*
* @return void
*/
public function down()
{
Schema::dropIfExists('extension_logs');
}
}
{{-- <div class="input-group" style="max-width: 220px;z-index: 1;">
"current" <span class="input-group-btn">
"count" <button @if($current != 1) onclick="{{$onclick . '(' . ($current - 1 ). ')'}}" @else disabled @endif class="btn btn-default" type="button">{{__("Önceki")}}</button>
"onclick" </span>
--}} <select onchange="{{$onclick . '(this.value)'}}" class="form-control">
<ul class="pagination" style="cursor:pointer"> @for($i = 1 ; $i <= intval($count); $i++)
<li class="paginate_button previous @if($current == 1) disabled @endif" id="example2_previous"> <option value="{{$i}}"@if($i == $current) selected @endif">{{$i}}</option>
<a @if($current != 1) onclick="{{$onclick . '(' . ($current - 1 ). ')'}}" @endif data-dt-idx="0" tabindex="0">{{__("Önceki")}}</a> @endfor
</li> </select>
@for($i = 1 ; $i <= intval($count); $i++) <span class="input-group-btn">
<li class="paginate_button @if($i == $current) active @endif"> <button @if($current != $count) onclick="{{$onclick . '(' . ($current + 1 ). ')'}}" @else disabled @endif class="btn btn-default" type="button">{{__("Sonraki")}}</button>
<a onclick="{{$onclick . '(' . ($i). ')'}}" tabindex="0">{{$i}}</a> </span>
</li> </div>
@endfor \ No newline at end of file
<li class="paginate_button next @if($current == $count) disabled @endif" id="example2_next">
<a @if($current != $count) onclick="{{$onclick . '(' . ($current + 1 ). ')'}}" @endif data-dt-idx="0" tabindex="0">{{__("Sonraki")}}</a>
</li>
</ul>
\ No newline at end of file
...@@ -114,7 +114,7 @@ ...@@ -114,7 +114,7 @@
@endif @endif
@if(\App\Permission::can(user()->id,'liman','id','view_logs')) @if(\App\Permission::can(user()->id,'liman','id','view_logs'))
<li class="nav-item"> <li class="nav-item">
<a class="nav-link" data-toggle="pill" href="#logsTab" onclick="getLogs()" role="tab">{{__("Günlük Kayıtları")}}</a> <a class="nav-link" data-toggle="pill" href="#logsTab" onclick="getLogs()" role="tab">{{__("Erişim Kayıtları")}}</a>
</li> </li>
@endif @endif
<li class="nav-item"> <li class="nav-item">
...@@ -275,10 +275,19 @@ ...@@ -275,10 +275,19 @@
@endif @endif
@endif @endif
<div class="tab-pane fade show" id="logsTab" role="tabpanel"> <div class="tab-pane fade show" id="logsTab" role="tabpanel">
<div class="form-group">
<label>{{__('Arama Terimi')}}</label>
<div class="input-group">
<input id="logQueryFilter" type="text" class="form-control" placeholder="{{__('Arama Terimi')}}">
<span class="input-group-append">
<button type="button" class="btn btn-primary btn-flat" onclick="getLogs()"><i class="fa fa-search" aria-hidden="true"></i></button>
</span>
</div>
</div>
<div id="logsWrapper">
</div>
</div> </div>
<div class="tab-pane fade show" id="openPortsTab" role="tabpanel"> <div class="tab-pane fade show" id="openPortsTab" role="tabpanel">
</div> </div>
<div class="tab-pane fade show" id="settingsTab" role="tabpanel"> <div class="tab-pane fade show" id="settingsTab" role="tabpanel">
...@@ -560,6 +569,22 @@ ...@@ -560,6 +569,22 @@
</div> </div>
</div> </div>
@endcomponent @endcomponent
@component('modal-component',[
"id"=>"logDetailModal",
"title" => "Log Detayı"
])
<div class="row">
<div class="col-4">
<div class="list-group" role="tablist" id="logTitleWrapper">
</div>
</div>
<div class="col-8">
<div class="tab-content" id="logContentWrapper">
</div>
</div>
</div>
@endcomponent
<script> <script>
...@@ -865,11 +890,44 @@ ...@@ -865,11 +890,44 @@
}) })
} }
function getLogs() { function getLogs(page = 1) {
showSwal('{{__("Okunuyor...")}}','info');
let form = new FormData();
form.append('page',page);
let query = $("#logQueryFilter").val();
if(query.length !== 0){
form.append('query',query);
}
request('{{route('server_get_logs')}}', form, function (response) {
let json = JSON.parse(response);
$("#logsWrapper").html(json.message.table);
setTimeout(function () {
Swal.close();
}, 1500);
}, function(response){
let error = JSON.parse(response);
showSwal(error.message,'error',2000);
})
}
function getLogDetails(element){
let log_id = element.querySelector('#id').innerHTML;
showSwal('{{__("Okunuyor...")}}','info'); showSwal('{{__("Okunuyor...")}}','info');
request('{{route('server_get_logs')}}', new FormData(), function (response) { let form = new FormData();
$("#logsTab").html(response); form.append('log_id',log_id);
$("#logsTab table").DataTable(dataTablePresets('normal')); request('{{route('server_get_log_details')}}', form, function (response) {
let json = JSON.parse(response);
let modal = $("#logDetailModal");
let logTitleWrapper = $("#logTitleWrapper");
let logContentWrapper = $("#logContentWrapper");
logTitleWrapper.html("");
logContentWrapper.html("");
$.each(json.message,function (index,current) {
current.id = "a" + Math.random().toString(36).substr(2, 9);
logTitleWrapper.append("<a class='list-group-item list-group-item-action' id='"+ current.id + "_title' href='#" + current.id + "_content' data-toggle='list' role='tab' aria-controls='home'>" + current.title + "</a>");
logContentWrapper.append("<div class='tab-pane fade' id='" + current.id + "_content' role='tabpanel' aria-labelledby='" + current.id +"_title'>" + current.message + "</div>");
});
modal.modal("show");
setTimeout(function () { setTimeout(function () {
Swal.close(); Swal.close();
}, 1500); }, 1500);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment