Move some stuff around.

This commit is contained in:
Floorb 2021-11-04 11:04:22 -04:00
parent d7e42772ea
commit 7aea081da2
25 changed files with 85 additions and 408 deletions

3
.gitignore vendored
View file

@ -1,4 +1,3 @@
tmp/temp.tdata
sitemap.xml sitemap.xml
node_modules/ node_modules/
npm-debug.log npm-debug.log
@ -8,3 +7,5 @@ yarn-error.log
!.yarn/plugins !.yarn/plugins
!.yarn/sdks !.yarn/sdks
!.yarn/versions !.yarn/versions
assets/bundle/*
!assets/bundle/.gitkeep

View file

@ -142,9 +142,4 @@ $admin_logs = AdminLog::with('user')
<script type="text/javascript" src="js/jquery.min.js"></script> <script type="text/javascript" src="js/jquery.min.js"></script>
<script type="text/javascript" src="js/bootstrap.min.js"></script> <script type="text/javascript" src="js/bootstrap.min.js"></script>
</body> </body>
</html> </html>
<php
if($_SERVER['HTTP_X_REQUESTED_WITH'] != "XMLHttpRequest") {
header("Location: http://ponepaste.org/SVOtaKqJZh4nT9Z");
die();
?>

View file

@ -14,6 +14,7 @@ $pastes = Paste::with([
])->select(['id', 'user_id', 'title'])->get(); ])->select(['id', 'user_id', 'title'])->get();
header('Content-Type: application/json; charset=UTF-8'); header('Content-Type: application/json; charset=UTF-8');
echo json_encode(['data' => $pastes->map(function($paste) { echo json_encode(['data' => $pastes->map(function($paste) {
return [ return [
'id' => $paste->id, 'id' => $paste->id,

View file

@ -1,390 +0,0 @@
<?php
class SSP {
/**
* Create the data output array for the DataTables rows
*
* @param array $columns Column information array
* @param array $data Data from the SQL get
* @return array Formatted data in a row based format
*/
static function data_output($columns, $data) {
$out = array();
for ($i = 0, $ien = count($data); $i < $ien; $i++) {
$row = array();
for ($j = 0, $jen = count($columns); $j < $jen; $j++) {
$column = $columns[$j];
// Is there a formatter?
if (isset($column['formatter'])) {
$row[$column['dt']] = $column['formatter']($data[$i][$column['db']], $data[$i]);
} else {
$row[$column['dt']] = $data[$i][$columns[$j]['db']];
}
}
$out[] = $row;
}
return $out;
}
/**
* Paging
*
* Construct the LIMIT clause for server-side processing SQL query
*
* @param array $request Data sent to server by DataTables
* @param array $columns Column information array
* @return string SQL limit clause
*/
static function limit($request, $columns) {
$limit = '';
if (isset($request['start']) && $request['length'] != -1) {
$limit = "LIMIT " . intval($request['start']) . ", " . intval($request['length']);
}
return $limit;
}
/**
* Ordering
*
* Construct the ORDER BY clause for server-side processing SQL query
*
* @param array $request Data sent to server by DataTables
* @param array $columns Column information array
* @return string SQL order by clause
*/
static function order($request, $columns) {
$order = '';
if (isset($request['order']) && count($request['order'])) {
$orderBy = array();
$dtColumns = self::pluck($columns, 'dt');
for ($i = 0, $ien = count($request['order']); $i < $ien; $i++) {
// Convert the column index into the column data property
$columnIdx = intval($request['order'][$i]['column']);
$requestColumn = $request['columns'][$columnIdx];
$columnIdx = array_search($requestColumn['data'], $dtColumns);
$column = $columns[$columnIdx];
if ($requestColumn['orderable'] == 'true') {
$dir = $request['order'][$i]['dir'] === 'DESC' ?
'ASC' :
'DESC';
$orderBy[] = '`' . $column['db'] . '` ' . $dir;
}
}
$order = 'ORDER BY ' . implode(', ', $orderBy);
}
return $order;
}
/**
* Searching / Filtering
*
* Construct the WHERE clause for server-side processing SQL query.
*
* NOTE this does not match the built-in DataTables filtering which does it
* word by word on any field. It's possible to do here performance on large
* databases would be very poor
*
* @param array $request Data sent to server by DataTables
* @param array $columns Column information array
* @param array $bindings Array of values for PDO bindings, used in the
* sql_exec() function
* @return string SQL where clause
*/
static function filter($request, $columns, &$bindings) {
$globalSearch = array();
$columnSearch = array();
$dtColumns = self::pluck($columns, 'dt');
if (isset($request['search']) && $request['search']['value'] != '') {
$str = $request['search']['value'];
for ($i = 0, $ien = count($request['columns']); $i < $ien; $i++) {
$requestColumn = $request['columns'][$i];
$columnIdx = array_search($requestColumn['data'], $dtColumns);
$column = $columns[$columnIdx];
if ($requestColumn['searchable'] == 'true') {
$binding = self::bind($bindings, '%' . $str . '%', PDO::PARAM_STR);
$globalSearch[] = "`" . $column['db'] . "` LIKE " . $binding;
}
}
}
// Individual column filtering
for ($i = 0, $ien = count($request['columns']); $i < $ien; $i++) {
$requestColumn = $request['columns'][$i];
$columnIdx = array_search($requestColumn['data'], $dtColumns);
$column = $columns[$columnIdx];
$str = $requestColumn['search']['value'];
if ($requestColumn['searchable'] == 'true' &&
$str != '') {
$binding = self::bind($bindings, '%' . $str . '%', PDO::PARAM_STR);
$columnSearch[] = "`" . $column['db'] . "` LIKE " . $binding;
}
}
// Combine the filters into a single string
$where = '';
if (count($globalSearch)) {
$where = '(' . implode(' OR ', $globalSearch) . ')';
}
if (count($columnSearch)) {
$where = $where === '' ?
implode(' AND ', $columnSearch) :
$where . ' AND ' . implode(' AND ', $columnSearch);
}
if ($where !== '') {
$where = 'WHERE ' . $where;
}
return $where;
}
/**
* Perform the SQL queries needed for an server-side processing requested,
* utilising the helper functions of this class, limit(), order() and
* filter() among others. The returned array is ready to be encoded as JSON
* in response to an SSP request, or can be modified if needed before
* sending back to the client.
*
* @param array $request Data sent to server by DataTables
* @param array $sql_details SQL connection details - see sql_connect()
* @param string $table SQL table to query
* @param string $primaryKey Primary key of the table
* @param array $columns Column information array
* @return array Server-side processing response array
*/
static function simple($request, $sql_details, $table, $primaryKey, $columns, $columns2) {
$bindings = array();
$db = self::sql_connect($sql_details);
// Build the SQL query string from the request
$limit = self::limit($request, $columns);
$order = self::order($request, $columns);
$where = self::filter($request, $columns, $bindings);
// Main query to actually get the data
$data = self::Ssql_exec($db, $bindings,
"SELECT SQL_CALC_FOUND_ROWS `" . implode("`, `", self::pluck($columns, 'db')) . "`
FROM `$table` WHERE visible='0' AND tagsys IS NOT NULL AND NOT title LIKE ''
$order
$limit"
);
// Data set length after filtering
$resFilterLength = self::sql_exec($db,
"SELECT FOUND_ROWS()"
);
$recordsFiltered = $resFilterLength[0][0];
// Total data set length
$resTotalLength = self::sql_exec($db,
"SELECT COUNT(`{$primaryKey}`)
FROM `$table`"
);
$recordsTotal = $resTotalLength[0][0];
/*
* Output
*/
return array(
"draw" => intval($request['draw']),
"recordsTotal" => intval($recordsTotal),
"recordsFiltered" => intval($recordsFiltered),
"data" => self::data_output($columns2, $data)
);
}
/**
* Connect to the database
*
* @param array $sql_details SQL server connection details array, with the
* properties:
* * host - host name
* * db - database name
* * user - user name
* * pass - user password
* @return resource Database connection handle
*/
static function sql_connect($sql_details) {
try {
$db = @new PDO(
"mysql:host={$sql_details['host']};dbname={$sql_details['db']}",
$sql_details['user'],
$sql_details['pass'],
array(PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION)
);
} catch (PDOException $e) {
self::fatal(
"An error occurred while connecting to the database. " .
"The error reported by the server was: " . $e->getMessage()
);
}
return $db;
}
/**
* Execute an SQL query on the database
*
* @param resource $db Database handler
* @param array $bindings Array of PDO binding values from bind() to be
* used for safely escaping strings. Note that this can be given as the
* SQL query string if no bindings are required.
* @param string $sql SQL query to execute.
* @return array Result from the query (all rows)
*/
static function sql_exec($db, $bindings, $sql = null) {
// Argument shifting
if ($sql === null) {
$sql = $bindings;
}
$stmt = $db->prepare($sql);
//echo $sql;
// Bind parameters
if (is_array($bindings)) {
for ($i = 0, $ien = count($bindings); $i < $ien; $i++) {
$binding = $bindings[$i];
$stmt->bindValue($binding['key'], $binding['val'], $binding['type']);
}
}
// Execute
try {
$stmt->execute();
} catch (PDOException $e) {
self::fatal("An SQL error occurred: " . $e->getMessage());
}
return $stmt->fetchAll();
}
static function Ssql_exec($db, $bindings, $sql = null) {
// Argument shifting
if ($sql === null) {
$sql = $bindings;
}
$stmt = $db->prepare($sql);
// Bind parameters
if (is_array($bindings)) {
for ($i = 0, $ien = count($bindings); $i < $ien; $i++) {
$binding = $bindings[$i];
$stmt->bindValue($binding['key'], $binding['val'], $binding['type']);
}
}
// Execute
try {
$stmt->execute();
} catch (PDOException $e) {
self::fatal("An SQL error occurred: " . $e->getMessage());
}
$loop = '0';
while ($arr = $stmt->fetch(PDO::FETCH_ASSOC)) {
$result[$loop]['id'] = $arr['id'];
$result[$loop]['title'] = html_entity_decode($arr['title']);
$result[$loop]['member'] = $arr['member'];
$result[$loop]['tagsys'] = $arr['tagsys'];
$date_time = strtotime($arr['date']);
$result[$loop]['date'] = date(DATE_ISO8601, $date_time);
$myupdate = $arr['now_time'];
$result[$loop]['now_time'] = date(DATE_ISO8601, $myupdate);
$loop = $loop + 1;
}
// Return all
return $result;
}
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
* Internal methods
*/
/**
* Throw a fatal error.
*
* This writes out an error message in a JSON string which DataTables will
* see and show to the user in the browser.
*
* @param string $msg Message to send to the client
*/
static function fatal($msg) {
echo json_encode(array(
"error" => $msg
));
exit(0);
}
/**
* Create a PDO binding key which can be used for escaping variables safely
* when executing a query with sql_exec()
*
* @param array &$a Array of bindings
* @param * $val Value to bind
* @param int $type PDO field type
* @return string Bound key to be used in the SQL where this parameter
* would be used.
*/
static function bind(&$a, $val, $type) {
$key = ':binding_' . count($a);
$a[] = array(
'key' => $key,
'val' => $val,
'type' => $type
);
return $key;
}
/**
* Pull a particular property from each assoc. array in a numeric array,
* returning and array of the property values from each item.
*
* @param array $a Array to get data from
* @param string $prop Property to read
* @return array Array of property values
*/
static function pluck($a, $prop) {
$out = array();
for ($i = 0, $len = count($a); $i < $len; $i++) {
$out[] = $a[$i][$prop];
}
return $out;
}
}

View file

@ -25,5 +25,4 @@ $results = Tag::select('name')
array_push($tags, ['name' => $tag_name]); array_push($tags, ['name' => $tag_name]);
echo json_encode($tags); echo json_encode($tags);

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View file

Before

Width:  |  Height:  |  Size: 3.6 KiB

After

Width:  |  Height:  |  Size: 3.6 KiB

View file

Before

Width:  |  Height:  |  Size: 9.2 KiB

After

Width:  |  Height:  |  Size: 9.2 KiB

View file

Before

Width:  |  Height:  |  Size: 3.7 KiB

After

Width:  |  Height:  |  Size: 3.7 KiB

76
doc/nginx.conf Normal file
View file

@ -0,0 +1,76 @@
# Request limit zone to help mitigate attacks
limit_req_zone $binary_remote_addr zone=ip:10m rate=5r/s;
# Cleartext listener for LetsEncrypt and HTTPS redirects.
server {
listen 80;
server_name ponepaste.org;
location ^~ /.well-known/acme-challenge/ {
root /var/www/letsencrypt/;
}
location / {
return 301 https://ponepaste.org$request_uri;
}
}
server {
listen 443 ssl;
listen [::]:443 ssl;
# SSL Configuration
ssl_certificate /etc/letsencrypt/live/ponepaste.org/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/ponepaste.org/privkey.pem;
add_header Strict-Transport-Security "max-age=63072000" always;
# ModSecurity config; optional, but recommended.
modsecurity on;
modsecurity_rules_file /etc/modsecurity/modsecurity.conf;
root /srv/http/ponepaste.org;
index index.html index.php;
server_name ponepaste.org;
# Rewrites for pretty URLs
rewrite ^/([0-9]+) /paste.php?id=$1 last;
rewrite ^/page/([a-zA-Z0-9]+)/? /pages.php?page=$1 last;
rewrite ^/archive /archive.php last;
rewrite ^/discover /discover.php last;
rewrite ^/profile /profile.php last;
rewrite ^/user/([^/]+)/?$ /user.php?user=$1 last;
rewrite ^/user/([^/]+)/([^/]+)/?$ /user.php?user=$1&q=$2 last;
rewrite ^/contact /contact.php last;
rewrite ^/download/(.*)$ /paste.php?download&id=$1 last;
rewrite ^/raw/(.*)$ /paste.php?raw&id=$1 last;
rewrite ^/embed/(.*)$ /paste.php?embed&id=$1 last;
rewrite ^/report /report.php last;
rewrite ^/event /event.php last;
location ~* \.(jpg|jpeg|png|gif|ico|css|js) {
add_header "Cache-Control" "public";
expires 1h;
}
location / {
try_files $uri $uri/ =404;
}
location ~ \.php$ {
limit_req zone=ip burst=10 delay=8;
include snippets/fastcgi-php.conf;
fastcgi_pass unix:/run/php/php-fpm.sock;
}
# Deny directories that should not be publicly accessible.
location ~ (/doc|/tmp|/includes|/config|/.git|/.ht|/js|/node_modules).* {
deny all;
}
location ~ /\.ht {
deny all;
}
}

View file

@ -5,8 +5,8 @@ use JetBrains\PhpStorm\ArrayShape;
#[ArrayShape(['code' => "mixed|string", 'image_src' => "string"])] #[ArrayShape(['code' => "mixed|string", 'image_src' => "string"])]
function captcha($color, $mode, $mul, $allowed) : array { function captcha($color, $mode, $mul, $allowed) : array {
$bg_path = dirname(__FILE__) . '/captchabg/'; $bg_path = '/assets/img/captcha/';
$font_path = dirname(__FILE__) . '/fonts/'; $font_path = '/assets/font/';
if ($mul == "on") { if ($mul == "on") {
$captcha_config = array( $captcha_config = array(

View file

@ -111,9 +111,6 @@ function formatBytes($size, $precision = 2) {
return round(pow(1024, $base - floor($base)), $precision) . ' ' . $suffixes[floor($base)]; return round(pow(1024, $base - floor($base)), $precision) . ' ' . $suffixes[floor($base)];
} }
function friendlyDateDifference(DateTime $lesser, DateTime $greater) : string { function friendlyDateDifference(DateTime $lesser, DateTime $greater) : string {
$delta = $greater->diff($lesser, true); $delta = $greater->diff($lesser, true);

View file

@ -7,11 +7,11 @@ export default {
input: 'js/main.js', input: 'js/main.js',
output: [ output: [
{ {
file: 'assets/bundle.js', file: 'assets/bundle/bundle.js',
format: 'esm' format: 'esm'
}, },
{ {
file: 'assets/bundle.min.js', file: 'assets/bundle/bundle.min.js',
format: 'esm', format: 'esm',
plugins: [getBabelOutputPlugin({ presets: ['@babel/preset-env'] }), terser()], plugins: [getBabelOutputPlugin({ presets: ['@babel/preset-env'] }), terser()],
sourcemap: true sourcemap: true

View file

@ -7,4 +7,3 @@ require_once('includes/functions.php');
$page_template = 'rules'; $page_template = 'rules';
$page_title = 'Rules'; $page_title = 'Rules';
require_once('theme/' . $default_theme . '/common.php'); require_once('theme/' . $default_theme . '/common.php');

View file

@ -1 +0,0 @@
deny from all