Condition not matching the expected behaviour

Viewed 27

I have two records which are being passed to below if else

Record1 : START SUITE: Android [ ]

Record2 : START SUITE: Android.Test the user dashboard [ ]

in the string match i am trying to differentiate these both one has Android [ ] while other is Android.

here is my conditions

if  record.message ~= nil and string.match(record.message, "START SUITE: Android[ ]") then
    new_record["name"] = "A"
    if string.match(record.message, "START SUITE: Android.") then
        getname(record.message)
        new_record["name"] = "B"
    end
end

Here the problem is the 1st record is coming to second condition even it don't have the Android. in the record and getting the name "B" instead of staying in 1st condition how can i resolve this?

Note: i have multiple records and getting them dynamically so that's why not adding directly Android.Test the user dashboard to the second condition to stop the entry of 1st.

1 Answers

string.match takes a pattern:

  • . in a pattern matches any character;
  • [...] in a pattern is a character class where ... are a bunch of ranges or characters. [ ] matches exactly the space character .

Anything that matches "START SUITE: Android [ ]" - equivalent to "START SUITE: Android " as a pattern - will thus match "START SUITE: Android.", because the space character ( ) matches any character (.).

To avoid this, escape your patterns properly using the % sign:

  • "START SUITE: Android [ ]" becomes "START SUITE: Android %[ %]"
  • "START SUITE: Android." becomes "START SUITE: Android%."

As you just want to check whether the string contains a substring and don't care about the match, you might want to use string.find (s, pattern [, init [, plain]]) instead of string.match. This will return nil - which is falsy - if the substring is not found, or an index (and more which usually gets discarded) - which is truthy - if the substring is found. Additionally, you can pass the plain parameter to make sure pattern is interpreted as a plain substring rather than a pattern. Using this, you could rewrite your code as follows:

if record.message ~= nil and string.find(record.message, "START SUITE: Android [ ]", 1, true) then
    new_record["name"] = "A"
elseif string.find(record.message, "START SUITE: Android.", 1, true) then
    getname(record.message)
    new_record["name"] = "B"
end

you might want to write yourself a handy utility for this "contains" check equivalent to not not string.find(s, pattern, 1, true).

The nested if becomes obsolete; if the first if matches, the second if can't possibly match unless the subject string contains both strings. I have thus moved it to an elseif branch.

Related