diff options
| author | nsfisis <nsfisis@gmail.com> | 2026-06-29 01:30:42 +0900 |
|---|---|---|
| committer | nsfisis <nsfisis@gmail.com> | 2026-06-29 01:31:37 +0900 |
| commit | 1036b7e33a4360df8b99f81ef03492fee8328bd0 (patch) | |
| tree | d963d6f83674884dabbd20fd60c5c8f75c661347 /crates/shirabe/src/json/json_file.rs | |
| parent | 9be0f98f71fe8071ab839ac1036b4064ac3172b4 (diff) | |
| download | php-shirabe-1036b7e33a4360df8b99f81ef03492fee8328bd0.tar.gz php-shirabe-1036b7e33a4360df8b99f81ef03492fee8328bd0.tar.zst php-shirabe-1036b7e33a4360df8b99f81ef03492fee8328bd0.zip | |
refactor(json): replace seld/jsonlint with serde_json
Validate JSON syntax with serde_json's parse errors in JsonFile, and detect
duplicate keys in ConfigValidator with a hand-written serde visitor, dropping
the now-unused JsonParser/Lexer/DuplicateKeyException ports. ParsingException
is kept as the thrown error type and downcast signal.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Diffstat (limited to 'crates/shirabe/src/json/json_file.rs')
| -rw-r--r-- | crates/shirabe/src/json/json_file.rs | 55 |
1 files changed, 26 insertions, 29 deletions
diff --git a/crates/shirabe/src/json/json_file.rs b/crates/shirabe/src/json/json_file.rs index 0f609f2..b95732f 100644 --- a/crates/shirabe/src/json/json_file.rs +++ b/crates/shirabe/src/json/json_file.rs @@ -10,8 +10,7 @@ use crate::util::HttpDownloader; use crate::util::Silencer; use indexmap::IndexMap; use shirabe_external_packages::composer::pcre::{CaptureKey, Preg}; -use shirabe_external_packages::seld::json_lint::JsonParser; -use shirabe_external_packages::seld::json_lint::ParsingException; +use shirabe_external_packages::seld::json_lint::{ParsingException, ParsingExceptionDetails}; use shirabe_php_shim::{ InvalidArgumentException, JSON_PRETTY_PRINT, JSON_UNESCAPED_SLASHES, JSON_UNESCAPED_UNICODE, PhpMixed, RuntimeException, UnexpectedValueException, dirname, file_exists, file_get_contents, @@ -537,39 +536,37 @@ impl JsonFile { /// @throws ParsingException /// @return bool true on success pub(crate) fn validate_syntax(json: &str, file: Option<&str>) -> anyhow::Result<bool> { - let mut parser = JsonParser::new(); - let result = parser.lint(json); - if result.is_none() { - // TODO(phase-c): Rust's &str is guaranteed as UTF-8, but PHP string is not. Change `json` - // to &[u8] and check UTF-8 validity here. + // TODO(phase-d): make json_decode() returns an error object with details. + let error = match serde_json::from_str::<serde_json::Value>(json) { + Ok(_) => { + // TODO(phase-c): Rust's &str is guaranteed as UTF-8, but PHP string is not. Change `json` + // to &[u8] and check UTF-8 validity here. - // if (defined('JSON_ERROR_UTF8') && JSON_ERROR_UTF8 === json_last_error()) { - // if ($file === null) { - // throw new \UnexpectedValueException('The input is not UTF-8, could not parse as JSON'); - // } else { - // throw new \UnexpectedValueException('"' . $file . '" is not UTF-8, could not parse as JSON'); - // } - // } + // if (defined('JSON_ERROR_UTF8') && JSON_ERROR_UTF8 === json_last_error()) { + // if ($file === null) { + // throw new \UnexpectedValueException('The input is not UTF-8, could not parse as JSON'); + // } else { + // throw new \UnexpectedValueException('"' . $file . '" is not UTF-8, could not parse as JSON'); + // } + // } - return Ok(true); - } + return Ok(true); + } + Err(e) => e, + }; - let result = result.unwrap(); + let details = ParsingExceptionDetails { + line: Some(error.line() as i64), + ..Default::default() + }; Err(match file { None => ParsingException::new( - format!( - "The input does not contain valid JSON\n{}", - result.get_message() - ), - result.get_details().clone(), + format!("The input does not contain valid JSON\n{error}"), + details, ), - Some(f) => ParsingException::new( - format!( - "\"{}\" does not contain valid JSON\n{}", - f, - result.get_message() - ), - result.get_details().clone(), + Some(file) => ParsingException::new( + format!("\"{file}\" does not contain valid JSON\n{error}"), + details, ), } .into()) |
