用于PHP标记的WordPress代码结构的某些部分的样式不一致。WordPress正在努力通过帮助用户保持一致的样式来逐步改善此问题,从而使代码可以一目了然且易于阅读。
在为WordPress编写PHP代码时,无论是核心编程代码,插件还是主题,都请牢记以下几点。该准则在许多方面类似于Pear标准,但在一些关键方面有所不同。
另请参阅:PHP文档标准。
PHP
单引号和双引号
适当时使用单引号和双引号。如果您不评估字符串中的任何内容,请使用单引号。您几乎永远都不必转义字符串中的引号,因为您可以仅更改引号样式,如下所示:
echo '<a href="/static/link" title="Yeah yeah!">Link name</a>';
echo "<a href='$link' title='$linktitle'>$linkname</a>";
进入属性的文本应经过贯穿始终,esc_attr()
以使单引号或双引号不会引起属性值的结尾并使HTML无效并使安全问题。
缩进
缩进应始终反映逻辑结构。使用真实的制表符,而不要使用空格,因为这样可以在客户端之间提供最大的灵活性。
例外:如果您的代码块在对齐时会更易读,请使用空格:
$foo = 'somevalue';
$foo2 = 'somevalue2';
$foo34 = 'somevalue3';
$foo5 = 'somevalue4';
对于关联数组,当数组包含多个项目时,每个项目都应从新行开始:
$query = new WP_Query( array( 'ID' => 123 ) );
$query = new WP_Query( array(
'post_type' => 'page',
'post_author' => 123,
'post_status' => 'publish',
) );
请注意最后一个数组项后面的逗号:建议这样做,因为这样可以更轻松地更改数组的顺序,并在添加新项时使差异更清晰。
$my_array = array(
'foo' => 'somevalue',
'foo2' => 'somevalue2',
'foo3' => 'somevalue3',
'foo34' => 'somevalue3',
);
对于switch
结构,case
应在switch
语句中缩进一个选项卡,在语句中缩进一个选项break
卡case
。
switch ( $type ) {
case 'foo':
some_function();
break;
case 'bar':
some_function();
break;
}
经验法则:应在行的开头使用制表符来缩进,而在行的中间可以使用空格来对齐。
括号样式
括号应按以下所示样式用于所有块:
if ( condition ) {
action1();
action2();
} elseif ( condition2 && condition3 ) {
action3();
action4();
} else {
defaultaction();
}
如果您有一个很长的块,请考虑是否可以将其分成两个或更多个较短的块,函数或方法,以降低复杂性,提高测试的简便性并提高可读性。
即使不需要,也应始终使用大括号:
if ( condition ) {
action0();
}
if ( condition ) {
action1();
} elseif ( condition2 ) {
action2a();
action2b();
}
foreach ( $items as $item ) {
process_item( $item );
}
请注意,要求使用花括号仅表示禁止单语句内联控制结构。您可以随意使用其他语法来控制结构(例如if
/ endif
,while
/ endwhile
),特别是在HTML代码嵌入HTML的模板中,例如:
<div class="hfeed">
<article id="post-" class="">
<!-- ... -->
</article>
</div>
使用elseif
,而不是else if
else if
与if|elseif
块的冒号语法不兼容 。因此,请使用elseif
条件句。
正则表达式
应优先使用与Perl兼容的正则表达式(PCRE,preg_
函数),而不要使用与之对应的POSIX。切勿使用/e
开关,preg_replace_callback
而应使用。
将单引号字符串用于正则表达式是最方便的,因为与双引号字符串相反,它们只有两个元序列:\'
和\\
。
打开和关闭PHP标记
在HTML块中嵌入多行PHP代码段时,PHP打开和关闭标签必须单独位于一行上。
正确(多行):
function foo() {
?>
<div>
</div>
<?php
}
正确(单行):
<input name="" />
不正确:
if ( $a === $b ) { ?>
<?php }
删除尾随空格
在每行代码的末尾删除尾随空格。最好省略文件末尾的PHP结束标记。如果使用标签,请确保删除尾随空格。
使用空格
始终在逗号后以及逻辑,比较,字符串和赋值运算符的两侧放置空格。
x == 23
foo && bar
! foo
array( 1, 2, 3 )
$baz . '-5'
$term .= 'X'
在if
,elseif
,foreach
,for
,和switch
块的左括号和右括号两边加空格
foreach ( $foo as $bar ) { ...
定义函数时,请像这样:
function my_function( $param1 = 'foo', $param2 = 'bar' ) { ...
function my_other_function() { ...
调用函数时,请这么做:
my_function( $param1, func_param( $param2 ) );
my_other_function();
在执行逻辑比较时,请像这样:
if ( ! $foo ) { ...
在进行类型转换时,请像这样进行:
foreach ( (array) $foo as $bar ) { ...
$foo = (boolean) $bar;
引用数组项时,如果它是变量,则仅在索引周围包括一个空格,例如:
$x = $foo['bar']; // correct
$x = $foo[ 'bar' ]; // incorrect
$x = $foo[0]; // correct
$x = $foo[ 0 ]; // incorrect
$x = $foo[ $bar ]; // correct
$x = $foo[$bar]; // incorrect
在一个switch
块中,冒号之前不能有任何空格以用于case语句。
switch ( $foo ) {
case 'bar': // correct
case 'ba' : // incorrect
}
同样,返回类型声明中的冒号前不应有空格。
function sum( $a, $b ): float {
return $a + $b;
}
除非另有说明,否则括号内应有空格。
if ( $foo && ( $bar || $baz ) ) { ...
my_function( ( $x - 1 ) * 5, $y );
格式化SQL语句
在格式化SQL语句时,您可以将其分成几行,并缩进它是否足够复杂以至于无法保证。大多数语句虽然可以很好地作为一行使用。始终大写语句的SQL部分,例如UPDATE
或WHERE
。
更新数据库的函数在传递时应期望其参数缺少SQL斜杠转义。转义应尽可能接近查询时间,最好使用$wpdb->prepare()
$wpdb->prepare()
是一种处理SQL查询的转义,引用和内部转换的方法。它使用sprintf()
格式化样式的子集。范例:
$var = "dangerous'"; // raw data that may or may not need to be escaped
$id = some_foo_number(); // data we expect to be an integer, but we're not certain
$wpdb->query( $wpdb->prepare( "UPDATE $wpdb->posts SET post_title = %s WHERE ID = %d", $var, $id ) );
%s
用于字符串占位符,%d
并用于整数占位符。请注意,它们不是“引用”的!$wpdb->prepare()
将负责为我们转义和报价。这样做的好处是,我们不必记住手动使用esc_sql()
,并且一目了然,可以轻松查看是否已转义某些内容,因为它是在查询发生时立即发生的。
有关更多信息,请参见数据验证。
数据库查询
避免直接接触数据库。如果有定义的函数可以获取所需的数据,请使用它。数据库抽象(使用函数而不是查询)有助于保持代码前向兼容,并且在将结果缓存在内存中的情况下,它可以快很多倍。
如果您必须接触数据库,请通过在wp-hackers邮件列表中发布一条消息来与一些开发人员联系。他们可能要考虑为下一个WordPress版本创建函数,以涵盖所需的功能。
命名约定
在变量,操作/过滤器和函数名称中使用小写字母(从不camelCase
)。通过下划线将单词分开。不要不必要地缩写变量名;让代码明确且具有自我说明性。
function some_name( $some_variable ) { [...] }
类名应使用下划线分隔的大写单词。首字母缩写词均应全部大写。
class Walker_Category extends Walker { [...] }
class WP_HTTP { [...] }
常量应全部大写,并用下划线分隔单词:
define( 'DOING_AJAX', true );
文件应使用小写字母描述性地命名。连字符应分隔单词。
my-plugin-name.php
类文件名应基于带class-
前缀的类名,并且类名中的下划线用连字符代替,例如WP_Error
:
class
-wp-error.php
该文件命名标准适用于所有具有类的当前文件和新文件。对于包含移植到BackPress中的代码的三个文件,有一个例外:class.wp-dependencies.php,class.wp-scripts.php,class.wp-styles.php。这些文件class.
在单词class之前加点号,而不是连字符。
包含模板标签的文件wp-includes
应-template
附加到名称的末尾,以便它们显而易见。
general-template.php
不言自明的标志值的函数参数
在调用函数时,建议将字符串值优先于仅仅是 true
和false
。
// Incorrect
function eat( $what, $slowly = true ) {
...
}
eat( 'mushrooms' );
eat( 'mushrooms', true ); // what does true mean?
eat( 'dogfood', false ); // what does false mean? The opposite of true?
由于PHP不支持命名参数,因此标志的值是没有意义的,并且每次遇到上述示例的函数调用时,我们都必须搜索函数定义。通过使用描述性字符串值而不是布尔值,可使代码更具可读性。
// Correct
function eat( $what, $speed = 'slowly' ) {
...
}
eat( 'mushrooms' );
eat( 'mushrooms', 'slowly' );
eat( 'dogfood', 'quickly' );
当需要更多的单词来描述功能参数时,$args
数组可能是更好的模式。
// Even Better
function eat( $what, $args ) {
...
}
eat ( 'noodles', array( 'speed' => 'moderate' ) );
动态钩子插补式命名
动态挂钩应该使用插值而不是串联来命名,以提高可读性和可发现性。
动态挂钩是在其标记名称中包含动态值的挂钩,例如{$new_status}_{$post->post_type}
(publish_post)。
钩形标签中使用的变量应该用大括号{
和括}
起来,完整的外部标签名称用双引号引起来。这是为了确保PHP可以正确解析插值字符串中给定变量的类型。
do_action( "{$new_status}_{$post->post_type}", $post->ID, $post );
在可能的情况下,标记名称中的动态值也应尽可能简洁明了。$user_id
比起,它具有更多的自我记录能力$this->id
。
三元运算符
三元运算符很好,但是始终让它们测试语句是否为真,而不是假。否则,它将变得混乱。(使用例外! empty()
,因为这里测试false通常更直观。
// (if statement is true) ? (do this) : (else, do this);
$musictype = ( 'jazz' == $music ) ? 'cool' : 'blah';
// (if field is not empty ) ? (do this) : (else, do this);
Yoda条件
if ( true == $the_force ) {
$victorious = you_will( $be );
}
在进行涉及变量的逻辑比较时,始终将变量放在右侧,将常量,文字或函数调用放在左侧。如果双方都不是变量,则顺序并不重要。(用计算机科学的术语来说,在比较中总是尝试将l值放在右边,将r值放在左边。)
在上面的示例中,如果省略等号(承认,即使对我们中最有经验的人也是如此),您会遇到解析错误,因为您不能将常量赋给like true
。如果该语句是相反的( $the_force = true )
,则该赋值将是完全有效的,返回1
,导致if语句的计算结果为true
,并且您可能会追逐该错误一段时间。
阅读有点奇怪。习惯了,您会的。
这适用于==,!=,===和!==,<,>,<=或> =的Yoda条件明显更难阅读,最好避免。
聪明的代码
通常,可读性比聪明或简短更为重要。
isset( $var ) || $var = some_function();
尽管上面这行很聪明,但是如果您不熟悉它,还需要花费一些时间。所以,就这样写:
if ( ! isset( $var ) ) {
$var = some_function();
}
在一条switch
语句中,可以有多个空的情况落入一个公共块。如果一个案例包含一个块,则进入下一个块,但是,必须对此进行明确注释。
switch ( $foo ) {
case 'bar': // Correct, an empty case can fall through without comment.
case 'baz':
echo $foo; // Incorrect, a case with a block must break, return, or have a comment.
case 'cat':
echo 'mouse';
break; // Correct, a case with a break does not require a comment.
case 'dog':
echo 'horse';
// no break // Correct, a case can have a comment to explicitly mention the fall through.
case 'fish':
echo 'bird';
break;
}
决不能使用goto
语句。
该eval()
构造非常危险,无法固定。此外,PHP 7.2不推荐使用create_function()
内部执行的函数eval()
。这两个都不能使用。
错误控制运算符
如PHP文档所述:
PHP支持一种错误控制运算符:at符号(@)。当在PHP表达式中添加前缀时,该表达式可能生成的任何错误消息都将被忽略。
虽然此运算符确实存在于Core中,但通常懒惰地使用它,而不是进行适当的错误检查。不鼓励使用它,甚至PHP文档也声明:
警告:当前,“ @”错误控制运算符前缀甚至将针对严重错误禁用错误报告,这些错误将终止脚本执行。除其他外,这意味着如果您使用“ @”抑制某个功能的错误,并且该功能不可用或输入错误,该脚本将在那里死掉,而没有任何指示。
不要extract()
extract()
是一个可怕的功能,使代码更难调试和理解。我们应该阻止它的[sic]使用,并删除我们对它的所有使用。
约瑟夫·斯科特(Joseph Scott)写了一篇很好的文章,说明它为什么不好。
延伸阅读
- WordPress函数:load_plugin_textdomain(插件本地化) (1.000)
- 如何用代码实现自定义和美化WordPress登陆页面? (1.000)
- WordPress开发编码规范——WordPress编码标准 (1.000)
- WordPress开发编码规范——CSS编码标准 (1.000)
- WordPress开发编码规范——HTML编码标准 (1.000)
- WordPress开发编码规范——JavaScript编码标准 (1.000)
- WordPress删除和自定义后台管理菜单 (RANDOM - 1.000)