Compare commits
4 Commits
v9.18.0
...
89e8f79cae
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
89e8f79cae | ||
|
|
d9bcb577d7 | ||
|
|
8613e8977b | ||
|
|
1a027e5c7d |
@@ -13,16 +13,26 @@ declare(strict_types=1);
|
||||
* build return json
|
||||
*
|
||||
* @param array<string,mixed> $http_headers
|
||||
* @param string $body
|
||||
* @param ?string $body
|
||||
* @return string
|
||||
*/
|
||||
function buildContent(array $http_headers, string $body): string
|
||||
function buildContent(array $http_headers, ?string $body): string
|
||||
{
|
||||
if (is_string($body) && !empty($body)) {
|
||||
$_body = json_decode($body, true);
|
||||
if (!is_array($_body)) {
|
||||
$body = [$body];
|
||||
} else {
|
||||
$body = $_body;
|
||||
}
|
||||
} elseif (is_string($body)) {
|
||||
$body = [];
|
||||
}
|
||||
return json_encode([
|
||||
'HEADERS' => $http_headers,
|
||||
"REQUEST_TYPE" => $_SERVER['REQUEST_METHOD'],
|
||||
"PARAMS" => $_GET,
|
||||
"BODY" => json_decode($body, true)
|
||||
"BODY" => $body,
|
||||
]);
|
||||
}
|
||||
|
||||
@@ -41,11 +51,15 @@ if (!empty($http_headers['HTTP_AUTHORIZATION']) && !empty($http_headers['HTTP_RU
|
||||
exit;
|
||||
}
|
||||
|
||||
if (($file_get = file_get_contents('php://input')) === false) {
|
||||
// if server request type is get set file_get to null -> no body
|
||||
if ($_SERVER['REQUEST_METHOD'] == "GET") {
|
||||
$file_get = null;
|
||||
} elseif (($file_get = file_get_contents('php://input')) === false) {
|
||||
header("HTTP/1.1 404 Not Found");
|
||||
print buildContent($http_headers, '{"code": 404, "content": {"Error": "file_get_contents failed"}}');
|
||||
exit;
|
||||
}
|
||||
|
||||
print buildContent($http_headers, $file_get);
|
||||
|
||||
// __END__
|
||||
|
||||
46
4dev/tests/DB/CoreLibsDBSqLiteTest.php
Normal file
46
4dev/tests/DB/CoreLibsDBSqLiteTest.php
Normal file
@@ -0,0 +1,46 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace tests;
|
||||
|
||||
use PHPUnit\Framework\TestCase;
|
||||
|
||||
/**
|
||||
* Test class for DB\SqLite
|
||||
* This will only test the SqLite parts
|
||||
* @coversDefaultClass \CoreLibs\DB\SqLite
|
||||
* @testdox \CoreLibs\SqLite method tests for extended DB interface
|
||||
*/
|
||||
final class CoreLibsDBESqLiteTest extends TestCase
|
||||
{
|
||||
/**
|
||||
* Undocumented function
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
protected function setUp(): void
|
||||
{
|
||||
if (!extension_loaded('sqlite')) {
|
||||
$this->markTestSkipped(
|
||||
'The SqLite extension is not available.'
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Undocumented function
|
||||
*
|
||||
* @testdox DB\SqLite Class tests
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function testSqLite()
|
||||
{
|
||||
$this->markTestIncomplete(
|
||||
'DB\SqLite Tests have not yet been implemented'
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
// __END__
|
||||
@@ -768,7 +768,7 @@ final class CoreLibsUrlRequestsCurlTest extends TestCase
|
||||
'type' => $type,
|
||||
'options' => null,
|
||||
'return_code' => "200",
|
||||
'return_content' => '{"HEADERS":{"HTTP_USER_AGENT":"CoreLibsUrlRequestCurl\/1","HTTP_ACCEPT":"*\/*","HTTP_HOST":"soba.egplusww.jp"},"REQUEST_TYPE":"' . strtoupper($type) . '","PARAMS":[],"BODY":null}'
|
||||
'return_content' => '{"HEADERS":{"HTTP_USER_AGENT":"CoreLibsUrlRequestCurl\/1","HTTP_ACCEPT":"*\/*","HTTP_HOST":"soba.egplusww.jp"},"REQUEST_TYPE":"' . strtoupper($type) . '","PARAMS":[],"BODY":[]}'
|
||||
];
|
||||
$provider["basic " . $type . ", query options"] = [
|
||||
'type' => $type,
|
||||
@@ -776,7 +776,7 @@ final class CoreLibsUrlRequestsCurlTest extends TestCase
|
||||
"query" => ["foo" => "bar"],
|
||||
],
|
||||
'return_code' => "200",
|
||||
'return_content' => '{"HEADERS":{"HTTP_USER_AGENT":"CoreLibsUrlRequestCurl\/1","HTTP_ACCEPT":"*\/*","HTTP_HOST":"soba.egplusww.jp"},"REQUEST_TYPE":"' . strtoupper($type) . '","PARAMS":{"foo":"bar"},"BODY":null}'
|
||||
'return_content' => '{"HEADERS":{"HTTP_USER_AGENT":"CoreLibsUrlRequestCurl\/1","HTTP_ACCEPT":"*\/*","HTTP_HOST":"soba.egplusww.jp"},"REQUEST_TYPE":"' . strtoupper($type) . '","PARAMS":{"foo":"bar"},"BODY":[]}'
|
||||
];
|
||||
$provider["basic " . $type . ", query/body options"] = [
|
||||
'type' => $type,
|
||||
@@ -787,6 +787,22 @@ final class CoreLibsUrlRequestsCurlTest extends TestCase
|
||||
'return_code' => "200",
|
||||
'return_content' => '{"HEADERS":{"HTTP_USER_AGENT":"CoreLibsUrlRequestCurl\/1","HTTP_ACCEPT":"*\/*","HTTP_HOST":"soba.egplusww.jp"},"REQUEST_TYPE":"' . strtoupper($type) . '","PARAMS":{"foo":"bar"},"BODY":{"foobar":"barbaz"}}'
|
||||
];
|
||||
$provider["basic " . $type . ", body options"] = [
|
||||
'type' => $type,
|
||||
'options' => [
|
||||
"body" => ["foobar" => "barbaz"],
|
||||
],
|
||||
'return_code' => "200",
|
||||
'return_content' => '{"HEADERS":{"HTTP_USER_AGENT":"CoreLibsUrlRequestCurl\/1","HTTP_ACCEPT":"*\/*","HTTP_HOST":"soba.egplusww.jp"},"REQUEST_TYPE":"' . strtoupper($type) . '","PARAMS":[],"BODY":{"foobar":"barbaz"}}'
|
||||
];
|
||||
$provider["basic " . $type . ", body options as string"] = [
|
||||
'type' => $type,
|
||||
'options' => [
|
||||
"body" => "body is a string",
|
||||
],
|
||||
'return_code' => "200",
|
||||
'return_content' => '{"HEADERS":{"HTTP_USER_AGENT":"CoreLibsUrlRequestCurl\/1","HTTP_ACCEPT":"*\/*","HTTP_HOST":"soba.egplusww.jp"},"REQUEST_TYPE":"' . strtoupper($type) . '","PARAMS":[],"BODY":["body is a string"]}'
|
||||
];
|
||||
}
|
||||
// MARK: post/put/patch
|
||||
foreach (['post', 'put', 'patch'] as $type) {
|
||||
@@ -814,7 +830,24 @@ final class CoreLibsUrlRequestsCurlTest extends TestCase
|
||||
'return_code' => "200",
|
||||
'return_content' => '{"HEADERS":{"HTTP_USER_AGENT":"CoreLibsUrlRequestCurl\/1","HTTP_ACCEPT":"*\/*","HTTP_HOST":"soba.egplusww.jp"},"REQUEST_TYPE":"' . strtoupper($type) . '","PARAMS":{"foo":"bar"},"BODY":{"foobar":"barbaz"}}'
|
||||
];
|
||||
$provider["basic " . $type . ", body options"] = [
|
||||
'type' => $type,
|
||||
'options' => [
|
||||
"body" => ["foobar" => "barbaz"],
|
||||
],
|
||||
'return_code' => "200",
|
||||
'return_content' => '{"HEADERS":{"HTTP_USER_AGENT":"CoreLibsUrlRequestCurl\/1","HTTP_ACCEPT":"*\/*","HTTP_HOST":"soba.egplusww.jp"},"REQUEST_TYPE":"' . strtoupper($type) . '","PARAMS":[],"BODY":{"foobar":"barbaz"}}'
|
||||
];
|
||||
$provider["basic " . $type . ", body option as string"] = [
|
||||
'type' => $type,
|
||||
'options' => [
|
||||
"body" => "body is a string",
|
||||
],
|
||||
'return_code' => "200",
|
||||
'return_content' => '{"HEADERS":{"HTTP_USER_AGENT":"CoreLibsUrlRequestCurl\/1","HTTP_ACCEPT":"*\/*","HTTP_HOST":"soba.egplusww.jp"},"REQUEST_TYPE":"' . strtoupper($type) . '","PARAMS":[],"BODY":["body is a string"]}'
|
||||
];
|
||||
}
|
||||
// $provider['"basic post']
|
||||
return $provider;
|
||||
// phpcs:enable Generic.Files.LineLength
|
||||
}
|
||||
@@ -917,7 +950,7 @@ final class CoreLibsUrlRequestsCurlTest extends TestCase
|
||||
);
|
||||
}
|
||||
|
||||
// TODO: multi requests with same base connection
|
||||
// MARK: multi requests with same base connection
|
||||
|
||||
/**
|
||||
* Undocumented function
|
||||
@@ -970,7 +1003,7 @@ final class CoreLibsUrlRequestsCurlTest extends TestCase
|
||||
. '"HTTP_THIRD_CALL":"delete","HTTP_ACCEPT":"*\/*",'
|
||||
. '"HTTP_HOST":"soba.egplusww.jp"},'
|
||||
. '"REQUEST_TYPE":"DELETE",'
|
||||
. '"PARAMS":[],"BODY":null}',
|
||||
. '"PARAMS":[],"BODY":[]}',
|
||||
$response['content'],
|
||||
'multi call: delete content not matching'
|
||||
);
|
||||
|
||||
@@ -10,7 +10,7 @@ parameters:
|
||||
# lineAfter: 3
|
||||
level: 8 # max is now 9
|
||||
# strictRules:
|
||||
# allRules: true
|
||||
# allRules: false
|
||||
checkMissingCallableSignature: true
|
||||
treatPhpDocTypesAsCertain: false
|
||||
paths:
|
||||
|
||||
@@ -16,16 +16,26 @@ $log = new CoreLibs\Logging\Logging([
|
||||
* build return json
|
||||
*
|
||||
* @param array<string,mixed> $http_headers
|
||||
* @param string $body
|
||||
* @param ?string $body
|
||||
* @return string
|
||||
*/
|
||||
function buildContent(array $http_headers, string $body): string
|
||||
function buildContent(array $http_headers, ?string $body): string
|
||||
{
|
||||
if (is_string($body) && !empty($body)) {
|
||||
$_body = Json::jsonConvertToArray($body);
|
||||
if (Json::jsonGetLastError()) {
|
||||
$body = [$body];
|
||||
} else {
|
||||
$body = $_body;
|
||||
}
|
||||
} elseif (is_string($body)) {
|
||||
$body = [];
|
||||
}
|
||||
return Json::jsonConvertArrayTo([
|
||||
'HEADERS' => $http_headers,
|
||||
"REQUEST_TYPE" => $_SERVER['REQUEST_METHOD'],
|
||||
"PARAMS" => $_GET,
|
||||
"BODY" => Json::jsonConvertToArray($body),
|
||||
"BODY" => $body,
|
||||
// "STRING_BODY" => $body,
|
||||
]);
|
||||
}
|
||||
@@ -45,7 +55,10 @@ if (!empty($http_headers['HTTP_AUTHORIZATION']) && !empty($http_headers['HTTP_RU
|
||||
exit;
|
||||
}
|
||||
|
||||
if (($file_get = file_get_contents('php://input')) === false) {
|
||||
// if server request type is get set file_get to null -> no body
|
||||
if ($_SERVER['REQUEST_METHOD'] == "GET") {
|
||||
$file_get = null;
|
||||
} elseif (($file_get = file_get_contents('php://input')) === false) {
|
||||
header("HTTP/1.1 404 Not Found");
|
||||
print buildContent($http_headers, '{"code": 404, "content": {"Error": "file_get_contents failed"}}');
|
||||
exit;
|
||||
|
||||
157
www/admin/class_test.db.sqlite.php
Normal file
157
www/admin/class_test.db.sqlite.php
Normal file
@@ -0,0 +1,157 @@
|
||||
<?php // phpcs:ignore warning
|
||||
|
||||
/**
|
||||
* @phan-file-suppress PhanTypeSuspiciousStringExpression
|
||||
*/
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
// turn on all error reporting
|
||||
error_reporting(E_ALL | E_STRICT | E_ERROR | E_WARNING | E_PARSE | E_COMPILE_ERROR);
|
||||
|
||||
ob_start();
|
||||
|
||||
// basic class test file
|
||||
define('USE_DATABASE', true);
|
||||
define('DATABASE', 'sqlite' . DIRECTORY_SEPARATOR);
|
||||
// sample config
|
||||
require 'config.php';
|
||||
// define log file id
|
||||
$LOG_FILE_ID = 'classTest-db';
|
||||
ob_end_flush();
|
||||
|
||||
$sql_file = BASE . MEDIA . DATABASE . "class_test.db.sqlite.sq3";
|
||||
|
||||
use CoreLibs\DB\SqLite;
|
||||
use CoreLibs\Debug\Support;
|
||||
use CoreLibs\Convert\SetVarType;
|
||||
|
||||
$log = new CoreLibs\Logging\Logging([
|
||||
'log_folder' => BASE . LOG,
|
||||
'log_file_id' => $LOG_FILE_ID,
|
||||
'log_per_date' => true,
|
||||
]);
|
||||
// db connection and attach logger
|
||||
$db = new CoreLibs\DB\SqLite($log, "sqlite:" . $sql_file);
|
||||
$db->log->debug('START', '=============================>');
|
||||
|
||||
$PAGE_NAME = 'TEST CLASS: DB: SqLite';
|
||||
print "<!DOCTYPE html>";
|
||||
print "<html><head><title>" . $PAGE_NAME . "</title></head>";
|
||||
print "<body>";
|
||||
print '<div><a href="class_test.php">Class Test Master</a></div>';
|
||||
|
||||
print "<hr>";
|
||||
|
||||
echo "Create Tables on demand<br>";
|
||||
|
||||
$query = <<<SQL
|
||||
CREATE TABLE IF NOT EXISTS test (
|
||||
test_id INTEGER PRIMARY KEY,
|
||||
c_text TEXT,
|
||||
c_integer INTEGER,
|
||||
c_integer_default INTEGER DEFAULT -1,
|
||||
c_bool BOOLEAN,
|
||||
c_datetime TEXT,
|
||||
c_datetime_microseconds TEXT,
|
||||
c_datetime_default TEXT DEFAULT CURRENT_TIMESTAMP,
|
||||
c_date TEXT,
|
||||
c_julian REAL,
|
||||
c_unixtime DATETIME,
|
||||
c_unixtime_alt DATETIME,
|
||||
c_numeric NUMERIC,
|
||||
c_real REAL,
|
||||
c_blob
|
||||
)
|
||||
SQL;
|
||||
$db->dbExec($query);
|
||||
// **********************
|
||||
$query = <<<SQL
|
||||
CREATE TABLE IF NOT EXISTS test_no_pk (
|
||||
c_text TEXT,
|
||||
c_integer INTEGER
|
||||
)
|
||||
SQL;
|
||||
$db->dbExec($query);
|
||||
|
||||
print "<hr>";
|
||||
|
||||
$table = 'test';
|
||||
echo "Table info for: " . $table . "<br>";
|
||||
|
||||
if (($table_info = $db->dbShowTableMetaData($table)) === false) {
|
||||
print "Read problem for: $table<br>";
|
||||
} else {
|
||||
print "TABLE INFO: <pre>" . print_r($table_info, true) . "</pre><br>";
|
||||
}
|
||||
|
||||
print "<hr>";
|
||||
|
||||
echo "Insert into 'test'<br>";
|
||||
|
||||
$query = <<<SQL
|
||||
INSERT INTO test (
|
||||
c_text, c_integer, c_bool,
|
||||
c_datetime, c_datetime_microseconds, c_date,
|
||||
c_julian, c_unixtime, c_unixtime_alt,
|
||||
c_numeric, c_real, c_blob
|
||||
) VALUES (
|
||||
?, ?, ?,
|
||||
?, ?, ?,
|
||||
julianday(?), ?, unixepoch(?),
|
||||
?, ?, ?
|
||||
)
|
||||
SQL;
|
||||
$db->dbExecParams($query, [
|
||||
'test', rand(1, 100), true,
|
||||
date('Y-m-d H:i:s'), date_format(date_create("now"), 'Y-m-d H:i:s.u'), date('Y-m-d'),
|
||||
// julianday pass through
|
||||
date('Y-m-d H:i:s'),
|
||||
// use "U" if no unixepoch in query
|
||||
date('U'), date('Y-m-d H:i:s'),
|
||||
1.5, 10.5, 'Anything'
|
||||
]);
|
||||
|
||||
print "<hr>";
|
||||
|
||||
echo "Insert into 'test_no_pk'<br>";
|
||||
|
||||
$query = <<<SQL
|
||||
INSERT INTO test_no_pk (
|
||||
c_text, c_integer
|
||||
) VALUES (
|
||||
?, ?
|
||||
)
|
||||
SQL;
|
||||
$db->dbExecParams($query, ['test no pk', rand(100, 200)]);
|
||||
|
||||
print "<hr>";
|
||||
|
||||
$query = <<<SQL
|
||||
SELECT test_id, c_text, c_integer, c_integer_default, c_datetime_default
|
||||
FROM test
|
||||
SQL;
|
||||
while (is_array($row = $db->dbReturnArray($query))) {
|
||||
print "ROW: PK(test_id): " . $row["test_id"]
|
||||
. ", Text: " . $row["c_text"] . ", Int: " . $row["c_integer"]
|
||||
. ", Int Default: " . $row["c_integer_default"]
|
||||
. ", Date Default: " . $row["c_datetime_default"]
|
||||
. "<br>";
|
||||
}
|
||||
|
||||
echo "<hr>";
|
||||
|
||||
$query = <<<SQL
|
||||
SELECT rowid, c_text, c_integer
|
||||
FROM test_no_pk
|
||||
SQL;
|
||||
|
||||
while (is_array($row = $db->dbReturnArray($query))) {
|
||||
print "ROW[CURSOR]: PK(rowid): " . $row["rowid"]
|
||||
. ", Text: " . $row["c_text"] . ", Int: " . $row["c_integer"]
|
||||
. "<br>";
|
||||
}
|
||||
|
||||
print "</body></html>";
|
||||
|
||||
// __END__
|
||||
@@ -73,6 +73,7 @@ $test_files = [
|
||||
'class_test.db.query-placeholder.php' => 'Class Test: DB query placeholder convert',
|
||||
'class_test.db.dbReturn.php' => 'Class Test: DB dbReturn',
|
||||
'class_test.db.single.php' => 'Class Test: DB single query tests',
|
||||
'class_test.db.sqlite.php' => 'Class Test: DB: SqLite',
|
||||
'class_test.convert.colors.php' => 'Class Test: CONVERT COLORS',
|
||||
'class_test.check.colors.php' => 'Class Test: CHECK COLORS',
|
||||
'class_test.mime.php' => 'Class Test: MIME',
|
||||
@@ -134,7 +135,7 @@ print "<div>READ _ENV ARRAY:</div>";
|
||||
print Support::dumpVar(array_map('htmlentities', $_ENV));
|
||||
// set + check edit access id
|
||||
$edit_access_id = 3;
|
||||
if (is_object($login) && isset($login->loginGetAcl()['unit'])) {
|
||||
if (isset($login->loginGetAcl()['unit'])) {
|
||||
print "ACL UNIT: " . print_r(array_keys($login->loginGetAcl()['unit']), true) . "<br>";
|
||||
print "ACCESS CHECK: " . (string)$login->loginCheckEditAccess($edit_access_id) . "<br>";
|
||||
if ($login->loginCheckEditAccess($edit_access_id)) {
|
||||
@@ -177,25 +178,23 @@ $log->debug('SOME MARK', 'Some error output');
|
||||
|
||||
// INTERNAL SET
|
||||
print "EDIT ACCESS ID: " . $backend->edit_access_id . "<br>";
|
||||
if (is_object($login)) {
|
||||
// print "ACL: <br>".$backend->print_ar($login->loginGetAcl())."<br>";
|
||||
// $log->debug('ACL', "ACL: " . \CoreLibs\Debug\Support::dumpVar($login->loginGetAcl()));
|
||||
// print "DEFAULT ACL: <br>".$backend->print_ar($login->default_acl_list)."<br>";
|
||||
// print "DEFAULT ACL: <br>".$backend->print_ar($login->default_acl_list)."<br>";
|
||||
// $result = array_flip(
|
||||
// array_filter(
|
||||
// array_flip($login->default_acl_list),
|
||||
// function ($key) {
|
||||
// if (is_numeric($key)) {
|
||||
// return $key;
|
||||
// }
|
||||
// }
|
||||
// )
|
||||
// );
|
||||
// print "DEFAULT ACL: <br>".$backend->print_ar($result)."<br>";
|
||||
// DEPRICATED CALL
|
||||
// $backend->adbSetACL($login->loginGetAcl());
|
||||
}
|
||||
// print "ACL: <br>".$backend->print_ar($login->loginGetAcl())."<br>";
|
||||
// $log->debug('ACL', "ACL: " . \CoreLibs\Debug\Support::dumpVar($login->loginGetAcl()));
|
||||
// print "DEFAULT ACL: <br>".$backend->print_ar($login->default_acl_list)."<br>";
|
||||
// print "DEFAULT ACL: <br>".$backend->print_ar($login->default_acl_list)."<br>";
|
||||
// $result = array_flip(
|
||||
// array_filter(
|
||||
// array_flip($login->default_acl_list),
|
||||
// function ($key) {
|
||||
// if (is_numeric($key)) {
|
||||
// return $key;
|
||||
// }
|
||||
// }
|
||||
// )
|
||||
// );
|
||||
// print "DEFAULT ACL: <br>".$backend->print_ar($result)."<br>";
|
||||
// DEPRICATED CALL
|
||||
// $backend->adbSetACL($login->loginGetAcl());
|
||||
|
||||
print "THIS HOST: " . HOST_NAME . ", with PROTOCOL: " . HOST_PROTOCOL . " is running SSL: " . HOST_SSL . "<br>";
|
||||
print "DIR: " . DIR . "<br>";
|
||||
|
||||
@@ -121,6 +121,23 @@ $data = $client->request(
|
||||
]
|
||||
);
|
||||
print "[request] _POST RESPONSE: <pre>" . print_r($data, true) . "</pre>";
|
||||
print "<hr>";
|
||||
$data = $client->request(
|
||||
"post",
|
||||
'https://soba.egplusww.jp/developers/clemens/core_data/php_libraries/trunk/www/admin/UrlRequests.target.php'
|
||||
. '?other=post_a',
|
||||
[
|
||||
"body" => 'string body here',
|
||||
"headers" => [
|
||||
'Content-Type' => 'application/json',
|
||||
'Accept' => 'application/json',
|
||||
'test-header' => 'ABC',
|
||||
'info-request-type' => '_POST',
|
||||
],
|
||||
"query" => ['foo' => 'BAR post'],
|
||||
]
|
||||
);
|
||||
print "[request|string body] _POST RESPONSE: <pre>" . print_r($data, true) . "</pre>";
|
||||
|
||||
print "<hr>";
|
||||
$data = $client->put(
|
||||
|
||||
90
www/lib/CoreLibs/DB/Interface/DatabaseInterface.php
Normal file
90
www/lib/CoreLibs/DB/Interface/DatabaseInterface.php
Normal file
@@ -0,0 +1,90 @@
|
||||
<?php
|
||||
|
||||
/**
|
||||
* AUTHOR: Clemens Schwaighofer
|
||||
* CREATED: Ymd
|
||||
* DESCRIPTION:
|
||||
* DescriptionHere
|
||||
*/
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace CoreLibs\DB\Interface;
|
||||
|
||||
interface DatabaseInterface
|
||||
{
|
||||
/**
|
||||
* Table meta data
|
||||
* Note that if columns have multi
|
||||
*
|
||||
* @param string $table
|
||||
* @return array<array<string,mixed>>|false
|
||||
*/
|
||||
public function dbShowTableMetaData(string $table): array|false;
|
||||
|
||||
/**
|
||||
* for reading or simple execution, no return data
|
||||
*
|
||||
* @param string $query
|
||||
* @return int|false
|
||||
*/
|
||||
public function dbExec(string $query): int|false;
|
||||
|
||||
/**
|
||||
* Run a simple query and return its statement
|
||||
*
|
||||
* @param string $query
|
||||
* @return \PDOStatement|false
|
||||
*/
|
||||
public function dbQuery(string $query): \PDOStatement|false;
|
||||
|
||||
/**
|
||||
* Execute one query with params
|
||||
*
|
||||
* @param string $query
|
||||
* @param array<mixed> $params
|
||||
* @return \PDOStatement|false
|
||||
*/
|
||||
public function dbExecParams(string $query, array $params): \PDOStatement|false;
|
||||
|
||||
/**
|
||||
* Prepare query
|
||||
*
|
||||
* @param string $query
|
||||
* @return \PDOStatement|false
|
||||
*/
|
||||
public function dbPrepare(string $query): \PDOStatement|false;
|
||||
|
||||
/**
|
||||
* execute a cursor
|
||||
*
|
||||
* @param \PDOStatement $cursor
|
||||
* @param array<mixed> $params
|
||||
* @return bool
|
||||
*/
|
||||
public function dbCursorExecute(\PDOStatement $cursor, array $params): bool;
|
||||
|
||||
/**
|
||||
* return array with data, when finshed return false
|
||||
* also returns false on error
|
||||
*
|
||||
* TODO: This is currently a one time run
|
||||
* if the same query needs to be run again, the cursor_ext must be reest
|
||||
* with dbCacheReset
|
||||
*
|
||||
* @param string $query
|
||||
* @param array<mixed> $params
|
||||
* @return array<mixed>|false
|
||||
*/
|
||||
public function dbReturnArray(string $query, array $params = []): array|false;
|
||||
|
||||
/**
|
||||
* get current db handler
|
||||
* this is for raw access
|
||||
*
|
||||
* @return \PDO
|
||||
*/
|
||||
public function getDbh(): \PDO;
|
||||
}
|
||||
|
||||
// __END__
|
||||
432
www/lib/CoreLibs/DB/SqLite.php
Normal file
432
www/lib/CoreLibs/DB/SqLite.php
Normal file
@@ -0,0 +1,432 @@
|
||||
<?php
|
||||
|
||||
/**
|
||||
* AUTHOR: Clemens Schwaighofer
|
||||
* CREATED: 2024/8/21
|
||||
* DESCRIPTION:
|
||||
* SQL Lite interface
|
||||
* Note: This is a very simple library and in future should perhaps merge with the master
|
||||
* CoreLibs SQL interface
|
||||
*
|
||||
* TODO: This should move to the CoreLibs\DB\IO class as a sub type for "sqlite" next to "pgsql"
|
||||
*/
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace CoreLibs\DB;
|
||||
|
||||
use CoreLibs\Create\Hash;
|
||||
|
||||
class SqLite implements Interface\DatabaseInterface
|
||||
{
|
||||
/** @var \CoreLibs\Logging\Logging logging */
|
||||
public \CoreLibs\Logging\Logging $log;
|
||||
|
||||
/** @var string database connection string */
|
||||
private string $dsn;
|
||||
/** @var \PDO database handler */
|
||||
private \PDO $dbh;
|
||||
/** @var PDOStatement|false one cursor, for internal handling */
|
||||
// private \PDOStatement|false $cursor;
|
||||
/** @var array<string,mixed> extended cursoers string index with content */
|
||||
private array $cursor_ext = [];
|
||||
|
||||
/**
|
||||
* init database system
|
||||
*
|
||||
* @param \CoreLibs\Logging\Logging $log
|
||||
* @param string $dsn
|
||||
*/
|
||||
public function __construct(
|
||||
\CoreLibs\Logging\Logging $log,
|
||||
string $dsn
|
||||
) {
|
||||
$this->log = $log;
|
||||
// open new connection
|
||||
if ($this->__connectToDB($dsn) === false) {
|
||||
throw new \ErrorException("Cannot load database: " . $dsn, 1);
|
||||
}
|
||||
}
|
||||
|
||||
// *********************************************************************
|
||||
// MARK: PRIVATE METHODS
|
||||
// *********************************************************************
|
||||
|
||||
/**
|
||||
* Get a cursor dump with all info
|
||||
*
|
||||
* @param \PDOStatement $cursor
|
||||
* @return string|false
|
||||
*/
|
||||
private function __dbGetCursorDump(\PDOStatement $cursor): string|false
|
||||
{
|
||||
// get the cursor info
|
||||
ob_start();
|
||||
$cursor->debugDumpParams();
|
||||
$cursor_dump = ob_get_contents();
|
||||
ob_end_clean();
|
||||
return $cursor_dump;
|
||||
}
|
||||
|
||||
/**
|
||||
* fetch rows from a cursor (post execute)
|
||||
*
|
||||
* @param \PDOStatement $cursor
|
||||
* @return array<mixed>|false
|
||||
*/
|
||||
private function __dbFetchArray(\PDOStatement $cursor): array|false
|
||||
{
|
||||
try {
|
||||
// on empty array return false
|
||||
// TODO make that more elegant?
|
||||
return empty($row = $cursor->fetch(mode:\PDO::FETCH_NAMED)) ? false : $row;
|
||||
} catch (\PDOException $e) {
|
||||
$this->log->error(
|
||||
"Cannot fetch from cursor",
|
||||
[
|
||||
"dsn" => $this->dsn,
|
||||
"DumpParams" => $this->__dbGetCursorDump($cursor),
|
||||
"PDOException" => $e
|
||||
]
|
||||
);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: open database
|
||||
|
||||
/**
|
||||
* Open database
|
||||
* reports errors for wrong DSN or failed connection
|
||||
*
|
||||
* @param string $dsn
|
||||
* @return bool
|
||||
*/
|
||||
private function __connectToDB(string $dsn): bool
|
||||
{
|
||||
// check if dsn starts with ":"
|
||||
if (!str_starts_with($dsn, "sqlite:")) {
|
||||
$this->log->error(
|
||||
"Invalid dsn string",
|
||||
[
|
||||
"dsn" => $dsn
|
||||
]
|
||||
);
|
||||
return false;
|
||||
}
|
||||
// TODO: if not ":memory:" check if path to file is writeable by system
|
||||
// avoid double open
|
||||
if (!empty($this->dsn) && $dsn == $this->dsn && $this->dbh instanceof \PDO) {
|
||||
$this->log->info(
|
||||
"Connection already establisehd with this dsn",
|
||||
[
|
||||
"dsn" => $dsn,
|
||||
]
|
||||
);
|
||||
return true;
|
||||
}
|
||||
// TODO: check that folder is writeable
|
||||
// set DSN and open connection
|
||||
$this->dsn = $dsn;
|
||||
try {
|
||||
$this->dbh = new \PDO($this->dsn);
|
||||
} catch (\PDOException $e) {
|
||||
$this->log->error(
|
||||
"Cannot open database",
|
||||
[
|
||||
"dsn" => $this->dsn,
|
||||
"PDOException" => $e
|
||||
]
|
||||
);
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
// *********************************************************************
|
||||
// MARK: PUBLIC METHODS
|
||||
// *********************************************************************
|
||||
|
||||
// MARK: db meta data (table info)
|
||||
|
||||
/**
|
||||
* Table meta data
|
||||
* Note that if columns have multi
|
||||
*
|
||||
* @param string $table
|
||||
* @return array<array<string,mixed>>|false
|
||||
*/
|
||||
public function dbShowTableMetaData(string $table): array|false
|
||||
{
|
||||
$table_info = [];
|
||||
$query = <<<SQL
|
||||
SELECT
|
||||
ti.cid, ti.name, ti.type, ti.'notnull', ti.dflt_value, ti.pk,
|
||||
il_ii.idx_name, il_ii.idx_unique, il_ii.idx_origin, il_ii.idx_partial
|
||||
FROM
|
||||
sqlite_schema AS m,
|
||||
pragma_table_info(m.name) AS ti
|
||||
LEFT JOIN (
|
||||
SELECT
|
||||
il.name AS idx_name, il.'unique' AS idx_unique, il.origin AS idx_origin, il.partial AS idx_partial,
|
||||
ii.cid AS tbl_cid
|
||||
FROM
|
||||
sqlite_schema AS m,
|
||||
pragma_index_list(m.name) AS il,
|
||||
pragma_index_info(il.name) AS ii
|
||||
WHERE m.name = ?1
|
||||
) AS il_ii ON (ti.cid = il_ii.tbl_cid)
|
||||
WHERE
|
||||
m.name = ?1
|
||||
SQL;
|
||||
while (is_array($row = $this->dbReturnArray($query, [$table]))) {
|
||||
$table_info[] = [
|
||||
'cid' => $row['cid'],
|
||||
'name' => $row['name'],
|
||||
'type' => $row['type'],
|
||||
'notnull' => $row['notnull'],
|
||||
'dflt_value' => $row['dflt_value'],
|
||||
'pk' => $row['pk'],
|
||||
'idx_name' => $row['idx_name'],
|
||||
'idx_unique' => $row['idx_unique'],
|
||||
'idx_origin' => $row['idx_origin'],
|
||||
'idx_partial' => $row['idx_partial'],
|
||||
];
|
||||
}
|
||||
|
||||
if (!$table_info) {
|
||||
return false;
|
||||
}
|
||||
return $table_info;
|
||||
}
|
||||
|
||||
// MARK: db exec
|
||||
|
||||
/**
|
||||
* for reading or simple execution, no return data
|
||||
*
|
||||
* @param string $query
|
||||
* @return int|false
|
||||
*/
|
||||
public function dbExec(string $query): int|false
|
||||
{
|
||||
try {
|
||||
return $this->dbh->exec($query);
|
||||
} catch (\PDOException $e) {
|
||||
$this->log->error(
|
||||
"Cannot execute query",
|
||||
[
|
||||
"dsn" => $this->dsn,
|
||||
"query" => $query,
|
||||
"PDOException" => $e
|
||||
]
|
||||
);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: db query
|
||||
|
||||
/**
|
||||
* Run a simple query and return its statement
|
||||
*
|
||||
* @param string $query
|
||||
* @return \PDOStatement|false
|
||||
*/
|
||||
public function dbQuery(string $query): \PDOStatement|false
|
||||
{
|
||||
try {
|
||||
return $this->dbh->query($query, \PDO::FETCH_NAMED);
|
||||
} catch (\PDOException $e) {
|
||||
$this->log->error(
|
||||
"Cannot run query",
|
||||
[
|
||||
"dsn" => $this->dsn,
|
||||
"query" => $query,
|
||||
"PDOException" => $e
|
||||
]
|
||||
);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: db prepare & execute calls
|
||||
|
||||
/**
|
||||
* Execute one query with params
|
||||
*
|
||||
* @param string $query
|
||||
* @param array<mixed> $params
|
||||
* @return \PDOStatement|false
|
||||
*/
|
||||
public function dbExecParams(string $query, array $params): \PDOStatement|false
|
||||
{
|
||||
// prepare query
|
||||
if (($cursor = $this->dbPrepare($query)) === false) {
|
||||
return false;
|
||||
}
|
||||
// execute the query, on failure return false
|
||||
if ($this->dbCursorExecute($cursor, $params) === false) {
|
||||
return false;
|
||||
}
|
||||
return $cursor;
|
||||
}
|
||||
|
||||
/**
|
||||
* Prepare query
|
||||
*
|
||||
* @param string $query
|
||||
* @return \PDOStatement|false
|
||||
*/
|
||||
public function dbPrepare(string $query): \PDOStatement|false
|
||||
{
|
||||
try {
|
||||
// store query with cursor so we can reference?
|
||||
return $this->dbh->prepare($query);
|
||||
} catch (\PDOException $e) {
|
||||
$this->log->error(
|
||||
"Cannot open cursor",
|
||||
[
|
||||
"dsn" => $this->dsn,
|
||||
"query" => $query,
|
||||
"PDOException" => $e
|
||||
]
|
||||
);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* execute a cursor
|
||||
*
|
||||
* @param \PDOStatement $cursor
|
||||
* @param array<mixed> $params
|
||||
* @return bool
|
||||
*/
|
||||
public function dbCursorExecute(\PDOStatement $cursor, array $params): bool
|
||||
{
|
||||
try {
|
||||
return $cursor->execute($params);
|
||||
} catch (\PDOException $e) {
|
||||
// write error log
|
||||
$this->log->error(
|
||||
"Cannot execute prepared query",
|
||||
[
|
||||
"dsn" => $this->dsn,
|
||||
"params" => $params,
|
||||
"DumpParams" => $this->__dbGetCursorDump($cursor),
|
||||
"PDOException" => $e
|
||||
]
|
||||
);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: db return array
|
||||
|
||||
/**
|
||||
* Returns hash for query
|
||||
* Hash is used in all internal storage systems for return data
|
||||
*
|
||||
* @param string $query The query to create the hash from
|
||||
* @param array<mixed> $params If the query is params type we need params
|
||||
* data to create a unique call one, optional
|
||||
* @return string Hash, as set by hash long
|
||||
*/
|
||||
public function dbGetQueryHash(string $query, array $params = []): string
|
||||
{
|
||||
return Hash::__hashLong(
|
||||
$query . (
|
||||
$params !== [] ?
|
||||
'#' . json_encode($params) : ''
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* resets all data stored to this query
|
||||
* @param string $query The Query whose cache should be cleaned
|
||||
* @param array<mixed> $params If the query is params type we need params
|
||||
* data to create a unique call one, optional
|
||||
* @return bool False if query not found, true if success
|
||||
*/
|
||||
public function dbCacheReset(string $query, array $params = []): bool
|
||||
{
|
||||
$query_hash = $this->dbGetQueryHash($query, $params);
|
||||
// clears cache for this query
|
||||
if (empty($this->cursor_ext[$query_hash]['query'])) {
|
||||
$this->log->error('Cannot reset cursor_ext with given query and params', [
|
||||
"query" => $query,
|
||||
"params" => $params,
|
||||
]);
|
||||
return false;
|
||||
}
|
||||
unset($this->cursor_ext[$query_hash]);
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* return array with data, when finshed return false
|
||||
* also returns false on error
|
||||
*
|
||||
* TODO: This is currently a one time run
|
||||
* if the same query needs to be run again, the cursor_ext must be reest
|
||||
* with dbCacheReset
|
||||
*
|
||||
* @param string $query
|
||||
* @param array<mixed> $params
|
||||
* @return array<mixed>|false
|
||||
*/
|
||||
public function dbReturnArray(string $query, array $params = []): array|false
|
||||
{
|
||||
$query_hash = $this->dbGetQueryHash($query, $params);
|
||||
if (!isset($this->cursor_ext[$query_hash])) {
|
||||
$this->cursor_ext[$query_hash] = [
|
||||
// cursor null: unset, if set \PDOStatement
|
||||
'cursor' => null,
|
||||
// the query used in this call
|
||||
'query' => $query,
|
||||
// parameter
|
||||
'params' => $params,
|
||||
// how many rows have been read from db
|
||||
'read_rows' => 0,
|
||||
// when fetch array or cache read returns false
|
||||
// in loop read that means dbReturn retuns false without error
|
||||
'finished' => false,
|
||||
];
|
||||
if (!empty($params)) {
|
||||
if (($cursor = $this->dbExecParams($query, $params)) === false) {
|
||||
return false;
|
||||
}
|
||||
} else {
|
||||
if (($cursor = $this->dbQuery($query)) === false) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
$this->cursor_ext[$query_hash]['cursor'] = $cursor;
|
||||
}
|
||||
// flag finished if row is false
|
||||
$row = $this->__dbFetchArray($this->cursor_ext[$query_hash]['cursor']);
|
||||
if ($row === false) {
|
||||
$this->cursor_ext[$query_hash]['finished'] = true;
|
||||
} else {
|
||||
$this->cursor_ext[$query_hash]['read_rows']++;
|
||||
}
|
||||
return $row;
|
||||
}
|
||||
|
||||
// MARK other interface
|
||||
|
||||
/**
|
||||
* get current db handler
|
||||
* this is for raw access
|
||||
*
|
||||
* @return \PDO
|
||||
*/
|
||||
public function getDbh(): \PDO
|
||||
{
|
||||
return $this->dbh;
|
||||
}
|
||||
}
|
||||
|
||||
// __END__
|
||||
@@ -175,7 +175,7 @@ class Curl implements Interface\RequestsInterface
|
||||
* @param array{0:string,1:string,2:string} $auth
|
||||
* @return array{auth_basic_header:string,auth_type:int,auth_userpwd:string}
|
||||
*/
|
||||
private function authParser(?array $auth): array
|
||||
private function authParser(array $auth): array
|
||||
{
|
||||
$return_auth = [
|
||||
'auth_basic_header' => '',
|
||||
@@ -376,6 +376,8 @@ class Curl implements Interface\RequestsInterface
|
||||
// convert to string as JSON block if it is an array
|
||||
if (is_array($body)) {
|
||||
$params = Json::jsonConvertArrayTo($body);
|
||||
} elseif (is_string($body)) {
|
||||
$params = $body;
|
||||
}
|
||||
return $params ?? '';
|
||||
}
|
||||
@@ -505,36 +507,59 @@ class Curl implements Interface\RequestsInterface
|
||||
return $headers;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the array block that is sent to the request call
|
||||
* Make sure that if headers is set as key but null it stays null and set to empty array
|
||||
* if headers key is missing
|
||||
* "get" calls do not set any body (null)
|
||||
*
|
||||
* phpcs:disable Generic.Files.LineLength
|
||||
* @param string $type if set as get do not add body, else add body
|
||||
* @param array{auth?:null|array{0:string,1:string,2:string},headers?:null|array<string,string|array<string>>,query?:null|array<string,string>,body?:null|string|array<mixed>,http_errors?:null|bool} $options Request options
|
||||
* @return array{auth:null|array{0:string,1:string,2:string},headers:null|array<string,string|array<string>>,query:null|array<string,string>,body:null|string|array<mixed>,http_errors:null|bool}
|
||||
* phpcs:enable Generic.Files.LineLength
|
||||
*/
|
||||
private function setOptions(string $type, array $options): array
|
||||
{
|
||||
return [
|
||||
"auth" => !array_key_exists('auth', $options) ? ['', '', ''] : $options['auth'],
|
||||
"headers" => !array_key_exists('headers', $options) ? [] : $options['headers'],
|
||||
"query" => $options['query'] ?? null,
|
||||
"http_errors" => !array_key_exists('http_errors', $options) ? null : $options['http_errors'],
|
||||
"body" => $options["body"] ??
|
||||
// check if we need a payload data set, set empty on not set
|
||||
(in_array($type, self::MANDATORY_POST_FIELDS) && !isset($options['body']) ? [] : null)
|
||||
];
|
||||
}
|
||||
|
||||
// MARK: main curl request
|
||||
|
||||
/**
|
||||
* Overall request call
|
||||
*
|
||||
* @param string $type get, post, pathc, put, delete:
|
||||
* if not set or invalid throw error
|
||||
* @param string $url The URL being requested,
|
||||
* including domain and protocol
|
||||
* @param null|array<string,string|array<string>> $headers Headers to be used in the request
|
||||
* @param null|array<string,string> $query Optinal query parameters
|
||||
* @param null|string|array<string,mixed> $body Data body, converted to JSON
|
||||
* @param null|bool $http_errors Throw exception on http response
|
||||
* 400 or higher if set to true
|
||||
* @param null|array{0:string,1:string,2:string} $auth auth array, if null reset global set auth
|
||||
* @return array{code:string,headers:array<string,array<string>>,content:string}
|
||||
* phpcs:disable Generic.Files.LineLength
|
||||
* @param string $type get, post, pathc, put, delete:
|
||||
* if not set or invalid throw error
|
||||
* @param string $url The URL being requested,
|
||||
* including domain and protocol
|
||||
* @param array{auth?:null|array{0:string,1:string,2:string},headers?:null|array<string,string|array<string>>,query?:null|array<string,string>,body?:null|string|array<mixed>,http_errors?:null|bool} $options Request options
|
||||
* @return array{code:string,headers:array<string,array<string>>,content:string} Return content
|
||||
* code: HTTP code, if http_errors if off, this can also hold 400 or 500 type codes
|
||||
* headers: earch header entry has an array of the entries, can be more than one if proxied, etc
|
||||
* content: content string as is, if JSON type must be decoded afterwards
|
||||
* @throws \RuntimeException if type param is not valid
|
||||
* phpcs:enable Generic.Files.LineLength
|
||||
*/
|
||||
private function curlRequest(
|
||||
string $type,
|
||||
string $url,
|
||||
null|array $headers,
|
||||
null|array $query,
|
||||
null|string|array $body,
|
||||
null|bool $http_errors,
|
||||
null|array $auth,
|
||||
array $options,
|
||||
): array {
|
||||
// check if we need a payload data set, set empty on not set
|
||||
$options = $this->setOptions($type, $options);
|
||||
// set auth from override
|
||||
if (is_array($auth)) {
|
||||
$auth_data = $this->authParser($auth);
|
||||
if (is_array($options['auth'])) {
|
||||
$auth_data = $this->authParser($options['auth']);
|
||||
} else {
|
||||
$auth_data = [
|
||||
'auth_basic_header' => null,
|
||||
@@ -543,9 +568,9 @@ class Curl implements Interface\RequestsInterface
|
||||
];
|
||||
}
|
||||
// build url
|
||||
$this->url = $this->buildQuery($url, $query);
|
||||
$this->url = $this->buildQuery($url, $options['query']);
|
||||
$this->headers = $this->convertHeaders($this->buildHeaders(
|
||||
$headers,
|
||||
$options['headers'],
|
||||
$auth_data['auth_basic_header']
|
||||
));
|
||||
if (!in_array($type, self::VALID_REQUEST_TYPES)) {
|
||||
@@ -578,8 +603,8 @@ class Curl implements Interface\RequestsInterface
|
||||
curl_setopt($handle, CURLOPT_CUSTOMREQUEST, strtoupper($type));
|
||||
}
|
||||
// set body data if not null, will send empty [] for empty data
|
||||
if (in_array($type, self::HAVE_POST_FIELDS) && $body !== null) {
|
||||
curl_setopt($handle, CURLOPT_POSTFIELDS, $this->convertPayloadData($body));
|
||||
if (in_array($type, self::HAVE_POST_FIELDS) && $options['body'] !== null) {
|
||||
curl_setopt($handle, CURLOPT_POSTFIELDS, $this->convertPayloadData($options['body']));
|
||||
}
|
||||
// reset all headers before we start the call
|
||||
$this->received_headers = [];
|
||||
@@ -588,7 +613,7 @@ class Curl implements Interface\RequestsInterface
|
||||
// for debug
|
||||
// print "CURLINFO_HEADER_OUT: <pre>" . curl_getinfo($handle, CURLINFO_HEADER_OUT) . "</pre>";
|
||||
// get response code and bail on not authorized
|
||||
$http_response = $this->handleCurlResponse($handle, $http_result, $http_errors);
|
||||
$http_response = $this->handleCurlResponse($handle, $http_result, $options['http_errors']);
|
||||
// close handler
|
||||
$this->handleCurlClose($handle);
|
||||
// return response and result
|
||||
@@ -641,7 +666,7 @@ class Curl implements Interface\RequestsInterface
|
||||
* @param array{auth_type:?int,auth_userpwd:?string} $auth_data auth options to override global
|
||||
* @return void
|
||||
*/
|
||||
private function setCurlOptions(\CurlHandle $handle, array $headers, ?array $auth_data): void
|
||||
private function setCurlOptions(\CurlHandle $handle, array $headers, array $auth_data): void
|
||||
{
|
||||
// for not Basic auth only, basic auth sets its own header
|
||||
if ($auth_data['auth_type'] !== null || $auth_data['auth_userpwd'] !== null) {
|
||||
@@ -674,8 +699,7 @@ class Curl implements Interface\RequestsInterface
|
||||
$timeout_requires_no_signal = false;
|
||||
// if we have a timeout signal
|
||||
if (!empty($this->config['timeout'])) {
|
||||
$timeout_requires_no_signal = $timeout_requires_no_signal ||
|
||||
$this->config['timeout'] < 1;
|
||||
$timeout_requires_no_signal = $this->config['timeout'] < 1;
|
||||
curl_setopt($handle, CURLOPT_TIMEOUT_MS, $this->config['timeout'] * 1000);
|
||||
}
|
||||
if (!empty($this->config['connection_timeout'])) {
|
||||
@@ -772,9 +796,10 @@ class Curl implements Interface\RequestsInterface
|
||||
* Handle curl response, will throw exception on anything that is lower 400
|
||||
* can be turned off by setting http_errors to false
|
||||
*
|
||||
* @param string $http_result result string from the url call
|
||||
* @param ?bool $http_errors if we should throw an exception on error, override config setting
|
||||
* @param \CurlHandle $handle Curl handler
|
||||
* @param string $http_result result string from the url call
|
||||
* @param ?bool $http_errors if we should throw an exception on error,
|
||||
* override config setting
|
||||
* @return string http response code
|
||||
* @throws \RuntimeException if http_errors is true then will throw exception on any response code >= 400
|
||||
*/
|
||||
@@ -1000,21 +1025,15 @@ class Curl implements Interface\RequestsInterface
|
||||
// can have
|
||||
// - headers
|
||||
// - query
|
||||
// - auth: null for no auth at all
|
||||
// - http_errors: false for no exception on http error
|
||||
// depending on type, must have (post/put/patch), optional for (delete)
|
||||
// - body
|
||||
$type = strtolower($type);
|
||||
// check if we need a payload data set, set empty on not set
|
||||
if (in_array($type, self::MANDATORY_POST_FIELDS) && !isset($options['body'])) {
|
||||
$options['body'] = [];
|
||||
}
|
||||
return $this->curlRequest(
|
||||
$type,
|
||||
$url,
|
||||
!array_key_exists('headers', $options) ? [] : $options['headers'],
|
||||
$options['query'] ?? null,
|
||||
$options['body'] ?? null,
|
||||
!array_key_exists('http_errors', $options) ? null : $options['http_errors'],
|
||||
!array_key_exists('auth', $options) ? [] : $options['auth'],
|
||||
$options,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -18,30 +18,6 @@ namespace CoreLibs\UrlRequests;
|
||||
|
||||
trait CurlTrait
|
||||
{
|
||||
/**
|
||||
* Set the array block that is sent to the request call
|
||||
* Make sure that if headers is set as key but null it stays null and set to empty array
|
||||
* if headers key is missing
|
||||
* "get" calls do not set any body
|
||||
*
|
||||
* @param string $type if set as get do not add body, else add body
|
||||
* @param array{auth?:null|array{0:string,1:string,2:string},headers?:null|array<string,string|array<string>>,query?:null|array<string,string>,body?:null|string|array<mixed>,http_errors?:null|bool} $options Request options
|
||||
* @return array{auth?:array{0:string,1:string,2:string},headers?:null|array<string,string|array<string>>,query?:null|array<string,string>,body?:null|string|array<mixed>,http_errors?:null|bool}
|
||||
*/
|
||||
private function setOptions(string $type, array $options): array
|
||||
{
|
||||
$base = [
|
||||
"auth" => !array_key_exists('auth', $options) ? [] : $options['auth'],
|
||||
"headers" => !array_key_exists('headers', $options) ? [] : $options['headers'],
|
||||
"query" => $options['query'] ?? null,
|
||||
"http_errors" => !array_key_exists('http_errors', $options) ? null : $options['http_errors'],
|
||||
];
|
||||
if ($type != "get") {
|
||||
$base["body"] = $options['body'] ?? null;
|
||||
}
|
||||
return $base;
|
||||
}
|
||||
|
||||
/**
|
||||
* combined set call for any type of request with options type parameters
|
||||
* The following options can be set:
|
||||
@@ -71,7 +47,7 @@ trait CurlTrait
|
||||
return $this->request(
|
||||
"get",
|
||||
$url,
|
||||
$this->setOptions('get', $options),
|
||||
$options,
|
||||
);
|
||||
}
|
||||
|
||||
@@ -89,7 +65,7 @@ trait CurlTrait
|
||||
return $this->request(
|
||||
"post",
|
||||
$url,
|
||||
$this->setOptions('post', $options),
|
||||
$options,
|
||||
);
|
||||
}
|
||||
|
||||
@@ -107,7 +83,7 @@ trait CurlTrait
|
||||
return $this->request(
|
||||
"put",
|
||||
$url,
|
||||
$this->setOptions('put', $options),
|
||||
$options,
|
||||
);
|
||||
}
|
||||
|
||||
@@ -125,7 +101,7 @@ trait CurlTrait
|
||||
return $this->request(
|
||||
"patch",
|
||||
$url,
|
||||
$this->setOptions('patch', $options),
|
||||
$options,
|
||||
);
|
||||
}
|
||||
|
||||
@@ -144,7 +120,7 @@ trait CurlTrait
|
||||
return $this->request(
|
||||
"delete",
|
||||
$url,
|
||||
$this->setOptions('delete', $options),
|
||||
$options,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user