首頁  >  文章  >  Java  >  程式碼異味 - 未經測試的正規表示式

程式碼異味 - 未經測試的正規表示式

Susan Sarandon
Susan Sarandon原創
2024-10-26 08:25:30352瀏覽

沒有測試的正規表示式是自找麻煩 - 不要偷懶。它是免費的人工智慧!

TL;DR:使用清晰簡潔的正規表示式,並徹底測試它們。

問題

  • 可讀性
  • 沒有測試用例
  • 錯過了邊緣狀況
  • 調試挑戰
  • 不清楚的失敗
  • 隱藏缺陷

解決方案

  1. 讓你最喜歡的人工智慧寫測試案例
  2. 將複雜的正規表示式分解為更小、更易讀的部分。
  3. 檢查邊緣狀況
  4. 驗證輸出
  5. 建立測試後重構正規表示式
  6. 改進錯誤訊息

情境

正規表示式很強大,但也很棘手。

如果您在沒有測試的情況下編寫正規表示式,則會出現意外錯誤。

如果您編寫神秘的正規表示式並跳過自動化測試,您可能會錯過重要的案例,從而導致安全問題或使用者沮喪。

範例程式碼

錯誤的

public class PasswordValidator {
    public static boolean isValidPassword(String password) {
        return password.matches(
            "^(?=.*[a-z])(?=.*[A-Z])(?=.*\d)[a-zA-Z\d]{8,}$");
        // This is a cryptic Regular Expression
    }
}

正確的

import java.util.ArrayList;
import java.util.List;

public class PasswordValidator {
    public static List<String> validatePassword(String password) {
        List<String> errors = new ArrayList<>();

        if (password.length() < 8) {
            errors.add(
                "Password must be at least 8 characters long.");
        }
        if (!password.matches(".*[A-Z].*")) {
            errors.add(
                "Password must contain at least one uppercase letter.");
        }
        if (!password.matches(".*[a-z].*")) {
            errors.add(
                "Password must contain at least one lowercase letter.");
        }
        if (!password.matches(".*\d.*")) {
            errors.add(
                "Password must contain at least one digit.");
        }
        if (errors.isEmpty()) {
            errors.add(
                "Password is valid.");
        }
        return errors;
        // You no longer need a Regular Expression!!
    }
}

import static org.junit.Assert.*;
import org.junit.Test;

public class PasswordValidatorTest {
    // Now you have a lot of tests
    // You can use a Regular Expression,
    // a String Validator
    // an External Library
    // Whatever you want as long as it passes the tests!

    @Test
    public void testValidPassword() {
        List<String> result = 
            PasswordValidator.validatePassword(
            "StrongPass1");
        assertEquals("Password is valid.", result.get(0));
    }

    @Test
    public void testTooShortPassword() {
        List<String> result = PasswordValidator.validatePassword(
            "Short1");
        assertTrue(result.contains(
            "Password must be at least 8 characters long."));
    }

    @Test
    public void testNoUppercase() {
        List<String> result = PasswordValidator.validatePassword(
            "nouppercase1");
        assertTrue(
            result.contains(
                "Password must contain at least one uppercase letter."));
    }

    @Test
    public void testNoLowercase() {
        List<String> result = PasswordValidator.validatePassword(
            "NOLOWERCASE1");
        assertTrue(result.contains(
            "Password must contain at least one lowercase letter."));
    }

    @Test
    public void testNoNumber() {
        List<String> result = PasswordValidator.validatePassword(
            "NoNumberPass");
        assertTrue(result.contains(
            "Password must contain at least one digit."));
    }
}

偵測

[X] 自動

您可以透過將正規表示式變更為失敗並執行所有測試來偵測它何時被發現。

如果您的驗證傳回「false」而沒有使用者友善的解釋,則明確表明您需要重構它並改善回饋。

標籤

  • 測試

等級

[X] 初學者

人工智慧世代

人工智慧可以產生正規表示式,但通常無法提供有用的錯誤訊息。

如果沒有適當的說明,人工智慧產生的驗證器可能無法指導使用者修復他們的輸入。

人工智慧檢測

人工智慧可以偵測基本的正規表示式模式和缺失的回饋,並提供清晰的提示。

除非特別要求,否則它可能不會自動建立詳細的測試案例或描述。

嘗試一下!

記住:人工智慧助理會犯很多錯誤

Without Proper Instructions With Specific Instructions
ChatGPT ChatGPT
Claude Claude
Perplexity Perplexity
Copilot Copilot
Gemini Gemini

結論

沒有明確回饋的正規表示式對使用者不友善且容易出錯。

如果您描述了它們失敗的原因並編寫了徹底的測試以確保您的正規表示式按預期工作,這將會有所幫助。

關係

免責聲明

程式碼味道是我的觀點。

製作人員

照片由 Unsplash 上的 rc.xyz NFT 圖庫拍攝


回饋是冠軍的早餐。

肯·布蘭查德


本文是 CodeSmell 系列的一部分。

以上是程式碼異味 - 未經測試的正規表示式的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn