2015-01-15 60 views
0

我有一個看起來像這樣的組件:創建定製的「模板」,爲ReactJS組件內使用,無需

var MyTemplatedComponent = React.createClass({ 

    getDefaultProps: function() { 
    return { 
     discountValue: '10% off', 
     welcomeMessage: 'Want {{discountValue}} off your next order?' 
    }; 
    }, 

    getWelcomeMessage: function() { 
    return this.props.welcomeMessage.replace('{{discountValue}}', '<strong>'+this.props.discountValue+'</strong>'); 
    }, 

    render: function() { 
    return (
     <p className='lead' dangerouslySetInnerHTML={{ __html: this.getWelcomeMessage() }} /> 
    ); 
    } 

}); 

我們的目標是讓我們的客戶定製{{discountValue}},以滿足他們的喜好。然後我們想要加粗它在渲染時的折扣價值。

目前我發現正確做到這一點的唯一方法是使用dangerouslySetInnerHTML,但感覺很危險!還有一點難看。

任何人都可以想到更好的方式來處理這個問題嗎?

+1

如若 '{{welcomeMessage}}'在getWelcomeMessage()函數中是'{{discountValue}}'? – 2015-01-15 19:23:48

+0

你希望他們能夠自定義歡迎信息和/或折扣價值嗎? – 2015-01-15 19:33:37

+0

@DanielRobinson啊是的,這是一個錯字 - 修正。是的,應該可以自定義兩者。對於這個問題,假設客戶端永遠不會從{{welcomeMessage}}'中刪除'{{discountValue}}'。 – 2015-01-15 19:40:12

回答

1

在這種情況下使用dangerouslySetInnerHTML並不危險(因爲welcomeMessage將由客戶端寫入)。但是,如果您擔心客戶端可能會搞砸並將用戶輸入放入歡迎消息中,則只需在開始放入HTML之前轉義歡迎消息模板即可。

以下換碼從react itself採取:

var ESCAPE_LOOKUP = { 
    '&': '&amp;', 
    '>': '&gt;', 
    '<': '&lt;', 
    '"': '&quot;', 
    '\'': '&#x27;' 
}; 

var ESCAPE_REGEX = /[&><"']/g; 

function escaper(match) { 
    return ESCAPE_LOOKUP[match]; 
} 

function escapeTextForBrowser(text) { 
    return ('' + text).replace(ESCAPE_REGEX, escaper); 
} 

一旦你的功能,你可以修復getWelcomeMessage功能,像這樣:

getWelcomeMessage: function() { 
    return escapeTextForBrowser(this.props.welcomeMessage).replace('{{discountValue}}', '<strong>'+this.props.discountValue+'</strong>'); 
    },