From 79b504e55cd4c4d1da102c3a076dc2a2e1edcd65 Mon Sep 17 00:00:00 2001 From: nsfisis Date: Mon, 17 Aug 2026 08:05:42 +0900 Subject: refactor(pcre): return the Preg $matches instead of filling an out-param `Composer\Pcre\Preg` fills `$matches` through a by-ref parameter, and the port mirrored that with a `&mut` (or `Option<&mut>`) out-param plus a bool or count return. Callers had to declare an empty map one line ahead of the call, and the type never said the map is only meaningful when the call matched. Return the matches instead: - match3/match4/is_match3/is_match4 -> Option - is_match_named -> Option - match_all2/is_match_all -> PregMatchesAll - is_match_all_with_offsets3 -> PregMatchesAllWithOffsets Nothing is lost: the bool is `Option::is_some()`, and the occurrence count is the length of any one column of a PREG_PATTERN_ORDER map, now spelled `PregMatchesAll::occurrence_count()`. is_match() still answers the bool question directly for callers that want no groups. Co-Authored-By: Claude Opus 5 (1M context) --- .../shirabe/src/repository/composer_repository.rs | 17 +- .../shirabe/src/repository/platform_repository.rs | 223 +++++++-------------- .../shirabe/src/repository/vcs/forgejo_driver.rs | 5 +- .../src/repository/vcs/git_bitbucket_driver.rs | 10 +- crates/shirabe/src/repository/vcs/git_driver.rs | 55 +++-- crates/shirabe/src/repository/vcs/github_driver.rs | 50 ++--- crates/shirabe/src/repository/vcs/gitlab_driver.rs | 19 +- crates/shirabe/src/repository/vcs/hg_driver.rs | 65 +++--- crates/shirabe/src/repository/vcs/svn_driver.rs | 139 ++++++------- 9 files changed, 217 insertions(+), 366 deletions(-) (limited to 'crates/shirabe/src/repository') diff --git a/crates/shirabe/src/repository/composer_repository.rs b/crates/shirabe/src/repository/composer_repository.rs index 33703709..6feb4359 100644 --- a/crates/shirabe/src/repository/composer_repository.rs +++ b/crates/shirabe/src/repository/composer_repository.rs @@ -37,7 +37,7 @@ use futures::StreamExt; use futures::stream::FuturesOrdered; use indexmap::IndexMap; use shirabe_metadata_minifier::MetadataMinifier; -use shirabe_pcre::{CaptureKey, Preg, PregMatchedGroups}; +use shirabe_pcre::{CaptureKey, Preg}; use shirabe_php_shim::Catch as _; use shirabe_php_shim::{ AnyThrowable, CmpOp, InvalidArgumentException, LogicException, PHP_EOL, PhpMixed, @@ -245,11 +245,9 @@ impl ComposerRepository { .to_string(); // force url for packagist.org to repo.packagist.org - let mut match_packagist = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(match_packagist) = Preg::is_match3( php_regex!(r"{^(?Phttps?)://packagist\.org/?$}i"), &url, - Some(&mut match_packagist), ) { let proto = match_packagist .get(&CaptureKey::ByName("proto".to_string())) @@ -781,11 +779,9 @@ impl ComposerRepository { if self.has_providers()? || self.lazy_providers_url.is_some() { // optimize search for "^foo/bar" where at least "^foo/" is present by loading this directly from the listUrl if present - let mut match_groups = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(match_groups) = Preg::is_match3( php_regex!(r"{^\^(?P(?P[a-z0-9_.-]+)/[a-z0-9_.-]*)\*?$}i"), &query, - Some(&mut match_groups), ) && let Some(list_url) = self.list_url.as_ref() { let q = match_groups @@ -2430,12 +2426,7 @@ impl ComposerRepository { } if url.starts_with('/') { - let mut matches = PregMatchedGroups::new(); - if Preg::is_match3( - php_regex!(r"{^[^:]++://[^/]*+}"), - &self.url, - Some(&mut matches), - ) { + if let Some(matches) = Preg::is_match3(php_regex!(r"{^[^:]++://[^/]*+}"), &self.url) { return Ok(format!( "{}{}", matches diff --git a/crates/shirabe/src/repository/platform_repository.rs b/crates/shirabe/src/repository/platform_repository.rs index 6c25d967..29f66647 100644 --- a/crates/shirabe/src/repository/platform_repository.rs +++ b/crates/shirabe/src/repository/platform_repository.rs @@ -16,7 +16,7 @@ use crate::plugin::plugin_interface::{self}; use crate::repository::ArrayRepository; use crate::repository::RepositoryInterface; use indexmap::IndexMap; -use shirabe_pcre::{CaptureKey, Preg, PregMatchedGroups}; +use shirabe_pcre::{CaptureKey, Preg}; use shirabe_php_rpc::PlatformInfo; use shirabe_php_shim::{ InvalidArgumentException, PhpMixed, UnexpectedValueException, array_map_str_fn, @@ -316,11 +316,9 @@ impl PlatformRepository { let info = platform_info.get_extension_info(name); // librabbitmq version => 0.9.0 - let mut librabbitmq_matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(librabbitmq_matches) = Preg::is_match3( php_regex!("/^librabbitmq version => (?.+)$/im"), info, - Some(&mut librabbitmq_matches), ) { self.add_library( &mut libraries, @@ -335,11 +333,9 @@ impl PlatformRepository { } // AMQP protocol version => 0-9-1 - let mut protocol_matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(protocol_matches) = Preg::is_match3( php_regex!("/^AMQP protocol version => (?.+)$/im"), info, - Some(&mut protocol_matches), ) { let version_str = protocol_matches .get(&CaptureKey::ByName("version".to_string())) @@ -360,12 +356,9 @@ impl PlatformRepository { let info = platform_info.get_extension_info(name); // BZip2 Version => 1.0.6, 6-Sept-2010 - let mut matches = PregMatchedGroups::new(); - if Preg::is_match3( - php_regex!("/^BZip2 Version => (?.*),/im"), - info, - Some(&mut matches), - ) { + if let Some(matches) = + Preg::is_match3(php_regex!("/^BZip2 Version => (?.*),/im"), info) + { self.add_library( &mut libraries, name, @@ -393,11 +386,9 @@ impl PlatformRepository { let info = platform_info.get_extension_info(name); // SSL Version => OpenSSL/1.0.1t - let mut ssl_matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(ssl_matches) = Preg::is_match3( php_regex!("{^SSL Version => (?[^/]+)/(?.+)$}im"), info, - Some(&mut ssl_matches), ) { let ssl_library_raw = ssl_matches .get(&CaptureKey::ByName("library".to_string())) @@ -428,11 +419,9 @@ impl PlatformRepository { } else { let (shortlib, ssl_lib); if library.starts_with("(securetransport)") { - let mut securetransport_matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(securetransport_matches) = Preg::is_match3( php_regex!("{^\\(securetransport\\) ([a-z0-9]+)}"), &library, - Some(&mut securetransport_matches), ) { shortlib = "securetransport".to_string(); let m1 = securetransport_matches @@ -460,13 +449,11 @@ impl PlatformRepository { } // libSSH Version => libssh2/1.4.3 - let mut ssh_matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(ssh_matches) = Preg::is_match3( php_regex!( "{^libSSH Version => (?[^/]+)/(?.+?)(?:/.*)?$}im" ), info, - Some(&mut ssh_matches), ) { let ssh_library = ssh_matches .get(&CaptureKey::ByName("library".to_string())) @@ -487,12 +474,9 @@ impl PlatformRepository { } // ZLib Version => 1.2.8 - let mut zlib_matches = PregMatchedGroups::new(); - if Preg::is_match3( - php_regex!("{^ZLib Version => (?.+)$}im"), - info, - Some(&mut zlib_matches), - ) { + if let Some(zlib_matches) = + Preg::is_match3(php_regex!("{^ZLib Version => (?.+)$}im"), info) + { self.add_library( &mut libraries, &format!("{}-zlib", name), @@ -510,12 +494,9 @@ impl PlatformRepository { let info = platform_info.get_extension_info(name); // timelib version => 2018.03 - let mut timelib_matches = PregMatchedGroups::new(); - if Preg::is_match3( - php_regex!("/^timelib version => (?.+)$/im"), - info, - Some(&mut timelib_matches), - ) { + if let Some(timelib_matches) = + Preg::is_match3(php_regex!("/^timelib version => (?.+)$/im"), info) + { self.add_library( &mut libraries, &format!("{}-timelib", name), @@ -529,23 +510,19 @@ impl PlatformRepository { } // Timezone Database => internal - let mut zoneinfo_source_matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(zoneinfo_source_matches) = Preg::is_match3( php_regex!("/^Timezone Database => (?internal|external)$/im"), info, - Some(&mut zoneinfo_source_matches), ) { let external = zoneinfo_source_matches .get(&CaptureKey::ByName("source".to_string())) .map(|s| s == "external") .unwrap_or(false); - let mut zoneinfo_matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(zoneinfo_matches) = Preg::is_match3( php_regex!( "/^\"Olson\" Timezone Database Version => (?.+?)(?:\\.system)?$/im" ), info, - Some(&mut zoneinfo_matches), ) { let zoneinfo_version = zoneinfo_matches .get(&CaptureKey::ByName("version".to_string())) @@ -554,15 +531,15 @@ impl PlatformRepository { // If the timezonedb is provided by ext/timezonedb, register that version as a replacement if external && loaded_extensions.iter().any(|n| n == "timezonedb") { self.add_library( - &mut libraries, - "timezonedb-zoneinfo", - Some(&zoneinfo_version), - Some( - "zoneinfo (\"Olson\") database for date (replaced by timezonedb)", - ), - &[format!("{}-zoneinfo", name)], - &[], - )?; + &mut libraries, + "timezonedb-zoneinfo", + Some(&zoneinfo_version), + Some( + "zoneinfo (\"Olson\") database for date (replaced by timezonedb)", + ), + &[format!("{}-zoneinfo", name)], + &[], + )?; } else { self.add_library( &mut libraries, @@ -581,12 +558,9 @@ impl PlatformRepository { let info = platform_info.get_extension_info(name); // libmagic => 537 - let mut magic_matches = PregMatchedGroups::new(); - if Preg::is_match3( - php_regex!("/^libmagic => (?.+)$/im"), - info, - Some(&mut magic_matches), - ) { + if let Some(magic_matches) = + Preg::is_match3(php_regex!("/^libmagic => (?.+)$/im"), info) + { self.add_library( &mut libraries, &format!("{}-libmagic", name), @@ -617,11 +591,9 @@ impl PlatformRepository { let info = platform_info.get_extension_info(name); - let mut libjpeg_matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(libjpeg_matches) = Preg::is_match3( php_regex!("/^libJPEG Version => (?.+?)(?: compatible)?$/im"), info, - Some(&mut libjpeg_matches), ) { let libjpeg_version = libjpeg_matches .get(&CaptureKey::ByName("version".to_string())) @@ -638,12 +610,9 @@ impl PlatformRepository { )?; } - let mut libpng_matches = PregMatchedGroups::new(); - if Preg::is_match3( - php_regex!("/^libPNG Version => (?.+)$/im"), - info, - Some(&mut libpng_matches), - ) { + if let Some(libpng_matches) = + Preg::is_match3(php_regex!("/^libPNG Version => (?.+)$/im"), info) + { self.add_library( &mut libraries, &format!("{}-libpng", name), @@ -656,11 +625,9 @@ impl PlatformRepository { )?; } - let mut freetype_matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(freetype_matches) = Preg::is_match3( php_regex!("/^FreeType Version => (?.+)$/im"), info, - Some(&mut freetype_matches), ) { self.add_library( &mut libraries, @@ -674,11 +641,9 @@ impl PlatformRepository { )?; } - let mut libxpm_matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(libxpm_matches) = Preg::is_match3( php_regex!("/^libXpm Version => (?\\d+)$/im"), info, - Some(&mut libxpm_matches), ) { let version_id: i64 = libxpm_matches .get(&CaptureKey::ByName("versionId".to_string())) @@ -748,12 +713,9 @@ impl PlatformRepository { &[], )?; } else { - let mut matches = PregMatchedGroups::new(); - if Preg::is_match3( - php_regex!("/^ICU version => (?.+)$/im"), - info, - Some(&mut matches), - ) { + if let Some(matches) = + Preg::is_match3(php_regex!("/^ICU version => (?.+)$/im"), info) + { self.add_library( &mut libraries, "icu", @@ -768,11 +730,9 @@ impl PlatformRepository { } // ICU TZData version => 2019c - let mut zoneinfo_matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(zoneinfo_matches) = Preg::is_match3( php_regex!("/^ICU TZData version => (?.*)$/im"), info, - Some(&mut zoneinfo_matches), ) { let zi_version = zoneinfo_matches .get(&CaptureKey::ByName("version".to_string())) @@ -833,11 +793,9 @@ impl PlatformRepository { Self::imagick_get_version_string(image_magick_version); // 6.x: ImageMagick 6.2.9 08/24/06 Q16 http://www.imagemagick.org // 7.x: ImageMagick 7.0.8-34 Q16 x86_64 2019-03-23 https://imagemagick.org - let mut matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(matches) = Preg::is_match3( php_regex!("/^ImageMagick (?[\\d.]+)(?:-(?\\d+))?/"), &image_magick_version_str, - Some(&mut matches), ) { let mut version_built = matches .get(&CaptureKey::ByName("version".to_string())) @@ -861,17 +819,12 @@ impl PlatformRepository { "ldap" => { let info = platform_info.get_extension_info(name); - let mut matches = PregMatchedGroups::new(); - let mut vendor_matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(matches) = Preg::is_match3( php_regex!("/^Vendor Version => (?\\d+)$/im"), info, - Some(&mut matches), - ) && Preg::is_match3( - php_regex!("/^Vendor Name => (?.+)$/im"), - info, - Some(&mut vendor_matches), - ) { + ) && let Some(vendor_matches) = + Preg::is_match3(php_regex!("/^Vendor Name => (?.+)$/im"), info) + { let version_id: i64 = matches .get(&CaptureKey::ByName("versionId".to_string())) .and_then(|s| s.parse().ok()) @@ -921,12 +874,9 @@ impl PlatformRepository { let info = platform_info.get_extension_info(name); // libmbfl version => 1.3.2 - let mut libmbfl_matches = PregMatchedGroups::new(); - if Preg::is_match3( - php_regex!("/^libmbfl version => (?.+)$/im"), - info, - Some(&mut libmbfl_matches), - ) { + if let Some(libmbfl_matches) = + Preg::is_match3(php_regex!("/^libmbfl version => (?.+)$/im"), info) + { self.add_library( &mut libraries, &format!("{}-libmbfl", name), @@ -957,13 +907,11 @@ impl PlatformRepository { // Multibyte regex (oniguruma) version => 5.9.5 // oniguruma version => 6.9.0 } else { - let mut oniguruma_matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(oniguruma_matches) = Preg::is_match3( php_regex!( "/^(?:oniguruma|Multibyte regex \\(oniguruma\\)) version => (?.+)$/im" ), info, - Some(&mut oniguruma_matches), ) { self.add_library( &mut libraries, @@ -983,11 +931,9 @@ impl PlatformRepository { let info = platform_info.get_extension_info(name); // libmemcached version => 1.0.18 - let mut matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(matches) = Preg::is_match3( php_regex!("/^libmemcached version => (?.+)$/im"), info, - Some(&mut matches), ) { self.add_library( &mut libraries, @@ -1009,11 +955,9 @@ impl PlatformRepository { _ => "".to_string(), }; // OpenSSL 1.1.1g 21 Apr 2020 - let mut matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(matches) = Preg::is_match3( php_regex!("{^(?:OpenSSL|LibreSSL)?\\s*(?\\S+)}i"), &openssl_text_str, - Some(&mut matches), ) { let version = matches .get(&CaptureKey::ByName("version".to_string())) @@ -1050,11 +994,9 @@ impl PlatformRepository { let info = platform_info.get_extension_info(name); // PCRE Unicode Version => 12.1.0 - let mut pcre_unicode_matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(pcre_unicode_matches) = Preg::is_match3( php_regex!("/^PCRE Unicode Version => (?.+)$/im"), info, - Some(&mut pcre_unicode_matches), ) { self.add_library( &mut libraries, @@ -1072,13 +1014,11 @@ impl PlatformRepository { "mysqlnd" | "pdo_mysql" => { let info = platform_info.get_extension_info(name); - let mut matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(matches) = Preg::is_match3( php_regex!( "/^(?:Client API version|Version) => mysqlnd (?.+?) /mi" ), info, - Some(&mut matches), ) { self.add_library( &mut libraries, @@ -1096,11 +1036,9 @@ impl PlatformRepository { "mongodb" => { let info = platform_info.get_extension_info(name); - let mut libmongoc_matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(libmongoc_matches) = Preg::is_match3( php_regex!("/^libmongoc bundled version => (?.+)$/im"), info, - Some(&mut libmongoc_matches), ) { self.add_library( &mut libraries, @@ -1114,11 +1052,9 @@ impl PlatformRepository { )?; } - let mut libbson_matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(libbson_matches) = Preg::is_match3( php_regex!("/^libbson bundled version => (?.+)$/im"), info, - Some(&mut libbson_matches), ) { self.add_library( &mut libraries, @@ -1152,11 +1088,9 @@ impl PlatformRepository { // intentional fall-through to next case... let info = platform_info.get_extension_info(name); - let mut matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(matches) = Preg::is_match3( php_regex!("/^PostgreSQL\\(libpq\\) Version => (?.*)$/im"), info, - Some(&mut matches), ) { self.add_library( &mut libraries, @@ -1175,11 +1109,9 @@ impl PlatformRepository { "pdo_pgsql" => { let info = platform_info.get_extension_info(name); - let mut matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(matches) = Preg::is_match3( php_regex!("/^PostgreSQL\\(libpq\\) Version => (?.*)$/im"), info, - Some(&mut matches), ) { self.add_library( &mut libraries, @@ -1199,11 +1131,9 @@ impl PlatformRepository { // Used Library => Compiled => Linked // libpq => 14.3 (Ubuntu 14.3-1.pgdg22.04+1) => 15.0.2 - let mut matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(matches) = Preg::is_match3( php_regex!("/^libpq => (?.+) => (?.+)$/im"), info, - Some(&mut matches), ) { self.add_library( &mut libraries, @@ -1277,12 +1207,9 @@ impl PlatformRepository { "sqlite3" | "pdo_sqlite" => { let info = platform_info.get_extension_info(name); - let mut matches = PregMatchedGroups::new(); - if Preg::is_match3( - php_regex!("/^SQLite Library => (?.+)$/im"), - info, - Some(&mut matches), - ) { + if let Some(matches) = + Preg::is_match3(php_regex!("/^SQLite Library => (?.+)$/im"), info) + { self.add_library( &mut libraries, &format!("{}-sqlite", name), @@ -1299,12 +1226,9 @@ impl PlatformRepository { "ssh2" => { let info = platform_info.get_extension_info(name); - let mut matches = PregMatchedGroups::new(); - if Preg::is_match3( - php_regex!("/^libssh2 version => (?.+)$/im"), - info, - Some(&mut matches), - ) { + if let Some(matches) = + Preg::is_match3(php_regex!("/^libssh2 version => (?.+)$/im"), info) + { self.add_library( &mut libraries, &format!("{}-libssh2", name), @@ -1335,13 +1259,11 @@ impl PlatformRepository { )?; let info = platform_info.get_extension_info("xsl"); - let mut matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(matches) = Preg::is_match3( php_regex!( "/^libxslt compiled against libxml Version => (?.+)$/im" ), info, - Some(&mut matches), ) { self.add_library( &mut libraries, @@ -1359,12 +1281,9 @@ impl PlatformRepository { "yaml" => { let info = platform_info.get_extension_info("yaml"); - let mut matches = PregMatchedGroups::new(); - if Preg::is_match3( - php_regex!("/^LibYAML Version => (?.+)$/im"), - info, - Some(&mut matches), - ) { + if let Some(matches) = + Preg::is_match3(php_regex!("/^LibYAML Version => (?.+)$/im"), info) + { self.add_library( &mut libraries, &format!("{}-libyaml", name), @@ -1416,11 +1335,9 @@ impl PlatformRepository { // Linked Version => 1.2.8 } else { let info = platform_info.get_extension_info(name); - let mut matches = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(matches) = Preg::is_match3( php_regex!("/^Linked Version => (?.+)$/im"), info, - Some(&mut matches), ) { self.add_library( &mut libraries, @@ -1619,11 +1536,9 @@ impl PlatformRepository { Ok(v) => v, Err(_) => { extra_description = Some(format!(" (actual version: {})", pretty_version)); - let mut m = PregMatchedGroups::new(); - if Preg::is_match3( + if let Some(m) = Preg::is_match3( php_regex!("{^(\\d+\\.\\d+\\.\\d+(?:\\.\\d+)?)}"), &pretty_version, - Some(&mut m), ) { pretty_version = m.get(&CaptureKey::ByIndex(1)).cloned().unwrap_or_default(); } else { diff --git a/crates/shirabe/src/repository/vcs/forgejo_driver.rs b/crates/shirabe/src/repository/vcs/forgejo_driver.rs index 9a656a65..9e156418 100644 --- a/crates/shirabe/src/repository/vcs/forgejo_driver.rs +++ b/crates/shirabe/src/repository/vcs/forgejo_driver.rs @@ -15,7 +15,7 @@ use crate::util::ForgejoRepositoryData; use crate::util::ForgejoUrl; use crate::util::http::Response; use indexmap::IndexMap; -use shirabe_pcre::{CaptureKey, Preg, PregMatchedGroups}; +use shirabe_pcre::{CaptureKey, Preg}; use shirabe_php_shim::Catch as _; use shirabe_php_shim::{ PhpMixed, RuntimeException, base64_decode, explode, extension_loaded, php_regex, urlencode, @@ -584,8 +584,7 @@ impl ForgejoDriver { let links = explode(",", &header); for link in links { - let mut m = PregMatchedGroups::new(); - if Preg::match3(php_regex!(r#"{<(.+?)>; *rel="next"}"#), &link, Some(&mut m)) + if let Some(m) = Preg::match3(php_regex!(r#"{<(.+?)>; *rel="next"}"#), &link) && let Some(url) = m.get(&CaptureKey::ByIndex(1)) { return Some(url.clone()); diff --git a/crates/shirabe/src/repository/vcs/git_bitbucket_driver.rs b/crates/shirabe/src/repository/vcs/git_bitbucket_driver.rs index 964c4b10..cf1f5f98 100644 --- a/crates/shirabe/src/repository/vcs/git_bitbucket_driver.rs +++ b/crates/shirabe/src/repository/vcs/git_bitbucket_driver.rs @@ -15,7 +15,7 @@ use crate::util::Bitbucket; use crate::util::http::Response; use chrono::{DateTime, FixedOffset}; use indexmap::IndexMap; -use shirabe_pcre::{CaptureKey, Preg, PregMatchedGroups}; +use shirabe_pcre::{CaptureKey, Preg}; use shirabe_php_shim::Catch as _; use shirabe_php_shim::{ InvalidArgumentException, LogicException, PhpMixed, RuntimeException, array_key_exists, @@ -84,18 +84,16 @@ impl GitBitbucketDriver { /// @inheritDoc pub fn initialize(&mut self) -> anyhow::Result<()> { - let mut m = PregMatchedGroups::new(); - if !Preg::is_match3( + let Some(m) = Preg::is_match3( php_regex!(r"#^https?://bitbucket\.org/([^/]+)/([^/]+?)(?:\.git|/?)?$#i"), &self.inner.url, - Some(&mut m), - ) { + ) else { return Err(InvalidArgumentException::new(format!( "The Bitbucket repository URL {} is invalid. It must be the HTTPS URL of a Bitbucket repository.", self.inner.url.clone(), )) .into()); - } + }; self.owner = m.get(&CaptureKey::ByIndex(1)).cloned().unwrap_or_default(); self.repository = m.get(&CaptureKey::ByIndex(2)).cloned().unwrap_or_default(); diff --git a/crates/shirabe/src/repository/vcs/git_driver.rs b/crates/shirabe/src/repository/vcs/git_driver.rs index c46a6664..99275e98 100644 --- a/crates/shirabe/src/repository/vcs/git_driver.rs +++ b/crates/shirabe/src/repository/vcs/git_driver.rs @@ -14,7 +14,7 @@ use crate::util::Url; use chrono::TimeZone; use chrono::{DateTime, FixedOffset, Utc}; use indexmap::IndexMap; -use shirabe_pcre::{CaptureKey, Preg, PregMatchedGroups}; +use shirabe_pcre::{CaptureKey, Preg}; use shirabe_php_shim::Catch as _; use shirabe_php_shim::{ InvalidArgumentException, RuntimeException, dirname, is_dir, is_writable, realpath, @@ -198,14 +198,12 @@ impl GitDriver { let branches = self.inner.process.borrow().split_lines(&output); if !branches.contains(&"* master".to_string()) { for branch in &branches { - if !branch.is_empty() { - let mut caps = PregMatchedGroups::new(); - if Preg::match3(php_regex!(r"{^\* +(\S+)}"), branch, Some(&mut caps)) - && let Some(name) = caps.get(&CaptureKey::ByIndex(1)) - { - self.root_identifier = Some(name.clone()); - break; - } + if !branch.is_empty() + && let Some(caps) = Preg::match3(php_regex!(r"{^\* +(\S+)}"), branch) + && let Some(name) = caps.get(&CaptureKey::ByIndex(1)) + { + self.root_identifier = Some(name.clone()); + break; } } } @@ -310,21 +308,20 @@ impl GitDriver { Some(&self.repo_dir), ); for tag in self.inner.process.borrow().split_lines(&output) { - if !tag.is_empty() { - let mut caps = PregMatchedGroups::new(); - if Preg::match3( + if !tag.is_empty() + && let Some(caps) = Preg::match3( php_regex!(r"{^([a-f0-9]{40}) refs/tags/(\S+?)(\^\{\})?$}"), &tag, - Some(&mut caps), - ) && let (Some(hash), Some(name)) = ( + ) + && let (Some(hash), Some(name)) = ( caps.get(&CaptureKey::ByIndex(1)), caps.get(&CaptureKey::ByIndex(2)), - ) { - self.tags - .as_mut() - .unwrap() - .insert(name.clone(), hash.clone()); - } + ) + { + self.tags + .as_mut() + .unwrap() + .insert(name.clone(), hash.clone()); } } } @@ -349,19 +346,19 @@ impl GitDriver { Some(&self.repo_dir), ); for branch in self.inner.process.borrow().split_lines(&output) { - if !branch.is_empty() && !Preg::is_match(php_regex!(r"{^ *[^/]+/HEAD }"), &branch) { - let mut caps = PregMatchedGroups::new(); - if Preg::match3( + if !branch.is_empty() + && !Preg::is_match(php_regex!(r"{^ *[^/]+/HEAD }"), &branch) + && let Some(caps) = Preg::match3( php_regex!(r"{^(?:\* )? *(\S+) *([a-f0-9]+)(?: .*)?$}"), &branch, - Some(&mut caps), - ) && let (Some(name), Some(hash)) = ( + ) + && let (Some(name), Some(hash)) = ( caps.get(&CaptureKey::ByIndex(1)), caps.get(&CaptureKey::ByIndex(2)), - ) && !name.starts_with('-') - { - branches.insert(name.clone(), hash.clone()); - } + ) + && !name.starts_with('-') + { + branches.insert(name.clone(), hash.clone()); } } diff --git a/crates/shirabe/src/repository/vcs/github_driver.rs b/crates/shirabe/src/repository/vcs/github_driver.rs index 10a61feb..7cbceaf2 100644 --- a/crates/shirabe/src/repository/vcs/github_driver.rs +++ b/crates/shirabe/src/repository/vcs/github_driver.rs @@ -14,7 +14,7 @@ use crate::util::GitHub; use crate::util::http::Response; use chrono::{DateTime, FixedOffset}; use indexmap::IndexMap; -use shirabe_pcre::{CaptureKey, Preg, PregMatchedGroups}; +use shirabe_pcre::{CaptureKey, Preg}; use shirabe_php_shim::Catch as _; use shirabe_php_shim::{ InvalidArgumentException, PhpMixed, RuntimeException, array_diff, array_map, @@ -70,20 +70,18 @@ impl GitHubDriver { } pub fn initialize(&mut self) -> anyhow::Result<()> { - let mut match_ = PregMatchedGroups::new(); - if !Preg::is_match3( + let Some(match_) = Preg::is_match3( php_regex!( r"#^(?:(?:https?|git)://([^/]+)/|git@([^:]+):/?)([^/]+)/([^/]+?)(?:\.git|/)?$#" ), &self.inner.url, - Some(&mut match_), - ) { + ) else { return Err(InvalidArgumentException::new(format!( "The GitHub repository URL {} is invalid.", self.inner.url.clone(), )) .into()); - } + }; self.owner = match_ .get(&CaptureKey::ByIndex(3)) @@ -495,16 +493,14 @@ impl GitHubDriver { let mut key: Option = None; for line in preg_split(php_regex!(r"{\r?\n}"), &funding) { let line = trim(&line, None); - let mut m = PregMatchedGroups::new(); - if Preg::is_match3(php_regex!(r"{^(\w+)\s*:\s*(.+)$}"), &line, Some(&mut m)) { + if let Some(m) = Preg::is_match3(php_regex!(r"{^(\w+)\s*:\s*(.+)$}"), &line) { let g1 = m.get(&CaptureKey::ByIndex(1)).cloned().unwrap_or_default(); let g2 = m.get(&CaptureKey::ByIndex(2)).cloned().unwrap_or_default(); if g2 == "[" { key = Some(g1); continue; } - let mut m2 = PregMatchedGroups::new(); - if Preg::is_match3(php_regex!(r"{^\[(.*?)\](?:\s*#.*)?$}"), &g2, Some(&mut m2)) { + if let Some(m2) = Preg::is_match3(php_regex!(r"{^\[(.*?)\](?:\s*#.*)?$}"), &g2) { let inner = m2.get(&CaptureKey::ByIndex(1)).cloned().unwrap_or_default(); for item in array_map( |s: &String| trim(s, None), @@ -518,11 +514,9 @@ impl GitHubDriver { ); result.push(entry); } - } else if Preg::is_match3( - php_regex!(r"{^([^#].*?)(?:\s+#.*)?$}"), - &g2, - Some(&mut m2), - ) { + } else if let Some(m2) = + Preg::is_match3(php_regex!(r"{^([^#].*?)(?:\s+#.*)?$}"), &g2) + { let mut entry = IndexMap::new(); entry.insert("type".to_string(), PhpMixed::String(g1.clone())); entry.insert( @@ -535,17 +529,12 @@ impl GitHubDriver { result.push(entry); } key = None; - } else if Preg::is_match3(php_regex!(r"{^(\w+)\s*:\s*#\s*$}"), &line, Some(&mut m)) { + } else if let Some(m) = Preg::is_match3(php_regex!(r"{^(\w+)\s*:\s*#\s*$}"), &line) { key = Some(m.get(&CaptureKey::ByIndex(1)).cloned().unwrap_or_default()); - } else if key.is_some() && { - let mut tmp = PregMatchedGroups::new(); - Preg::is_match3(php_regex!(r"{^-\s*(.+)(?:\s+#.*)?$}"), &line, Some(&mut m)) - || Preg::is_match3(php_regex!(r"{^(.+),(?:\s*#.*)?$}"), &line, Some(&mut tmp)) - && { - m = tmp; - true - } - } { + } else if key.is_some() + && let Some(m) = Preg::is_match3(php_regex!(r"{^-\s*(.+)(?:\s+#.*)?$}"), &line) + .or_else(|| Preg::is_match3(php_regex!(r"{^(.+),(?:\s*#.*)?$}"), &line)) + { let mut entry = IndexMap::new(); entry.insert( "type".to_string(), @@ -936,16 +925,14 @@ impl GitHubDriver { url: &str, _deep: bool, ) -> anyhow::Result { - let mut matches = PregMatchedGroups::new(); - if !Preg::is_match3( + let Some(matches) = Preg::is_match3( php_regex!( r"#^((?:https?|git)://([^/]+)/|git@([^:]+):/?)([^/]+)/([^/]+?)(?:\.git|/)?$#" ), url, - Some(&mut matches), - ) { + ) else { return Ok(false); - } + }; let origin_url = matches .get(&CaptureKey::ByIndex(2)) @@ -1284,8 +1271,7 @@ impl GitHubDriver { let links = explode(",", &header); for link in &links { - let mut m = PregMatchedGroups::new(); - if Preg::is_match3(php_regex!(r#"{<(.+?)>; *rel="next"}"#), link, Some(&mut m)) { + if let Some(m) = Preg::is_match3(php_regex!(r#"{<(.+?)>; *rel="next"}"#), link) { return Some(m.get(&CaptureKey::ByIndex(1)).cloned().unwrap_or_default()); } } diff --git a/crates/shirabe/src/repository/vcs/gitlab_driver.rs b/crates/shirabe/src/repository/vcs/gitlab_driver.rs index c141cc9a..1887ddc4 100644 --- a/crates/shirabe/src/repository/vcs/gitlab_driver.rs +++ b/crates/shirabe/src/repository/vcs/gitlab_driver.rs @@ -15,7 +15,7 @@ use crate::util::HttpDownloader; use crate::util::http::Response; use chrono::{DateTime, FixedOffset}; use indexmap::IndexMap; -use shirabe_pcre::{CaptureKey, Preg, PregMatchedGroups}; +use shirabe_pcre::{CaptureKey, Preg}; use shirabe_php_shim::Catch as _; use shirabe_php_shim::{ InvalidArgumentException, LogicException, PhpMixed, RuntimeException, array_search_mixed, @@ -81,14 +81,13 @@ impl GitLabDriver { /// /// SSH urls use https by default. Set "secure-http": false on the repository config to use http instead. pub fn initialize(&mut self) -> anyhow::Result<()> { - let mut match_ = PregMatchedGroups::new(); - if !Preg::is_match3(Self::URL_REGEX, &self.inner.url, Some(&mut match_)) { + let Some(match_) = Preg::is_match3(Self::URL_REGEX, &self.inner.url) else { return Err(InvalidArgumentException::new(format!( "The GitLab repository URL {} is invalid. It must be the HTTP URL of a GitLab project.", self.inner.url.clone(), )) .into()); - } + }; let guessed_domain = match_ .get(&CaptureKey::ByName("domain".to_string())) @@ -945,10 +944,9 @@ impl GitLabDriver { url: &str, _deep: bool, ) -> anyhow::Result { - let mut match_ = PregMatchedGroups::new(); - if !Preg::is_match3(Self::URL_REGEX, url, Some(&mut match_)) { + let Some(match_) = Preg::is_match3(Self::URL_REGEX, url) else { return Ok(false); - } + }; let scheme = match_ .get(&CaptureKey::ByName("scheme".to_string())) @@ -1011,12 +1009,7 @@ impl GitLabDriver { let links = explode(",", &header); for link in &links { - let mut match_ = PregMatchedGroups::new(); - if Preg::is_match3( - php_regex!(r#"{<(.+?)>; *rel="next"}"#), - link, - Some(&mut match_), - ) { + if let Some(match_) = Preg::is_match3(php_regex!(r#"{<(.+?)>; *rel="next"}"#), link) { return Some( match_ .get(&CaptureKey::ByIndex(1)) diff --git a/crates/shirabe/src/repository/vcs/hg_driver.rs b/crates/shirabe/src/repository/vcs/hg_driver.rs index d617099e..0933a643 100644 --- a/crates/shirabe/src/repository/vcs/hg_driver.rs +++ b/crates/shirabe/src/repository/vcs/hg_driver.rs @@ -11,7 +11,7 @@ use crate::util::Hg as HgUtils; use crate::util::Url; use chrono::{DateTime, FixedOffset, Utc}; use indexmap::IndexMap; -use shirabe_pcre::{CaptureKey, Preg, PregMatchedGroups}; +use shirabe_pcre::{CaptureKey, Preg}; use shirabe_php_shim::Catch as _; use shirabe_php_shim::{PhpMixed, RuntimeException, dirname, is_dir, is_writable, php_regex}; @@ -232,14 +232,13 @@ impl HgDriver { Some(&self.repo_dir), ); for tag in self.inner.process.borrow().split_lines(&output) { - if !tag.is_empty() { - let mut m = PregMatchedGroups::new(); - if Preg::match3(php_regex!(r"(^([^\s]+)\s+\d+:(.*)$)"), &tag, Some(&mut m)) { - tags.insert( - m.get(&CaptureKey::ByIndex(1)).cloned().unwrap_or_default(), - m.get(&CaptureKey::ByIndex(2)).cloned().unwrap_or_default(), - ); - } + if !tag.is_empty() + && let Some(m) = Preg::match3(php_regex!(r"(^([^\s]+)\s+\d+:(.*)$)"), &tag) + { + tags.insert( + m.get(&CaptureKey::ByIndex(1)).cloned().unwrap_or_default(), + m.get(&CaptureKey::ByIndex(2)).cloned().unwrap_or_default(), + ); } } tags.shift_remove("tip"); @@ -262,20 +261,16 @@ impl HgDriver { Some(&self.repo_dir), ); for branch in self.inner.process.borrow().split_lines(&output) { - if !branch.is_empty() { - let mut m = PregMatchedGroups::new(); - if Preg::match3( - php_regex!(r"(^([^\s]+)\s+\d+:([a-f0-9]+))"), - &branch, - Some(&mut m), - ) { - let name = m.get(&CaptureKey::ByIndex(1)).cloned().unwrap_or_default(); - if !name.starts_with('-') { - branches.insert( - name, - m.get(&CaptureKey::ByIndex(2)).cloned().unwrap_or_default(), - ); - } + if !branch.is_empty() + && let Some(m) = + Preg::match3(php_regex!(r"(^([^\s]+)\s+\d+:([a-f0-9]+))"), &branch) + { + let name = m.get(&CaptureKey::ByIndex(1)).cloned().unwrap_or_default(); + if !name.starts_with('-') { + branches.insert( + name, + m.get(&CaptureKey::ByIndex(2)).cloned().unwrap_or_default(), + ); } } } @@ -287,20 +282,16 @@ impl HgDriver { Some(&self.repo_dir), ); for branch in self.inner.process.borrow().split_lines(&output) { - if !branch.is_empty() { - let mut m = PregMatchedGroups::new(); - if Preg::match3( - php_regex!(r"(^(?:[\s*]*)([^\s]+)\s+\d+:(.*)$)"), - &branch, - Some(&mut m), - ) { - let name = m.get(&CaptureKey::ByIndex(1)).cloned().unwrap_or_default(); - if !name.starts_with('-') { - bookmarks.insert( - name, - m.get(&CaptureKey::ByIndex(2)).cloned().unwrap_or_default(), - ); - } + if !branch.is_empty() + && let Some(m) = + Preg::match3(php_regex!(r"(^(?:[\s*]*)([^\s]+)\s+\d+:(.*)$)"), &branch) + { + let name = m.get(&CaptureKey::ByIndex(1)).cloned().unwrap_or_default(); + if !name.starts_with('-') { + bookmarks.insert( + name, + m.get(&CaptureKey::ByIndex(2)).cloned().unwrap_or_default(), + ); } } } diff --git a/crates/shirabe/src/repository/vcs/svn_driver.rs b/crates/shirabe/src/repository/vcs/svn_driver.rs index db8c43f0..05380a17 100644 --- a/crates/shirabe/src/repository/vcs/svn_driver.rs +++ b/crates/shirabe/src/repository/vcs/svn_driver.rs @@ -13,7 +13,7 @@ use crate::util::Svn as SvnUtil; use crate::util::Url; use chrono::{DateTime, FixedOffset, Utc}; use indexmap::IndexMap; -use shirabe_pcre::{CaptureKey, Preg, PregMatchedGroups}; +use shirabe_pcre::{CaptureKey, Preg}; use shirabe_php_shim::Catch as _; use shirabe_php_shim::{ PhpMixed, RuntimeException, php_regex, stripos, strrpos, strtr, substr, trim, @@ -317,18 +317,14 @@ impl SvnDriver { &format!("{}{}{}", self.base_url, path, rev), )?; for line in self.inner.process.borrow().split_lines(&output) { - if !line.is_empty() { - let mut m = PregMatchedGroups::new(); - if Preg::is_match3( - php_regex!(r"{^Last Changed Date: ([^(]+)}"), - &line, - Some(&mut m), - ) { - let date_str = m.get(&CaptureKey::ByIndex(1)).cloned().unwrap_or_default(); - return Ok(shirabe_php_shim::date_create::(date_str.trim()) - .ok() - .map(|d| d.fixed_offset())); - } + if !line.is_empty() + && let Some(m) = + Preg::is_match3(php_regex!(r"{^Last Changed Date: ([^(]+)}"), &line) + { + let date_str = m.get(&CaptureKey::ByIndex(1)).cloned().unwrap_or_default(); + return Ok(shirabe_php_shim::date_create::(date_str.trim()) + .ok() + .map(|d| d.fixed_offset())); } } @@ -349,28 +345,23 @@ impl SvnDriver { let mut last_rev: i64 = 0; for line in self.inner.process.borrow().split_lines(&output) { let line = trim(&line, None); - if !line.is_empty() { - let mut m = PregMatchedGroups::new(); - if Preg::is_match3( - php_regex!(r"{^\s*(\S+).*?(\S+)\s*$}"), - &line, - Some(&mut m), - ) { - let rev: i64 = m - .get(&CaptureKey::ByIndex(1)) - .and_then(|s| s.parse().ok()) - .unwrap_or(0); - let path = - m.get(&CaptureKey::ByIndex(2)).cloned().unwrap_or_default(); - if path == "./" { - last_rev = rev; - } else { - let identifier = self.build_identifier( - &format!("/{}/{}", self.tags_path, path), - std::cmp::max(last_rev, rev), - ); - tags.insert(path.trim_end_matches('/').to_string(), identifier); - } + if !line.is_empty() + && let Some(m) = + Preg::is_match3(php_regex!(r"{^\s*(\S+).*?(\S+)\s*$}"), &line) + { + let rev: i64 = m + .get(&CaptureKey::ByIndex(1)) + .and_then(|s| s.parse().ok()) + .unwrap_or(0); + let path = m.get(&CaptureKey::ByIndex(2)).cloned().unwrap_or_default(); + if path == "./" { + last_rev = rev; + } else { + let identifier = self.build_identifier( + &format!("/{}/{}", self.tags_path, path), + std::cmp::max(last_rev, rev), + ); + tags.insert(path.trim_end_matches('/').to_string(), identifier); } } } @@ -400,27 +391,23 @@ impl SvnDriver { if !output.is_empty() { for line in self.inner.process.borrow().split_lines(&output) { let line = trim(&line, None); - if !line.is_empty() { - let mut m = PregMatchedGroups::new(); - if Preg::is_match3( - php_regex!(r"{^\s*(\S+).*?(\S+)\s*$}"), - &line, - Some(&mut m), - ) { - let rev: i64 = m - .get(&CaptureKey::ByIndex(1)) - .and_then(|s| s.parse().ok()) - .unwrap_or(0); - let path = m.get(&CaptureKey::ByIndex(2)).cloned().unwrap_or_default(); - if path == "./" { - let identifier = self.build_identifier( - &format!("/{}", self.trunk_path.clone().unwrap_or_default()), - rev, - ); - branches.insert("trunk".to_string(), identifier.clone()); - self.root_identifier = Some(identifier); - break; - } + if !line.is_empty() + && let Some(m) = + Preg::is_match3(php_regex!(r"{^\s*(\S+).*?(\S+)\s*$}"), &line) + { + let rev: i64 = m + .get(&CaptureKey::ByIndex(1)) + .and_then(|s| s.parse().ok()) + .unwrap_or(0); + let path = m.get(&CaptureKey::ByIndex(2)).cloned().unwrap_or_default(); + if path == "./" { + let identifier = self.build_identifier( + &format!("/{}", self.trunk_path.clone().unwrap_or_default()), + rev, + ); + branches.insert("trunk".to_string(), identifier.clone()); + self.root_identifier = Some(identifier); + break; } } } @@ -442,29 +429,23 @@ impl SvnDriver { .split_lines(&trim(&output, None)) { let line = trim(&line, None); - if !line.is_empty() { - let mut m = PregMatchedGroups::new(); - if Preg::is_match3( - php_regex!(r"{^\s*(\S+).*?(\S+)\s*$}"), - &line, - Some(&mut m), - ) { - let rev: i64 = m - .get(&CaptureKey::ByIndex(1)) - .and_then(|s| s.parse().ok()) - .unwrap_or(0); - let path = - m.get(&CaptureKey::ByIndex(2)).cloned().unwrap_or_default(); - if path == "./" { - last_rev = rev; - } else { - let identifier = self.build_identifier( - &format!("/{}/{}", self.branches_path, path), - std::cmp::max(last_rev, rev), - ); - branches - .insert(path.trim_end_matches('/').to_string(), identifier); - } + if !line.is_empty() + && let Some(m) = + Preg::is_match3(php_regex!(r"{^\s*(\S+).*?(\S+)\s*$}"), &line) + { + let rev: i64 = m + .get(&CaptureKey::ByIndex(1)) + .and_then(|s| s.parse().ok()) + .unwrap_or(0); + let path = m.get(&CaptureKey::ByIndex(2)).cloned().unwrap_or_default(); + if path == "./" { + last_rev = rev; + } else { + let identifier = self.build_identifier( + &format!("/{}/{}", self.branches_path, path), + std::cmp::max(last_rev, rev), + ); + branches.insert(path.trim_end_matches('/').to_string(), identifier); } } } -- cgit v1.3.1-4-g156e