|
4 | 4 | * Available under MIT license <http://mths.be/mit> |
5 | 5 | */ |
6 | 6 |
|
7 | | -;(function(window) { |
| 7 | +;(function(root) { |
8 | 8 |
|
9 | 9 | /** |
10 | | - * The `Punycode` object. |
11 | | - * @name Punycode |
| 10 | + * The `punycode` object. |
| 11 | + * @name punycode |
12 | 12 | * @type Object |
13 | 13 | */ |
14 | | - var Punycode, |
| 14 | + var punycode, |
15 | 15 |
|
16 | | - /** Detect free variables `define`, `exports`, and `require` */ |
| 16 | + /** Detect free variables `define`, `exports`, `module` and `require` */ |
17 | 17 | freeDefine = typeof define == 'function' && typeof define.amd == 'object' && |
18 | 18 | define.amd && define, |
19 | | - freeExports = typeof exports == 'object' && exports && |
20 | | - (typeof global == 'object' && global && global == global.global && |
21 | | - (window = global), exports), |
| 19 | + freeExports = typeof exports == 'object' && exports, |
| 20 | + freeModule = typeof module == 'object' && module, |
22 | 21 | freeRequire = typeof require == 'function' && require, |
23 | 22 |
|
24 | 23 | /** Highest positive signed 32-bit float value */ |
|
35 | 34 | delimiter = '-', // '\x2D' |
36 | 35 |
|
37 | 36 | /** Regular expressions */ |
38 | | - regexASCII = /[^\x20-\x7e]/, |
| 37 | + regexNonASCII = /[^ -~]/, // matches unprintable ASCII chars + non-ASCII chars |
39 | 38 | regexPunycode = /^xn--/, |
40 | 39 |
|
41 | 40 | /** Error messages */ |
|
50 | 49 | /** Convenience shortcuts */ |
51 | 50 | baseMinusTMin = base - tMin, |
52 | 51 | floor = Math.floor, |
53 | | - stringFromCharCode = String.fromCharCode; |
| 52 | + stringFromCharCode = String.fromCharCode, |
| 53 | + |
| 54 | + /** Temporary variable */ |
| 55 | + key; |
54 | 56 |
|
55 | 57 | /*--------------------------------------------------------------------------*/ |
56 | 58 |
|
|
97 | 99 | /** |
98 | 100 | * Creates an array containing the decimal code points of each character in |
99 | 101 | * the string. |
100 | | - * @see `Punycode.utf16.encode` |
101 | | - * @memberOf Punycode.utf16 |
| 102 | + * @see `punycode.utf16.encode` |
| 103 | + * @see <http://tools.ietf.org/html/rfc2781> |
| 104 | + * @memberOf punycode.utf16 |
102 | 105 | * @name decode |
103 | 106 | * @param {String} string The Unicode input string. |
104 | 107 | * @returns {Array} The new array. |
|
125 | 128 |
|
126 | 129 | /** |
127 | 130 | * Creates a string based on an array of decimal code points. |
128 | | - * @see `Punycode.utf16.decode` |
129 | | - * @memberOf Punycode.utf16 |
| 131 | + * @see `punycode.utf16.decode` |
| 132 | + * @see <http://tools.ietf.org/html/rfc2781> |
| 133 | + * @memberOf punycode.utf16 |
130 | 134 | * @name encode |
131 | 135 | * @param {Array} codePoints The array of decimal code points. |
132 | 136 | * @returns {String} The new string. |
|
215 | 219 | /** |
216 | 220 | * Converts a Punycode string of ASCII code points to a string of Unicode |
217 | 221 | * code points. |
218 | | - * @memberOf Punycode |
| 222 | + * @memberOf punycode |
219 | 223 | * @param {String} input The Punycode string of ASCII code points. |
220 | | - * @param {Boolean} preserveCase A boolean value indicating if character |
221 | | - * case should be preserved or not. |
222 | 224 | * @returns {String} The resulting string of Unicode code points. |
223 | 225 | */ |
224 | | - function decode(input, preserveCase) { |
| 226 | + function decode(input) { |
225 | 227 | // Don't use UTF-16 |
226 | 228 | var output = [], |
227 | | - /** |
228 | | - * The `caseFlags` array needs room for at least `output.length` values, |
229 | | - * or it can be `undefined` if the case information is not needed. A |
230 | | - * truthy value suggests that the corresponding Unicode character be |
231 | | - * forced to uppercase (if possible), while falsy values suggest that it |
232 | | - * be forced to lowercase (if possible). ASCII code points are output |
233 | | - * already in the proper case, but their flags will be set appropriately |
234 | | - * so that applying the flags would be harmless. |
235 | | - */ |
236 | | - caseFlags = [], |
237 | 229 | inputLength = input.length, |
238 | 230 | out, |
239 | 231 | i = 0, |
|
261 | 253 | } |
262 | 254 |
|
263 | 255 | for (j = 0; j < basic; ++j) { |
264 | | - if (preserveCase) { |
265 | | - caseFlags[output.length] = input.charCodeAt(j) - 65 < 26; |
266 | | - } |
267 | 256 | // if it's not a basic code point |
268 | 257 | if (input.charCodeAt(j) >= 0x80) { |
269 | 258 | error('not-basic'); |
270 | 259 | } |
271 | 260 | output.push(input.charCodeAt(j)); |
272 | 261 | } |
273 | 262 |
|
274 | | - // Main decoding loop: start just after the last delimiter if any basic |
275 | | - // code points were copied; start at the beginning otherwise. |
| 263 | + // Main decoding loop: start just after the last delimiter if any basic code |
| 264 | + // points were copied; start at the beginning otherwise. |
276 | 265 |
|
277 | 266 | for (index = basic > 0 ? basic + 1 : 0; index < inputLength; /* no final expression */) { |
278 | 267 |
|
|
322 | 311 | i %= out; |
323 | 312 |
|
324 | 313 | // Insert `n` at position `i` of the output |
325 | | - // The case of the last character determines `uppercase` flag |
326 | | - if (preserveCase) { |
327 | | - caseFlags.splice(i, 0, input.charCodeAt(index - 1) - 65 < 26); |
328 | | - } |
329 | | - |
330 | | - output.splice(i, 0, n); |
331 | | - i++; |
| 314 | + output.splice(i++, 0, n); |
332 | 315 |
|
333 | 316 | } |
334 | 317 |
|
335 | | - if (preserveCase) { |
336 | | - for (i = 0, length = output.length; i < length; i++) { |
337 | | - if (caseFlags[i]) { |
338 | | - output[i] = (stringFromCharCode(output[i]).toUpperCase()).charCodeAt(0); |
339 | | - } |
340 | | - } |
341 | | - } |
342 | 318 | return utf16encode(output); |
343 | 319 | } |
344 | 320 |
|
345 | 321 | /** |
346 | 322 | * Converts a string of Unicode code points to a Punycode string of ASCII |
347 | 323 | * code points. |
348 | | - * @memberOf Punycode |
| 324 | + * @memberOf punycode |
349 | 325 | * @param {String} input The string of Unicode code points. |
350 | | - * @param {Boolean} preserveCase A boolean value indicating if character |
351 | | - * case should be preserved or not. |
352 | 326 | * @returns {String} The resulting Punycode string of ASCII code points. |
353 | 327 | */ |
354 | | - function encode(input, preserveCase) { |
| 328 | + function encode(input) { |
355 | 329 | var n, |
356 | 330 | delta, |
357 | 331 | handledCPCount, |
|
363 | 337 | k, |
364 | 338 | t, |
365 | 339 | currentValue, |
366 | | - /** |
367 | | - * The `caseFlags` array will hold `inputLength` boolean values, where |
368 | | - * `true` suggests that the corresponding Unicode character be forced |
369 | | - * to uppercase after being decoded (if possible), and `false` |
370 | | - * suggests that it be forced to lowercase (if possible). ASCII code |
371 | | - * points are encoded literally, except that ASCII letters are forced |
372 | | - * to uppercase or lowercase according to the corresponding uppercase |
373 | | - * flags. If `caseFlags` remains `undefined` then ASCII letters are |
374 | | - * left as they are, and other code points are treated as if their |
375 | | - * uppercase flags were `true`. |
376 | | - */ |
377 | | - caseFlags, |
378 | 340 | output = [], |
379 | 341 | /** `inputLength` will hold the number of code points in `input`. */ |
380 | 342 | inputLength, |
|
383 | 345 | baseMinusT, |
384 | 346 | qMinusT; |
385 | 347 |
|
386 | | - if (preserveCase) { |
387 | | - // Preserve case, step 1 of 2: get a list of the unaltered string |
388 | | - caseFlags = utf16decode(input); |
389 | | - } |
390 | | - |
391 | 348 | // Convert the input in UTF-16 to Unicode |
392 | 349 | input = utf16decode(input); |
393 | 350 |
|
394 | 351 | // Cache the length |
395 | 352 | inputLength = input.length; |
396 | 353 |
|
397 | | - if (preserveCase) { |
398 | | - // Preserve case, step 2 of 2: modify the list to true/false |
399 | | - for (j = 0; j < inputLength; j++) { |
400 | | - caseFlags[j] = input[j] != caseFlags[j]; |
401 | | - } |
402 | | - } |
403 | | - |
404 | 354 | // Initialize the state |
405 | 355 | n = initialN; |
406 | 356 | delta = 0; |
|
410 | 360 | for (j = 0; j < inputLength; ++j) { |
411 | 361 | currentValue = input[j]; |
412 | 362 | if (currentValue < 0x80) { |
413 | | - output.push( |
414 | | - stringFromCharCode( |
415 | | - caseFlags ? encodeBasic(currentValue, caseFlags[j]) : currentValue |
416 | | - ) |
417 | | - ); |
| 363 | + output.push(stringFromCharCode(currentValue)); |
418 | 364 | } |
419 | 365 | } |
420 | 366 |
|
|
433 | 379 |
|
434 | 380 | // All non-basic code points < n have been handled already. Find the next |
435 | 381 | // larger one: |
436 | | - |
437 | 382 | for (m = maxInt, j = 0; j < inputLength; ++j) { |
438 | 383 | currentValue = input[j]; |
439 | 384 | if (currentValue >= n && currentValue < m) { |
|
473 | 418 | q = floor(qMinusT / baseMinusT); |
474 | 419 | } |
475 | 420 |
|
476 | | - output.push(stringFromCharCode(digitToBasic(q, preserveCase && caseFlags[j] ? 1 : 0))); |
| 421 | + output.push(stringFromCharCode(digitToBasic(q, 0))); |
477 | 422 | bias = adapt(delta, handledCPCountPlusOne, handledCPCount == basicLength); |
478 | 423 | delta = 0; |
479 | 424 | ++handledCPCount; |
|
492 | 437 | * Punycoded parts of the domain name will be converted, i.e. it doesn't |
493 | 438 | * matter if you call it on a string that has already been converted to |
494 | 439 | * Unicode. |
495 | | - * @memberOf Punycode |
| 440 | + * @memberOf punycode |
496 | 441 | * @param {String} domain The Punycode domain name to convert to Unicode. |
497 | 442 | * @returns {String} The Unicode representation of the given Punycode |
498 | 443 | * string. |
|
509 | 454 | * Converts a Unicode string representing a domain name to Punycode. Only the |
510 | 455 | * non-ASCII parts of the domain name will be converted, i.e. it doesn't |
511 | 456 | * matter if you call it with a domain that's already in ASCII. |
512 | | - * @memberOf Punycode |
| 457 | + * @memberOf punycode |
513 | 458 | * @param {String} domain The domain name to convert, as a Unicode string. |
514 | 459 | * @returns {String} The Punycode representation of the given domain name. |
515 | 460 | */ |
516 | 461 | function toASCII(domain) { |
517 | 462 | return mapDomain(domain, function(string) { |
518 | | - return regexASCII.test(string) |
| 463 | + return regexNonASCII.test(string) |
519 | 464 | ? 'xn--' + encode(string) |
520 | 465 | : string; |
521 | 466 | }); |
|
524 | 469 | /*--------------------------------------------------------------------------*/ |
525 | 470 |
|
526 | 471 | /** Define the public API */ |
527 | | - Punycode = { |
528 | | - 'version': '0.1.1', |
| 472 | + punycode = { |
| 473 | + /** |
| 474 | + * A string representing the current Punycode.js version number. |
| 475 | + * @memberOf punycode |
| 476 | + * @type String |
| 477 | + */ |
| 478 | + 'version': '0.2.1', |
529 | 479 | /** |
530 | 480 | * An object of methods to convert from JavaScript's internal character |
531 | 481 | * representation to Unicode and back. |
532 | | - * @memberOf Punycode |
| 482 | + * @memberOf punycode |
533 | 483 | * @type Object |
534 | 484 | */ |
535 | 485 | 'utf16': { |
|
542 | 492 | 'toUnicode': toUnicode |
543 | 493 | }; |
544 | 494 |
|
545 | | - /** Expose Punycode */ |
| 495 | + /** Expose `punycode` */ |
546 | 496 | if (freeExports) { |
547 | | - if (typeof module == 'object' && module && module.exports == freeExports) { |
548 | | - // in Node.js |
549 | | - module.exports = Punycode; |
| 497 | + if (freeModule && freeModule.exports == freeExports) { |
| 498 | + // in Node.js or Ringo 0.8+ |
| 499 | + freeModule.exports = punycode; |
550 | 500 | } else { |
551 | | - // in Narwhal or Ringo |
552 | | - freeExports.Punycode = Punycode; |
| 501 | + // in Narwhal or Ringo 0.7- |
| 502 | + for (key in punycode) { |
| 503 | + punycode.hasOwnProperty(key) && (freeExports[key] = punycode[key]); |
| 504 | + } |
553 | 505 | } |
554 | 506 | } else if (freeDefine) { |
555 | 507 | // via curl.js or RequireJS |
556 | | - freeDefine(function() { |
557 | | - return Punycode; |
558 | | - }); |
| 508 | + define('punycode', punycode); |
559 | 509 | } else { |
560 | 510 | // in a browser or Rhino |
561 | | - window.Punycode = Punycode; |
| 511 | + root.punycode = punycode; |
562 | 512 | } |
563 | 513 |
|
564 | 514 | }(this)); |
0 commit comments