Simple PHP strpos function not working, why? - php

Why isn't this standalone code working:
$link = 'https://google.com';
$unacceptables = array('https:','.doc','.pdf', '.jpg', '.jpeg', '.gif', '.bmp', '.png');
foreach ($unacceptables as $unacceptable) {
if (strpos($link, $unacceptable) === true) {
echo 'Unacceptable Found<br />';
} else {
echo 'Acceptable!<br />';
}
}
It's printing acceptable every time even though https is contained within the $link variable.

When in doubt, read the docs:
[strpos] Returns the numeric position of the first occurrence of needle in the haystack string.
So you want to try something more like:
// ...
if (strpos($link, $unacceptable) !== false) {
Because otherwise strpos is returning a number, and you're looking for a boolean true.

strpos() does not return true when it finds a match, it returns the position of the first matching string. Watchout, if the match is a the beginning of the string it will return an index of zero which will compare as equal to false unless you use the === operator.

Your failure condition is wrong.
strpos returns false if match is not found, so you need to explicitly check
if (strpos($link, $unacceptable) !== false) {

Strpos always return position like you search "httpsL" in your string('https://google.com';) then it return 0th position and PHP evaluate it as false.
please see this link:(Hope its very usefull for you):
http://php.net/manual/en/function.strpos.php

strpos
function may return Boolean FALSE, but may also return a non-Boolean value which evaluates to FALSE.
So I did like this
if (strpos($link, $unacceptable) !== false) {
//Code
}

Related

strpos fails to filter the keyword

From given url, I want to check whether it contains //t.co or twitter.com. If yes then skip it and while loop should continue.
if(preg_match($reg_exUrl, $tweet, $url)) {
preg_match_all($reg_exUrl, $tweet, $urls);
foreach ($urls[0] as $url) {
echo "Tiny url : {$url}<br>";
$full = MyURLDecode($url);
echo "Full url : $full<br>";
if (strpos($full, '//t.co') === true)
continue;
if (strpos($full, '//twitter.com') === true)
continue;
else if (strpos($full, '//bit.ly') !== true)
$full = MyURLDecode($full);
}
But though url contains above keyword it does not get skipped, what strpos fails? what is alternative for this?
strpos() never returns true.either it will return the position when mathed or will return false when match is not found.
Read Here
use
strpos($full, '//t.co') === true
as
if(strpos($full, '//t.co') !== false)

How to return a boolean if a string contains one of an array of substrings?

I'm struggling with a simple function that loops through an array and returns true only if it finds a given substring in one of the array's elements.
For some reason, I'm ALWAYS getting false... even when the $email parameter is contains one of the valid domains. Ex: scoobydoo#domain1.com.
function check_email($email) {
$whitelist_domains = array(
'#domain1.com',
'#domain2.com',
'#domain3.com'
);
$output = FALSE;
foreach ($whitelist_domains as $domain) {
$pos = strpos( $email, $domain );
if ( $pos ) {
$output = TRUE;
}
}
return $output;
}
you are not breaking the loop if you find the domain, so what you are getting is actually the result for the LAST string checked only.
just add break; after $output = TRUE;
From the official doc of strpos:
Warning
This function may return Boolean FALSE, but may also return a
non-Boolean value which evaluates to FALSE. Please read the section on
Booleans for more information. Use the === operator for testing the
return value of this function.
And make sure to add a break after you set $output to true.
This is a good function to use the === operator with as it makes sure the value and type are equal (1==true, but 1!==true)
if (strpos( $email, $domain )!==false) {
$output = TRUE;
}
Change
if ( $pos ) {
to
if ( $pos !== false) {
this is because is strpos returns 0, that will equate to false, even though the string was found.
Here are two direct/common methods that have different advantages:
Method #1: non-regex approach
function check_email1($email){
$whitelist_domains=['#domain1.com','#domain2.com','#domain3.com'];
foreach($whitelist_domains as $domain){
if(strpos($email,$domain)!==false){
return true; // allow quick return (exit loop & function asap)
}
}
return false; // default response
}
Method #2: regex approach
function check_email2($email){
$whitelist_pattern='/#(?:domain1\.com|domain2\.com|domain3\.com)$/'; // condense if possible /#domain[123]\.com$/
return (bool)preg_match($whitelist_pattern,$email); // convert 0 or 1 output to boolean (false/true)
}
Demo Link
Input / Function Call:
$emails=['user#domain1.com','bad#bad.com'];
foreach($emails as $email){
echo "$email\n";
var_export(check_email1($email));
echo "\n";
var_export(check_email2($email));
echo "\n\n";
}
Output:
user#domain1.com
true
true
bad#bad.com
false
false
Advantages/Disadvantages:
strpos() in the majority of situations will outperform regex functions. Your default method should be to use string functions and only change to regex when string functions are less efficient or too convoluted to code. A related page: Which is more efficient, PHP string functions or regex in PHP?
Looping $whitelist_domains in #1 makes for a clunkier looking code block compared to #2 (which can be condensed to a one-liner if you write the pattern directly into preg_match()).
Simple/common mistakes sometimes occur when dealing with strpos(). These mistakes may include:
not checking for false in the if condition
writing the haystack and needle in the wrong order
#2 does require some knowledge about regex (escaping, character classes, alternatives, etc.) which can be a deterrent for inexperienced coders. Depending on how you write your regex pattern and how many domains will be whitelisted, #2 is likely to be harder to maintain than #1.
#2 has the added benefit of being able to check that the domain.com substring appears at the end of the word via the $ metacharacter. For this reason, regex offers stronger validation.
You should change your code in this:
function check_email($email) {
$whitelist_domains = array(
'#domain1.com',
'#domain2.com',
'#domain3.com'
);
foreach ($whitelist_domains as $domain) {
if ( strpos( $email, $domain ) !== false ) {
return true;
}
}
return false;
}
Documentation of strpos
Quoting from the manual (http://php.net/manual/en/function.strpos.php):
The !== operator can also be used. Using != would not work as expected
because the position of 'a' is 0. The statement (0 != false) evaluates
to false.
Example code
<?php
$mystring = 'abc';
$findme = 'a';
$pos = strpos($mystring, $findme);
// The !== operator can also be used. Using != would not work as expected
// because the position of 'a' is 0. The statement (0 != false) evaluates
// to false.
if ($pos !== false) {
echo "The string '$findme' was found in the string '$mystring'";
echo " and exists at position $pos";
} else {
echo "The string '$findme' was not found in the string '$mystring'";
}
?>

How to use strpos to determine if a string exists in input string?

$filename = 'my_upgrade(1).zip';
$match = 'my_upgrade';
if(!strpos($filename, $match))
{
die();
}
else
{
//proceed
}
In the code above, I'm trying to die out of the script when the filename does not contain the text string "my_upgrade". However, in the example given, it should not die since "my_upgrade(1).zip" contains the string "my_upgrade".
What am I missing?
strpos returns false if the string is not found, and 0 if it is found at the beginning. Use the identity operator to distinguish the two:
if (strpos($filename, $match) === false) {
By the way, this fact is documented with a red background and an exclamation mark in the official documentation.
The strpos() function is case-sensitive.
if(strpos($filename, $match) !== false)
{
// $match is present in $filename
}
else
{
// $match is not present in $filename
}
For using case-insensitive.
use stripos() that is it finds the position of the first occurrence of a string inside another string (case-insensitive)
if (strpos($filename, $match) === false)
Otherwise, strpos will return 0 (the index of the match), which is false.
The === operator will also compare type of the variables (boolean != integer)
false === strpos($filename, $match)
The strpos functionDocs returns false if not found or 0 if found on position 0 (programmers like to start counting at 0 often):
Warning This function may return Boolean FALSE, but may also return a non-Boolean value which evaluates to FALSE, such as 0 or "". Please read the section on Booleans for more information. Use the === operator for testing the return value of this function.
strpos returns false if the string is not found, and 0 if it is found at the beginning.
so try this:
if (strpos($filename, $match) === false) {
conditon
}
Note we use a strict comparison (===) If we don't, both types (false and false or an integer) will be coerced to the same type, and 0 when coerced to a bool is false.
more details: https://zdevtips.com/guid/strpos-in-php-example4-example-codes/
This working for me when everything other fail in some situations:
$filename = 'my_upgrade(1).zip';
$match = 'my_upgrade';
$checker == false;
if(strpos($filename, $match))
{
$checker == true;
}
if ($checker === false)
{
die();
}
else
{
//proceed
}
Or in short:
$filename = 'my_upgrade(1).zip';
$match = 'my_upgrade';
$checker == false;
if(strpos($filename, $match))
{
$checker == true;
//proceed
}
if ($checker === false)
{
die();
}
$data = 'match';
$line = 'match word in this line';
if(strpos($line,$data) !== false){
echo "data found";
}else{
echo "no data found";
}
strpos in this case will return a zero, which is then interpretted as false when you do the logical negation. You should check explicitly for the boolean false.

php problem: strpos function not working

why is the following php code not working:
$string = "123";
$search = "123";
if(strpos($string,$search))
{
echo "found";
}else{
echo "not found";
}
as $search is in $string - shouldn't it be triggered as found?
This is mentioned in the Manual: strpos()
This function may return Boolean FALSE, but may also return a non-Boolean value which evaluates to FALSE, such as 0 or "". Please read the section on Booleans for more information. Use the === operator for testing the return value of this function.
In your case the string is found at the index 0 and in php 0 == false
The solution is to just use the strict comparator
echo strpos($string,$search) === false
? "not found"
: "found";
Another one
echo is_int(strpos($string,$search))
? "found"
: "not found";
Or something ... lets say interesting :D Just for illustration. I don't recommend this one.
echo strpos('_' . $string,$search) // we just shift the string 1 to the right
? "found"
: "not found";
This is happening because the search string is being found at position 0.
Try
if(strpos($string,$search) !== FALSE)
instead of
if(strpos($string,$search))
strpos returns the first offset where $search was found - 0. 0 in turn evaluates to false. Therefore the if fails.
If $search was not found, strpos returns FALSE. First check the return value for !== FALSE, and then check the offset.
Thanks to everyone who pointed this out in the comments.
see: http://php.net/manual/en/function.strpos.php
From the manual:
This function may return Boolean
FALSE, but may also return a
non-Boolean value which evaluates to
FALSE, such as 0 or "". Please read
the section on Booleans for more
information. Use the === operator
for testing the return value of this
function.
In your example, you should use
$string = "123";
$search = "123";
if ( false !== strpos( $string, $search ) ) {
echo "found";
} else {
echo "not found";
}
strpos returns the numeric position of the string you want to search for if it finds it. So in your case, you want to be doing this instead:
$search = "123";
$string = "123";
if (strpos($string,$search)===false) { echo "not found"; }
else { echo "found"; }
basically it returns a false if it doesn't find your string
You can use this:
<?php
$string = "123";
$find = "123";
$strpos = strpos($string, $find);
if($strpos || $strpos === (int)0) {
echo "Found it!";
} else {
echo "Not Found!";
}
?>
Well documented issue explained here. strpos is simply returning '0'

how can I do a string check inside a string in php?

Does anyone know how can I do a string check inside a string?
for example:
$variable = "Pensioner (other)";
If I want to check whether $variable contain the word 'Pensioner', how can I do it in PHP? I have tried the following code in php, but it's always return me false :(
$pos = strripos($variable,"Pensioner");
if($pos) echo "found one";
else echo "not found";
In the manual, the example uses a === for comparison. The === operator also compares the type of both operands. To check for 'not equal', use !==.
Your search target 'Pensioner' is at position 0, and the function returns 0, which equal false, hence if ($pos) failed all the time. To correct that, your code should read:
$pos = strripos($variable,"Pensioner");
if($pos !== false) echo "found one";
else echo "not found";
Update:
You are using the reverse function strripos, you need to use stripos.
if (stripos($variable, "Pensioner") !== FALSE){
// found
}
else{
// not found
}
This should do:
if (strripos($variable, "Pensioner") !== FALSE){
// found
}
else{
// not found
}
The strict type comparison (!==) is important there when using strpos/stripos.
The problem with strripos and its siblings is that they return the position of the substring found. So if the substring you're searching happens to be at the start, it returns 0 which in a boolean test is false.
Use:
if ( $pos !== FALSE ) ...
$variable = 'Pensioner (other)';
$pos = strripos($variable, 'pensioner');
if ($pos !== FALSE) {
echo 'found one';
} else {
echo 'not found';
}
^ Works for me. Note that strripos() is case insensitive. If you wanted it to be a case-sensitive search, use strrpos() instead.

Categories