비밀번호에 대한 정규식입니다. 특수 문자 제한

비밀번호에 대한 정규식입니다. 특수 문자 제한

AWS 클라우드 형성 템플릿에 일부 암호 항목을 입력하려고 합니다. 그리고 비밀번호를 영숫자 및 특수 문자의 하위 집합으로 제한하세요. 나는 다음을 시도했다:

"^(?=.*?[A-Z])(?=.*?[a-z])(?=.*?[0-9])(?=.*?[#@$?]).{8,}$"

이는 최소 하나의 소문자와 대문자, 하나의 숫자가 있어야 함을 나타냅니다. 또한 특수 문자 세트를 다음으로 제한하십시오.[#@$?]

나는 모든 특수 문자(마지막 문자인 경우)가 허용되는 것을 관찰했습니다. 예상대로 다른 곳에서는 금지됨

그래서 Hello*E1허용되지 않지만 HelloE1*허용됩니다.

[#@$?]나타나는 위치 에 관계없이 모든 특수 문자를 비활성화하는 방법은 무엇입니까 ?

또한 전체 특수 문자 세트를 비활성화하려면 어떻게 해야 합니까? "^(?=.*?[A-Z])(?=.*?[a-z])(?=.*?[0-9]).{8,}$도움이 안돼. 이렇게 하면 모든 특수 문자가 허용됩니다.

도움을 주시면 감사하겠습니다.

답변1

정규식:

^(?=[a-zA-Z0-9#@$?]{8,}$)(?=.*?[a-z])(?=.*?[A-Z])(?=.*?[0-9]).*

설명하다:

제공한 정규식에서 미리보기는 문자열이 특정 조건을 충족하는지 확인하는 데 사용되지만 원치 않는 문자열을 차단하는 실제 필터는 아닙니다. 다음 조건을 지정했습니다.

  • (?=.*?[A-Z]): 하나 이상의 대문자와 일치합니다.
  • (?=.*?[a-z]): 하나 이상의 소문자와 일치합니다.
  • (?=.*?[0-9]): 하나 이상의 숫자와 일치합니다.
  • (?=.*?[#@$?]): 다음 문자 중 하나 이상과 일치합니다.#@$?
  • .{8,}: 임의의 문자를 8번 이상 일치시킵니다.

그러나 적어도 두 가지 결함이 있습니다.

  • (?=.*?[#@$?])특수문자는 필수가 아닌 선택이므로 불필요한 부분입니다[1].

  • 이전에 말했듯이 실제 필터를 지정하지 않았으므로 해당 .{8,}부분으로 인해 정규 표현식은 원치 않는 특수 문자가 포함된 경우에도 미리보기에 의해 설정된 조건을 충족하는 한 모든 문자열을 허용합니다 [1].

따라서 이러한 결함을 해결하려면 다음이 필요합니다.

  • (?=.*?[#@$?])섹션을 삭제하세요.

  • 위에서 언급한 필터 역할을 하는 새로운 미리보기를 추가합니다.

이 필터를 구축하려면 "어떤 문자를 허용하지 않을 것인가?"보다는 "어떤 문자를 허용할 것인가?"를 생각해야 합니다. 왜냐하면 이 특정한 경우는 처리하기가 더 쉽기 때문입니다. a-z, A-Z및 문자 0-9만 허용되기를 원한다고 말하면 #@$?미리보기는 다음과 같아야 합니다.

(?=[a-zA-Z0-9#@$?])

하지만 이 단계에서는 최소 길이를 설정하고 미리보기에 시작 위치와 중지 위치(이 경우 문자열의 시작과 끝)를 알려줄 수도 있습니다.

(?=[a-zA-Z0-9#@$?]{8,}$)

여기서는 이미 모든 것의 시작 부분에 있으므로 생략 했으므로 ^중복할 필요가 없습니다. 이제 모든 예측을 함께 설정하고 다음 명령을 사용하여 .*유효한 비밀번호를 일치시키기만 하면 됩니다 .{8,}.

^(?=[a-zA-Z0-9#@$?]{8,}$)(?=.*?[a-z])(?=.*?[A-Z])(?=.*?[0-9]).*

노트:

  1. 귀하가 제공한 정규 표현식과 예제에서 그 이유는 잘 모르겠습니다. 1) #@$?필수로 간주되지 않습니다. 2) 원하지 않는 문자는 문자열 끝에서만 허용되며 다른 곳에서는 허용되지 않습니다. 아마도 이것은 AWS에서 사용하는 정규식 엔진과 관련이 있을 것입니다. 왜냐하면 제가 직접 테스트했을 때 모든 것이 예상대로 작동했기 때문입니다.

답변2

우리는 필요한 각 문자 유형과 길이 요구 사항에 대해 문자열 시작 부분에 미리보기를 고정하려고 합니다. 그런 다음 .*모든 것을 삼켜 버리십시오.

^(?=[0-9a-zA-Z#@\$\?]{8,}$)(?=[^a-z]*[a-z])(?=[^A-Z]*[A-Z])(?=[^0-9]*[0-9]).*

설명하다:

먼저, 다음과 같은 이유로 필수 char 유형(예: 대문자)을 일치시킬 때 게으른 수량자를 사용하지 않기로 결정했습니다.

  • 그것들은 비싸.
  • 정규식 엔진마다 게으름을 표현하는 방법이 다릅니다. (부부는 전혀 지지하지 않았습니다.)
  • 그것들은 대안만큼 일반적이거나 친숙하지 않습니다.

그래서 효율성, 가독성, "이식성"을 위해 이 ^[^x]*[x]구조를 사용했습니다.

이제 나머지도 분해해 보세요...

^: 모든 것은 처음부터 시작된다

(?=[0-9a-zA-Z#@\$\?]{8,}$): 문자열의 시작과 끝 사이에 허용되는 문자 8개 이상을 사용하여 미리 봅니다.

다음 세 개는 동일한 패턴을 사용합니다. 즉, 0개 이상의 문자 미리보기와 일치합니다.아니요원하는 문자를 일치시킨 다음 원하는 문자를 일치시키십시오. 이는 시작 부분에 고정되어 있으므로 원하는 문자가 문자열의 어느 위치에서나 일치되도록 하는 효과가 있습니다.

(?=[^a-z]*[a-z]): 소문자 하나 이상.

(?=[^A-Z]*[A-Z]): 적어도 하나의 대문자.

(?=[^0-9]*[0-9]) : 최소한 한 자리.

.*: 위의 모든 내용은 미래지향적이며 아무것도 소비하지 않으므로 여기서는 모두 소비하세요. 첫 번째 미리보기에서는 전체 문자열이 유효한 문자인지 확인하므로 안전합니다.

나는 이것이 최적화되었다고 주장하지 않습니다(게으른 수량자를 피하는 것 외에는). 이것은 이해하기 쉬운 형식 중 하나일 뿐입니다.


참고: 관찰한 문제의 원인은 #@$?미리보기가 문자열 끝에 고정되지 않았기 때문입니다.어느문자는 이 4개 문자 중 하나 이후에 일치합니다(마지막 위치에서만 일치할 필요는 없음). 물론 $유효한 문자를 제외시키므로 추가할 수는 없습니다. 이것이 바로 동일한 예측에 유효한 모든 문자를 포함시키는 이유입니다.

답변3

귀하의 정규식에는 없습니다금지하다어떤 캐릭터든 그냥 그래필요모든 클래스에는 인스턴스가 있습니다. 허용되는 문자 .를 제한하려면어느문자)를 허용되는 문자 세트로:

^(?=.*?[A-Z])(?=.*?[a-z])(?=.*?[0-9])(?=.*?[#@$?])[a-zA-Z0-9#@$?]{8,}$

문자열을 의미하는 경우 s와 s를 이스케이프 처리하거나 큰 따옴표( 또는 )를 사용해야 perl합니다 . 또한 정규식이 ASCII 모드( 영어 문자만 일치하고 모든 바이트와 일치)에서 작동하는지 확인해야 합니다.$@'...'q{...}a-z.

(?=.*?[#@$?])안되면 삭제하세요필요하다기호 중 하나 이상입니다.

관련 정보