FR3DLdapBundle Login with email - symfony

I'm new on LDAP concept and i have to make a integration with LDAP and FosUserBundle.
I've installed both bundles, fosuser and FR3DLdapBundle, fosuser is working but i'm missing something about LDAP login.
I need to login with email.
I have the following config: http://pastebin.com/USkJqtbD
I'm using this website for tests: http://www.forumsys.com/tutorials/integration-how-to/ldap/online-ldap-test-server/
I'm using email: riemann#ldap.forumsys.com and password: password
But i have the following error
[2015-05-18 16:36:58] ldap_driver.DEBUG: ldap_search(cn=read-only-admin,dc=example,dc=com, (&(objectClass=*)(uid=riemann#ldap.forumsys.com)), uid,mail) [] []
[2015-05-18 16:36:58] security.INFO: User riemann#ldap.forumsys.com not found on ldap [] []
Thank you in advance for you help

With the FR3D Ldap bundle the first attribute that you add in the attributes list is then one that it uses to search by.
In your config the first attribute is uid, so I would suspect that if you used the uid as the username then it would properly. To sort it you will just need to switch up the order so the your mail attribute is first in the list.
fr3d_ldap:
// ...
user:
// ...
attributes: # Specify ldap attributes mapping [ldap attribute, user object method]
- { ldap_attr: mail, user_method: setEmail } # Default
- { ldap_attr: uid, user_method: setUsername }

You have to adapt the search query for find by email.
https://github.com/Maks3w/FR3DLdapBundle/blob/master/Resources/doc/index.md#4-configure-configyml
# app/config/config.yml
fr3d_ldap:
driver:
accountFilterFormat: (&(email=%s)) # Optional. sprintf format %s will be the username

Related

JWTRefreshTokenBundle change user_identity_field Symfony 5.4 + ApiPlatform

I am using : Symfony 5.4 + ApiPlatform + JWTRefreshTokenBundle 1.1
JWTRefreshTokenBundle => https://github.com/markitosgv/JWTRefreshTokenBundle
I need to change this parameter "user_identity_field" but there is no way to change this :
I tried to change the Yaml =>
gesdinet_jwt_refresh_token:
user_identity_field: email
user_provider: app_user_provider
I tried to modify this function in my user provider (app_user_provider) entity User.php :
public function getUserIdentifier(): string
{
return (string) $this->id;
}
Right now the better I can get is to have the ID instead of the E-mail in the user name column in my database, but as soon as I try to refresh the token, I get this message => " 401 "Invalid credentials".
I am tried to have "ID" instead of "E-MAIL" as user_identity_field.
Has anyone found a solution ?
Thanks.
Sf 5,4+
#gesdinet_jwt_refresh_token.yaml
gesdinet_jwt_refresh_token:
user_identity_field: email
ttl: 2592000
firewall: login
user_provider: security.user.provider.concrete.app_user_provider
i think you need to change the app_user_provider in the security.yaml file :
app_user_provider:
entity:
class: App\Entity\User
property: id
jwt:
lexik_jwt:
class: App\Entity\User
i think the problem is : symfony try to authneticate user with the app_user_provider and you have a conflict because id's are in your JWT but framework search for email.
For verify that you can check your tokens on : https://jwt.io/
The JWTRefreshTokenBundle (gesdinet/jwt-refresh-token-bundle) is build upon the JWTAuthenticationBundle (lexik/jwt-authentication-bundle), which is the bundle that defines the user_identity_field configuration:
# config/packages/lexik_jwt_authentication.yaml
lexik_jwt_authentication:
user_identity_field: 'email'

Which Claims should I use to map an ADFS user to GCIP

We have a SaaS product on the firebase platform, one of our customer asked us to provide a SSO experience to their users. They have an old ADFS as an IdP.
I though first to use Passport-Saml but then noticed that firebase auth could use Google Cloud Identity Platform for custom SAML IdP.
It worked pretty well and we got a user logged in first try. However, the user created in firebase is pretty empty.
Here is the user from the auth creation hook:
{
customClaims: {
}
disabled: false
displayName: null
email: null
emailVerified: false
metadata: {
creationTime: "2020-09-21T22:43:36Z"
lastSignInTime: "2020-09-21T22:43:36Z"
}
passwordHash: null
passwordSalt: null
phoneNumber: null
photoURL: null
providerData: [
0: {
providerId: "saml.xxxx"
uid: "xxxx"
}
]
tokensValidAfterTime: null
uid: "xxxx"
}
On the ADFS side, our customer has configured the claims to map LDAP as
E-mail-Addresses -> E-mail Address
SAM-Account-Name -> Name ID
If anyone has an idea on which SAML claim maps to firebase user attribute I would be very grateful, no luck in the doc.
edit
I created the ServiceProvider.xml using saml tools
<?xml version="1.0"?>
<md:EntityDescriptor xmlns:md="urn:oasis:names:tc:SAML:2.0:metadata"
validUntil="2020-09-25T02:53:54Z"
cacheDuration="PT604800S"
entityID="xxxx">
<md:SPSSODescriptor AuthnRequestsSigned="false" WantAssertionsSigned="false" protocolSupportEnumeration="urn:oasis:names:tc:SAML:2.0:protocol">
<md:NameIDFormat>urn:oasis:names:tc:SAML:1.1:nameid-format:unspecified</md:NameIDFormat>
<md:AssertionConsumerService Binding="urn:oasis:names:tc:SAML:2.0:bindings:HTTP-POST"
Location="https://xxx.firebaseapp.com/__/auth/handler"
index="1" />
</md:SPSSODescriptor>
</md:EntityDescriptor>
And did a bit more testing using saml test which was a great sandbox
The answer is twofold:
The ServiceProvider.xml file needs to specify the nameid format as email address
<md:NameIDFormat>urn:oasis:names:tc:SAML:1.1:nameid-format:emailAddress</md:NameIDFormat>
And the claim mapping from ADFS needs to be
E-mail-Addresses -> Name ID

Set the display name using memory provider in Symfony2

I am currently trying to create some tests for an application, but I'm stuck on authentication.
In the app I use ldap authentication, which also determines the role of each user. It works well, but to simplify the testing (and to not use real users) I use the in_memory provider in my tests.
The problem is that in my views I use {{ app.user.displayname }}, and the display name is not available with the in_memory provider.
Is there a way to add it ? For example this solution (which does not work) would be perfect :
providers:
in_memory:
memory:
users:
john: { password: john, roles: 'ROLE_USER', displayname: 'John Doe' }
admin: { password: admin, roles: 'ROLE_ADMIN', displayname: 'Admin' }
You could either modify the class
src/Symfony/Component/Security/Core/User/InMemoryUserProvider.php
so it uses the displayname as well or (even better) create your own class which will extend the InMemoryUserProvider and use your own provider (http://symfony.com/doc/current/cookbook/security/custom_provider.html)

how to use addCredential() function while authenticating

I have a custom user table for managing users.
User:
connection: doctrine
tableName: user
columns:
user_login:
type: string(50)
notnull: true
primary: true
user_pass:
type: string(100)
notnull: true
after user click login with login form, username and password is checked against the database. If it is matched the user is set as authenticated with below line of code..
$this->getUser()->setAuthenticated(true);
Now how would I set the credential of the user using the following function? and is it necessary?
$this->getUser()->addCredential($WHAT ARE_THE_VALUES_THIS_ARRAY_SHOULD_CONTAINS);
what are the values should be in argument of the above method? Please explain more about this.
It's up to you whether to use credentials or not. Credentials just unique strings cached in the session.
$this->getUser()->addCredentials(array('admin', 'user', 'chief', 'asd'));
// or
$this->getUser()->addCredentials('admin', 'user', 'chief', 'asd');
For mode examples look at the tests and/or the sfDoctrineGuardUser plugin.
You can use credentials to secure actions, but it's in the docs.

FOSFacebookBundle : Choose username before registration

I installed FOSUserBundle and FOSFacebookBundle using this method : How to make a separate url for signin via Facebook using FOSFacebookBundle in Symfony2. Actually I didn't really understand the whole security thing process, but it is working fine now.
When someone is using facebook signup, I would like the possibility to choose an username before being registred (instead of the facebook id as username)... what I do is that I send a POST parameter to the facebook login route but I can't find the controller where the registration is being processed.
What would be the best practise ? Where should I retrieve the username (the POST param) and set it ?
Here is my configuration in security.yml :
firewalls:
public:
pattern: ^/
fos_facebook:
app_url: "http://www.appName.com"
server_url: "http://local.appName.com/app_dev.php/"
login_path: /login
check_path: /login_check/facebook
provider: appName.facebook.provider
form_login:
login_path: /login
check_path: /login_check/form
provider: fos_userbundle
csrf_provider: form.csrf_provider
and here is the routing I use to signup with facebook :
_security_check_facebook:
pattern: /login_check/facebook
There is no controller processing authentication, ever authentication method add a listener that will trigger on check_path, and do the trick.
Authentication process shouldn't be responsible to add custom user data. If you followed FOSFacebookBundle documentation you should have a custom user provider that store the user on database, this may confuse a bit but this is not a registration step, is an authentication step. Adding a username is much similar to a profile editing.
To help you i should see your implementation (how do you send post parameter ? ) but you could try something like this:
send post parameter to a custom controller (implemented by you)
temporary store username (maybe user session data ?)
trigger authentication process (this depend on your implementation but essentially we are talking about authenticate on facebook and then post to login_check path)
add username at the authenticated user
This could work, but I never did something like this.
Old question, but I was working on a similar problem. I wanted to add a role to a user when they were registered on the first time they connected with Facebook.
If you follower these steps from the FOSFacebookBundle documentation, then you can tap into the Facebook connected user's "registration", take a look at the FacebookProvider class.
In loadUserByUsername method there is this part:
if (!empty($fbdata)) {
if (empty($user)) {
$user = $this->userManager->createUser();
$user->setEnabled(true);
$user->setPassword('');
}
$user->setFBData($fbdata);
...
After the setPassword within the if is where I added the role for my user.
For your original problem of choosing the username... notice that call to setFBData?
In the User entity the method looks like this:
public function setFBData($fbdata)
{
if (isset($fbdata['id'])) {
$this->setFacebookId($fbdata['id']);
$this->addRole('ROLE_FACEBOOK');
}
if (isset($fbdata['first_name'])) {
$this->setFirstname($fbdata['first_name']);
}
if (isset($fbdata['last_name'])) {
$this->setLastname($fbdata['last_name']);
}
if (isset($fbdata['email'])) {
$this->setEmail($fbdata['email']);
}
}
and setFacebookId() looks like this:
public function setFacebookId($facebookId)
{
$this->facebookId = $facebookId;
$this->setUsername($facebookId);
}
So that's where the username comes from. I guess that is a flow where you could plug your chosen username into and set it instead of the $facebookId.
I did another way for this.
I used GraphAPI.
public function setFacebookId($facebookId)
{
$this->facebookId = $facebookId;
$username = json_decode(file_get_contents('http://graph.facebook.com/'.$this->facebookId))->username;
$this->setUsername($username);
}
It takes the Facebook username, an unique one.

Resources