Using Flask Login with LDAP safe and secure - ldap

I am creating a login page with an authentication using LDAP. I could see LDAP3 packages for flask with login forms as well. I am looking for a form where the developer of the portal(say me or anyone in our team) should not be able to add any print statements and sniff the username and password when someone log in...
The flask form is exposing the password variable as a plain string. Even if it doesn't expose , it is possible to put a print statement in the flask_form validate function.
Is there any option available like the form is bundled as binary or c-python module where the developer has no option to sniff the credentials at all..
If not possible or no options available as they know off, any other framework like django helps for these usecase?

By design, server-side LDAP authentication requires the server receive the username & password from the user and relay that information to the LDAP server. This means a developer could insert a line that logs all credentials out somewhere, grab the passwords from process traces, dump memory, etc. If you don't want any of the developers or system administrators to have access to user passwords, use some type of federated authentication instead of LDAP.
In a federated authentication scheme, the user auths against some other source (e.g. ADFS) and your app checks a token that essentially says "this trusted other auth source says the person is Lisa".

Related

Login another salesforce org from salesforce record page

I was wondering if it was possible to login to different salesforce environments (Sandboxes, scratch orgs, production env, etc) using either Apex/LWC/Aura (or anything that I can make a quick action to). For example, I have a list of credential records, with the username and password, and I would like to have a login button that creates a separate tab that can automatically redirect to that specific instance and log in.
Currently, if a user wants to login to a particular instance, they have to either go to test.salesforce.com or login.salesforce.com (depending on if it's a sandbox or production) manually, then copy the password and username in. The ideal situation is to have a login button that can do this automatically from the record page where the username and password is located.
I think previously this could have been accomplished through the URL, but salesforce has recently patched this out due to security concerns. Is there another good way to do this?
It sounds like you're trying to solve two specific challenges:
Your users need to be able to manage very high volume of credentials.
You need authentication to survive password resets.
The clear solution, in my mind, is to use the OAuth Web Server flow to execute initial authentication and then store the refresh token that results from this flow. This token survives password resets, and may be used more or less indefinitely to create new access tokens - which users can then use to log in via a frontdoor link.
There's an out-of-the-box tool that does this already: the Salesforce CLI. You can authenticate orgs to its toolchain, name them, and subsequently access them with a single command (sfdx force:org:open). Users that prefer a GUI can access the exact same functions in Visual Studio Code.
If you're hellbent on doing custom development to handle this use case, you can, but you need to be very careful of the security implications. As one example, you could implement an LWC + Apex solution that executed the relevant OAuth flows against orgs and stored the resulting data in an sObject, then allowing users to click a button to generate a new access token and do a one-click login.
But... if you do this, you're storing highly sensitive credentials in an sObject, which can be accessed by your system administrators and potentially other users who have relevant permissions. That data could be exfiltrated from your Salesforce instance by an attacker and misused. There's all kinds of risks involved in storing that kind of credential, especially if any of them unlock orgs that contain PII or customer data.
One of the two best answers for that (the other one being 'pure Apex' and relatively more complex) is using Flow.
"You can use a login flow to customize the login experience and integrate business processes with Salesforce authentication. Common use cases include collecting and updating user data at login, configuring multi-factor authentication, or integrating third-party strong authentication methods.enter image description here"
"You can use login flows to interact with external third-party authentication providers by using an API.
For example, Yubico offers strong authentication using a physical security key called a YubiKey. Yubico also provides an example Apex library and login flow on GitHub. The library supplies Apex classes for validating YubiKey one-time passwords (OTPs). The classes allow Salesforce users to use a YubiKey as a second authentication factor at login. For more information, see yubikey-salesforce-client.
You can also implement a third-party SMS or voice delivery service, like Twilio or TeleSign, to implement an SMS-based multi-factor authentication and identity verification flow. For more information, see Deploy Third-Party SMS-Based Multi-Factor Authentication."
learn more here: enter link description here

Is it a loophole to join ldap authentication?

If multiple systems join ldap authentication, then any administrator of any one of them can get the password of any user's account.right?
Applications authenticating against an LDAP directory are not going to be able to access all of the user passwords en mass provided you do not not permit direct read access to the attribute or you do not store your passwords in clear text (if you use something like ldapsearch to dump an entry and have userpassword:: followed by a bunch of random looking 'stuff', that's an easily decoded clear text password). App I allow to access my LDAP server aren't given access to read all of the userPassword values to attempt reversing them out to clear text (and I'm using a decent encryption mechanism to store userPassword value). I restrict the application service account to reading contact-type attributes (phone number, address) and group objects. The only way they get the user's password is by asking the user for it and binding against my directory with those credentials. Can an app admin grab credentials for those who use the application? Sure, they could.
On an out of the box application, I could attach a debugger and access the username/password values as they transit the application. With custom-written applications, it's even easier to grab the credentials. The application takes the username and password as user input and binds to the LDAP server to validate the username and password. As an LDAP server admin, there's nothing I can do to prevent the application developer from making calls and doing other things with that username and password. "Other things" may be legit -- I've handled LDAP directory migrations by authenticating against the old system and, on success, creating the user in the new directory LDAP with the password the old directory just accepted. It was an ugly way to migrate directories, but it worked. "Other things" may be malicious. Is it likely to encounter an app admin or developer who is siphoning off credentials? Depends on who authenticating through your LDAP directory.
This isn't a unique failing of LDAP -- any authentication back-end that you let other people use directly suffers from the same problem. If you don't want the app admins/developers intercepting user credentials, look into federated identify management (FIM) -- an authentication mechanisms where the app (service provider, in FIM terminology) doesn't have access to the username and password but rather validates a token of some sort that was created after a trusted "identity provider" authenticated the username and password.

What is best suited to interface with authentication servers for a CLI tool?

I am developing two linux programs, a CLI client and a server communicating via gRPC, and I now would like to authenticate users against a given private authorization server such as LDAP, Active Directory, etc.
I am confused regarding the various possible authentication flows. I think I can't use any classical flow including HTTP redirects since I shouldn't rely on a browser being installed or having internet access. I can't even define an endpoint I could redirect to (servers don't have internet access, and both are behind NATs).
So I was thinking of trying to store user's credentials as a JWT token file in the user's computer and then load it from my CLI client program to include it in my RPC requests and then validate it on the server-side. But, supposing I'm right, then what would be the best standard way of getting this token file?
If you had a browser you could use OAuth and the 'oob' (out of band) method where the CLI opens the browser and after the user authenticates it displays a number which the user copy/pastes into the CLI. This how my flickr backup CLI works. The number they copy/paste is because the CLI has no OAuth endpoint and the number is their access token to allow me to call the flickr api on their behalf.
If you can't use a browser the CLI can just accept a username/password from the user, send it to the server and receive a token in return. You don't really need anything fancy like JWT. A simple UUID would be enough. The UUID 'asserts' that the user is allowed to access the server's other RPC methods. The server would validate the UUID token to make sure it's still valid. If you need user information from the token, the server could do that. Keeps the user information off the client's disk and only the CLI can access that information, if the token is still valid.
So in effect, you need a new server RPC method, perhaps, authenticate, that accepts a username and password and returns a UUID token. All other RPC methods then need to accept that token and validate it before performing the requested function. As part of the server-side authentication process, the server could associate that token with the user information it got from the LDAP server so you don't need to store that information on the client. Lets you encrypt it on the server too and if the client needs it, it asks for it using the UUID token if it's still valid (time to live?). If it's no longer valid, the client just needs to ask for username/password again and the server can re-authenticate the user via LDAP and refresh the token and user information.
gRPC has authentication protocols but the SSL/TLS doesn't seem to match your needs and the OAuth won't work as you don't have a browser. So perhaps rolling your own simple token service (authenticate) combined with LDAP authentication might be a workable option.

Best practices for a Password Management System

I'm working on a password management system which stores the passwords of a bunch of services (gmail, bank of america account, youtube etc). The user will be able to launch each of these services by logging into my application. The application will then POST the username and password associated with that service to that service's login url in a new tab and you will be immediately logged in. My question is, this method exposes the actual password of the user to the client side (since I'm creating a form with username and password, in plain text, as hidden fields and calling form.submit). I'm wondering is there any other method by which this can be achieved? How do all the password management sites work? Your help is appreciated.
Do it server side, what else can I say? Anyway, I can only see this as a learning experience, not something that would eventually go into production. cUrl could be a good start. Why do you use form.submit anyway?
This is called "formfill" in terms of access management terminology, if you are thinking about access gateway (http). If you are thinking about browser plugin, have a look at the firefox autofill plugin. And which finally reduces to single sign-on.
Single sign-on are done different ways,-
some servers uses active directory to store all the passwords and later access using the master password , i.e. the active directory password of that user to access his credentials.
Some uses SAML
Some uses e-directory
Whatever you use, if it is server-side application (e.g. Appache supports formfill), it parses all the forms based on form name or resource path and fills credentials based on the authenticated session from the user.

Best way for a remote web app to authenticate users in my current web app?

So a bit of background, I'm working on an existing web application which has a set of users, who are able to log in via a traditional login screen with a user name and password, etc.
Recently we've managed to score a client (who have their own Intranet site), who are wanting to be able to have their users log into their Intranet site, and then have their users click a link on their Intranet which redirects to our application and logs them into it automatically.
I've had two suggestions on how to implement this so far:
Create a URL which takes 2 parameters (which are "username" and "password") and have the Intranet site pass those parameters to us (our connection is via SSL/TLS so it's all encrypted). This would work fine, but it seems a little "hacky", and also means that the logins and passwords have to be the same on both systems (and having to write some kind of web service which can update the passwords for users - which also seems a bit insecure)
Provide a token to the Intranet, so when the client clicks on a link on the Intranet, it sends the token to us, along with the user name (and no password) which means they're authenticated. Again, this sounds a bit hacky as isn't that essentially the same as providing everyone with the same password to log in?
So to summarise, I'm after the following things:
A way for the users who are already authenticated on the Intranet to log into our system without too much messing around, and without using an external system to authenticate, i.e. LDAP / Kerberos
Something which isn't too specific to this client, and can easily be implemented by other Intranets to log in
Both of your suggested options are insecure, even if you use SSL. Never pass credentials on a URL, put them in the HTTP request by using POST.
There is a standard called SAML and this can be used to solve your problem. The challenge is choosing which version to implement. I would choose SAML 2.0.
Google Apps implements a flavor of SAML 2.0 and allow you to authenticate using your intranet credentials. In the case of your application, you would be the service provider and your client would be the identity provider. As long as you implement the standard correctly you should be able to support any new client (identity provider). Here is a list of SAML implementations you might want to take a look at. If you need the client to pass over information in addition to the authentication information then SAML can facilitate this with metadata.
You will still need to implement SSL to encrypt network traffic.
I hate to answer my own question, but I hate even more a question with no answer. In the end we went with a very similar implementation of SalesForce's delegated authentication SSO implementation.
http://wiki.developerforce.com/page/How_to_Implement_Single_Sign-On_with_Force.com
Essentially the solution has a trusted site, known as the delegated authentication authority, who has a list of users who are logged into the company intranet.
When the user logs into the company intranet, and they click a link to our application, the company intranet will pass the user name and a generated token (which expires after a set amount of time) to our application.
Our application will then check if the user name is on our site, and if so, send the username / token (along with the source IP and a few other parameters) to the delegated authentication authority. If all those items match on the delegated authentication authority, it returns true and the user can log in. If it returns false the user is denied access.
We've found this system to work quite well, and even implemented a couple of extra security features like SSL, client side certificates, VPN tunnel, and even restricting the IP addresses which can access the site and the delegated authentication authority.
I know it's bad form to answer your own question but I hope this helps someone else who might be having the same problem ...