Total Complexity | 91 |
Complexity/F | 2.68 |
Lines of Code | 342 |
Function Count | 34 |
Duplicated Lines | 0 |
Ratio | 0 % |
Changes | 0 |
Complex classes like src/ub.strings.asserts.js often do a lot of different things. To break such a class down, we need to identify a cohesive component within that class. A common approach to find such a component is to look for fields/methods that share the same prefixes, or suffixes.
Once you have determined the fields that belong together, you can apply the Extract Class refactoring. If the component makes sense as a sub-class, Extract Subclass is also a candidate, and is often faster.
1 | /** global: UB */ |
||
3 | var stringFuncs = { |
||
4 | |||
5 | |||
6 | // checks |
||
7 | isAllCaps: function(){ |
||
8 | var str = this; |
||
9 | return (str.toUpperCase() == str); |
||
10 | }, |
||
11 | isUppercase: function(){ |
||
12 | var str = this; |
||
13 | return (str.toUpperCase() == str); |
||
14 | }, |
||
15 | isLowercase: function(){ |
||
16 | var str = this; |
||
17 | return (str.toLowerCase() == str); |
||
18 | }, |
||
19 | isAcronym: function(){ |
||
20 | var str = this; |
||
21 | if (str.length >= 2) { |
||
22 | var c1 = str.charAt(0); |
||
23 | var c2 = str.charAt(1); |
||
24 | return (c1 == c1.toUpperCase() && c2 == c2.toUpperCase()); |
||
25 | } |
||
26 | return false; |
||
27 | }, |
||
28 | isComplexNumber: function(){ |
||
29 | var text = this; |
||
30 | return text.contains("0x") || text.contains("0X") || text.contains("+e") || text.contains("+E") || text.contains("-e") || text.contains("-E"); |
||
31 | }, |
||
32 | |||
33 | isBlank: function(trimAndCheck = true){ |
||
34 | var str = this; |
||
35 | if (str == null || str == "") { |
||
1 ignored issue
–
show
|
|||
36 | return true; |
||
37 | } |
||
38 | if (trimAndCheck) { |
||
39 | return str.trim() == ""; |
||
40 | } |
||
41 | return false; |
||
42 | }, |
||
43 | isWhitespace: function(newlines){ |
||
44 | var char = this; |
||
45 | if (newlines) { |
||
46 | return char == ' ' || char == '\r' || char == '\n' || char == '\t'; |
||
47 | } else { |
||
48 | return char == ' ' || char == '\t'; |
||
49 | } |
||
50 | }, |
||
51 | isNumber: function(){ |
||
52 | var char = this; |
||
53 | var code = char.charCodeAt(0); |
||
54 | return (code >= UB.charCodes._0 && code <= UB.charCodes._9); |
||
55 | }, |
||
56 | isAlphaNumeric: function(){ |
||
57 | var char = this; |
||
58 | var code = char.charCodeAt(0); |
||
59 | if (code >= 48 && code <= 57){ |
||
60 | return true; |
||
61 | } |
||
62 | if (code >= 65 && code <= 90){ |
||
63 | return true; |
||
64 | } |
||
65 | if (code >= 97 && code <= 122){ |
||
66 | return true; |
||
67 | } |
||
68 | return false; |
||
69 | }, |
||
70 | isAlphabet: function(){ |
||
71 | var char = this; |
||
72 | var code = char.charCodeAt(0); |
||
73 | if (code >= 65 && code <= 90){ |
||
74 | return true; |
||
75 | } |
||
76 | if (code >= 97 && code <= 122){ |
||
77 | return true; |
||
78 | } |
||
79 | return false; |
||
80 | }, |
||
81 | isLetter: function(){ |
||
82 | var char = this; |
||
83 | var code = char.charCodeAt(0); |
||
84 | if (code >= 65 && code <= 90){ |
||
85 | return true; |
||
86 | } |
||
87 | if (code >= 97 && code <= 122){ |
||
88 | return true; |
||
89 | } |
||
90 | return false; |
||
91 | }, |
||
92 | isQuote: function(){ |
||
93 | var char = this; |
||
94 | return (char == '"' || char == "'"); |
||
95 | }, |
||
96 | isMultiline: function(trimAndCheck = true){ |
||
97 | var str = this; |
||
98 | |||
99 | // if the trimmed string has newline chars then is multiline |
||
100 | if (trimAndCheck) { |
||
101 | str = str.replace(UB.regex.Trim, ""); |
||
102 | } |
||
103 | return (str.indexOf("\n") > -1 || str.indexOf("\r") > -1); |
||
104 | }, |
||
105 | isNewline: function(){ |
||
106 | var str = this; |
||
107 | |||
108 | // if the trimmed string has newline chars then is multiline |
||
109 | return str == "\n" || str == "\r"; |
||
110 | }, |
||
111 | isSingleline: function(){ |
||
112 | var str = this; |
||
113 | |||
114 | // if the trimmed string has no newline chars then is singleline |
||
115 | return !str.isMultiline(); |
||
116 | }, |
||
117 | isDigit: function(){ |
||
118 | var ch = this; |
||
119 | return ( ch >= '0' && ch <= '9' ); |
||
120 | }, |
||
121 | isHexDigit: function(){ |
||
122 | var ch = this; |
||
123 | return ( (ch >= '0' && ch <= '9') || ( ch >= 'A' && ch <= 'F' ) || ( ch >= 'a' && ch <= 'f' ) ); |
||
124 | }, |
||
125 | isAny: function(haystacks, doTrim = true, caseSensitive = true){ |
||
126 | var needle = this; |
||
127 | |||
128 | // return true if any haystack equals the needle |
||
129 | for (var s = 0, sl = haystacks.length;s<sl;s++){ |
||
130 | var str = haystacks[s]; |
||
131 | if (doTrim) { |
||
132 | str = str.trim(); |
||
133 | } |
||
134 | if (caseSensitive) { |
||
135 | if (needle == str) { |
||
136 | return true; |
||
137 | } |
||
138 | }else { |
||
139 | if (needle.isEqual(str, false)) { |
||
140 | return true; |
||
141 | } |
||
142 | } |
||
143 | } |
||
144 | return false; |
||
145 | }, |
||
146 | isPrefixNums: function(prefix){ |
||
147 | var prefixAndNums = this; |
||
148 | // INPUT: "Mesh100", "Mesh" |
||
149 | // OUTPUT: true |
||
150 | // INPUT: "Mesh", "Mesh" |
||
151 | // OUTPUT: false |
||
152 | // INPUT: "Bash100", "Mesh" |
||
153 | // OUTPUT: false |
||
154 | |||
155 | // prefix not found |
||
156 | if (prefixAndNums.indexOf(prefix) === -1) { |
||
157 | return false; |
||
158 | } |
||
159 | |||
160 | // split by prefix |
||
161 | var parts = prefixAndNums.splitAfter(prefix); |
||
162 | |||
163 | // check if prefix matches |
||
164 | // check if 2nd part is NUMERIC |
||
165 | return (parts[0] == prefix && parts[1].isNumeric()); |
||
166 | }, |
||
167 | isEmpty: function(){ |
||
168 | var text = this; |
||
169 | return text.trim().length === 0; |
||
170 | }, |
||
171 | isNumeric: function(withDot = true, withDash = true){ |
||
172 | var str = this; |
||
173 | |||
174 | // per char |
||
175 | for (var c = 0, cl = str.length;c<cl;c++){ |
||
176 | var code = str.charCodeAt(c); |
||
177 | |||
178 | // if char not number ... or dot and dot not ok ... or dash and dash not ok |
||
179 | if (!((code >= UB.charCodes._0 && code <= UB.charCodes._9) || (withDot && code == UB.charCodes.Dot) || (withDash && code == UB.charCodes.Minus && c === 0))) { |
||
180 | return false; |
||
181 | } |
||
182 | } |
||
183 | |||
184 | // if all chars OK then is numeric |
||
185 | return true; |
||
186 | }, |
||
187 | isInt: function(){ |
||
188 | var text = this; |
||
189 | return String(parseInt(text)) == text; |
||
190 | }, |
||
191 | isNumericUnknown: function(){ |
||
192 | var text = this; |
||
193 | // ????????? |
||
194 | return UB.regex.IsNumeric.test(text); |
||
195 | }, |
||
196 | isWindowsPath: function(){ |
||
197 | var str = this; |
||
198 | |||
199 | /// c:\temp |
||
200 | /// D:\My\Data\File.txt |
||
201 | |||
202 | if (str.charAt(1) == ":"){ |
||
203 | if (str.indexOf("\\") == 2) { |
||
204 | if(str.charAt(0).isAlphaNumeric()){ |
||
205 | return true; |
||
206 | } |
||
207 | } |
||
208 | } |
||
209 | return false; |
||
210 | }, |
||
211 | isWindowsPathAll: function(){ |
||
212 | var str = this; |
||
213 | |||
214 | /* |
||
215 | * WORKS FOR: |
||
216 | * |
||
217 | c:\temp |
||
218 | D:\directoryname\testing\ |
||
219 | \john-desktop\tempdir\ |
||
220 | */ |
||
221 | |||
222 | var c0 = str.charAt(0); |
||
223 | var c1 = str.charAt(1); |
||
224 | var c2 = str.charAt(2); |
||
225 | if(c0 != "\\" || c1 != "\\"){ |
||
226 | if(c0.match(new RegExp("^[a-zA-Z]"))){ |
||
227 | if (c1.match(new RegExp("^[:]"))){ |
||
228 | if (c2.match(new RegExp("^[\\/\\\\]"))) { |
||
229 | return true; |
||
230 | } |
||
231 | } |
||
232 | } |
||
233 | } |
||
234 | return false; |
||
235 | }, |
||
236 | isURL: function(){ |
||
237 | var str = this; |
||
238 | if (str.indexOf("/") > -1) { |
||
239 | return UB.regex.IsURL.test(str); |
||
240 | } |
||
241 | return false; |
||
242 | }, |
||
243 | isEmail: function(){ |
||
244 | var str = this; |
||
245 | |||
246 | // perform quick tests before regex |
||
247 | var lastAtPos = str.lastIndexOf('@'); |
||
248 | if (lastAtPos === -1) { |
||
249 | return false; |
||
250 | } |
||
251 | var lastDotPos = str.lastIndexOf('.'); |
||
252 | if (lastDotPos === -1) { |
||
253 | return false; |
||
254 | } |
||
255 | |||
256 | // Last "@" before last "." since "@" cannot be part of server name |
||
257 | // something (the email username) before the last @ |
||
258 | // no "@@" in the address. Even if "@" appears as the last character in email username, it has to be quoted so " would be between that "@" and the last "@" in the address |
||
259 | // at least 3 characters before the last dot, for example "[email protected]" |
||
260 | // enough characters after the last dot to form a two-character domain |
||
261 | if ((lastAtPos < lastDotPos && lastAtPos > 0 && str.indexOf('@@') === -1 && lastDotPos > 2 && (str.length - lastDotPos) > 2) == false) { |
||
1 ignored issue
–
show
|
|||
262 | return false; |
||
263 | } |
||
264 | |||
265 | // perform slow regex test |
||
266 | /// http://stackoverflow.com/a/46181 |
||
267 | return UB.regex.IsEmail.test(str); |
||
268 | }, |
||
269 | isIPAddress: function(){ |
||
270 | var str = this; |
||
271 | if (str.indexOf(".") > -1) { |
||
272 | return UB.regex.IsIP.test(str); |
||
273 | } |
||
274 | return false; |
||
275 | }, |
||
276 | isSymbol: function(){ |
||
277 | var char = this; |
||
278 | return UB.commonSymbols.indexOf(char) > -1; |
||
279 | }, |
||
280 | isVariable: function(spaceOk = false){ |
||
281 | var str = this; |
||
282 | |||
283 | // if first char is LETTER.. |
||
284 | if (str.length > 0 && str.charAt(0).isOfCharRange("letter")) { |
||
285 | |||
286 | // ..and other chars are LETTER, DIGIT or "_" |
||
287 | for (var c = 1, cl = str.length;c<cl;c++){ |
||
288 | var char = str.charAt(c); |
||
289 | if (char.isDigit() || char.isLetter() || char == "_" || (spaceOk && char == " ")) { |
||
290 | }else { |
||
291 | return false; |
||
292 | } |
||
293 | } |
||
294 | return true; |
||
295 | } |
||
296 | |||
297 | return false; |
||
298 | }, |
||
299 | |||
300 | // counting |
||
301 | countStartingChars: function(char){ |
||
302 | var str = this; |
||
303 | for (var c = 0, cl = str.length;c<cl;c++){ |
||
304 | if (str.charAt(c) != char) { |
||
305 | return c; |
||
306 | } |
||
307 | } |
||
308 | return cl; |
||
309 | }, |
||
310 | countEndingChars: function(char){ |
||
311 | var str = this; |
||
312 | var cl = str.length; |
||
313 | for (var c = cl;c >= 0;c--){ |
||
314 | if (str.charAt(c) != char) { |
||
315 | return cl - c; |
||
316 | } |
||
317 | } |
||
318 | return cl; |
||
319 | }, |
||
320 | countStartingUppercase: function(){ |
||
321 | var str = this; |
||
322 | for (var c = 0, cl = str.length;c<cl;c++){ |
||
323 | if (!str.charAt(c).isUppercase()) { |
||
324 | return c; |
||
325 | } |
||
326 | } |
||
327 | return 0; |
||
328 | }, |
||
329 | countStartingLowercase: function(){ |
||
330 | var str = this; |
||
331 | for (var c = 0, cl = str.length;c<cl;c++){ |
||
332 | if (!str.charAt(c).isLowercase()) { |
||
333 | return c; |
||
334 | } |
||
335 | } |
||
336 | return 0; |
||
337 | }, |
||
338 | |||
339 | |||
340 | none:null |
||
341 | }; |
||
342 | |||
343 | // register funcs |
||
344 | UB.registerFuncs(String.prototype, stringFuncs); |
||
345 |