Thymeleafでエスケープ処理はされるのかという問いです。
用語整理
サニタイズ・・・意図しない動作を生んでしまう文字を無効化する
エスケープ・・・意図しない動作を生んでしまう文字を別の文字列に置き換える。
初めに、下記簡単なformを作り値の表示を行いました。
Controller
@GetMapping("/test")
public String c(@ModelAttribute Hoge hoge) {
return "test";
}
@PostMapping("/test")
public String ck(@ModelAttribute Hoge hoge, Model model) {
System.out.println(hoge.isChexckBox());
model.addAttribute("test", hoge.getName());
return "test";
}
test.html
<html xmlns:th="http://www.thmeleaf.org">
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
<form th:action="@{/test}" th:object="${hoge}" method=post>
<input type="checkbox" th:field="*{checkBox}" value="true">
<input type="text" id=name, name=name>
<button>sousinn</button>
</form>
<div th:utext="${test}"></div>
</body>
</html>
①ここで、<script>alert('aaa')</script>などと打つと、th:utextはサニタイズをしないので、左記コードが実行されてしまいます。
th:textや変数式で表示する分には実行されません。
②では、他のメタ文字はどうでしょうか。
例えば「\」です。
デバッグでnameの値を見ると「\\」となっています。
③では、HtmlUtils.escape()ではどうでしょうか。
<script>alert('aaa')</script>は<script>alert('初めての脆弱性')</script>
Viewでは...
th:utextは<script>alert('初めての脆弱性')</script>
変数式は<script>alert('初めての脆弱性')</script>
「\」はデバッグだと「\\」。Viewは「\」です。
結論
①、②より、Thymeleaf側かSpring Boot側でエスケープ処理される文字とされていない文字がある。
③より、HtmlUtils.escape()を使用するとサニタイズしていなくてもスクリプトの実行を防げた。
③より、呼び出した際に、元の文字列に戻っている事から返した値をエスケープ処理せずに表示する場合は気を付ける。例えば、JavaScriptで何も対策せずに処理をする際は気を付けなくてはいけない。
日記
このブログは閲覧者がいるわけではないので、日々思った事を綴りたい。
昨年あたりの転職活動の際も感じていた事だが、Twitterの方々の言う「市場価値」というのが、思いのほか刺さる。
個人でWebアプリをリリースし、他にも考えている活動を通して、ゆくゆくは、そこから広げた面白い取り組みをしたいと思っているわけだが、この市場価値がない内はそもそも開発に携われないので苦しい。
幸いな事に、会社の方々との出会いには恵まれて、時間も、教えていただける環境もあるので実現可能とは思うが、まるで、この「市場価値=自分そのもの」のような感覚に囚われて、意味もなく焦ったり、落ち込んだりするわけだ。2月あたりは落ち込みが酷かった。
しかし、まあ、やるしかないって事です。今の会社で頑張ると決めたので、頑張るだけです。