Estou fazendo aqui um script e preciso fazer uma autenticação em uma base
LDAP!!
O que eu queria era apenas fornecer o nome do usuário e senha e solicitar
uma autenticação, até agora o que eu vi é que primeiro o cara tem que fazer
um login usando a senha de administrador no domínio ( no meu caso eu to
usando o Active Directory ), fazer a autenticação do usuário e depois
deslogar do usuário administrador.
Isso para mim é ruim pois teria que colocar no código python a senha do
administrador e isso não dar, alguém sabe o que eu poderia fazer?
--
Fagner Patrício
João Pessoa - PB
Brasil
[As partes desta mensagem que não continham texto foram removidas]
------------------------------------
,-----------------------------------------------------------.
| Antes de enviar um e-mail para o grupo leia: |
| http://www.pythonbrasil.com.br/moin.cgi/AntesDePerguntar |
| E se você é usuário do BOL lembre-se de cadastrar o |
| e-mail do grupo na lista branca do seu sistema anti-spam. |
`-----------------------------------------------------------´Links do Yahoo! Grupos
<*> Para visitar o site do seu grupo na web, acesse:
http://br.groups.yahoo.com/group/python-brasil/
<*> Para sair deste grupo, envie um e-mail para:
python-brasi...@yahoogrupos.com.br
<*> O uso que você faz do Yahoo! Grupos está sujeito aos:
http://br.yahoo.com/info/utos.html
On 08/06/2010 08:17 AM, Fagner Patricio wrote:
> Olá Pessoal!!!
>
> Estou fazendo aqui um script e preciso fazer uma autenticação em uma base
> LDAP!!
>
> O que eu queria era apenas fornecer o nome do usuário e senha e solicitar
> uma autenticação, até agora o que eu vi é que primeiro o cara tem que fazer
> um login usando a senha de administrador no domínio ( no meu caso eu to
> usando o Active Directory ), fazer a autenticação do usuário e depois
> deslogar do usuário administrador.
>
> Isso para mim é ruim pois teria que colocar no código python a senha do
> administrador e isso não dar, alguém sabe o que eu poderia fazer?
>
Acho que a questão é menos Python e mais LDAP/conceitos, não ? Então, por partes
<OFF-TOPIC>
A senha não precisa ser, necessariamente, a do administrador do domínio. Basta ser de um usuário que tenha permissão de ler o hash
de senhas do usuário. Não trabalho com AD, mas temos algumas aplicações, em Django inclusive, que autenticam-se no AD através de um
usuário sem privilégios de administrador.
</OFF-TOPIC>
Mesmo assim, você continua tendo o problema de ter que informar a senha dentro do script. Eu recomendo que você a coloque num
arquivo ini criptografado com algum algorítmo simétrico. Um bom começo é usar o PyCrypto [1]. Seu código decriptografaria esse ini e
faria seu parser [2], lendo a senha, que não estaria no seu código. Se armazenar o arquivo ini em um lugar seguro, com permissões
seguras, acredito que resolva seu problema.
[1] http://bityard.blogspot.com/2010/01/symmetric-encryption-with-pycrypto-part.html
[2] http://docs.python.org/library/configparser.html
- --
Um abraço
.0. MrBiTs - mrbit...@gmail.com
..0 GnuPG - http://pgp.mit.edu:11371/pks/lookup?op=get&search=0x6EC818FC2B3CA5AB
000 http://www.mrbits.com.br
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.4.10 (GNU/Linux)
iQEcBAEBCAAGBQJMXAQiAAoJEG7IGPwrPKWrDXAH/RY1cYn3YcJEGhyOm4R5YkvY
pqNYcYZ3wV4ntaCZaKJJ3FNuQe0/abEBFkNNgKOfsyuDGgdyt2TQRGUjT9gEWYSz
hgVpYa35TH4hV5X/VL3PHoK8W0QSm+OF24V+T5WfE5n2O5wALNNANzkMFSinHLqk
/H49jTsNRNnTFt/o1dnAZVj7K3VEdBg6hvQ+nyaBS/Og1yC+HxuaFRI+tDhr/DBJ
6EkMylwgQcU99jpd3JM/M735Nb6Mi7bdROkxLNwURT1dVZZMRK1YzCqgcD4yZ5je
6J/XVCs9RimIHxkuCamfb+yCkbiOvft31+6gbdh2aMtQZ3rR3qtQMA2f+0LtpBE=
=NnNV
-----END PGP SIGNATURE-----
Olha eu estava tentando justamente usar no Django, e consegui, e foi até
mais fácil, olha como ficou meu código, se quiser pode sugerir que ainda não
fiz uma análise de segurança nele:
import ldap
>
> from django.conf import settings
> from django.contrib.auth.models import User
>
> DOMINIO = '@dominio.com'
> SERVIDOR_LDAP = 'ldap://ip_servidor:porta'
>
> class LdapBackend:
> """
> Autenticacao de usuarios em uma base LDAP
>
> Usa o nome do usuario, dominio e senha, por exemplo
>
> usuario = 'teste'
> dominio = '@teste.com'
> senha = 'teste'
> """
> def authenticate(self, username=None, password=None):
> usuario = None
> l = ldap.initialize(SERVIDOR_LDAP)
>
> try:
> if l.bind_s(username + DOMINIO,password)[0] == 97:
> try:
> usuario = User.objects.get(username=username)
> except User.DoesNotExist:
> #Criacao de um novo usuario.
> usuario = User(username=username,
> password=password)
> usuario.save()
> except ldap.INVALID_CREDENTIALS:
> #Nao precisa tratar nenhuma execao
> pass
>
> l.unbind()
> return usuario
>
> def get_user(self, user_id):
> try:
> return User.objects.get(pk=user_id)
> except User.DoesNotExist:
> return None
>
--
Fagner Patrício
João Pessoa - PB
Brasil
[As partes desta mensagem que não continham texto foram removidas]
------------------------------------
> Olha eu estava tentando justamente usar no Django, e consegui, e foi até
> mais fácil, olha como ficou meu código, se quiser pode sugerir que ainda não
> fiz uma análise de segurança nele:
Olá, Fagner
Basicamente é o mesmo que usamos aqui.
O que eu faria:
1) Criaria um arquivo chamado app_auth.ini (realmente um nome arrumado às pressas) assim:
[ldap]
username = userparaconsulta
password = senhadouser
domain = dominiodouser
2) Criptografaria esse cara assim:
import mcrypt
chave = 'umachavequalquer'
x = mcrypt.MCRYPT('blowfish','cbc')
plaintext = open('app_auth.ini', 'r').read()
x.init(chave)
cypheredtext = x.encrypt(plaintext)
f = open('app_auth.ini', 'w')
f.write(cypheredtext)
f.close()
3) Decriptografaria, seguindo o caminho contrário
x = mcrypt.MCRYPT('blowfish','cbc')
cypheredtext = open('app_auth.ini', 'r').read()
x.init(chave)
plaintext = x.decrypt(cypheredtext)
f = open('app_auth.ini', 'w')
f.write(plaintext)
f.close()
4) O leria assim:
import ConfigParser
t = ConfigParser.ConfigParser()
t.readfp(open('app_auth.ini'))
username = t.get('ldap','username')
password = t.get('ldap','password')
domain = t.get('ldap','domain')
5) Voltaria para (2), criptografando o arquivo novamente.
Imagino que possam aparecer vários códigos melhores, mas é um começo para você brincar.
Não há muita documentação do python-mcrypt, mas para você listar os modos e os algorítmos que ele tem, basta fazer:
>>> mcrypt.list_modes()
['cbc', 'cfb', 'ctr', 'ecb', 'ncfb', 'nofb', 'ofb', 'stream']
>>> mcrypt.list_algorithms()
['cast-128', 'gost', 'rijndael-128', 'twofish', 'arcfour', 'cast-256', 'loki97', 'rijndael-192', 'saferplus', 'wake',
'blowfish-compat', 'des', 'rijndael-256', 'serpent', 'xtea', '
blowfish', 'enigma', 'rc2', 'tripledes']
- --
Um abraço
.0. MrBiTs - mrbit...@gmail.com
..0 GnuPG - http://pgp.mit.edu:11371/pks/lookup?op=get&search=0x6EC818FC2B3CA5AB
000 http://www.mrbits.com.br
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.4.10 (GNU/Linux)
iQEcBAEBCAAGBQJMXCh3AAoJEG7IGPwrPKWrS6wIALM0ZdpE7biw0mjXwVrKF9Qp
NUL0pevRshO+MWjVhuw4AT/SS6jHIZEB87+o7pxKdPJPxlqFKFrw/dD9LkGOQUIe
rENnjlWGiTwskJj9I1wSjeRWVG0KLl3Rmpv8FzaZ3HS69yHiAmcJV29TQYo27cRt
0PHS5rdj2xc6qGGXHfhUKtFfHqFi1/7umLOyha1/bNam+DZiPKaljkjbaUJ3Itrr
znKbexV4cI0EwbiCfXcNJNcn3gwD1O+6ewsdCGAL4I1eL9+UcApcm0wMPiftUPRg
ZZyzuyL2XDQZJYTZ/jQZK2ZECoJyxPvyEPvJIYV2J8WwMhlRTv2s4wyGJbA81UM=
=4aRj
-----END PGP SIGNATURE-----
Mas eu nem preciso mais disso, a única necessidade que eu tenho é a de
checar se o login do usuário é válido ou não!!
Mas a questão que eu vou ver depois é se não há maneira de burlar isso, do
tipo!!!
Com o teste que eu faço:
if l.bind_s(username + DOMINIO,password)[0] == 97:
>
ele checa apenas o código de retorno foi com sucesso ( 97 ) ou não ( !97 ),
mas o problema que eu vejo é que com a função ldap.simple_bind_s(), só basta
o nome do usuário para obter sucesso na consulta, ou seja tenho que confiar
no Django para não da problema do jeito que está.
Queria colocar uma checagem mais robusta, visto que esse sistema será um
pouco crítico!
> .0. MrBiTs - mrbit...@gmail.com <mrbits.dcf%40gmail.com>
> ..0 GnuPG -
> http://pgp.mit.edu:11371/pks/lookup?op=get&search=0x6EC818FC2B3CA5AB
> 000 http://www.mrbits.com.br
>
> -----BEGIN PGP SIGNATURE-----
> Version: GnuPG v1.4.10 (GNU/Linux)
>
> iQEcBAEBCAAGBQJMXCh3AAoJEG7IGPwrPKWrS6wIALM0ZdpE7biw0mjXwVrKF9Qp
> NUL0pevRshO+MWjVhuw4AT/SS6jHIZEB87+o7pxKdPJPxlqFKFrw/dD9LkGOQUIe
> rENnjlWGiTwskJj9I1wSjeRWVG0KLl3Rmpv8FzaZ3HS69yHiAmcJV29TQYo27cRt
> 0PHS5rdj2xc6qGGXHfhUKtFfHqFi1/7umLOyha1/bNam+DZiPKaljkjbaUJ3Itrr
> znKbexV4cI0EwbiCfXcNJNcn3gwD1O+6ewsdCGAL4I1eL9+UcApcm0wMPiftUPRg
> ZZyzuyL2XDQZJYTZ/jQZK2ZECoJyxPvyEPvJIYV2J8WwMhlRTv2s4wyGJbA81UM=
> =4aRj
> -----END PGP SIGNATURE-----
>
>
--
Fagner Patrício
João Pessoa - PB
Brasil
[As partes desta mensagem que não continham texto foram removidas]
------------------------------------
On 08/06/2010 12:37 PM, Fagner Patricio wrote:
> Olá MrBiTs
>
> Mas eu nem preciso mais disso, a única necessidade que eu tenho é a de
> checar se o login do usuário é válido ou não!!
PÔ. Na sua primeira mensagem você fala que não quer a senha em plaintext no seu código, e agora diz que não precisa disso ?
>
> Mas a questão que eu vou ver depois é se não há maneira de burlar isso, do
> tipo!!!
>
> Com o teste que eu faço:
>
> if l.bind_s(username + DOMINIO,password)[0] == 97:
>>
>
> ele checa apenas o código de retorno foi com sucesso ( 97 ) ou não ( !97 ),
> mas o problema que eu vejo é que com a função ldap.simple_bind_s(), só basta
> o nome do usuário para obter sucesso na consulta, ou seja tenho que confiar
> no Django para não da problema do jeito que está.
Usamos aqui com Django (e eu acho que se avançarmos mais, vamos ter que ir discutir isso na DjangoBrasil) uma classezinha chamada
ldapBackend [1]. Essa classe vale-se do simple_bind_s e não deixa o usuário entrar se a senha estiver incorreta. Veja que os testes
são mais elaborados.
[1] http://pastebin.com/CQMwsT67
- --
Um abraço
.0. MrBiTs - mrbit...@gmail.com
..0 GnuPG - http://pgp.mit.edu:11371/pks/lookup?op=get&search=0x6EC818FC2B3CA5AB
000 http://www.mrbits.com.br
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.4.10 (GNU/Linux)
iQEcBAEBCAAGBQJMXDGOAAoJEG7IGPwrPKWrovkH/1I0KKb268DFDZrWq4orBT8P
pGXJwI38IV5scb9Em5WV1qD6w5aLgNbBy+d+bQyZP8UcpG/lT6DjG7ytv9kD76Wz
+O6O+D8xNdXF1S2uLhr0NR/ZPWNM5DBlW/9lsREUJOxcvR2fXzM/pEH5ufjr1+WE
t/On001cSChqTXV3Oq9bRxZuJiG63iQ8uzLwkqLeasXdTHuOEMBaXu4Q0BlEDNkr
SkLs8gC7EulPbaR6gqKqdl+fdMfT/VTVMzmJqz6/SP2d7dj9ScvL7e/2jVAP24zx
ZHBz2EWpB6/gmnEmQPiHSkiXNP3MPcBfH2XRM822andljyUHE5aFeRFDXDywmRI=
=uUq3
-----END PGP SIGNATURE-----
PÔ. Na sua primeira mensagem você fala que não quer a senha em plaintext no
> seu código, e agora diz que não precisa disso ?
>
Desculpa cara, mas eu estava me baseando em tudo que eu estava vendo na
internet!!
Inclusive nesse código que você enviou no link, para fazer as "Query" na
base LDAP precisa de um usuário com esse poder, e eu acho que só usuário com
permissão de administrador, por isso minha preocupação, mas quando você quer
apenas verificar se o usuário e senha informados são válidos, precisamos
apenas fazer um bind simples com o nome de usuário e senha, e checar se
obtivemos sucesso, mas veja só, eu dei uma olhada muito rápido, depois vou
analisar melhor o código e fazer alguns testes mas logo no começo ele faz o
seguinte:
conn.simple_bind_s( settings.LDAP_BASE_USER, settings.LDAP_BASE_PASS )
>
os argumentos de usuário (1º) e senha (2º) são opcionais nessa função, então
( ainda não testei ) mas essa função também funciona assim:
conn.simple_bind_s( settings.LDAP_BASE_USER)
>
mas vou executar um teste com esse código, mas só segunda-feira agora :), to
de saída, falou MrBiTs, falou galera.
> .0. MrBiTs - mrbit...@gmail.com <mrbits.dcf%40gmail.com>
> ..0 GnuPG -
> http://pgp.mit.edu:11371/pks/lookup?op=get&search=0x6EC818FC2B3CA5AB
> 000 http://www.mrbits.com.br
>
> -----BEGIN PGP SIGNATURE-----
> Version: GnuPG v1.4.10 (GNU/Linux)
>
> iQEcBAEBCAAGBQJMXDGOAAoJEG7IGPwrPKWrovkH/1I0KKb268DFDZrWq4orBT8P
> pGXJwI38IV5scb9Em5WV1qD6w5aLgNbBy+d+bQyZP8UcpG/lT6DjG7ytv9kD76Wz
> +O6O+D8xNdXF1S2uLhr0NR/ZPWNM5DBlW/9lsREUJOxcvR2fXzM/pEH5ufjr1+WE
> t/On001cSChqTXV3Oq9bRxZuJiG63iQ8uzLwkqLeasXdTHuOEMBaXu4Q0BlEDNkr
> SkLs8gC7EulPbaR6gqKqdl+fdMfT/VTVMzmJqz6/SP2d7dj9ScvL7e/2jVAP24zx
> ZHBz2EWpB6/gmnEmQPiHSkiXNP3MPcBfH2XRM822andljyUHE5aFeRFDXDywmRI=
> =uUq3
> -----END PGP SIGNATURE-----
>
>
--
Fagner Patrício
João Pessoa - PB
Brasil
[As partes desta mensagem que não continham texto foram removidas]
------------------------------------
http://200.143.198.43/svn/gads/suap/trunk/conexaoLDAP/
Em 6 de agosto de 2010 10:59, Fagner Patricio
<fagner....@gmail.com>escreveu:
>
>
> Olá MrBits
>
> Olha eu estava tentando justamente usar no Django, e consegui, e foi até
> mais fácil, olha como ficou meu código, se quiser pode sugerir que ainda
> não
> fiz uma análise de segurança nele:
>
> import ldap
> >
> > from django.conf import settings
> > from django.contrib.auth.models import User
> >
> > DOMINIO = '@dominio.com <%27%40dominio.com>'
> > SERVIDOR_LDAP = 'ldap://ip_servidor:porta'
> >
> > class LdapBackend:
> > """
> > Autenticacao de usuarios em uma base LDAP
> >
> > Usa o nome do usuario, dominio e senha, por exemplo
> >
> > usuario = 'teste'
> > dominio = '@teste.com <%27%40teste.com>'
> > senha = 'teste'
> > """
> > def authenticate(self, username=None, password=None):
> > usuario = None
> > l = ldap.initialize(SERVIDOR_LDAP)
> >
> > try:
> > if l.bind_s(username + DOMINIO,password)[0] == 97:
> > try:
> > usuario = User.objects.get(username=username)
> > except User.DoesNotExist:
> > #Criacao de um novo usuario.
> > usuario = User(username=username,
> > password=password)
> > usuario.save()
> > except ldap.INVALID_CREDENTIALS:
> > #Nao precisa tratar nenhuma execao
> > pass
> >
> > l.unbind()
> > return usuario
> >
> > def get_user(self, user_id):
> > try:
> > return User.objects.get(pk=user_id)
> > except User.DoesNotExist:
> > return None
> >
>
> Em 6 de agosto de 2010 09:46, MrBiTs <mrbit...@gmail.com<mrbits.dcf%40gmail.com>>
> > .0. MrBiTs - mrbit...@gmail.com <mrbits.dcf%40gmail.com>
> > ..0 GnuPG -
> > http://pgp.mit.edu:11371/pks/lookup?op=get&search=0x6EC818FC2B3CA5AB
> > 000 http://www.mrbits.com.br
> >
> >
> > -----BEGIN PGP SIGNATURE-----
> > Version: GnuPG v1.4.10 (GNU/Linux)
> >
> > iQEcBAEBCAAGBQJMXAQiAAoJEG7IGPwrPKWrDXAH/RY1cYn3YcJEGhyOm4R5YkvY
> > pqNYcYZ3wV4ntaCZaKJJ3FNuQe0/abEBFkNNgKOfsyuDGgdyt2TQRGUjT9gEWYSz
> > hgVpYa35TH4hV5X/VL3PHoK8W0QSm+OF24V+T5WfE5n2O5wALNNANzkMFSinHLqk
> > /H49jTsNRNnTFt/o1dnAZVj7K3VEdBg6hvQ+nyaBS/Og1yC+HxuaFRI+tDhr/DBJ
> > 6EkMylwgQcU99jpd3JM/M735Nb6Mi7bdROkxLNwURT1dVZZMRK1YzCqgcD4yZ5je
> > 6J/XVCs9RimIHxkuCamfb+yCkbiOvft31+6gbdh2aMtQZ3rR3qtQMA2f+0LtpBE=
> > =NnNV
> > -----END PGP SIGNATURE-----
> >
>
> --
> Fagner Patrício
> João Pessoa - PB
> Brasil
>
> [As partes desta mensagem que não continham texto foram removidas]
>
>
>
--
Tiago Samahá Cordeiro
Linux User #468901