challenge 改行をBRタグに置き換える

一部のHTMLタグを通すフィルタ どう書く?の続編です。 前回の条件を満たしつつ、入力中の改行を<br/>に置き換えてください。ただし、たとえば"<a\nhref=...>"といったようにタグの中に改行がある場合、単純に置換するわけには行かないことに注意してください。

また、ユーザの入力注の<br>は<br/>に変換してください。

このお題はperezvonさんの提案を元にした三部作の二問目です。ご協力ありがとうございました。

Posted feedbacks - Java

#2906を元に改造しました。
</br>は取り除くように変更しています(<br></br>の変換結果が不正になるのを防ぐため)。
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
import java.util.regex.*;

public class Sample {
    private static final Pattern TAG_FILTER = Pattern.compile
        ("<(¥¥w+)((¥¥s+¥¥w+(¥¥s*=¥¥s*(¥"[^¥"]*¥"|'[^']*'|[¥¥w-:]*))?)*)¥¥s*/?¥¥s*>");
    private static final Pattern END_TAG_FILTER = Pattern.compile
        ("(?i)</(A|STRONG)¥¥s*>");
    private static final Pattern ATTR_FILTER = Pattern.compile
        ("(¥¥w+)¥¥s*=¥¥s*(¥"[^¥"]*¥"|'[^']*'|[¥¥w-:]*)");
    public static String sanitizing(String fragment) {
        fragment = fragment.replaceAll("[¥¥p{Cntrl}&&[^¥¥s]]", "");
        Matcher m = TAG_FILTER.matcher(fragment);
        StringBuffer sb = new StringBuffer();
        while (m.find()) {
            if ("A".equalsIgnoreCase(m.group(1))) {
                String href = null, name = null;
                Matcher m2 = ATTR_FILTER.matcher(m.group(2));
                while (m2.find()) {
                    if ("href".equalsIgnoreCase(m2.group(1))) {
                        href = m2.group(2);
                    } else if ("name".equalsIgnoreCase(m2.group(1))) {
                        name = m2.group(2);
                    }
                }
                String tag = "¥001"+m.group(1) + ((href != null)?" href="+href
                    : "") + ((name != null)? " name="+name : "") + "¥002";
                m.appendReplacement(sb, m.quoteReplacement(tag));
            } else if ("BR".equalsIgnoreCase(m.group(1))) {
                m.appendReplacement(sb, "¥001" + m.group(1) + "/¥002"); 
            } else if ("STRONG".equalsIgnoreCase(m.group(1))) {
                m.appendReplacement(sb, "¥001" + m.group(1) + "¥002");
            }
        }
        m.appendTail(sb);
        fragment = END_TAG_FILTER.matcher(sb).replaceAll("¥001/$1¥002");
        fragment = fragment.replaceAll("(?i)</BR¥¥s*>", "");
        fragment = fragment.replace("<", "&lt;").replace(">", "&gt;");
        fragment = fragment.replaceAll("¥r¥n|¥r|¥n", "<br/>");
        fragment = fragment.replace("¥001", "<").replace("¥002", ">");
        return fragment;
    }
    public static void main(String[] args) throws Exception {
        System.out.println(sanitizing("<script>¥r¥n¥r¥n<abc>¥r¥n<def¥r¥n ghi=jkl>¥r¥n<br></BR  >"));
        System.out.println(sanitizing("<script foo=¥"<script>alert(¥'bar¥')</script>¥">alert(¥'foo¥')¥n</script>¥n</BR  >"));
        System.out.println(sanitizing("<script foo=¥"<a href=¥'link¥'>link</a>¥" center>alert(¥'foo¥')</script><BR / >"));
        System.out.println(sanitizing("<a¥nhref='www.g>oogle.com' id=125>link</a>"));
    }
}

Index

Feed

Other

Link

Pathtraq

loading...