Patryk
Patryk

Reputation: 24092

Why is JavaScript regex catching whitespace when I do not tell it to do so?

With the following code:

var firefox = "Mozilla/5.0 (Android; Mobile; rv:32.0) Gecko/32.0 Firefox/32.0";
var chrome = "Mozilla/5.0 (Linux; Android 4.4.4; Nexus 4 Build/KTU84Q) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/38.0.2125.57 Mobile Safari/537.36";

var newf = firefox.replace(/.*?(Firefox|Chrome)\/([\d\.]*?)/, "$1 $2");
var newc = chrome.replace(/.*?(Firefox|Chrome)\/([\d\.]*?)/, "$1 $2");
console.log(newf);
console.log(newc);

I get this in console:

Firefox 32.0
Chrome 38.0.2125.57 Mobile Safari/537.36 

and I only want to get browser_name version. What am I doing wrong?

Upvotes: 1

Views: 109

Answers (2)

Your regex is not taking into account the last Mobile Safari/537.36; as vks pointed out the regex ignores that last bit since your pattern succeeds completely after Chrome/38.0.2125.57 matches.

Had you added the end-terminator character ($) to your pattern, it would have failed and it would have be apparent as to the problem. replace() in Javascript finds the part of the text that matches the regex and replaces it, not the whole input string.


You could add .* at the end to sort of 'burn' through those last characters, causing the regex to match the whole line and thus causing a replace to remove those bits. This also requires you make the previous match group non-lazy by removing the ? after [\d\.]*.

I'd also add ^ and $ at the beginning/end of your pattern to signify the beginning and end of the input string (it's good form to do so), as well as optionally add /gm, which tells the regex to match each line (could potentially be useful in your case), though neither of these additions are required.

/^.*?(Firefox|Chrome)\/([\d\.]*).*$/gm

Upvotes: 4

anubhava
anubhava

Reputation: 784898

You need to use this regex:

var newc = chrome.replace(/.*?(Firefox|Chrome)\/([\d\.]*).*/, "$1 $2");
//=> "Chrome 38.0.2125.57"
  1. Don't make [\d\.]* lazy using [\d\.]*?
  2. Add .* after [\d\.]* to remove all the text after version #

Upvotes: 3

Related Questions