validate.js 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274
  1. "use strict";
  2. /**
  3. * Copyright (C) 2016-2019 Michael Kourlas
  4. *
  5. * Licensed under the Apache License, Version 2.0 (the "License");
  6. * you may not use this file except in compliance with the License.
  7. * You may obtain a copy of the License at
  8. *
  9. * http://www.apache.org/licenses/LICENSE-2.0
  10. *
  11. * Unless required by applicable law or agreed to in writing, software
  12. * distributed under the License is distributed on an "AS IS" BASIS,
  13. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  14. * See the License for the specific language governing permissions and
  15. * limitations under the License.
  16. */
  17. Object.defineProperty(exports, "__esModule", { value: true });
  18. exports.isUndefined = exports.fixName = exports.validateName = exports.validateSingleChar = exports.fixChar = exports.validateChar = void 0;
  19. /**
  20. * Returns true if the specified string only contains characters permitted by
  21. * the XML specification.
  22. */
  23. function validateChar(str) {
  24. for (var i = 0; i < str.length; i++) {
  25. var firstChar = str.charCodeAt(i);
  26. if (firstChar === 0x9 || firstChar === 0xA || firstChar === 0xD
  27. || (firstChar >= 0x20 && firstChar <= 0xD7FF)
  28. || (firstChar >= 0xE000 && firstChar <= 0xFFFD)) {
  29. continue;
  30. }
  31. if (i + 1 === str.length) {
  32. return false;
  33. }
  34. // UTF-16 surrogate characters
  35. var secondChar = str.charCodeAt(i + 1);
  36. if ((firstChar >= 0xD800 && firstChar <= 0xDBFF)
  37. && (secondChar >= 0xDC00 && secondChar <= 0xDFFF)) {
  38. i++;
  39. continue;
  40. }
  41. return false;
  42. }
  43. return true;
  44. }
  45. exports.validateChar = validateChar;
  46. /**
  47. * Returns a version of the specified string that only contains characters
  48. * permitted by the XML specification, with invalid characters replaced
  49. * by the replacement character U+FFFD.
  50. */
  51. function fixChar(str) {
  52. var newStr = "";
  53. for (var i = 0; i < str.length; i++) {
  54. var firstChar = str.charCodeAt(i);
  55. if (firstChar === 0x9 || firstChar === 0xA || firstChar === 0xD
  56. || (firstChar >= 0x20 && firstChar <= 0xD7FF)
  57. || (firstChar >= 0xE000 && firstChar <= 0xFFFD)) {
  58. newStr += str[i];
  59. continue;
  60. }
  61. if (i + 1 === str.length) {
  62. newStr += "\uFFFD";
  63. return newStr;
  64. }
  65. // UTF-16 surrogate characters
  66. var secondChar = str.charCodeAt(i + 1);
  67. if ((firstChar >= 0xD800 && firstChar <= 0xDBFF)
  68. && (secondChar >= 0xDC00 && secondChar <= 0xDFFF)) {
  69. newStr += str[i] + str[i + 1];
  70. i++;
  71. continue;
  72. }
  73. newStr += "\uFFFD";
  74. }
  75. return newStr;
  76. }
  77. exports.fixChar = fixChar;
  78. /**
  79. * Returns true if the specified string only contains a single character, and
  80. * that this character is permitted by the XML specification.
  81. */
  82. function validateSingleChar(str) {
  83. if (str.length === 0) {
  84. return false;
  85. }
  86. var firstChar = str.charCodeAt(0);
  87. if (str.length === 1) {
  88. return (firstChar === 0x9 || firstChar === 0xA || firstChar === 0xD
  89. || (firstChar >= 0x20 && firstChar <= 0xD7FF)
  90. || (firstChar >= 0xE000 && firstChar <= 0xFFFD));
  91. }
  92. if (str.length !== 2) {
  93. return false;
  94. }
  95. // UTF-16 surrogate characters
  96. var secondChar = str.charCodeAt(1);
  97. return ((firstChar >= 0xD800 && firstChar <= 0xDBFF)
  98. && (secondChar >= 0xDC00 && secondChar <= 0xDFFF));
  99. }
  100. exports.validateSingleChar = validateSingleChar;
  101. /**
  102. * Returns true if the specified string only contains characters permitted by
  103. * the XML specification for names.
  104. */
  105. function validateName(str) {
  106. if (str.length === 0) {
  107. return false;
  108. }
  109. var initialFirstChar = str.charCodeAt(0);
  110. var initialFirstCharMatch = (initialFirstChar === 0x3A
  111. || initialFirstChar === 0x5F
  112. || (initialFirstChar >= 0x41 && initialFirstChar <= 0x5A)
  113. || (initialFirstChar >= 0x61 && initialFirstChar <= 0x7A)
  114. || (initialFirstChar >= 0xC0 && initialFirstChar <= 0xD6)
  115. || (initialFirstChar >= 0xD8 && initialFirstChar <= 0xF6)
  116. || (initialFirstChar >= 0XF8 && initialFirstChar <= 0X2FF)
  117. || (initialFirstChar >= 0x370 && initialFirstChar <= 0x37D)
  118. || (initialFirstChar >= 0x37F && initialFirstChar <= 0X1FFF)
  119. || (initialFirstChar >= 0x200C && initialFirstChar <= 0x200D)
  120. || (initialFirstChar >= 0x2070 && initialFirstChar <= 0x218F)
  121. || (initialFirstChar >= 0x2C00 && initialFirstChar <= 0x2FEF)
  122. || (initialFirstChar >= 0x3001 && initialFirstChar <= 0xD7FF)
  123. || (initialFirstChar >= 0xF900 && initialFirstChar <= 0xFDCF)
  124. || (initialFirstChar >= 0xFDF0 && initialFirstChar <= 0xFFFD));
  125. if (str.length === 1) {
  126. return initialFirstCharMatch;
  127. }
  128. // UTF-16 surrogate characters
  129. var initialSecondChar = str.charCodeAt(1);
  130. var initialSecondCharMatch = ((initialFirstChar >= 0xD800 && initialFirstChar <= 0xDB7F)
  131. && (initialSecondChar >= 0xDC00 && initialSecondChar <= 0xDFFF));
  132. if (!initialFirstCharMatch && !initialSecondCharMatch) {
  133. return false;
  134. }
  135. var start = initialSecondCharMatch ? 2 : 1;
  136. for (var i = start; i < str.length; i++) {
  137. var firstChar = str.charCodeAt(i);
  138. if (firstChar === 0x3A
  139. || firstChar === 0x5F
  140. || firstChar === 0x2D
  141. || firstChar === 0x2E
  142. || firstChar === 0xB7
  143. || (firstChar >= 0x30 && firstChar <= 0x39)
  144. || (firstChar >= 0x41 && firstChar <= 0x5A)
  145. || (firstChar >= 0x61 && firstChar <= 0x7A)
  146. || (firstChar >= 0xC0 && firstChar <= 0xD6)
  147. || (firstChar >= 0xD8 && firstChar <= 0xF6)
  148. || (firstChar >= 0XF8 && firstChar <= 0X2FF)
  149. || (firstChar >= 0x300 && firstChar <= 0x36F)
  150. || (firstChar >= 0x370 && firstChar <= 0x37D)
  151. || (firstChar >= 0x37F && firstChar <= 0X1FFF)
  152. || (firstChar >= 0x200C && firstChar <= 0x200D)
  153. || (firstChar >= 0x203F && firstChar <= 0x2040)
  154. || (firstChar >= 0x2070 && firstChar <= 0x218F)
  155. || (firstChar >= 0x2C00 && firstChar <= 0x2FEF)
  156. || (firstChar >= 0x3001 && firstChar <= 0xD7FF)
  157. || (firstChar >= 0xF900 && firstChar <= 0xFDCF)
  158. || (firstChar >= 0xFDF0 && firstChar <= 0xFFFD)) {
  159. continue;
  160. }
  161. if (i + 1 === str.length) {
  162. return false;
  163. }
  164. // UTF-16 surrogate characters
  165. var secondChar = str.charCodeAt(i + 1);
  166. if ((firstChar >= 0xD800 && firstChar <= 0xDB7F)
  167. && (secondChar >= 0xDC00 && secondChar <= 0xDFFF)) {
  168. i++;
  169. continue;
  170. }
  171. return false;
  172. }
  173. return true;
  174. }
  175. exports.validateName = validateName;
  176. /**
  177. * Returns a version of the specified string that only contains characters
  178. * permitted by the XML specification for names, with invalid characters
  179. * replaced by the replacement character U+FFFD.
  180. */
  181. function fixName(str) {
  182. var newStr = "";
  183. if (str.length === 0) {
  184. return newStr;
  185. }
  186. var initialFirstChar = str.charCodeAt(0);
  187. var initialFirstCharMatch = (initialFirstChar === 0x3A
  188. || initialFirstChar === 0x5F
  189. || (initialFirstChar >= 0x41 && initialFirstChar <= 0x5A)
  190. || (initialFirstChar >= 0x61 && initialFirstChar <= 0x7A)
  191. || (initialFirstChar >= 0xC0 && initialFirstChar <= 0xD6)
  192. || (initialFirstChar >= 0xD8 && initialFirstChar <= 0xF6)
  193. || (initialFirstChar >= 0XF8 && initialFirstChar <= 0X2FF)
  194. || (initialFirstChar >= 0x370 && initialFirstChar <= 0x37D)
  195. || (initialFirstChar >= 0x37F && initialFirstChar <= 0X1FFF)
  196. || (initialFirstChar >= 0x200C && initialFirstChar <= 0x200D)
  197. || (initialFirstChar >= 0x2070 && initialFirstChar <= 0x218F)
  198. || (initialFirstChar >= 0x2C00 && initialFirstChar <= 0x2FEF)
  199. || (initialFirstChar >= 0x3001 && initialFirstChar <= 0xD7FF)
  200. || (initialFirstChar >= 0xF900 && initialFirstChar <= 0xFDCF)
  201. || (initialFirstChar >= 0xFDF0 && initialFirstChar <= 0xFFFD));
  202. if (str.length === 1) {
  203. if (initialFirstCharMatch) {
  204. newStr = str[0];
  205. }
  206. else {
  207. newStr = "\uFFFD";
  208. }
  209. return newStr;
  210. }
  211. // UTF-16 surrogate characters
  212. var initialSecondChar = str.charCodeAt(1);
  213. var initialSecondCharMatch = ((initialFirstChar >= 0xD800 && initialFirstChar <= 0xDB7F)
  214. && (initialSecondChar >= 0xDC00 && initialSecondChar <= 0xDFFF));
  215. if (initialSecondCharMatch) {
  216. newStr = str[0] + str[1];
  217. }
  218. else if (initialFirstCharMatch) {
  219. newStr = str[0];
  220. }
  221. else {
  222. newStr = "\uFFFD";
  223. }
  224. var start = initialSecondCharMatch ? 2 : 1;
  225. for (var i = start; i < str.length; i++) {
  226. var firstChar = str.charCodeAt(i);
  227. if (firstChar === 0x3A
  228. || firstChar === 0x5F
  229. || firstChar === 0x2D
  230. || firstChar === 0x2E
  231. || firstChar === 0xB7
  232. || (firstChar >= 0x30 && firstChar <= 0x39)
  233. || (firstChar >= 0x41 && firstChar <= 0x5A)
  234. || (firstChar >= 0x61 && firstChar <= 0x7A)
  235. || (firstChar >= 0xC0 && firstChar <= 0xD6)
  236. || (firstChar >= 0xD8 && firstChar <= 0xF6)
  237. || (firstChar >= 0XF8 && firstChar <= 0X2FF)
  238. || (firstChar >= 0x300 && firstChar <= 0x36F)
  239. || (firstChar >= 0x370 && firstChar <= 0x37D)
  240. || (firstChar >= 0x37F && firstChar <= 0X1FFF)
  241. || (firstChar >= 0x200C && firstChar <= 0x200D)
  242. || (firstChar >= 0x203F && firstChar <= 0x2040)
  243. || (firstChar >= 0x2070 && firstChar <= 0x218F)
  244. || (firstChar >= 0x2C00 && firstChar <= 0x2FEF)
  245. || (firstChar >= 0x3001 && firstChar <= 0xD7FF)
  246. || (firstChar >= 0xF900 && firstChar <= 0xFDCF)
  247. || (firstChar >= 0xFDF0 && firstChar <= 0xFFFD)) {
  248. newStr += str[i];
  249. continue;
  250. }
  251. if (i + 1 === str.length) {
  252. newStr += "\uFFFD";
  253. return newStr;
  254. }
  255. // UTF-16 surrogate characters
  256. var secondChar = str.charCodeAt(i + 1);
  257. if ((firstChar >= 0xD800 && firstChar <= 0xDB7F)
  258. && (secondChar >= 0xDC00 && secondChar <= 0xDFFF)) {
  259. newStr += str[i] + str[i + 1];
  260. i++;
  261. continue;
  262. }
  263. newStr += "\uFFFD";
  264. }
  265. return newStr;
  266. }
  267. exports.fixName = fixName;
  268. /**
  269. * Returns true if the specified value is undefined.
  270. */
  271. function isUndefined(val) {
  272. return Object.prototype.toString.call(val) === "[object Undefined]";
  273. }
  274. exports.isUndefined = isUndefined;