1+ function _objectWithoutProperties ( source , excluded ) { if ( source == null ) return { } ; var target = _objectWithoutPropertiesLoose ( source , excluded ) ; var key , i ; if ( Object . getOwnPropertySymbols ) { var sourceSymbolKeys = Object . getOwnPropertySymbols ( source ) ; for ( i = 0 ; i < sourceSymbolKeys . length ; i ++ ) { key = sourceSymbolKeys [ i ] ; if ( excluded . indexOf ( key ) >= 0 ) continue ; if ( ! Object . prototype . propertyIsEnumerable . call ( source , key ) ) continue ; target [ key ] = source [ key ] ; } } return target ; }
2+
3+ function _objectWithoutPropertiesLoose ( source , excluded ) { if ( source == null ) return { } ; var target = { } ; var sourceKeys = Object . keys ( source ) ; var key , i ; for ( i = 0 ; i < sourceKeys . length ; i ++ ) { key = sourceKeys [ i ] ; if ( excluded . indexOf ( key ) >= 0 ) continue ; target [ key ] = source [ key ] ; } return target ; }
4+
5+ function ownKeys ( object , enumerableOnly ) { var keys = Object . keys ( object ) ; if ( Object . getOwnPropertySymbols ) { keys . push . apply ( keys , Object . getOwnPropertySymbols ( object ) ) ; } if ( enumerableOnly ) keys = keys . filter ( function ( sym ) { return Object . getOwnPropertyDescriptor ( object , sym ) . enumerable ; } ) ; return keys ; }
6+
7+ function _objectSpread ( target ) { for ( var i = 1 ; i < arguments . length ; i ++ ) { var source = arguments [ i ] != null ? arguments [ i ] : { } ; if ( i % 2 ) { ownKeys ( source , true ) . forEach ( function ( key ) { _defineProperty ( target , key , source [ key ] ) ; } ) ; } else if ( Object . getOwnPropertyDescriptors ) { Object . defineProperties ( target , Object . getOwnPropertyDescriptors ( source ) ) ; } else { ownKeys ( source ) . forEach ( function ( key ) { Object . defineProperty ( target , key , Object . getOwnPropertyDescriptor ( source , key ) ) ; } ) ; } } return target ; }
8+
9+ function _defineProperty ( obj , key , value ) { if ( key in obj ) { Object . defineProperty ( obj , key , { value : value , enumerable : true , configurable : true , writable : true } ) ; } else { obj [ key ] = value ; } return obj ; }
10+
11+ var _global = global ,
12+ describe = _global . describe ,
13+ it = _global . it ,
14+ expect = _global . expect ;
15+ import stateFromElement from '../stateFromElement' ;
16+ import { TextNode , ElementNode } from 'synthetic-dom' ;
17+ import { convertToRaw } from 'draft-js' ;
18+ import fs from 'fs' ;
19+ import { join } from 'path' ; // This separates the test cases in `data/test-cases.txt`.
20+
21+ var SEP = '\n\n#' ;
22+ var testCasesRaw = fs . readFileSync ( join ( __dirname , '..' , '..' , 'test' , 'test-cases.txt' ) , 'utf8' ) ;
23+ var testCases = testCasesRaw . slice ( 1 ) . trim ( ) . split ( SEP ) . map ( function ( text ) {
24+ var lines = text . split ( '\n' ) ;
25+ var description = lines . shift ( ) . trim ( ) ;
26+ var state = removeBlockKeys ( JSON . parse ( lines [ 0 ] ) ) ;
27+ var html = lines . slice ( 1 ) . join ( '\n' ) ;
28+ return {
29+ description : description ,
30+ state : state ,
31+ html : html
32+ } ;
33+ } ) ;
34+ describe ( 'stateFromElement' , function ( ) {
35+ it ( 'should create content state' , function ( ) {
36+ var textNode = new TextNode ( 'Hello World' ) ;
37+ var element = new ElementNode ( 'div' , [ ] , [ textNode ] ) ;
38+ var contentState = stateFromElement ( element ) ;
39+ var rawContentState = removeBlockKeys ( convertToRaw ( contentState ) ) ;
40+ expect ( rawContentState ) . toEqual ( {
41+ entityMap : { } ,
42+ blocks : [ {
43+ text : 'Hello World' ,
44+ type : 'unstyled' ,
45+ data : { } ,
46+ depth : 0 ,
47+ inlineStyleRanges : [ ] ,
48+ entityRanges : [ ]
49+ } ]
50+ } ) ;
51+ } ) ;
52+ it ( 'should support option customBlockFn (type)' , function ( ) {
53+ var textNode = new TextNode ( 'Hello World' ) ;
54+ var element = new ElementNode ( 'center' , [ ] , [ textNode ] ) ;
55+ var options = {
56+ customBlockFn : function customBlockFn ( element ) {
57+ var tagName = element . tagName ;
58+
59+ if ( tagName === 'CENTER' ) {
60+ return {
61+ type : 'center-align'
62+ } ;
63+ }
64+ }
65+ } ;
66+ var contentState = stateFromElement ( element , options ) ;
67+ var rawContentState = removeBlockKeys ( convertToRaw ( contentState ) ) ;
68+ expect ( rawContentState ) . toEqual ( {
69+ entityMap : { } ,
70+ blocks : [ {
71+ text : 'Hello World' ,
72+ type : 'center-align' ,
73+ data : { } ,
74+ depth : 0 ,
75+ inlineStyleRanges : [ ] ,
76+ entityRanges : [ ]
77+ } ]
78+ } ) ;
79+ } ) ;
80+ it ( 'should support option customBlockFn (data)' , function ( ) {
81+ var textNode = new TextNode ( 'Hello World' ) ;
82+ var element = new ElementNode ( 'p' , [ {
83+ name : 'align' ,
84+ value : 'right'
85+ } ] , [ textNode ] ) ;
86+ var options = {
87+ customBlockFn : function customBlockFn ( element ) {
88+ var tagName = element . tagName ;
89+
90+ if ( tagName === 'P' && element . getAttribute ( 'align' ) === 'right' ) {
91+ return {
92+ data : {
93+ textAlign : 'right'
94+ }
95+ } ;
96+ }
97+ }
98+ } ;
99+ var contentState = stateFromElement ( element , options ) ;
100+ var rawContentState = removeBlockKeys ( convertToRaw ( contentState ) ) ;
101+ expect ( rawContentState ) . toEqual ( {
102+ entityMap : { } ,
103+ blocks : [ {
104+ text : 'Hello World' ,
105+ type : 'unstyled' ,
106+ data : {
107+ textAlign : 'right'
108+ } ,
109+ depth : 0 ,
110+ inlineStyleRanges : [ ] ,
111+ entityRanges : [ ]
112+ } ]
113+ } ) ;
114+ } ) ;
115+ it ( 'should support option customInlineFn' , function ( ) {
116+ var element = new ElementNode ( 'div' , [ ] , [ new ElementNode ( 'span' , [ {
117+ name : 'class' ,
118+ value : 'bold'
119+ } ] , [ new TextNode ( 'Hello' ) ] ) , new ElementNode ( 'span' , [ {
120+ name : 'class' ,
121+ value : 'link'
122+ } ] , [ new TextNode ( 'World' ) ] ) ] ) ;
123+ var options = {
124+ customInlineFn : function customInlineFn ( el , _ref ) {
125+ var Style = _ref . Style ,
126+ Entity = _ref . Entity ;
127+
128+ if ( el . tagName === 'SPAN' && el . className === 'bold' ) {
129+ return Style ( 'BOLD' ) ;
130+ }
131+
132+ if ( el . tagName === 'SPAN' && el . className === 'link' ) {
133+ return Entity ( 'LINK' , {
134+ url : '/abc'
135+ } ) ;
136+ }
137+ }
138+ } ;
139+ var contentState = stateFromElement ( element , options ) ;
140+ var rawContentState = removeBlockKeys ( convertToRaw ( contentState ) ) ;
141+ expect ( rawContentState ) . toEqual ( {
142+ entityMap : _defineProperty ( { } , 0 , {
143+ type : 'LINK' ,
144+ mutability : 'MUTABLE' ,
145+ data : {
146+ url : '/abc'
147+ }
148+ } ) ,
149+ blocks : [ {
150+ text : 'HelloWorld' ,
151+ type : 'unstyled' ,
152+ depth : 0 ,
153+ inlineStyleRanges : [ {
154+ offset : 0 ,
155+ length : 5 ,
156+ style : 'BOLD'
157+ } ] ,
158+ entityRanges : [ {
159+ offset : 5 ,
160+ length : 5 ,
161+ key : 0
162+ } ] ,
163+ data : { }
164+ } ]
165+ } ) ;
166+ } ) ;
167+ it ( 'should support option elementStyles' , function ( ) {
168+ var textNode = new TextNode ( 'Superscript' ) ;
169+ var element = new ElementNode ( 'sup' , [ ] , [ textNode ] ) ;
170+ var wrapperElement = new ElementNode ( 'div' , [ ] , [ element ] ) ;
171+ var options = {
172+ elementStyles : {
173+ sup : 'SUPERSCRIPT'
174+ }
175+ } ;
176+ var contentState = stateFromElement ( wrapperElement , options ) ;
177+ var rawContentState = removeBlockKeys ( convertToRaw ( contentState ) ) ;
178+ expect ( rawContentState ) . toEqual ( {
179+ entityMap : { } ,
180+ blocks : [ {
181+ text : 'Superscript' ,
182+ type : 'unstyled' ,
183+ data : { } ,
184+ depth : 0 ,
185+ inlineStyleRanges : [ {
186+ offset : 0 ,
187+ length : 11 ,
188+ style : 'SUPERSCRIPT'
189+ } ] ,
190+ entityRanges : [ ]
191+ } ]
192+ } ) ;
193+ } ) ;
194+ it ( 'should support images' , function ( ) {
195+ var imageNode = new ElementNode ( 'img' , [ {
196+ name : 'src' ,
197+ value : 'imgur.com/asdf.jpg'
198+ } ] ) ;
199+ var wrapperElement = new ElementNode ( 'div' , [ ] , [ imageNode ] ) ;
200+ var contentState = stateFromElement ( wrapperElement ) ;
201+ var rawContentState = removeBlockKeys ( convertToRaw ( contentState ) ) ;
202+ expect ( rawContentState ) . toEqual ( {
203+ blocks : [ {
204+ data : { } ,
205+ depth : 0 ,
206+ entityRanges : [ {
207+ key : 0 ,
208+ length : 1 ,
209+ offset : 0
210+ } ] ,
211+ inlineStyleRanges : [ ] ,
212+ text : ' ' ,
213+ type : 'unstyled'
214+ } ] ,
215+ entityMap : {
216+ // This is necessary due to flow not supporting non-string literal property keys
217+ // eslint-disable-next-line quote-props
218+ '0' : {
219+ data : {
220+ src : 'imgur.com/asdf.jpg'
221+ } ,
222+ mutability : 'MUTABLE' ,
223+ type : 'IMAGE'
224+ }
225+ }
226+ } ) ;
227+ } ) ;
228+ } ) ;
229+ describe ( 'stateFromHTML' , function ( ) {
230+ testCases . forEach ( function ( testCase ) {
231+ var description = testCase . description ,
232+ state = testCase . state ,
233+ html = testCase . html ;
234+ it ( "should render " . concat ( description ) , function ( ) {
235+ var element = parseHTML ( html ) ;
236+ var actualState = removeBlockKeys ( convertToRaw ( stateFromElement ( element ) ) ) ;
237+ expect ( actualState ) . toEqual ( state ) ;
238+ } ) ;
239+ } ) ;
240+ } ) ;
241+
242+ function parseHTML ( html ) {
243+ if ( document . documentElement ) {
244+ document . documentElement . innerHTML = html ;
245+ } // This makes Flow happy
246+
247+
248+ return document . body || document . createElement ( 'body' ) ;
249+ }
250+
251+ function removeBlockKeys ( content ) {
252+ var newContent = _objectSpread ( { } , content ) ;
253+
254+ newContent . blocks = content . blocks . map ( function ( block ) {
255+ var key = block . key ,
256+ other = _objectWithoutProperties ( block , [ "key" ] ) ; // eslint-disable-line no-unused-vars
257+
258+
259+ return other ;
260+ } ) ;
261+ return newContent ;
262+ }
0 commit comments