|
@@ -81,6 +81,20 @@ class NewsFfiService
|
|
|
return self::$instance;
|
|
return self::$instance;
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+ /**
|
|
|
|
|
+ * Safely encode data to JSON, replacing invalid UTF-8 bytes instead of failing.
|
|
|
|
|
+ * PHP 7.2+ provides JSON_INVALID_UTF8_SUBSTITUTE to handle malformed bytes gracefully.
|
|
|
|
|
+ * Falls back to '{}' on non-UTF8-related encoding failures (e.g. recursion).
|
|
|
|
|
+ */
|
|
|
|
|
+ private function safeJsonEncode(mixed $data): string
|
|
|
|
|
+ {
|
|
|
|
|
+ try {
|
|
|
|
|
+ return json_encode($data, JSON_INVALID_UTF8_SUBSTITUTE | JSON_THROW_ON_ERROR);
|
|
|
|
|
+ } catch (\JsonException) {
|
|
|
|
|
+ return '{}';
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
/**
|
|
/**
|
|
|
* Generic private method to handle FFI calls, reducing code duplication.
|
|
* Generic private method to handle FFI calls, reducing code duplication.
|
|
|
* It marshals arguments to C-compatible types and unmarshals the JSON result.
|
|
* It marshals arguments to C-compatible types and unmarshals the JSON result.
|
|
@@ -110,29 +124,31 @@ class NewsFfiService
|
|
|
public function getCategoryList(array $where = []): array
|
|
public function getCategoryList(array $where = []): array
|
|
|
{
|
|
{
|
|
|
$payload = empty($where) ? new \stdClass() : $where;
|
|
$payload = empty($where) ? new \stdClass() : $where;
|
|
|
- return $this->call('GetCategoryList', json_encode($payload));
|
|
|
|
|
|
|
+ return $this->call('GetCategoryList', $this->safeJsonEncode($payload));
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
public function getCategoryById(int $id): array
|
|
public function getCategoryById(int $id): array
|
|
|
{
|
|
{
|
|
|
- return $this->call('GetCategoryByID', $id);
|
|
|
|
|
|
|
+ $result = $this->call('GetCategoryByID', $id);
|
|
|
|
|
+ return is_array($result) ? $result : [];
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
public function createCategory(array $data): array
|
|
public function createCategory(array $data): array
|
|
|
{
|
|
{
|
|
|
$payload = empty($data) ? new \stdClass() : $data;
|
|
$payload = empty($data) ? new \stdClass() : $data;
|
|
|
- return $this->call('CreateCategory', json_encode($payload));
|
|
|
|
|
|
|
+ return $this->call('CreateCategory', $this->safeJsonEncode($payload));
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
public function updateCategory(int $id, array $data): array
|
|
public function updateCategory(int $id, array $data): array
|
|
|
{
|
|
{
|
|
|
$payload = empty($data) ? new \stdClass() : $data;
|
|
$payload = empty($data) ? new \stdClass() : $data;
|
|
|
- return $this->call('UpdateCategory', $id, json_encode($payload));
|
|
|
|
|
|
|
+ return $this->call('UpdateCategory', $id, $this->safeJsonEncode($payload));
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
public function deleteCategory(int $id): array
|
|
public function deleteCategory(int $id): array
|
|
|
{
|
|
{
|
|
|
- return $this->call('DeleteCategory', $id);
|
|
|
|
|
|
|
+ $result = $this->call('DeleteCategory', $id);
|
|
|
|
|
+ return is_array($result) ? $result : [];
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
// --- News Service Wrappers ---
|
|
// --- News Service Wrappers ---
|
|
@@ -140,34 +156,37 @@ class NewsFfiService
|
|
|
public function getNewsList(array $params = []): array
|
|
public function getNewsList(array $params = []): array
|
|
|
{
|
|
{
|
|
|
$payload = empty($params) ? new \stdClass() : $params;
|
|
$payload = empty($params) ? new \stdClass() : $params;
|
|
|
- return $this->call('GetNewsList', json_encode($payload));
|
|
|
|
|
|
|
+ return $this->call('GetNewsList', $this->safeJsonEncode($payload));
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
public function getNewsById(int $id): array
|
|
public function getNewsById(int $id): array
|
|
|
{
|
|
{
|
|
|
- return $this->call('GetNewsByID', $id);
|
|
|
|
|
|
|
+ $result = $this->call('GetNewsByID', $id);
|
|
|
|
|
+ return is_array($result) ? $result : [];
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
public function createNews(array $data): array
|
|
public function createNews(array $data): array
|
|
|
{
|
|
{
|
|
|
$payload = empty($data) ? new \stdClass() : $data;
|
|
$payload = empty($data) ? new \stdClass() : $data;
|
|
|
- $result = $this->call('CreateNews', json_encode($payload));
|
|
|
|
|
|
|
+ $result = $this->call('CreateNews', $this->safeJsonEncode($payload));
|
|
|
return is_array($result) ? $result : [];
|
|
return is_array($result) ? $result : [];
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
public function updateNews(int $id, array $data): array
|
|
public function updateNews(int $id, array $data): array
|
|
|
{
|
|
{
|
|
|
$payload = empty($data) ? new \stdClass() : $data;
|
|
$payload = empty($data) ? new \stdClass() : $data;
|
|
|
- return $this->call('UpdateNews', $id, json_encode($payload));
|
|
|
|
|
|
|
+ return $this->call('UpdateNews', $id, $this->safeJsonEncode($payload));
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
public function deleteNews(int $id): array
|
|
public function deleteNews(int $id): array
|
|
|
{
|
|
{
|
|
|
- return $this->call('DeleteNews', $id);
|
|
|
|
|
|
|
+ $result = $this->call('DeleteNews', $id);
|
|
|
|
|
+ return is_array($result) ? $result : [];
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
public function incrementNewsViews(int $id): array
|
|
public function incrementNewsViews(int $id): array
|
|
|
{
|
|
{
|
|
|
- return $this->call('IncrementNewsViews', $id);
|
|
|
|
|
|
|
+ $result = $this->call('IncrementNewsViews', $id);
|
|
|
|
|
+ return is_array($result) ? $result : [];
|
|
|
}
|
|
}
|
|
|
}
|
|
}
|