이 글은 기계 번역의 미러 문서이며, 원본 기사로 바로 이동하려면 여기를 클릭해 주세요.

보기: 12749|회답: 0

[출처] mybatis는 SQL 주입을 방지합니다

[링크 복사]
게시됨 2018. 8. 16. 오전 10:57:34 | | |
SQL 인젝션은 오늘날에도 여전히 매우 흔한 단순한 공격 벡터입니다. 그 이유는 바로 멍청한 자격이 없는 패치 때문입니다. 왜 그렇게 말씀하시나요? 예를 들어 JAVA를 들어 보겠습니다:

데이터베이스에 다음과 같은 테이블이 있다고 가정해 봅시다:


그 다음 JDBC 액션 테이블을 사용하세요:


위 코드는 일부 개발자들이 자주 사용합니다. 들어오는 userID 매개변수가 "3;"인 상황을 상상해 보세요. 드롭 테이블 사용자; 실행되는 SQL 문은 다음과 같습니다:


데이터베이스가 컴파일되고 실행된 후, 사용자 테이블은 삭제됩니다. 짜잔, 간단한 SQL 주입 공격이 효과를 발휘합니다! 이는 위 코드가 프로그래밍 명세에 부합하지 않기 때문입니다.

명세에 따라 프로그래밍할 때는 SQL 인젝션이 전혀 없습니다. 이것도 마찬가지입니다SQL 인젝션을 피하는 첫 번째 방법: 사전 컴파일된 문장, 코드는 다음과 같습니다:


위 코드에는 왜 SQL 인젝션이 존재하지 않을까요? 사전 컴파일된 문장이 사용되기 때문에, 사전 컴파일된 문은 "id=인 사용자 이름으로 선택하세요?"를 설정합니다. 문장은 실행 시 들어오는 파라미터로만 교체하면 되도록 미리 컴파일된 건가요? 임시 표시자도 괜찮습니다. 첫 번째 비준수 사례에서는 프로그램이 SQL 문장을 작성한 후 사용자가 전달한 내용으로 컴파일하는데, 이것이 바로 문제입니다.

사전 컴파일된 문장 외에도, 두 번째 옵션이 있습니다SQL 주입 공격을 피하는 방법: 저장 프로시저。 저장 프로시저란 특정 기능을 수행하는 SQL 문들의 집합으로, 컴파일되어 데이터베이스에 저장되며, 사용자는 저장 프로시저를 호출하고 매개변수를 입력함으로써 실행할 수 있습니다(저장 프로시저에 매개변수가 있는 경우). 이는 SQL 인젝션 공격을 피할 수도 있습니다

위 코드에 해당하는 저장 프로시저는 다음과 같습니다:

물론 사용자는 프론트엔드에서 문자 검사를 할 수도 있는데, 이는 SQL 인젝션을 피하는 방법이기도 합니다. 예를 들어, 위의 userId 매개변수에 대해 세미콜론이 있는지 확인하면 오류가 표시됩니다.
하지만 가장 근본적인 이유는 SQL 인젝션 공격이 존재하기 때문인데, 앱이 데이터베이스에 접근할 때 최소 권한을 사용하지 않기 때문입니다. 모두가 데이터베이스에 접근할 때 루트 계정을 사용하고 있는 것 같습니다.

그렇다면 MyBatis는 SQL 주입 공격을 어떻게 피할 수 있을까요? 또는 위의 테이블 사용자를 예로 들자:
예를 들어 맵퍼 파일이 다음과 같다고 가정해 봅시다:


해당 자바 파일들은 다음과 같습니다:


userId="34를 입력하면 입력 매개변수가 String 타입의 userId임을 알 수 있습니다; 드롭 테이블 사용자; 그 후 인쇄된 성명은 다음과 같습니다:


입력한 사용자 ID와 상관없이, 그의 SQL 문장은 다음과 같습니다. 이는 mybatis가 기본 구현에서 미리 컴파일된 문장을 사용하기 때문입니다. 데이터베이스가 그 문장을 실행할 때, 미리 컴파일된 문장을 직접 사용한 뒤, 자리 표시자를 전달하는 userID로 대체합니다. 그냥 가서 도망쳐. 먼저 자리 표시자를 교체하는 게 좋을까요? 컴파일 과정이 수행되기 때문에 SQL 인젝션이 살아남을 여지가 없습니다.

그렇다면 MyBatis는 SQL 사전 컴파일을 어떻게 하나요? 실제로 PreparedStatement 클래스는 프레임워크 하단에 사용됩니다. PreparedStaement 클래스는 SQL 주입을 피할 뿐만 아니라, 동일한 SQL 문장이 N번 실행될 경우 컴파일 시간을 (N-1) 절약하여 효율성을 높입니다.

위 문장을 다음과 같이 변경하면:

userId="34; 드롭 테이블 사용자; 그 후 인쇄된 성명은 다음과 같습니다:

현재 mybatis는 사전 컴파일된 문장을 사용하지 않고, 먼저 문자열을 스티치한 후 컴파일을 수행하는데, 이는 SQL 인젝션이 작동하는 방식과 정확히 일치합니다.
따라서 mybatis 매핑 명을 작성할 때는 "#{xxx}" 형식을 사용해 보세요. "${xxx}" 같은 매개변수를 사용해야 한다면, SQL 인젝션 공격을 막기 위해 수동으로 필터링해야 합니다.





이전의:C# 물음표인가요? 연산자
다음:IDEA에서의 다중 줄 주석 및 언코멘트 단축키
면책 조항:
Code Farmer Network에서 발행하는 모든 소프트웨어, 프로그래밍 자료 또는 기사는 학습 및 연구 목적으로만 사용됩니다; 위 내용은 상업적 또는 불법적인 목적으로 사용되지 않으며, 그렇지 않으면 모든 책임이 사용자에게 부담됩니다. 이 사이트의 정보는 인터넷에서 가져온 것이며, 저작권 분쟁은 이 사이트와는 관련이 없습니다. 위 내용은 다운로드 후 24시간 이내에 컴퓨터에서 완전히 삭제해야 합니다. 프로그램이 마음에 드신다면, 진짜 소프트웨어를 지원하고, 등록을 구매하며, 더 나은 진짜 서비스를 받아주세요. 침해가 있을 경우 이메일로 연락해 주시기 바랍니다.

Mail To:help@itsvse.com