Creating credentials for the user is always more troublesome than having a user create credentials and them sending them to you over a secure channel.
There are several threats a user might encounter:
Weak Credentials are created and can't be changed.
This is a rather common occurrence. A user registers for a site and for reasons of "convenience", the website generates a password for them. The generated password is
This password is rather easy to brute force and contains roughly 25 bits of entropy.
This wouldn't be a problem if the password was for the first login, upon which the user has to pick a strong password themselves. Though this begs the question, why not allow the user to pick a strong password from the beginning?
You claimed to use use TLS, as well as proper authentication and authorization schemes. However, there is still a lot that can go wrong.
For example, if your website is served both via
https://example.com. Thanks to "We've always done it this way", when a user types "example.com" into the address bar, even modern browsers default to opening "http://example.com" instead of the HTTPS counterpart. Of course, this behavior can be mitigated by browser extensions, although one should never rely on user having installed a certain extension for a system being secure.
Even if a web server is configured to always forward requests to
https://example.com, the initial redirect occurs over plain HTTP, as one cannot send an HTTP request and receive an HTTPS response. If an attacker were to intercept this initial forward, they could then act as a man-in-the-middle, serving the content to the user in plain HTTP, while the attacker communicates via HTTPS to the server, reading the credentials and possibly injecting malicious content into the site.
Even if a
Strict Transport Security (HSTS) header is being sent to the user, instructing them to always use HTTPS on subsequent visits, there is still an initial unsecure communication between your site and the user, giving the attacker an albeit small window of attack. Should an attacker already sit between the user and the server, they can simply drop the HSTS-header, ensuring that the site would always be served over plain HTTP to the victim.
In order to prevent this, the site should be put on a so-called "HSTS preload" list. Browsers who support HSTS preloading will check if
example.com is on an HSTS preload list and therefore always connect to
https://example.com. In fact, they will refuse to connect to
http://example.com and most browsers can't be forced to connect to plain HTTP unless HSTS as a whole is disabled.
Disregarding plain HTTP communication, an attacker can simply attempt to sit between a user and your server. Their browser will claim that the certificate could not be validated, but to users it sounds less like:
Hackers are trying to steal your data! Run!
and more like
Something complicated bla bla bla certificate bla bla bla stupid computer doesn't work again bla bla bla click here to make it work again bla bla bla
In the end, you can't stop OSI Layer 8 errors.
Keeping the Credentials insecured
In general, the server should never know the plaintext credentials. They should be stored in a hashed format. It is recommended to use a slow key derivation function, such as Argon2, scrypt, PBKDF2 or bcrypt to do so. The advantage is while you only need to calculate these once (or twice, if the user makes a mistake while typing the password), an attacker with access to the database needs to calculate millions of hashes for every possible password candidate.
The scheme itself should be alright, if everything around it is secure too.