15

In PHP, I have a string like this:

$string = "user@domain.com";

How do I get the "user" from email address only? Is there any easy way to get the value before @?

Mark Rotteveel
  • 90,369
  • 161
  • 124
  • 175
Steve Martin
  • 279
  • 1
  • 4
  • 10
  • 5
    Caution: Email addresses may contain more than one "@"...! – deceze Aug 14 '13 at 15:31
  • 2
    You can see this example with strstr() function : http://php.net/manual/en/function.strstr.php#example-4852 – Arno Oct 02 '17 at 14:00
  • $email = "youremail@somedomain.com"; $domain_name = substr(strrchr($email, "@"), 1); echo "Domain name is :" . $domain_name; – Erik Thiart May 30 '18 at 13:17
  • @deceze: I don't know who upvoted your caution. In no real life scenario you'll have to take care of more than one@ in an email address. In my whole life, and I have dealt with millions of mails, I've never seen that. – John Oct 29 '18 at 04:00
  • @John Unfortunately *in practice* you hardly ever see this, exactly because everyone just accepts just the minimal viable email address syntax. The spec would allow for it, if anybody would actually bother fully supporting it. – deceze Oct 29 '18 at 04:33
  • The above solutions are giving username instead of domain name as a result. I found a solution that helped me in getting domain name from the email, regardless of how many '@' it contains. it always gives you the correct domain name. function getDomain($email) { $brokenEmail = explode('@', $email); $brokenEmailCount = count($brokenEmail); return $brokenEmail[$brokenEmailCount - 1]; } – Jaskaran Singh Nov 01 '18 at 09:55
  • See my answer here: https://stackoverflow.com/questions/6850894/regex-split-email-address/36297137#36297137 – Brogan Jan 06 '19 at 01:47
  • 1
    @John - FYI, in my 'real life scenario', I have two email addresses that have two '@' that I use everyday - in fact, they are my primary emails. I've been using them for at least 20 years. Guess I've never logged into any place you process emails - but they certainly DO exist and are in common enough use! – Apps-n-Add-Ons Apr 28 '19 at 17:50
  • 1
    @CFPSupport Let's put it that way: You can easily ban any such e-mail addresses in any tool, shopping cart, website you can think about and the economic impact of this desicion is below noticable margin. It's like excluding Windows 3.11 support – John Apr 29 '19 at 17:12
  • Having an email with two @ symbols is a recipe for problems on the internet. Why on earth would you do that to yourself? – Eaten by a Grue May 13 '20 at 19:21

5 Answers5

28

Assuming the email address is valid, this textual approach should work:

$prefix = substr($email, 0, strrpos($email, '@'));

It takes everything up to (but not including) the last occurrence of @. It uses the last occurrence because this email address is valid:

"foo\@bar"@iana.org

If you haven't validated the string yet, I would advice using a filter function:

if (($email = filter_var($email, FILTER_VALIDATE_EMAIL)) !== false) {
    // okay, should be valid now
}
Ja͢ck
  • 166,373
  • 34
  • 252
  • 304
5

Try the following:

$string = "user@domain.com";

$explode = explode("@",$string);

array_pop($explode);

$newstring = join('@', $explode);

echo $newstring;

Modified for multiple '@' symbols.

Ben Fortune
  • 30,323
  • 10
  • 77
  • 78
  • This is not RFC compliant and may fail if an address contains more than one "@"! Yes, that's *possible* (though not much encountered in practice)! – deceze Aug 14 '13 at 15:32
  • 1
    This will fail for the address `"Abc\@def"@iana.org` any many others. – PeeHaa Aug 14 '13 at 15:32
  • str_getcsv() with a `@` separator, but allowing quotes for mailboxes might be an alternative solution `$explode = str_getcsv($string, '@','"');` – Mark Baker Aug 14 '13 at 15:33
  • Edited for multiple @ symbols, though it's probably not the best way to do it. – Ben Fortune Aug 14 '13 at 15:38
  • Could possibly use array_pop to remove the last element of the array then implode array using @ to return it to a string. May help with addresses with multiple @ symbols. –  Aug 14 '13 at 15:40
  • Using arrays is quite heavy compared to a simple `strrpos()` and `substr()`. – Ja͢ck Aug 14 '13 at 23:13
2

There’s a nice example in the PHP manual entry for the strpos() function: http://php.net/manual/en/function.strstr.php#117530

PHP makes this easy for you. When working with domain portion of email addresses, simply pass the return of strstr() to substr() and start at 1:

substr(strstr($haystack, '@'), 1);

Community
  • 1
  • 1
Martin Bean
  • 36,612
  • 23
  • 119
  • 192
2

You can use

$user = implode('@', explode('@', $email, -1));

or

$user = substr($email, 0, strrpos($mail, '@'));
Tsanyo Tsanev
  • 1,179
  • 9
  • 11
0

In the simplest form (assuming single '@'), you can follow @Ben Fortune's answer (using explode()).

Otherwise, try this:

$email1 = "foo@example.com";
$email2 = "b\@r@example.com";

preg_match_all ("/^(.+)@[^@]+$/", $email1, $e1);
preg_match_all ("/^(.+)@[^@]+$/", $email2, $e2);

echo "Emails: {$e1[1][0]} and {$e2[1][0]}\n";
// Result: Emails: foo and b\@r
Sutandiono
  • 1,728
  • 1
  • 12
  • 20
  • This works for multiple @ as well, it's just that regular expressions are not the right tool here :) – Ja͢ck Aug 14 '13 at 23:12
  • Yah, regular expression might be overkill here. Your answer is simpler. I didn't remember the function [strrpos()](http://php.net/manual/en/function.strrpos.php) existed. – Sutandiono Aug 15 '13 at 02:01