본문 바로가기
블로그 이미지

방문해 주셔서 감사합니다! 항상 행복하세요!

  
   - 문의사항은 메일 또는 댓글로 언제든 연락주세요.
   - "해줘","답 내놔" 같은 질문은 답변드리지 않습니다.
   - 메일주소 : lts06069@naver.com


Spring framework

Spring XSS 방지를 위한 lucy 필터(com.navercorp.lucy)

야근없는 행복한 삶을 위해 ~
by 마샤와 곰 2021. 10. 15.

xss공격 방지를 위해 다양한 방법이 나오지만 가장 쉬운 것은 잘 만들어진(?) 라이브러리를 사용하는 것 입니다.

이러한 라이브러리는 그만큼 많은 테스트와 검증이 되었을 테니까요.

스프링(전자정부)에서 XSS 공격을 방지하기 위해서 네이버 형님들께서 만드신 com.navercorp.lucy 패키지의 라이브러리를 사용하여 보았습니다.

 

아래 메이븐 리파지토리에서 자신의 빌드환경에 맞는 내용을 추가하여 주시면 됩니다.

https://mvnrepository.com/artifact/com.navercorp.lucy

 

2개가 보이네요!

 

메이븐 환경에서 위 2개의 라이브러리를 추가한 모습 입니다.

* 파일명 : pom.xml

<!-- https://mvnrepository.com/artifact/com.navercorp.lucy/lucy-xss-servlet -->
<dependency>
    <groupId>com.navercorp.lucy</groupId>
    <artifactId>lucy-xss-servlet</artifactId>
    <version>2.0.1</version>
</dependency>

<!-- https://mvnrepository.com/artifact/com.navercorp.lucy/lucy-xss -->
<dependency>
    <groupId>com.navercorp.lucy</groupId>
    <artifactId>lucy-xss</artifactId>
    <version>1.6.3</version>
</dependency>

 

먼저 첫번째 라이브러리를 주목해야 합니다.

해당 라이브러리를 메이븐 또는 그레이들 환경에 추가하여 준 다음에 간단한 필터 설정을 통해서 개발자가 원하는 패턴에 대해서 XSS공격을 하지 못하도록 변경 할 수 있습니다.

web.xml 파일에 lucy xss필터를 넣어줍니다.

* 파일명 : web.xml

<!-- XSS filter -->
<filter>
    <filter-name>xssEscapeServletFilter</filter-name>
    <filter-class>com.navercorp.lucy.security.xss.servletfilter.XssEscapeServletFilter</filter-class>
</filter>
<filter-mapping>
    <filter-name>xssEscapeServletFilter</filter-name>
    <url-pattern>필터를적용할매핑규칙(*, *.do등)</url-pattern>
</filter-mapping>

 

다음으로 resources 디렉토리나 클래스 첫번째 디렉토리에 lucy와 관련된 규칙 파일을 만들어 줍니다.

파일명은  lucy-xss-servlet-filter-rule.xml 이라고 해야 합니다.

저는 전자정부프레임워크입니다..ㅎ

 

이렇게 하고난 뒤에 lucy규칙파일을 아래 내용으로 채워 줍니다.

* 파일명 : lucy-xss-servlet-filter-rule.xml

<?xml version="1.0" encoding="UTF-8"?> 
  <config xmlns="http://www.navercorp.com/lucy-xss-servlet">  
    <defenders>   
      <!-- XssPreventer 등록 --> 
      <defender> 
        <name>xssPreventerDefender</name> 
        <class>com.navercorp.lucy.security.xss.servletfilter.defender.XssPreventerDefender</class>
      </defender> 
    
      <!-- XssSaxFilter 등록 --> 
      <defender>
        <name>xssSaxFilterDefender</name>
        <class>com.navercorp.lucy.security.xss.servletfilter.defender.XssSaxFilterDefender</class>
        <init-param> 
          <param-value>lucy-xss-sax.xml</param-value> <!-- lucy-xss-filter의 sax용 설정파일 -->       
          <param-value>false</param-value>      <!-- 필터링된 코멘트를 남길지 여부, 성능 효율상 false 추천 -->
        </init-param> 
      </defender> 
    
      <!-- XssFilter 등록 -->   
      <defender>
        <name>xssFilterDefender</name> 
        <class>com.navercorp.lucy.security.xss.servletfilter.defender.XssFilterDefender</class> 
        <init-param> 
          <param-value>lucy-xss.xml</param-value> <!-- lucy-xss-filter의 dom용 설정파일 -->       
          <param-value>false</param-value>     <!-- 필터링된 코멘트를 남길지 여부, 성능 효율상 false 추천 -->      
        </init-param> 
      </defender> 
    </defenders> 
    
    <!-- default defender 선언, 별다른 defender 선언이 없으면 default defender를 사용해 필터링 한다. --> 
    <default> 
      <defender>xssPreventerDefender</defender> 
    </default> 
    
    <!-- global 필터링 룰 선언 -->
<!--     <global>
      모든 url에서 들어오는 'gParam' 파라미터는 필터링 되지 않으며 또한 'g'로 시작하는 파라미터도 필터링 되지 않는다. 
      <params> 
        <param name="gParam" useDefender="false" />
        <param name="g" usePrefix="true" useDefender="false" /> 
      </params>
    </global> 
-->
    
    <!-- URL 별 필터링 룰 선언 -->
    <url-rule-set>
      <!-- url disable이 true이면 지정한 url 내의 모든 파라미터는 필터링되지 않는다.(기본값은 false) -->
      <url-rule>
        <url disable="true">/test.do</url>
      </url-rule>
      
      <!--
      1. '/xss/globalFilter.do' 내의 nParam은 필터링 되지 않는다.
      2. '/xss/globalFilter.do' 내의 'n'으로 시작하는 파라미터는 필터링 되지 않는다.(usePrefix=true)
       -->
      <url-rule>
        <url>/xss/globalFilter.do</url>
        <params>
          <param name="nParam" useDefender="false" />
          <param name="n" usePrefix="true" useDefender="false" />
        </params>
      </url-rule>
    </url-rule-set>
  </config>

 

xml 내부의 내용이 직관적이라 크게 어렵지는 않습니다.

기본적으로 web.xml에 적용된 패턴은 lucy필터의 영향을 받습니다.

그렇지만 url-rule-set 을 통해서 예외 url을 등록 할 수가 있습니다.

 

조금 아쉬운 것은, 예외 규칙에 적용 되었다 하더라도 데이터를 강제로 매핑하는 기능은 꺼지지 않는다는 것 입니다.

예를 들어,

/test/insertHtml 이라는 주소로 데이터를 넣는 기능을 만들었다면, 해당 파라미터들은 컨트롤러에 도착하는 경우 전부 특수문자가 치환되어있는 상태로 나타나게 됩니다.

 

다시말해,

예외규칙에 적용 된 대상은 필터링에서는 제외가 되지만 특수문자 치환에서는 제외되지 않는다는 점 입니다.

 

이를 수정하기 위해서는, web.xml에서 아에 해당 패턴을 제외하는 방법이 있으며,

아니면 com.nhncorp.lucy.security.xss 패키지에 존재하는 XssPreventer 클래스를 사용하여 주면 됩니다.

간단한 샘플 코드로 살펴보겠습니다.

import com.nhncorp.lucy.security.xss.XssPreventer;

@Service("TestService")
public class TestService {

    public void testMethod(HashMap<Object, Object> query){
        XssPreventer.unescape(param.get("scriptData").toString());
        XssPreventer.unescape(param.get("jsonData").toString());
    }
}

 

컨트롤러로 부터 받은 HashMap 데이터는 lucy에 의해서 이미 치환된 상태 입니다.

이럴 때는 XssPreventer 클래스의 unescape 메소드에 원래의 데이터 형태로 바꿀 대상의 값을 문자(String)형태로 넣어주면 치환된 데이터가 다시 원래대로 나타나게 됩니다.

이를 조금만 응용하면, XssPreventer의 escape 메소드를 사용하면 치환되지 않는 문자를 치환할 수 있습니다.

오..설명이 잘 나와있네요!

 

아래 사이트에서 좀 더 자세한 정보를 확인 할 수 있습니다.

http://naver.github.io/lucy-xss-filter/kr/

 

XSS 공격에 대한 규칙과 방법을 전부 만드는 것 또한 멋진일 일 것 입니다.

그러나 시간도 부족하고 전문적인 기능을 원한다면 lucy 라이브러리를 사용 해 보는 것은 어떨까요? ^-^

이상으로 Spring XSS 방지를 위한 lucy 필터 사용법에 대해서 살펴보았습니다.

궁금한점 또는 틀린부분은 언제든 연락주세요! 👻

반응형
* 위 에니메이션은 Html의 캔버스(canvas)기반으로 동작하는 기능 입니다. Html 캔버스 튜토리얼 도 한번 살펴보세요~ :)
* 직접 만든 Html 캔버스 애니메이션 도 한번 살펴보세요~ :)

댓글