Skip to content

Commit

Permalink
[WIP] auth_password_pwned: add tests
Browse files Browse the repository at this point in the history
  • Loading branch information
ap-wtioit committed Oct 4, 2024
1 parent 7486e65 commit 7c53b8b
Show file tree
Hide file tree
Showing 8 changed files with 184 additions and 1 deletion.
6 changes: 5 additions & 1 deletion auth_password_pwned/__manifest__.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,11 @@
"external_dependencies": {},
"license": "AGPL-3",
"data": [],
"assets": {},
"assets": {
'web.assets_tests': [
'auth_password_pwned/static/tests/tours/**/*',
],
},
"demo": [],
"installable": True,
}
2 changes: 2 additions & 0 deletions auth_password_pwned/controllers/__init__.py
Original file line number Diff line number Diff line change
@@ -1 +1,3 @@
from . import main
# TODO only in tests
from . import test_controllers
12 changes: 12 additions & 0 deletions auth_password_pwned/controllers/test_controllers.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
from odoo.http import Controller, route, Response

KNOWN_HASHES=[]


class TestRangeController(Controller):

@route("/auth_password_pwned/range/<string:range>", type="http", auth="none")
def test_pwned_range(self, range):
return Response("\n".join([
f"{k[len(range):]}:1" for k in KNOWN_HASHES if k.startswith(range)
]), content_type="text/plain", status=200)
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
/** @odoo-module **/

import tour from 'web_tour.tour';

/**
* This tour depends on data created by python test in charge of launching it.
* It is not intended to work when launched from interface.
* @see auth_password_pwned/tests/test_auth_password_pwned.py
*/
tour.register('auth_password_pwned/static/tests/tours/change_password_test_tour_pwned.js', {
test: true,
}, [{
content: "Open Settings",
trigger: ".o_app.o_menuitem:contains('Settings')",
}, {
content: "Open Users & Companies Dropdown",
trigger: ".o_main_navbar .o_menu_sections .o-dropdown:contains('Users & Companies') button",
}, {
content: "Open Users Lists",
trigger: ".o_main_navbar .o_menu_sections .o-dropdown:contains('Users & Companies') .dropdown-item:contains('Users')",
}, {
content: "Wait for users list to start loading",
trigger: "body:contains('Loading')",
run: () => null,
}, {
content: "Wait for loaded users list",
trigger: "body:not(:contains('Loading'))",
run: () => null,
}, {
content: "Select Demo User",
trigger: ".o_content tr:contains('Demo') .o_list_record_selector",
}, {
content: "Wait for Demo User to be selected",
trigger: ".o_content tr:contains('Demo') input[type='checkbox']:checked",
run: () => null,
}, {
content: "Open Actions Menu",
trigger: ".o_action_manager button:contains('Action')",
}, {
content: "Open Change Passwords Dialog",
trigger: ".o_action_manager .dropdown.show a.dropdown-item:contains('Change Password')",
}, {
content: "Enable input for setting Pwned Password",
trigger: ".modal-content tr:contains('demo')",
run: function(actions) {
var i=0;
while(this.$anchor.find("input[name='new_passwd']").length <= 0) {
actions.click(this.$anchor.find("div"));
i++;
if (i > 1000) assert(false);
}
}
}, {
content: "Set Pwned Password",
trigger: ".modal-content tr:contains('demo') input[name='new_passwd']",
run: "text demo",
}, {
content: "Change Password",
trigger: ".modal-footer btn-primary",
}, {
//TODO verify that alert is shown
}]);
28 changes: 28 additions & 0 deletions auth_password_pwned/static/tests/tours/login_test_tour_ok.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
/** @odoo-module **/

import tour from 'web_tour.tour';

/**
* This tour depends on data created by python test in charge of launching it.
* It is not intended to work when launched from interface.
* @see auth_password_pwned/tests/test_auth_password_pwned.py
*/
tour.register('auth_password_pwned/static/tests/tours/login_test_tour_ok.js', {
test: true,
}, [{
content: "Set login",
trigger: ".oe_login_form #login",
run: "text testuser",
}, {
content: "Set password",
trigger: ".oe_login_form #password",
run: "text testuser",
}, {
content: "Login to backend",
trigger: ".oe_login_form button[type='submit']",
}, {
content: "Check that backend is loading",
trigger: ".o_web_client",
// We are checking the error message here
run: () => null,
}]);
28 changes: 28 additions & 0 deletions auth_password_pwned/static/tests/tours/login_test_tour_pwned.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
/** @odoo-module **/

import tour from 'web_tour.tour';

/**
* This tour depends on data created by python test in charge of launching it.
* It is not intended to work when launched from interface.
* @see auth_password_pwned/tests/test_auth_password_pwned.py
*/
tour.register('auth_password_pwned/static/tests/tours/login_test_tour_pwned.js', {
test: true,
}, [{
content: "Set login",
trigger: ".oe_login_form #login",
run: "text testpassword",
}, {
content: "Set password",
trigger: ".oe_login_form #password",
run: "text testpassword",
}, {
content: "Try to login to backend",
trigger: ".oe_login_form button[type='submit']",
}, {
content: "Check that there is a warning for an unsafe password",
trigger: ".oe_login_form .alert:contains('This password is known by third parties an email has been sent with instructions how to reset it.')",
// We are checking the error message here
run: () => null,
}]);
1 change: 1 addition & 0 deletions auth_password_pwned/tests/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
from . import test_auth_password_pwned
46 changes: 46 additions & 0 deletions auth_password_pwned/tests/test_auth_password_pwned.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@

from odoo import Command
from odoo.tests.common import HttpCase, tagged
from odoo.addons.auth_password_pwned.controllers import test_controllers


@tagged('-at_install', 'post_install', 'auth_password_pwned')
class TestPwnedPasswords(HttpCase):

def setUp(self):
super(TestPwnedPasswords, self).setUp()
self.env['ir.config_parameter'].set_param("auth_password_pwned.range_url", "http://localhost:8069/auth_password_pwned/range/")
test_controllers.KNOWN_HASHES.clear()

def test_login_with_pwned_password(self):
return
self.env["res.users"].create(
{
"login": "testpassword",
"password": "testpassword",
"name": "my test user with unsafe password",
"groups_id": [Command.link(self.env.ref("base.group_user").id)],
}
)
test_controllers.KNOWN_HASHES += ["8BB6118F8FD6935AD0876A3BE34A717D32708FFD"] # sha1sum of testpassword
self.start_tour("/web/login","auth_password_pwned/static/tests/tours/login_test_tour_pwned.js", login="testpassword")

def test_login_with_ok_password(self):
return
self.env["res.users"].create(
{
"login": "testuser",
"password": "testuser",
"name": "my test user with safe password",
"groups_id": [Command.link(self.env.ref("base.group_user").id)],
}
)
self.start_tour("/web/login","auth_password_pwned/static/tests/tours/login_test_tour_ok.js", login="testuser")

def test_backend_password_pwned_backend(self):
test_controllers.KNOWN_HASHES += ["89E495E7941CF9E40E6980D14A16BF023CCD4C91"] # sha1sum of demo
self.start_tour("/web", "auth_password_pwned/static/tests/tours/change_password_test_tour_pwned.js", login="admin")

def test_backend_changing_ok_password(self):
# TODO
pass

0 comments on commit 7c53b8b

Please sign in to comment.