Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP

Loading…

Improve `String.prototype.contains` polyfill #556

Merged
merged 1 commit into from

2 participants

@mathiasbynens

This patch replaces the old String.prototype.contains polyfill with http://mths.be/contains, while also adding the tests from that project.

@mathiasbynens mathiasbynens Improve `String.prototype.contains` polyfill
This patch replaces the old `String.prototype.contains` polyfill with http://mths.be/contains, while also adding the tests from that project.
18c5d55
@arv
Admin

LGTM

I didn't know that contains takes a position param. I guess it makes sense even though I don't think we should have added the position parameters to these in the first place.

@arv arv merged commit 18c5d55 into from
@mathiasbynens mathiasbynens referenced this pull request from a commit in mathiasbynens/String.prototype.includes
@mathiasbynens mathiasbynens README: Note that Traceur now uses this polyfill 28b879f
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Commits on Dec 17, 2013
  1. @mathiasbynens

    Improve `String.prototype.contains` polyfill

    mathiasbynens authored
    This patch replaces the old `String.prototype.contains` polyfill with http://mths.be/contains, while also adding the tests from that project.
This page is out of date. Refresh to see the latest.
View
17 bin/traceur.js
@@ -68,8 +68,21 @@
}
return $lastIndexOf.call(string, searchString, start) == start;
}),
- contains: method(function(s) {
- return this.indexOf(s) !== - 1;
+ contains: method(function(search) {
+ if (this == null) {
+ throw TypeError();
+ }
+ var string = String(this);
+ var stringLength = string.length;
+ var searchString = String(search);
+ var searchLength = searchString.length;
+ var position = arguments[1];
+ var pos = position ? Number(position): 0;
+ if (isNaN(pos)) {
+ pos = 0;
+ }
+ var start = Math.min(Math.max(pos, 0), stringLength);
+ return $indexOf.call(string, searchString, pos) != - 1;
}),
codePointAt: method(function(position) {
var string = String(this);
View
20 src/runtime/runtime.js
@@ -99,8 +99,24 @@
}
return $lastIndexOf.call(string, searchString, start) == start;
}),
- contains: method(function(s) {
- return this.indexOf(s) !== -1;
+ // http://people.mozilla.org/~jorendorff/es6-draft.html#sec-string.prototype.contains
+ contains: method(function(search) {
+ /*! http://mths.be/contains v0.1.0 by @mathias */
+ if (this == null) {
+ throw TypeError();
+ }
+ var string = String(this);
+ var stringLength = string.length;
+ var searchString = String(search);
+ var searchLength = searchString.length;
+ var position = arguments[1];
+ // `ToInteger`
+ var pos = position ? Number(position) : 0;
+ if (isNaN(pos)) {
+ pos = 0;
+ }
+ var start = Math.min(Math.max(pos, 0), stringLength);
+ return $indexOf.call(string, searchString, pos) != -1;
}),
codePointAt: method(function(position) {
/*! http://mths.be/codepointat v0.1.0 by @mathias */
View
110 test/feature/StringExtras/Contains.js
@@ -1,3 +1,107 @@
-assert.isTrue('Hello World!'.contains('or'));
-assert.isFalse('Hello World!'.contains('and'));
-assert.isTrue('Hello World!'.contains(''));
+assert.equal(String.prototype.contains.length, 1);
+
+assert.equal('abc'.contains(), false);
+assert.equal('aundefinedb'.contains(), true);
+assert.equal('abc'.contains(undefined), false);
+assert.equal('aundefinedb'.contains(undefined), true);
+assert.equal('abc'.contains(null), false);
+assert.equal('anullb'.contains(null), true);
+assert.equal('abc'.contains(false), false);
+assert.equal('afalseb'.contains(false), true);
+assert.equal('abc'.contains(NaN), false);
+assert.equal('aNaNb'.contains(NaN), true);
+assert.equal('abc'.contains('abc'), true);
+assert.equal('abc'.contains('def'), false);
+assert.equal('abc'.contains(''), true);
+assert.equal(''.contains(''), true);
+
+assert.equal('abc'.contains('b', -Infinity), true);
+assert.equal('abc'.contains('b', -1), true);
+assert.equal('abc'.contains('b', -0), true);
+assert.equal('abc'.contains('b', +0), true);
+assert.equal('abc'.contains('b', NaN), true);
+assert.equal('abc'.contains('b', 'x'), true);
+assert.equal('abc'.contains('b', false), true);
+assert.equal('abc'.contains('b', undefined), true);
+assert.equal('abc'.contains('b', null), true);
+assert.equal('abc'.contains('b', 1), true);
+assert.equal('abc'.contains('b', 2), false);
+assert.equal('abc'.contains('b', 3), false);
+assert.equal('abc'.contains('b', 4), false);
+assert.equal('abc'.contains('b', +Infinity), false);
+assert.equal('abc'.contains('bc'), true);
+assert.equal('abc'.contains('bc\0'), false);
+
+assert.equal('abc123def'.contains(1, -Infinity), true);
+assert.equal('abc123def'.contains(1, -1), true);
+assert.equal('abc123def'.contains(1, -0), true);
+assert.equal('abc123def'.contains(1, +0), true);
+assert.equal('abc123def'.contains(1, NaN), true);
+assert.equal('abc123def'.contains(1, 'x'), true);
+assert.equal('abc123def'.contains(1, false), true);
+assert.equal('abc123def'.contains(1, undefined), true);
+assert.equal('abc123def'.contains(1, null), true);
+assert.equal('abc123def'.contains(1, 1), true);
+assert.equal('abc123def'.contains(1, 2), true);
+assert.equal('abc123def'.contains(1, 3), true);
+assert.equal('abc123def'.contains(1, 4), false);
+assert.equal('abc123def'.contains(1, 5), false);
+assert.equal('abc123def'.contains(1, +Infinity), false);
+
+assert.equal('abc123def'.contains(9, -Infinity), false);
+assert.equal('abc123def'.contains(9, -1), false);
+assert.equal('abc123def'.contains(9, -0), false);
+assert.equal('abc123def'.contains(9, +0), false);
+assert.equal('abc123def'.contains(9, NaN), false);
+assert.equal('abc123def'.contains(9, 'x'), false);
+assert.equal('abc123def'.contains(9, false), false);
+assert.equal('abc123def'.contains(9, undefined), false);
+assert.equal('abc123def'.contains(9, null), false);
+assert.equal('abc123def'.contains(9, 1), false);
+assert.equal('abc123def'.contains(9, 2), false);
+assert.equal('abc123def'.contains(9, 3), false);
+assert.equal('abc123def'.contains(9, 4), false);
+assert.equal('abc123def'.contains(9, 5), false);
+assert.equal('abc123def'.contains(9, +Infinity), false);
+
+assert.equal('foo[a-z]+(bar)?'.contains('[a-z]+'), true);
+assert.equal('foo[a-z]+(bar)?'.contains(/[a-z]+/), false);
+assert.equal('foo/[a-z]+/(bar)?'.contains(/[a-z]+/), true);
+assert.equal('foo[a-z]+(bar)?'.contains('(bar)?'), true);
+assert.equal('foo[a-z]+(bar)?'.contains(/(bar)?/), false);
+assert.equal('foo[a-z]+/(bar)?/'.contains(/(bar)?/), true);
+
+// http://mathiasbynens.be/notes/javascript-unicode#poo-test
+var string = 'I\xF1t\xEBrn\xE2ti\xF4n\xE0liz\xE6ti\xF8n\u2603\uD83D\uDCA9';
+assert.equal(string.contains(''), true);
+assert.equal(string.contains('\xF1t\xEBr'), true);
+assert.equal(string.contains('\xE0liz\xE6'), true);
+assert.equal(string.contains('\xF8n\u2603\uD83D\uDCA9'), true);
+assert.equal(string.contains('\u2603'), true);
+assert.equal(string.contains('\uD83D\uDCA9'), true);
+
+assertThrows(function() { String.prototype.contains.call(undefined); }, TypeError);
+assertThrows(function() { String.prototype.contains.call(undefined, 'b'); }, TypeError);
+assertThrows(function() { String.prototype.contains.call(undefined, 'b', 4); }, TypeError);
+assertThrows(function() { String.prototype.contains.call(null); }, TypeError);
+assertThrows(function() { String.prototype.contains.call(null, 'b'); }, TypeError);
+assertThrows(function() { String.prototype.contains.call(null, 'b', 4); }, TypeError);
+assert.equal(String.prototype.contains.call(42, '2'), true);
+assert.equal(String.prototype.contains.call(42, 'b', 4), false);
+assert.equal(String.prototype.contains.call(42, '2', 4), false);
+assert.equal(String.prototype.contains.call({ 'toString': function() { return 'abc'; } }, 'b', 0), true);
+assert.equal(String.prototype.contains.call({ 'toString': function() { return 'abc'; } }, 'b', 1), true);
+assert.equal(String.prototype.contains.call({ 'toString': function() { return 'abc'; } }, 'b', 2), false);
+
+assertThrows(function() { String.prototype.contains.apply(undefined); }, TypeError);
+assertThrows(function() { String.prototype.contains.apply(undefined, ['b']); }, TypeError);
+assertThrows(function() { String.prototype.contains.apply(undefined, ['b', 4]); }, TypeError);
+assertThrows(function() { String.prototype.contains.apply(null); }, TypeError);
+assertThrows(function() { String.prototype.contains.apply(null, ['b']); }, TypeError);
+assertThrows(function() { String.prototype.contains.apply(null, ['b', 4]); }, TypeError);
+assert.equal(String.prototype.contains.apply(42, ['2']), true);
+assert.equal(String.prototype.contains.apply(42, ['b', 4]), false);
+assert.equal(String.prototype.contains.apply(42, ['2', 4]), false);
+assert.equal(String.prototype.contains.apply({ 'toString': function() { return 'abc'; } }, ['b', 0]), true);
+assert.equal(String.prototype.contains.apply({ 'toString': function() { return 'abc'; } }, ['b', 1]), true);
+assert.equal(String.prototype.contains.apply({ 'toString': function() { return 'abc'; } }, ['b', 2]), false);
Something went wrong with that request. Please try again.