如何使用 Git Hooks 遵守 Drupal 编码标准

已发表: 2023-05-23

好的代码就像精心打造的乐高积木作品——它很强大,看起来不错,而且如果需要的话很容易改变。 当您在团队中编码、从事可扩展项目或参与 Drupal 等开源社区时,良好编码标准的重要性尤为重要。

与任何其他开源项目一样,Drupal 有数千名开发人员参与该项目。 他们每个人都有自己的专业水平。 您如何确保团队或社区中的每个人都遵循良好的编码实践? Git 钩子!

Git Hooks 是确保您的代码始终符合 Drupal 编码标准的一种简单且自动化的方法。 使用 Git hook 实施 Drupal 编码标准将帮助开发人员使用 Drupal 社区声明的适当编码标准提交和推送代码。 它还可以帮助提高您的项目管理技能,并允许开发人员使用适当的提交消息标准提交代码。 详细了解 Git 挂钩以及如何将它们付诸实践。

git 钩子

什么是 Git 钩子

Git Hooks 是每次调用 Git 命令时都会自动运行的脚本。 正如您将使用hook_form_alter来更改 Drupal 中的表单一样,您可以为每个 Git 操作设置单独的预定义挂钩。

git 钩子

Git hook 的图示

寻找 Git 钩子

您可以在.git/hooks下的项目文件夹中找到 Git 挂钩(前提是 Git 已初始化)。 在那里,您会找到所有带有.sample扩展名的钩子,以防止它们默认执行。

要使用所需的挂钩,您需要删除.sample扩展名并编辑执行代码。

有许多可用的 Git 挂钩,但我们将使用预提交Git 挂钩来启动 Drupal 编码标准。

预提交Git 挂钩是将在代码提交之前运行的挂钩。 它检查正在提交的代码行。

实施 Git 钩子

在开始之前,请确保您已准备好以下基本要求:

  • 作曲家
  • 混帐
  • PHP代码嗅探器
  • drupal/编码器:8.3.13

以下过程用于在 Mac 设备中安装它。 您可以在此处找到参考链接,了解在其他设备上的安装说明。

  • brew 安装 php-code-sniffer
  • composer global 需要 drupal/coder:8.3.13
  • phpcs --config-set installed_pa​​ths ~/.composer/vendor/drupal/coder/coder_sniffer
  • phpcs -i → 会给你安装编码标准。

让我们开始!

我正在创建一个名为demo的新 Drupal 项目。 您也可以在现有项目中使用它。

drupal项目演示

→ 使用 cd 命令我们进入了项目文件夹。
CD演示

→ 初始化 git 到项目中
初始化

→ 添加并进行我的第一次提交。
git commit -m “初始提交”

初始提交

→ 使用以下命令为 Mac 安装 php 代码嗅探器。
brew 安装 php-code-sniffer

自动更新

→ 使用 composer 安装 Drupal coder
composer global 需要 drupal/coder:8.3.13

→ 一旦定义了编码器及其路径,您将获得如下输出,如下图所示。
phpcs --config-set installed_pa​​ths ~/.composer/vendor/drupal/coder/coder_sniffer

→ phpcs -i
上面的命令会给你 Drupal 和 DrupalPractice

嗅探器

→ 现在您可以提交代码了。 如果您有任何语法或编码标准错误,您将在显示屏上收到通知,并且您的提交过程将被中止。

提交代码

→ 下面是自动修复错误的代码

phpcbf --standard=Drupal --extensions=php,module,inc,install,test,profile,theme,css,info,txt,md,yml web/modules/custom/demo

任何其他问题都需要手动修复。 完成后提交您的代码。

修复错误代码

一旦你的代码是干净的,它将允许你提交代码

测试代码

只需将代码复制并粘贴到 .git/hooks 中的 pre-commit.sample 中。 不要忘记删除示例扩展。

预提交代码示例:

 #!/bin/bash # Redirect output to stderr. exec 1>&2 # Color codes for the error message. redclr=`tput setaf 1` greenclr=`tput setaf 2` blueclr=`tput setaf 4` reset=`tput sgr0` # Printing the notification in the display screen. echo "${blueclr}" echo "................................. Validating your codes ……..…………....." echo "-----------------------------------------------------------${reset}" # Mentioning the directories which should be excluded. dir_exclude='\/kint\/|\/contrib\/|\/devel\/|\/libraries\/|\/vendor\/|\.info$|\.png$|\.gif$|\.jpg$|\.ico$|\.patch$|\.htaccess$|\.sh$|\.ttf$|\.woff$|\.eot$|\.svg$' # Checking for the debugging keyword in the commiting code base. keywords=(ddebug_backtrace debug_backtrace dpm print_r var_dump dump console\.log) keywords_for_grep=$(printf "|%s" "${keywords[@]}") keywords_for_grep=${keywords_for_grep:1} # Flags for the counter. synatx_error_found=0 debugging_function_found=0 merge_conflict=0 coding_standard_error=0 # Checking for PHP syntax errors. changed_files=`git diff-index --diff-filter=ACMRT --cached --name-only HEAD -- | egrep '\.theme$|\.module$|\.inc|\.php$'` if [ -n "$changed_files" ] then for FILE in $changed_files; do php -l $FILE > /dev/null 2>&1 compiler_result=$? if [ $compiler_result -eq 255 ] then if [ $synatx_error_found -eq 0 ] then echo "${redclr}" echo "# Compilation error(s):" echo "=========================${reset}" fi synatx_error_found=1 `php -l $FILE > /dev/null` fi done fi # Checking for debugging functions. files_changed=`git diff-index --diff-filter=ACMRT --cached --name-only HEAD -- | egrep -v $dir_exclude` if [ -n "$files_changed" ] then for FILE in $files_changed ; do for keyword in "${keywords[@]}" ; do pattern="^\+(.*)?$keyword(.*)?" resulted_files=`git diff --cached $FILE | egrep -x "$pattern"` if [ ! -z "$resulted_files" ] then if [ $debugging_function_found -eq 0 ] then echo "${redclr}" echo "Validating keywords" echo "================================================${reset}" fi debugging_function_found=1 echo "Debugging function" $keyword git grep -n $keyword $FILE | awk '{split($0,a,":"); printf "\found in " a[1] " in line " a[2] "\n"; }' fi done done fi # Checking for Drupal coding standards changed_files=`git diff-index --diff-filter=ACMRT --cached --name-only HEAD -- | egrep -v $dir_exclude | egrep '\.php$|\.module$|\.inc$|\.install$|\.test$|\.profile$|\.theme$|\.js$|\.css$|\.info$|\.txt$|\.yml$'` if [ -n "$changed_files" ] then phpcs_result=`phpcs --standard=Drupal --extensions=php,module,inc,install,test,profile,theme,css,info,txt,md,yml --report=csv $changed_files` if [ "$phpcs_result" != "File,Line,Column,Type,Message,Source,Severity,Fixable" ] then echo "${redclr}" echo "# Hey Buddy, The hook found some issue(s)." echo "---------------------------------------------------------------------------------------------${reset}" phpcs --standard=Drupal --extensions=php,module,inc,install,test,profile,theme,css,info,txt,md,yml $changed_files echo "<=======> Run below command to fix the issue(s)" echo "# phpcbf --standard=Drupal --extensions=php,module,inc,install,test,profile,theme,css,info,txt,md,yml your_custom_module_or_file_path" echo “<====================================================>" echo "# To skip the Drupal Coding standard issue(s), Please use this commands << git commit -m your commit Message --no-verify >>" echo "-----------------------------------------------------------------------------------------------------------------------------------------${reset}" coding_standard_error=1 fi fi # Checking for merge conflict markers. files_changed=`git diff-index --diff-filter=ACMRT --cached --name-only HEAD --` if [ -n "$files_changed" ] then for FILE in $files_changed; do pattern="(<<<<|====|>>>>)+.*(\n)?" resulted_files=`egrep -in "$pattern" $FILE` if [ ! -z "$resulted_files" ] then if [ $merge_conflict -eq 0 ] then echo "${redclr}" echo "-----------------------Unable to commit the file(s):------------------------" echo "-----------------------------------${reset}" fi merge_conflict=1 echo $FILE fi done fi # Printing final result errors_found=$((synatx_error_found+debugging_function_found+merge_conflict+coding_standard_error)) if [ $errors_found -eq 0 ] then echo "${greenclr}" echo "Wow! It is clean code" echo "${reset}" else echo "${redclr}" echo "Please Correct the errors mentioned above. We are aborting your commit." echo "${reset}" exit 1 fi

最后的想法

我希望您发现这篇文章很有趣,并且它可以帮助您编写更好的代码,因为更好的代码意味着更好的网络! 喜欢您刚刚阅读的内容? 考虑订阅我们的每周时事通讯,并将像这样的技术见解发送到您的收件箱!