Non-word characters don't terminate tag names.
[mediawiki.git] / tests / qunit / suites / resources / jquery / jquery.byteLimit.test.js
blob596c57c5ba935f2accb6a34b1530a32f55cd22d0
1 ( function ( $, mw ) {
2         var simpleSample, U_20AC, mbSample;
4         QUnit.module( 'jquery.byteLimit', QUnit.newMwEnvironment() );
6         // Simple sample (20 chars, 20 bytes)
7         simpleSample = '12345678901234567890';
9         // 3 bytes (euro-symbol)
10         U_20AC = '\u20AC';
12         // Multi-byte sample (22 chars, 26 bytes)
13         mbSample = '1234567890' + U_20AC + '1234567890' + U_20AC;
15         // Basic sendkey-implementation
16         function addChars( $input, charstr ) {
17                 var c, len;
19                 function x( $input, i ) {
20                         // Add character to the value
21                         return $input.val() + charstr.charAt( i );
22                 }
24                 for ( c = 0, len = charstr.length; c < len; c += 1 ) {
25                         $input
26                                 .val( x( $input, c ) )
27                                 .trigger( 'change' );
28                 }
29         }
31         /**
32          * Test factory for $.fn.byteLimit
33          *
34          * @param {Object} options
35          * @param {string} options.description Test name
36          * @param {jQuery} options.$input jQuery object in an input element
37          * @param {string} options.sample Sequence of characters to simulate being
38          *  added one by one
39          * @param {string} options.expected Expected final value of `$input`
40          */
41         function byteLimitTest( options ) {
42                 var opt = $.extend( {
43                         description: '',
44                         $input: null,
45                         sample: '',
46                         expected: ''
47                 }, options );
49                 QUnit.asyncTest( opt.description, 1, function ( assert ) {
50                         setTimeout( function () {
51                                 opt.$input.appendTo( '#qunit-fixture' );
53                                 // Simulate pressing keys for each of the sample characters
54                                 addChars( opt.$input, opt.sample );
56                                 assert.equal(
57                                         opt.$input.val(),
58                                         opt.expected,
59                                         'New value matches the expected string'
60                                 );
62                                 QUnit.start();
63                         }, 10 );
64                 } );
65         }
67         byteLimitTest( {
68                 description: 'Plain text input',
69                 $input: $( '<input type="text"/>' ),
70                 sample: simpleSample,
71                 expected: simpleSample
72         } );
74         byteLimitTest( {
75                 description: 'Plain text input. Calling byteLimit with no parameters and no maxlength attribute (bug 36310)',
76                 $input: $( '<input type="text"/>' )
77                         .byteLimit(),
78                 sample: simpleSample,
79                 expected: simpleSample
80         } );
82         byteLimitTest( {
83                 description: 'Limit using the maxlength attribute',
84                 $input: $( '<input type="text"/>' )
85                         .attr( 'maxlength', '10' )
86                         .byteLimit(),
87                 sample: simpleSample,
88                 expected: '1234567890'
89         } );
91         byteLimitTest( {
92                 description: 'Limit using a custom value',
93                 $input: $( '<input type="text"/>' )
94                         .byteLimit( 10 ),
95                 sample: simpleSample,
96                 expected: '1234567890'
97         } );
99         byteLimitTest( {
100                 description: 'Limit using a custom value, overriding maxlength attribute',
101                 $input: $( '<input type="text"/>' )
102                         .attr( 'maxlength', '10' )
103                         .byteLimit( 15 ),
104                 sample: simpleSample,
105                 expected: '123456789012345'
106         } );
108         byteLimitTest( {
109                 description: 'Limit using a custom value (multibyte)',
110                 $input: $( '<input type="text"/>' )
111                         .byteLimit( 14 ),
112                 sample: mbSample,
113                 expected: '1234567890' + U_20AC + '1'
114         } );
116         byteLimitTest( {
117                 description: 'Limit using a custom value (multibyte) overlapping a byte',
118                 $input: $( '<input type="text"/>' )
119                         .byteLimit( 12 ),
120                 sample: mbSample,
121                 expected: '1234567890' + '12'
122         } );
124         byteLimitTest( {
125                 description: 'Pass the limit and a callback as input filter',
126                 $input: $( '<input type="text"/>' )
127                         .byteLimit( 6, function ( val ) {
128                                 // Invalid title
129                                 if ( val === '' ) {
130                                         return '';
131                                 }
133                                 // Return without namespace prefix
134                                 return new mw.Title( String( val ) ).getMain();
135                         } ),
136                 sample: 'User:Sample',
137                 expected: 'User:Sample'
138         } );
140         byteLimitTest( {
141                 description: 'Limit using the maxlength attribute and pass a callback as input filter',
142                 $input: $( '<input type="text"/>' )
143                         .attr( 'maxlength', '6' )
144                         .byteLimit( function ( val ) {
145                                 // Invalid title
146                                 if ( val === '' ) {
147                                         return '';
148                                 }
150                                 // Return without namespace prefix
151                                 return new mw.Title( String( val ) ).getMain();
152                         } ),
153                 sample: 'User:Sample',
154                 expected: 'User:Sample'
155         } );
157         byteLimitTest( {
158                 description: 'Pass the limit and a callback as input filter',
159                 $input: $( '<input type="text"/>' )
160                         .byteLimit( 6, function ( val ) {
161                                 // Invalid title
162                                 if ( val === '' ) {
163                                         return '';
164                                 }
166                                 // Return without namespace prefix
167                                 return new mw.Title( String( val ) ).getMain();
168                         } ),
169                 sample: 'User:Example',
170                 // The callback alters the value to be used to calculeate
171                 // the length. The altered value is "Exampl" which has
172                 // a length of 6, the "e" would exceed the limit.
173                 expected: 'User:Exampl'
174         } );
176         byteLimitTest( {
177                 description: 'Input filter that increases the length',
178                 $input: $( '<input type="text"/>' )
179                 .byteLimit( 10, function ( text ) {
180                         return 'prefix' + text;
181                 } ),
182                 sample: simpleSample,
183                 // Prefix adds 6 characters, limit is reached after 4
184                 expected: '1234'
185         } );
187         // Regression tests for bug 41450
188         byteLimitTest( {
189                 description: 'Input filter of which the base exceeds the limit',
190                 $input: $( '<input type="text"/>' )
191                 .byteLimit( 3, function ( text ) {
192                         return 'prefix' + text;
193                 } ),
194                 sample: simpleSample,
195                 hasLimit: true,
196                 limit: 6, // 'prefix' length
197                 expected: ''
198         } );
200         QUnit.test( 'Confirm properties and attributes set', 4, function ( assert ) {
201                 var $el, $elA, $elB;
203                 $el = $( '<input type="text"/>' )
204                         .attr( 'maxlength', '7' )
205                         .appendTo( '#qunit-fixture' )
206                         .byteLimit();
208                 assert.strictEqual( $el.attr( 'maxlength' ), '7', 'maxlength attribute unchanged for simple limit' );
210                 $el = $( '<input type="text"/>' )
211                         .attr( 'maxlength', '7' )
212                         .appendTo( '#qunit-fixture' )
213                         .byteLimit( 12 );
215                 assert.strictEqual( $el.attr( 'maxlength' ), '12', 'maxlength attribute updated for custom limit' );
217                 $el = $( '<input type="text"/>' )
218                         .attr( 'maxlength', '7' )
219                         .appendTo( '#qunit-fixture' )
220                         .byteLimit( 12, function ( val ) {
221                                 return val;
222                         } );
224                 assert.strictEqual( $el.attr( 'maxlength' ), undefined, 'maxlength attribute removed for limit with callback' );
226                 $elA = $( '<input type="text"/>' )
227                         .addClass( 'mw-test-byteLimit-foo' )
228                         .attr( 'maxlength', '7' )
229                         .appendTo( '#qunit-fixture' );
231                 $elB = $( '<input type="text"/>' )
232                         .addClass( 'mw-test-byteLimit-foo' )
233                         .attr( 'maxlength', '12' )
234                         .appendTo( '#qunit-fixture' );
236                 $el = $( '.mw-test-byteLimit-foo' );
238                 assert.strictEqual( $el.length, 2, 'Verify that there are no other elements clashing with this test suite' );
240                 $el.byteLimit();
241         } );
243         QUnit.test( 'Trim from insertion when limit exceeded', 2, function ( assert ) {
244                 var $el;
246                 // Use a new <input /> because the bug only occurs on the first time
247                 // the limit it reached (bug 40850)
248                 $el = $( '<input type="text"/>' )
249                         .appendTo( '#qunit-fixture' )
250                         .byteLimit( 3 )
251                         .val( 'abc' ).trigger( 'change' )
252                         .val( 'zabc' ).trigger( 'change' );
254                 assert.strictEqual( $el.val(), 'abc', 'Trim from the insertion point (at 0), not the end' );
256                 $el = $( '<input type="text"/>' )
257                         .appendTo( '#qunit-fixture' )
258                         .byteLimit( 3 )
259                         .val( 'abc' ).trigger( 'change' )
260                         .val( 'azbc' ).trigger( 'change' );
262                 assert.strictEqual( $el.val(), 'abc', 'Trim from the insertion point (at 1), not the end' );
263         } );
264 }( jQuery, mediaWiki ) );