Php perl风格的regex mysqldump列定义
我正试图修复有关mysqldump列定义解析的一个bug 这些工具可以正确解析以下行:Php perl风格的regex mysqldump列定义,php,sql,regex,parsing,mysqldump,Php,Sql,Regex,Parsing,Mysqldump,我正试图修复有关mysqldump列定义解析的一个bug 这些工具可以正确解析以下行: `version_id` int(10) unsigned NOT NULL AUTO_INCREMENT, `ucm_item_id` int(10) unsigned NOT NULL, `ucm_type_id` int(10) unsigned NOT NULL, `version_note` varchar(255) COLLATE utf8mb4_unicode_ci NOT NULL DEFAU
`version_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
`ucm_item_id` int(10) unsigned NOT NULL,
`ucm_type_id` int(10) unsigned NOT NULL,
`version_note` varchar(255) COLLATE utf8mb4_unicode_ci NOT NULL DEFAULT '' COMMENT 'Optional version name',
但是,在存在故障的线路上发生故障;注释中的(分号)或/(斜杠)
`keep_forever` tinyint(4) NOT NULL DEFAULT '0' COMMENT '0=auto delete; 1=keep',
原始部分正则表达式是
'\((?<tableDefinition>[^;\/]+)\)';
这可以解释为“重复|否;或/|,然后是可选的DDL注释至少一次,然后是可选的|否;或/|”
然而,即使我尝试了许多类似的变体,我也无法用它们中的任何一个来解析上面的列
除此之外,注释还可能包含单引号““””(两个单引号)。我以前也用过这个
\'([^\']+|\'\'))\'
(见附件)
这也需要以某种方式整合到答案中
参考:匹配表和列的原始代码:
/**
* @return string
*/
public static function tables()
{
$pattern = '/(?<creationScript>CREATE\s+TABLE\s+`(?<tableName>\S+)`\s+';
$pattern .= '\((?<tableDefinition>[^;\/]+)\)';
$pattern .= '(?:\s+ENGINE=(?<engine>[^;\s]+))?\s*';
$pattern .= '(?:AUTO_INCREMENT=(?<autoIncrement>\d+))?\s*';
$pattern .= '(?:DEFAULT CHARSET=(?<defaultCharset>[^;\s]+))?\s*)';
$pattern .= '(?:COLLATE=.+?)?\s*';
$pattern .= '(?:\/\*.+?\*\/)?\s*';
$pattern .= ';/';
$pattern .= 's'; // modifier
return $pattern;
}
/**
* @return string
*/
public static function column()
{
$pattern = '/\s*';
$pattern .= '`(?<columnName>\S+?)`\s+';
$pattern .= sprintf('(?<columnType>%s)\s*', implode('|', self::$columnTypeRegExps));
$pattern .= '(?:CHARACTER SET\s+(?<characterSet>\S+))?\s*';
$pattern .= '(?:COLLATE\s+(?<collate>\S+))?\s*';
$pattern .= '(?<nullable>NULL|NOT NULL)?\s*';
$pattern .= '(?<autoIncrement>AUTO_INCREMENT)?\s*';
$pattern .= '(?:DEFAULT (?<defaultValue>\S+|\'[^\']+\'))?\s*';
$pattern .= '(?:ON UPDATE (?<onUpdateValue>\S+))?\s*';
$pattern .= '(?:COMMENT \'(?<comment>[^\']+)\')?\s*';
$pattern .= '(?:,|$)/';
return $pattern;
}
/**
*@返回字符串
*/
公共静态函数表()
{
$pattern='/(?创建\s+表\s+`(?\s+`\s+);
$pattern.='\((?[^;\/]+)\');
$pattern.='(?:\s+引擎=(?[^;\s]+)?\s*';
$pattern.='(?:自动增量=(?\d+))\s*;
$pattern.='(?:默认字符集=(?[^;\s]+)?\s*);
$pattern.='(?:COLLATE=.+?)?\s*';
$pattern.='(?:\/\*.+?\*\/)?\s*;
$pattern.=';/';
$pattern.='s';//修饰符
返回$模式;
}
/**
*@返回字符串
*/
公共静态函数列()
{
$pattern='/\s*';
$pattern.='`(?\S+?)`\S+';
$pattern.=sprintf(“(?%s)\s*”,内爆(“|”,self::$columnTypeRegExps));
$pattern.='(?:字符集\s+(?\s+))\s*';
$pattern.='(?:COLLATE\s+(?\s+))\s*';
$pattern.='(?NULL |非NULL)?\s*';
$pattern.='(?自动增量)?\s*';
$pattern.='(?:默认值(?\S+\'[^\']+\'))?\S*;
$pattern.='(?:更新时(?\S+))\S*;
$pattern.='(?:COMMENT\'(?[^\']+)\')?\s*;
$pattern.='(?:,|$)/';
返回$模式;
}
您可能需要明确地迎合评论:
修改注释模式:
(COMMENT\s\'[^\']+((\'\')+[^\']*)*\')?
修改tableDefinition模式:
\((?<tableDefinition>([^;\/]+?(.COMMENT.'[^']+(('')[^']*)*'(?!=')))+.*?|[^;\/]+?)\)
\((?([^;\/]+?(.COMMENT.[^']+(('')[^']*)*'(?!='))+*?[^;\/]+?)\)
您希望得到什么样的结果?你需要列名吗?我想到了一些(*跳过)(*失败)
机制。为了只获取列名,这个工具工作得非常好(注意`
,它被认为是Stackoverflow中的代码)。该工具只需要将每一行作为preg\u match\u all的结果,以便进一步解析。作为这个问题的结果,我希望简单地匹配冒犯的界线。我不想重写库,我已经添加了已经在使用的正则表达式来匹配表和列。我希望修复表regex中与列定义作为一个整体相匹配的部分。您是否还需要考虑诸如空注释字符串和并列字符串文本之类的特殊情况?我想这不会有什么坏处。我今天发现了这个工具,作者和我都非常感谢任何改进。感谢您的快速响应。我不知道&comment将如何工作,我是否应该粘贴此正则表达式行并重试?您的表达式中有一个错误,它应该是:“\(?[^;\/]+(&comment[^;\/]+)*)\”
(注意tableDefinition
后面的左括号)。perl和php正则表达式之间的细微差异使我成为牺牲品@简:谢谢;对我来说这似乎是合乎逻辑的,但不知何故失败了,介意在聊天中看看这个吗?只是看看我自己。向前和向后ping 10条评论将推荐一条
\((?<tableDefinition>([^;\/]+?(.COMMENT.'[^']+(('')[^']*)*'(?!=')))+.*?|[^;\/]+?)\)