From da676bb797ccc3e3022e27f329463d704f130557 Mon Sep 17 00:00:00 2001 From: Mitchell Dennett Date: Thu, 20 Sep 2018 19:13:58 -0400 Subject: [PATCH 01/20] Add Verify Email --- masonite/app.py | 2 +- masonite/auth/MustVerifyEmail.py | 22 ++ masonite/commands/AuthCommand.py | 8 +- masonite/middleware/VerifyEmailMiddleware.py | 22 ++ masonite/request.py | 4 +- masonite/routes.py | 5 +- .../auth/controllers/ConfirmController.py | 46 +++ .../auth/controllers/RegisterController.py | 8 +- .../snippets/auth/templates/auth/confirm.html | 12 + .../snippets/auth/templates/auth/error.html | 12 + .../snippets/auth/templates/auth/verify.html | 12 + .../auth/templates/auth/verifymail.html | 286 ++++++++++++++++++ 12 files changed, 429 insertions(+), 10 deletions(-) create mode 100644 masonite/auth/MustVerifyEmail.py create mode 100644 masonite/middleware/VerifyEmailMiddleware.py create mode 100644 masonite/snippets/auth/controllers/ConfirmController.py create mode 100644 masonite/snippets/auth/templates/auth/confirm.html create mode 100644 masonite/snippets/auth/templates/auth/error.html create mode 100644 masonite/snippets/auth/templates/auth/verify.html create mode 100644 masonite/snippets/auth/templates/auth/verifymail.html diff --git a/masonite/app.py b/masonite/app.py index c77d288b9..8691f6c03 100644 --- a/masonite/app.py +++ b/masonite/app.py @@ -76,7 +76,7 @@ def make(self, name): """ if name in self.providers: - print('inside app') + # print('inside app') obj = self.providers[name] self.fire_hook('make', name, obj) return obj diff --git a/masonite/auth/MustVerifyEmail.py b/masonite/auth/MustVerifyEmail.py new file mode 100644 index 000000000..fc2f84739 --- /dev/null +++ b/masonite/auth/MustVerifyEmail.py @@ -0,0 +1,22 @@ +""" CSRF Protection Module """ + +import time + +from masonite.auth.Sign import Sign + + + +class MustVerifyEmail: + """Class To Verify User Email + """ + + def verify_email(self): + sign = Sign() + + token = sign.sign('{0}::{1}'.format(self.id, time.time())) + link = '{0}/email/verify/{1}'.format(request().environ['HTTP_HOST'], token) + + mail_helper().to(self.email) \ + .template('auth/verifymail', { 'name': self.name, 'email': self.email, 'link':link }) \ + .subject('Please Confirm Your Email').send() + \ No newline at end of file diff --git a/masonite/commands/AuthCommand.py b/masonite/commands/AuthCommand.py index 0e75011a8..183b7bf80 100644 --- a/masonite/commands/AuthCommand.py +++ b/masonite/commands/AuthCommand.py @@ -23,7 +23,9 @@ def handle(self): f.write("Post().route('/login', 'LoginController@store'),\n ") f.write("Get().route('/register', 'RegisterController@show'),\n ") f.write("Post().route('/register', 'RegisterController@store'),\n ") - f.write("Get().route('/home', 'HomeController@show'),\n") + f.write("Get().route('/home', 'HomeController@show'),\n ") + f.write("Get().route('/email/verify', 'ConfirmController@verify_show'),\n ") + f.write("Get().route('/email/verify/@id:signed', 'ConfirmController@confirm_email'),\n") f.write(']\n') # move controllers @@ -33,9 +35,11 @@ def handle(self): os.getcwd()+"/app/http/controllers/RegisterController.py") shutil.copyfile(module_path+"/../snippets/auth/controllers/HomeController.py", os.getcwd()+"/app/http/controllers/HomeController.py") + shutil.copyfile(module_path+"/../snippets/auth/controllers/ConfirmController.py", + os.getcwd()+"/app/http/controllers/ConfirmController.py") # move templates shutil.copytree(module_path + "/../snippets/auth/templates/auth", os.getcwd()+"/resources/templates/auth") - self.info('Project Scaffolded. You now have 4 new controllers, 5 new templates and 6 new routes') + self.info('Project Scaffolded. You now have 5 new controllers, 7 new templates and 9 new routes') diff --git a/masonite/middleware/VerifyEmailMiddleware.py b/masonite/middleware/VerifyEmailMiddleware.py new file mode 100644 index 000000000..46b3c65cb --- /dev/null +++ b/masonite/middleware/VerifyEmailMiddleware.py @@ -0,0 +1,22 @@ +''' Verify Email Middleware ''' +from masonite.exceptions import InvalidCSRFToken +from masonite.request import Request +from masonite.view import View +from jinja2 import Markup + + +class VerifyEmailMiddleware: + ''' Verify Email Middleware ''' + + def __init__(self, request: Request, csrf: Csrf, view: View): + self.request = request + self.view = view + + def before(self): + user = self.request.user() + if(user.verified_at is None){ + self.request.redirect('/email/verify') + } + + def after(self): + pass diff --git a/masonite/request.py b/masonite/request.py index f3697f364..f6f9807af 100644 --- a/masonite/request.py +++ b/masonite/request.py @@ -231,7 +231,7 @@ def _get_standardized_value(self, value): try: return int(value) - except ValueError: + except (ValueError, TypeError): pass if isinstance(value, str): @@ -718,7 +718,7 @@ def compile_route_to_url(self, route, params={}): # if the url contains a parameter variable like @id:int if '@' in url: url = url.replace('@', '').replace( - ':int', '').replace(':string', '') + ':int', '').replace(':string', '').replace(':signed', '') compiled_url += str(params[url]) + '/' else: compiled_url += url + '/' diff --git a/masonite/routes.py b/masonite/routes.py index 3f775afd9..a815bc3bc 100644 --- a/masonite/routes.py +++ b/masonite/routes.py @@ -18,7 +18,8 @@ class Route: 'int': r'(\d+)', 'integer': r'(\d+)', 'string': r'([a-zA-Z]+)', - 'default': r'([\w.-]+)' + 'default': r'([\w.-]+)', + 'signed': r'([\w\-=]+)' } def __init__(self, environ=None): @@ -362,7 +363,7 @@ def compile_route_to_regex(self, router): # append the variable name passed @(variable):int to a list url_list.append( regex_route.replace('@', '').replace( - ':int', '').replace(':string', '') + ':int', '').replace(':string', '').replace(':signed', '') ) else: regex += regex_route + r'\/' diff --git a/masonite/snippets/auth/controllers/ConfirmController.py b/masonite/snippets/auth/controllers/ConfirmController.py new file mode 100644 index 000000000..661f5686f --- /dev/null +++ b/masonite/snippets/auth/controllers/ConfirmController.py @@ -0,0 +1,46 @@ +""" The ConfirmController Module """ +import time, datetime + +from masonite.auth import Auth +from masonite.auth.Sign import Sign +from masonite.request import Request +from masonite.view import View +from masonite.auth.MustVerifyEmail import MustVerifyEmail +from app.User import User + + +class ConfirmController: + """The ConfirmController class. + """ + + def __init__(self): + """The RegisterController Constructor + """ + pass + + def verify_show(self, request: Request, view: View): + return view.render('auth/verify', {'app': request.app().make('Application'), 'Auth': Auth(request)}) + + def confirm_email(self, request: Request, view: View): + sign = Sign() + token = sign.unsign(request.param('id')) + + if token is not None: + tokenParts = token.split("::") + if len(tokenParts) > 1: + id = tokenParts[0] + user = User.find(id) + + if user.verified_at is None: + timestamp = datetime.datetime.fromtimestamp(float(tokenParts[1])) + now = datetime.datetime.now() + timestamp_plus_10 = timestamp + datetime.timedelta(minutes = 10) + + if now < timestamp_plus_10: + user.verified_at = datetime.datetime.now() + user.save() + + return view.render('auth/confirm', {'app': request.app().make('Application'), 'Auth': Auth(request)}) + + + return view.render('auth/error', {'app': request.app().make('Application'), 'Auth': Auth(request)}) \ No newline at end of file diff --git a/masonite/snippets/auth/controllers/RegisterController.py b/masonite/snippets/auth/controllers/RegisterController.py index 88a7a61d2..1a4723efb 100644 --- a/masonite/snippets/auth/controllers/RegisterController.py +++ b/masonite/snippets/auth/controllers/RegisterController.py @@ -5,7 +5,7 @@ from masonite.helpers import password as bcrypt_password from masonite.request import Request from masonite.view import View - +from masonite.auth.MustVerifyEmail import MustVerifyEmail class RegisterController: """The RegisterController class. @@ -14,7 +14,6 @@ class RegisterController: def __init__(self): """The RegisterController Constructor """ - pass def show(self, request: Request, view: View): @@ -41,12 +40,15 @@ def store(self, request: Request): password = bcrypt_password(request.input('password')) - auth.AUTH['model'].create( + user = auth.AUTH['model'].create( name=request.input('name'), password=password, email=request.input('email'), ) + if isinstance(user, MustVerifyEmail): + user.verify_email() + # Login the user if Auth(request).login(request.input(auth.AUTH['model'].__auth__), request.input('password')): # Redirect to the homepage diff --git a/masonite/snippets/auth/templates/auth/confirm.html b/masonite/snippets/auth/templates/auth/confirm.html new file mode 100644 index 000000000..e99f052b0 --- /dev/null +++ b/masonite/snippets/auth/templates/auth/confirm.html @@ -0,0 +1,12 @@ +{% extends 'auth/base.html' %} + +{% block content %} +
+
+
Verify
+
+ Confirmed +
+
+
+{% endblock %} \ No newline at end of file diff --git a/masonite/snippets/auth/templates/auth/error.html b/masonite/snippets/auth/templates/auth/error.html new file mode 100644 index 000000000..f26e09ed8 --- /dev/null +++ b/masonite/snippets/auth/templates/auth/error.html @@ -0,0 +1,12 @@ +{% extends 'auth/base.html' %} + +{% block content %} +
+
+
Verify
+
+ Errored +
+
+
+{% endblock %} \ No newline at end of file diff --git a/masonite/snippets/auth/templates/auth/verify.html b/masonite/snippets/auth/templates/auth/verify.html new file mode 100644 index 000000000..c0f4f88ab --- /dev/null +++ b/masonite/snippets/auth/templates/auth/verify.html @@ -0,0 +1,12 @@ +{% extends 'auth/base.html' %} + +{% block content %} +
+
+
Verify
+
+ Must Verify +
+
+
+{% endblock %} \ No newline at end of file diff --git a/masonite/snippets/auth/templates/auth/verifymail.html b/masonite/snippets/auth/templates/auth/verifymail.html new file mode 100644 index 000000000..92b3c4d2a --- /dev/null +++ b/masonite/snippets/auth/templates/auth/verifymail.html @@ -0,0 +1,286 @@ + + + + + + + Document + + + + + + + + + + +
+
+ + + + +
+ + + + + + + + + + + + + +
+ Please confirm your email address by clicking the link below. +
+ We may need to send you critical information about our service and it is important that we have an accurate email address. +
+ Confirm Email Address +
+ — Masonite Framework +
+
+ +
+
+ + \ No newline at end of file From d0b01618a19b2660f9b5a1086e3414ff5d9ebb80 Mon Sep 17 00:00:00 2001 From: Mitchell Dennett Date: Thu, 20 Sep 2018 19:35:31 -0400 Subject: [PATCH 02/20] Resolve mail and request in MustVerifyEmail.py --- masonite/auth/MustVerifyEmail.py | 11 ++++++----- .../snippets/auth/controllers/RegisterController.py | 2 +- 2 files changed, 7 insertions(+), 6 deletions(-) diff --git a/masonite/auth/MustVerifyEmail.py b/masonite/auth/MustVerifyEmail.py index fc2f84739..5c4c9f507 100644 --- a/masonite/auth/MustVerifyEmail.py +++ b/masonite/auth/MustVerifyEmail.py @@ -1,22 +1,23 @@ -""" CSRF Protection Module """ +""" Verify Email Module """ import time from masonite.auth.Sign import Sign - +from masonite.managers import MailManager +from masonite.request import Request class MustVerifyEmail: """Class To Verify User Email """ - def verify_email(self): + def verify_email(self, mail: MailManager, request: Request): sign = Sign() token = sign.sign('{0}::{1}'.format(self.id, time.time())) - link = '{0}/email/verify/{1}'.format(request().environ['HTTP_HOST'], token) + link = '{0}/email/verify/{1}'.format(request.environ['HTTP_HOST'], token) - mail_helper().to(self.email) \ + mail.to(self.email) \ .template('auth/verifymail', { 'name': self.name, 'email': self.email, 'link':link }) \ .subject('Please Confirm Your Email').send() \ No newline at end of file diff --git a/masonite/snippets/auth/controllers/RegisterController.py b/masonite/snippets/auth/controllers/RegisterController.py index 1a4723efb..a8f1b433a 100644 --- a/masonite/snippets/auth/controllers/RegisterController.py +++ b/masonite/snippets/auth/controllers/RegisterController.py @@ -47,7 +47,7 @@ def store(self, request: Request): ) if isinstance(user, MustVerifyEmail): - user.verify_email() + request.app().resolve(user.verify_email) # Login the user if Auth(request).login(request.input(auth.AUTH['model'].__auth__), request.input('password')): From 01ed8fe9b65d501e43c2448d414af5a30cb73256 Mon Sep 17 00:00:00 2001 From: Mitchell Dennett Date: Thu, 20 Sep 2018 19:45:06 -0400 Subject: [PATCH 03/20] Add docstrings to ConfirmController --- .../auth/controllers/ConfirmController.py | 20 +++++++++++++++++++ 1 file changed, 20 insertions(+) diff --git a/masonite/snippets/auth/controllers/ConfirmController.py b/masonite/snippets/auth/controllers/ConfirmController.py index 661f5686f..a96696338 100644 --- a/masonite/snippets/auth/controllers/ConfirmController.py +++ b/masonite/snippets/auth/controllers/ConfirmController.py @@ -19,9 +19,29 @@ def __init__(self): pass def verify_show(self, request: Request, view: View): + """Show the Verify Email page for unverified users. + + Arguments: + Request {masonite.request.request} -- The Masonite request class. + Request {masonite.view.view} -- The Masonite view class. + + Returns: + [type] -- [description] + """ + return view.render('auth/verify', {'app': request.app().make('Application'), 'Auth': Auth(request)}) def confirm_email(self, request: Request, view: View): + """Confirm User email and show the correct response. + + Arguments: + Request {masonite.request.request} -- The Masonite request class. + Request {masonite.view.view} -- The Masonite view class. + + Returns: + [type] -- [description] + """ + sign = Sign() token = sign.unsign(request.param('id')) From bff1c4e3bd98be60ed52d861d87107a5ddf6b201 Mon Sep 17 00:00:00 2001 From: Mitchell Dennett Date: Thu, 20 Sep 2018 19:54:47 -0400 Subject: [PATCH 04/20] Clean up imports and edit view templates --- masonite/middleware/VerifyEmailMiddleware.py | 7 +------ masonite/snippets/auth/controllers/ConfirmController.py | 2 +- masonite/snippets/auth/templates/auth/confirm.html | 4 ++-- masonite/snippets/auth/templates/auth/error.html | 4 ++-- 4 files changed, 6 insertions(+), 11 deletions(-) diff --git a/masonite/middleware/VerifyEmailMiddleware.py b/masonite/middleware/VerifyEmailMiddleware.py index 46b3c65cb..de7a81021 100644 --- a/masonite/middleware/VerifyEmailMiddleware.py +++ b/masonite/middleware/VerifyEmailMiddleware.py @@ -1,16 +1,11 @@ ''' Verify Email Middleware ''' -from masonite.exceptions import InvalidCSRFToken from masonite.request import Request -from masonite.view import View -from jinja2 import Markup - class VerifyEmailMiddleware: ''' Verify Email Middleware ''' - def __init__(self, request: Request, csrf: Csrf, view: View): + def __init__(self, request: Request): self.request = request - self.view = view def before(self): user = self.request.user() diff --git a/masonite/snippets/auth/controllers/ConfirmController.py b/masonite/snippets/auth/controllers/ConfirmController.py index a96696338..502685341 100644 --- a/masonite/snippets/auth/controllers/ConfirmController.py +++ b/masonite/snippets/auth/controllers/ConfirmController.py @@ -14,7 +14,7 @@ class ConfirmController: """ def __init__(self): - """The RegisterController Constructor + """The ConfirmController Constructor """ pass diff --git a/masonite/snippets/auth/templates/auth/confirm.html b/masonite/snippets/auth/templates/auth/confirm.html index e99f052b0..301315126 100644 --- a/masonite/snippets/auth/templates/auth/confirm.html +++ b/masonite/snippets/auth/templates/auth/confirm.html @@ -3,9 +3,9 @@ {% block content %}
-
Verify
+
Verified
- Confirmed + Thank you for confirming your email. Click here to go to the home page.
diff --git a/masonite/snippets/auth/templates/auth/error.html b/masonite/snippets/auth/templates/auth/error.html index f26e09ed8..799602c92 100644 --- a/masonite/snippets/auth/templates/auth/error.html +++ b/masonite/snippets/auth/templates/auth/error.html @@ -3,9 +3,9 @@ {% block content %}
-
Verify
+
Verifying Error
- Errored + Confirming email failed. Click here to go home
From ce91f15af7d59c19a5c37f5b3c46976f7c437160 Mon Sep 17 00:00:00 2001 From: Mitchell Dennett Date: Thu, 20 Sep 2018 20:19:00 -0400 Subject: [PATCH 05/20] Resend Email Verification view --- .../snippets/auth/controllers/ConfirmController.py | 11 ++++++++++- masonite/snippets/auth/templates/auth/verify.html | 3 ++- 2 files changed, 12 insertions(+), 2 deletions(-) diff --git a/masonite/snippets/auth/controllers/ConfirmController.py b/masonite/snippets/auth/controllers/ConfirmController.py index 502685341..0fecaa3c8 100644 --- a/masonite/snippets/auth/controllers/ConfirmController.py +++ b/masonite/snippets/auth/controllers/ConfirmController.py @@ -63,4 +63,13 @@ def confirm_email(self, request: Request, view: View): return view.render('auth/confirm', {'app': request.app().make('Application'), 'Auth': Auth(request)}) - return view.render('auth/error', {'app': request.app().make('Application'), 'Auth': Auth(request)}) \ No newline at end of file + return view.render('auth/error', {'app': request.app().make('Application'), 'Auth': Auth(request)}) + + def send_verify_email(self, request: Request): + user = request.user() + + if isinstance(user, MustVerifyEmail): + request.app().resolve(user.verify_email) + + return request.redirect('/home') + diff --git a/masonite/snippets/auth/templates/auth/verify.html b/masonite/snippets/auth/templates/auth/verify.html index c0f4f88ab..6d3dca6c3 100644 --- a/masonite/snippets/auth/templates/auth/verify.html +++ b/masonite/snippets/auth/templates/auth/verify.html @@ -5,7 +5,8 @@
Verify
- Must Verify + Please check your email and follow the link to verify your email. If + you need us to resend the email. Click here
From e564af625a4fe81a94e9839b4636e678c62fbe6d Mon Sep 17 00:00:00 2001 From: Mitchell Dennett Date: Mon, 24 Sep 2018 13:10:04 -0400 Subject: [PATCH 06/20] Get Driver from Manager to send mail --- masonite/auth/MustVerifyEmail.py | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/masonite/auth/MustVerifyEmail.py b/masonite/auth/MustVerifyEmail.py index 5c4c9f507..d4a9f7684 100644 --- a/masonite/auth/MustVerifyEmail.py +++ b/masonite/auth/MustVerifyEmail.py @@ -11,7 +11,8 @@ class MustVerifyEmail: """Class To Verify User Email """ - def verify_email(self, mail: MailManager, request: Request): + def verify_email(self, mail_manager: MailManager, request: Request): + mail = mail_manager.helper() sign = Sign() token = sign.sign('{0}::{1}'.format(self.id, time.time())) From 97f3728f9ca9aae132fc10f340fad07a8621f2e4 Mon Sep 17 00:00:00 2001 From: Joseph Mancuso Date: Mon, 24 Sep 2018 22:27:15 -0400 Subject: [PATCH 07/20] added match routes --- app/http/controllers/ControllerTest.py | 2 +- masonite/helpers/routes.py | 16 ++++++++++++++++ masonite/providers/RouteProvider.py | 16 ++++++++-------- masonite/routes.py | 12 ++++++++++++ tests/providers/test_route_provider.py | 14 +++++++++++++- tests/test_routes.py | 4 +++- 6 files changed, 53 insertions(+), 11 deletions(-) diff --git a/app/http/controllers/ControllerTest.py b/app/http/controllers/ControllerTest.py index e3290b1c9..58c3c7649 100644 --- a/app/http/controllers/ControllerTest.py +++ b/app/http/controllers/ControllerTest.py @@ -13,7 +13,7 @@ def test(self): return 'test' def returns_a_view(self, view: View): - return View('index') + return view.render('index') def returns_a_dict(self): return {'id': 1} diff --git a/masonite/helpers/routes.py b/masonite/helpers/routes.py index 28b9ab73e..295a87c31 100644 --- a/masonite/helpers/routes.py +++ b/masonite/helpers/routes.py @@ -39,6 +39,22 @@ def get(url, controller): return Get().route(url, controller) +def match(method_type, url, controller): + """Shortcut for Match HTTP class. + + Arguments: + method_type {list} -- A list of the method types you want to accept + url {string} -- The url you want to use for the route + controller {string|object} -- This can be a string controller or a normal object controller + + Returns: + masonite.routes.Get -- The Masonite Get class. + """ + + from masonite.routes import Match + + return Match(method_type).route(url, controller) + def post(url, controller): """Shortcut for Post HTTP class. diff --git a/masonite/providers/RouteProvider.py b/masonite/providers/RouteProvider.py index fc55d59f2..e73b75419 100644 --- a/masonite/providers/RouteProvider.py +++ b/masonite/providers/RouteProvider.py @@ -30,7 +30,7 @@ def boot(self, router: Route, request: Request): one match. Routes are executed on a first come, first serve basis """ - if matchurl.match(router.url) and route.method_type == self.app.make('Environ')['REQUEST_METHOD']: + if matchurl.match(router.url) and request.get_request_method() in route.method_type: route.load_request(request) if request.has_subdomain(): # Check if the subdomain matches the routes domain @@ -53,12 +53,6 @@ def boot(self, router: Route, request: Request): except AttributeError: pass - """Execute Before Middleware - This is middleware that contains a before method. - """ - - route.run_middleware('before') - """Excute HTTP before middleware Only those middleware that have a "before" method are ran. """ @@ -70,9 +64,15 @@ def boot(self, router: Route, request: Request): if hasattr(located_middleware, 'before'): located_middleware.before() + """Execute Before Middleware + This is middleware that contains a before method. + """ + + route.run_middleware('before') + # Show a helper in the terminal of which route has been visited if self.app.make('Application').DEBUG: - print(route.method_type + ' Route: ' + router.url) + print(request.get_request_method() + ' Route: ' + router.url) if request.get_status_code() == '404 Not Found': request.status(200) diff --git a/masonite/routes.py b/masonite/routes.py index 93fd9f543..1b76aafb9 100644 --- a/masonite/routes.py +++ b/masonite/routes.py @@ -393,6 +393,18 @@ def __init__(self): self.list_middleware = [] +class Match(BaseHttpRoute): + """Class for specifying POST requests + """ + + def __init__(self, method_type=['GET']): + """Post constructor + """ + + self.method_type = method_type + self.list_middleware = [] + + class Put(BaseHttpRoute): """Class for specifying PUT requests """ diff --git a/tests/providers/test_route_provider.py b/tests/providers/test_route_provider.py index 129256810..f03381a7c 100644 --- a/tests/providers/test_route_provider.py +++ b/tests/providers/test_route_provider.py @@ -4,7 +4,7 @@ from masonite.helpers.routes import get from masonite.providers.RouteProvider import RouteProvider from masonite.request import Request -from masonite.routes import Get, Route +from masonite.routes import Get, Route, Match from masonite.testsuite.TestSuite import generate_wsgi from masonite.view import View @@ -52,6 +52,18 @@ def test_controller_does_not_return_with_non_matching_end_slash(self): assert self.app.make('Response') == 'Route not found. Error 404' + def test_match_route_returns_controller(self): + self.app.make('Route').url = '/view' + self.app.bind( + 'WebRoutes', [Match(['GET', 'POST']).route('/view', ControllerTest.returns_a_view)]) + + self.provider.boot( + self.app.make('Route'), + self.app.make('Request') + ) + + assert self.app.make('Response') == 'hey' + def test_provider_runs_through_routes(self): self.app.make('Route').url = '/test' self.app.bind('WebRoutes', [get('/test', ControllerTest.show)]) diff --git a/tests/test_routes.py b/tests/test_routes.py index d3d965869..c99daef6c 100644 --- a/tests/test_routes.py +++ b/tests/test_routes.py @@ -1,6 +1,6 @@ from masonite.routes import Route from masonite.request import Request -from masonite.routes import Get, Post, Put, Patch, Delete, RouteGroup +from masonite.routes import Get, Post, Put, Patch, Delete, RouteGroup, Match from masonite.helpers.routes import group, flatten_routes from masonite.testsuite.TestSuite import generate_wsgi from masonite.exceptions import InvalidRouteCompileException @@ -67,6 +67,8 @@ def test_route_gets_controllers(self): def test_route_doesnt_break_on_incorrect_controller(self): assert Get().route('test/url', 'BreakController@show') + def test_route_can_have_multiple_routes(self): + assert Match(['GET', 'POST']).route('test/url', 'TestController@show').method_type == ['GET', 'POST'] def test_group_route(self): routes = group('/example', [ From cb224c69d6416ac7986cc9a68a646b7b04acaa14 Mon Sep 17 00:00:00 2001 From: Joseph Mancuso Date: Mon, 24 Sep 2018 23:07:36 -0400 Subject: [PATCH 08/20] commented out unit test --- tests/testing/test_unit_test.py | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/tests/testing/test_unit_test.py b/tests/testing/test_unit_test.py index ef8b6fbc3..07f53a7e3 100644 --- a/tests/testing/test_unit_test.py +++ b/tests/testing/test_unit_test.py @@ -31,9 +31,9 @@ def test_unit_test_has_route_middleware(self): def test_unit_test_has_controller(self): assert self.route('/testing').has_controller(ControllerTest) - def test_user_can_be_loaded(self): - assert not self.route('/unit/test').user(None).can_view() - assert self.route('/unit/test').user(MockUser).can_view() + # def test_user_can_be_loaded(self): + # assert not self.route('/unit/test').user(None).can_view() + # assert self.route('/unit/test').user(MockUser).can_view() def test_view_contains(self): assert self.route('/test/route').contains('test') From 02a5476097b54ffd455574c95e838b071fff685a Mon Sep 17 00:00:00 2001 From: Joseph Mancuso Date: Mon, 24 Sep 2018 23:23:20 -0400 Subject: [PATCH 09/20] fixed unit test --- masonite/testing/MockRoute.py | 8 +++++--- tests/testing/test_unit_test.py | 6 +++--- 2 files changed, 8 insertions(+), 6 deletions(-) diff --git a/masonite/testing/MockRoute.py b/masonite/testing/MockRoute.py index 891a4d9f4..090782047 100644 --- a/masonite/testing/MockRoute.py +++ b/masonite/testing/MockRoute.py @@ -1,7 +1,9 @@ -from masonite.testsuite import generate_wsgi, TestSuite -from masonite.app import App import io +from masonite.app import App +from masonite.request import Request +from masonite.testsuite import TestSuite, generate_wsgi + class MockRoute: @@ -50,7 +52,7 @@ def can_view(self): def user(self, obj): self._user = obj - self.container.on_bind('Request', self._bind_user_to_request) + self.container.on_resolve(Request, self._bind_user_to_request) return self def is_post(self): diff --git a/tests/testing/test_unit_test.py b/tests/testing/test_unit_test.py index 07f53a7e3..ef8b6fbc3 100644 --- a/tests/testing/test_unit_test.py +++ b/tests/testing/test_unit_test.py @@ -31,9 +31,9 @@ def test_unit_test_has_route_middleware(self): def test_unit_test_has_controller(self): assert self.route('/testing').has_controller(ControllerTest) - # def test_user_can_be_loaded(self): - # assert not self.route('/unit/test').user(None).can_view() - # assert self.route('/unit/test').user(MockUser).can_view() + def test_user_can_be_loaded(self): + assert not self.route('/unit/test').user(None).can_view() + assert self.route('/unit/test').user(MockUser).can_view() def test_view_contains(self): assert self.route('/test/route').contains('test') From e94302426b43d83048a67d7fdb03a30e51a225ca Mon Sep 17 00:00:00 2001 From: Mitchell Dennett Date: Tue, 25 Sep 2018 19:32:18 -0400 Subject: [PATCH 10/20] Added MustVeriftAuth to init.py --- masonite/auth/__init__.py | 1 + masonite/snippets/auth/controllers/RegisterController.py | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/masonite/auth/__init__.py b/masonite/auth/__init__.py index af4ad94b5..21f3ca23f 100644 --- a/masonite/auth/__init__.py +++ b/masonite/auth/__init__.py @@ -1,3 +1,4 @@ from .Auth import Auth from .Csrf import Csrf from .Sign import Sign +from .MustVerifyEmail import MustVerifyEmail diff --git a/masonite/snippets/auth/controllers/RegisterController.py b/masonite/snippets/auth/controllers/RegisterController.py index a8f1b433a..6513cb7e5 100644 --- a/masonite/snippets/auth/controllers/RegisterController.py +++ b/masonite/snippets/auth/controllers/RegisterController.py @@ -5,7 +5,7 @@ from masonite.helpers import password as bcrypt_password from masonite.request import Request from masonite.view import View -from masonite.auth.MustVerifyEmail import MustVerifyEmail +from masonite.auth import MustVerifyEmail class RegisterController: """The RegisterController class. From c86159919e58a782a7966dabdcb4fdcdac9d997c Mon Sep 17 00:00:00 2001 From: Mitchell Dennett Date: Tue, 25 Sep 2018 19:36:12 -0400 Subject: [PATCH 11/20] Removed Verify Middleware from core --- masonite/middleware/VerifyEmailMiddleware.py | 17 ----------------- 1 file changed, 17 deletions(-) delete mode 100644 masonite/middleware/VerifyEmailMiddleware.py diff --git a/masonite/middleware/VerifyEmailMiddleware.py b/masonite/middleware/VerifyEmailMiddleware.py deleted file mode 100644 index de7a81021..000000000 --- a/masonite/middleware/VerifyEmailMiddleware.py +++ /dev/null @@ -1,17 +0,0 @@ -''' Verify Email Middleware ''' -from masonite.request import Request - -class VerifyEmailMiddleware: - ''' Verify Email Middleware ''' - - def __init__(self, request: Request): - self.request = request - - def before(self): - user = self.request.user() - if(user.verified_at is None){ - self.request.redirect('/email/verify') - } - - def after(self): - pass From f3bc01db829156c8dbec85e3ff77cec2d1ef9396 Mon Sep 17 00:00:00 2001 From: Mitchell Dennett Date: Tue, 25 Sep 2018 19:44:12 -0400 Subject: [PATCH 12/20] Fixing formatting errors --- masonite/commands/AuthCommand.py | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/masonite/commands/AuthCommand.py b/masonite/commands/AuthCommand.py index 0d19582d1..d5062a314 100644 --- a/masonite/commands/AuthCommand.py +++ b/masonite/commands/AuthCommand.py @@ -30,14 +30,14 @@ def handle(self): f.write(']\n') # move controllers - shutil.copyfile(module_path+"/../snippets/auth/controllers/LoginController.py", - os.getcwd()+"/app/http/controllers/LoginController.py") - shutil.copyfile(module_path+"/../snippets/auth/controllers/RegisterController.py", - os.getcwd()+"/app/http/controllers/RegisterController.py") - shutil.copyfile(module_path+"/../snippets/auth/controllers/HomeController.py", - os.getcwd()+"/app/http/controllers/HomeController.py") - shutil.copyfile(module_path+"/../snippets/auth/controllers/ConfirmController.py", - os.getcwd()+"/app/http/controllers/ConfirmController.py") + shutil.copyfile(module_path + "/../snippets/auth/controllers/LoginController.py", + os.getcwd() + "/app/http/controllers/LoginController.py") + shutil.copyfile(module_path + "/../snippets/auth/controllers/RegisterController.py", + os.getcwd() + "/app/http/controllers/RegisterController.py") + shutil.copyfile(module_path + "/../snippets/auth/controllers/HomeController.py", + os.getcwd() + "/app/http/controllers/HomeController.py") + shutil.copyfile(module_path + "/../snippets/auth/controllers/ConfirmController.py", + os.getcwd() + "/app/http/controllers/ConfirmController.py") # move templates shutil.copytree(module_path + "/../snippets/auth/templates/auth", From d91d92abdbb6ee3ef68c8f7f31a19c0b3abd3e35 Mon Sep 17 00:00:00 2001 From: Mitchell Dennett Date: Wed, 26 Sep 2018 16:43:41 -0400 Subject: [PATCH 13/20] Fixed Flake8 style errors --- masonite/auth/MustVerifyEmail.py | 5 ++--- .../auth/controllers/ConfirmController.py | 21 +++++++++---------- .../auth/controllers/RegisterController.py | 1 + 3 files changed, 13 insertions(+), 14 deletions(-) diff --git a/masonite/auth/MustVerifyEmail.py b/masonite/auth/MustVerifyEmail.py index d4a9f7684..119e6eced 100644 --- a/masonite/auth/MustVerifyEmail.py +++ b/masonite/auth/MustVerifyEmail.py @@ -19,6 +19,5 @@ def verify_email(self, mail_manager: MailManager, request: Request): link = '{0}/email/verify/{1}'.format(request.environ['HTTP_HOST'], token) mail.to(self.email) \ - .template('auth/verifymail', { 'name': self.name, 'email': self.email, 'link':link }) \ - .subject('Please Confirm Your Email').send() - \ No newline at end of file + .template('auth/verifymail', {'name': self.name, 'email': self.email, 'link': link}) \ + .subject('Please Confirm Your Email').send() diff --git a/masonite/snippets/auth/controllers/ConfirmController.py b/masonite/snippets/auth/controllers/ConfirmController.py index 0fecaa3c8..3045f3bfd 100644 --- a/masonite/snippets/auth/controllers/ConfirmController.py +++ b/masonite/snippets/auth/controllers/ConfirmController.py @@ -1,5 +1,6 @@ """ The ConfirmController Module """ -import time, datetime +import time +import datetime from masonite.auth import Auth from masonite.auth.Sign import Sign @@ -50,26 +51,24 @@ def confirm_email(self, request: Request, view: View): if len(tokenParts) > 1: id = tokenParts[0] user = User.find(id) - + if user.verified_at is None: timestamp = datetime.datetime.fromtimestamp(float(tokenParts[1])) now = datetime.datetime.now() - timestamp_plus_10 = timestamp + datetime.timedelta(minutes = 10) - + timestamp_plus_10 = timestamp + datetime.timedelta(minutes=10) + if now < timestamp_plus_10: user.verified_at = datetime.datetime.now() user.save() return view.render('auth/confirm', {'app': request.app().make('Application'), 'Auth': Auth(request)}) - return view.render('auth/error', {'app': request.app().make('Application'), 'Auth': Auth(request)}) - def send_verify_email(self, request: Request): - user = request.user() - - if isinstance(user, MustVerifyEmail): - request.app().resolve(user.verify_email) + def send_verify_email(self, request: Request): + user = request.user() - return request.redirect('/home') + if isinstance(user, MustVerifyEmail): + request.app().resolve(user.verify_email) + return request.redirect('/home') \ No newline at end of file diff --git a/masonite/snippets/auth/controllers/RegisterController.py b/masonite/snippets/auth/controllers/RegisterController.py index 6513cb7e5..dc8c50470 100644 --- a/masonite/snippets/auth/controllers/RegisterController.py +++ b/masonite/snippets/auth/controllers/RegisterController.py @@ -7,6 +7,7 @@ from masonite.view import View from masonite.auth import MustVerifyEmail + class RegisterController: """The RegisterController class. """ From 13f153539da86c750a994226a2929350105a188f Mon Sep 17 00:00:00 2001 From: Mitchell Dennett Date: Wed, 26 Sep 2018 16:49:30 -0400 Subject: [PATCH 14/20] Fixed no line at end off file --- masonite/snippets/auth/controllers/ConfirmController.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/masonite/snippets/auth/controllers/ConfirmController.py b/masonite/snippets/auth/controllers/ConfirmController.py index 3045f3bfd..7858fb520 100644 --- a/masonite/snippets/auth/controllers/ConfirmController.py +++ b/masonite/snippets/auth/controllers/ConfirmController.py @@ -71,4 +71,4 @@ def send_verify_email(self, request: Request): if isinstance(user, MustVerifyEmail): request.app().resolve(user.verify_email) - return request.redirect('/home') \ No newline at end of file + return request.redirect('/home') From 08b553d496e34e017d77a80d73e6b25196fedbf0 Mon Sep 17 00:00:00 2001 From: Mitchell Dennett Date: Wed, 26 Sep 2018 20:15:42 -0400 Subject: [PATCH 15/20] Resolved error in Travis build --- masonite/auth/MustVerifyEmail.py | 4 +--- masonite/snippets/auth/controllers/ConfirmController.py | 2 +- masonite/snippets/auth/controllers/RegisterController.py | 7 ++++--- 3 files changed, 6 insertions(+), 7 deletions(-) diff --git a/masonite/auth/MustVerifyEmail.py b/masonite/auth/MustVerifyEmail.py index 119e6eced..ea26af3a4 100644 --- a/masonite/auth/MustVerifyEmail.py +++ b/masonite/auth/MustVerifyEmail.py @@ -3,15 +3,13 @@ import time from masonite.auth.Sign import Sign -from masonite.managers import MailManager -from masonite.request import Request class MustVerifyEmail: """Class To Verify User Email """ - def verify_email(self, mail_manager: MailManager, request: Request): + def verify_email(self, mail_manager, request): mail = mail_manager.helper() sign = Sign() diff --git a/masonite/snippets/auth/controllers/ConfirmController.py b/masonite/snippets/auth/controllers/ConfirmController.py index 7858fb520..91474e1a3 100644 --- a/masonite/snippets/auth/controllers/ConfirmController.py +++ b/masonite/snippets/auth/controllers/ConfirmController.py @@ -6,7 +6,7 @@ from masonite.auth.Sign import Sign from masonite.request import Request from masonite.view import View -from masonite.auth.MustVerifyEmail import MustVerifyEmail +from masonite.auth import MustVerifyEmail from app.User import User diff --git a/masonite/snippets/auth/controllers/RegisterController.py b/masonite/snippets/auth/controllers/RegisterController.py index dc8c50470..a5c0c4fc8 100644 --- a/masonite/snippets/auth/controllers/RegisterController.py +++ b/masonite/snippets/auth/controllers/RegisterController.py @@ -5,7 +5,7 @@ from masonite.helpers import password as bcrypt_password from masonite.request import Request from masonite.view import View -from masonite.auth import MustVerifyEmail +from masonite.managers import MailManager class RegisterController: @@ -29,7 +29,7 @@ def show(self, request: Request, view: View): return view.render('auth/register', {'app': request.app().make('Application'), 'Auth': Auth(request)}) - def store(self, request: Request): + def store(self, request: Request, mail_manager: MailManager): """Register the user with the database. Arguments: @@ -38,6 +38,7 @@ def store(self, request: Request): Returns: masonite.request.Request -- The Masonite request class. """ + from masonite.auth.MustVerifyEmail import MustVerifyEmail password = bcrypt_password(request.input('password')) @@ -48,7 +49,7 @@ def store(self, request: Request): ) if isinstance(user, MustVerifyEmail): - request.app().resolve(user.verify_email) + user.verify_email(mail_manager, request) # Login the user if Auth(request).login(request.input(auth.AUTH['model'].__auth__), request.input('password')): From b4aa363dda773b63f697f265d0a93c6597d286f6 Mon Sep 17 00:00:00 2001 From: Mitchell Dennett Date: Wed, 26 Sep 2018 20:17:31 -0400 Subject: [PATCH 16/20] Added Import back to top --- masonite/snippets/auth/controllers/RegisterController.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/masonite/snippets/auth/controllers/RegisterController.py b/masonite/snippets/auth/controllers/RegisterController.py index a5c0c4fc8..77849caa9 100644 --- a/masonite/snippets/auth/controllers/RegisterController.py +++ b/masonite/snippets/auth/controllers/RegisterController.py @@ -5,6 +5,7 @@ from masonite.helpers import password as bcrypt_password from masonite.request import Request from masonite.view import View +from masonite.auth import MustVerifyEmail from masonite.managers import MailManager @@ -38,7 +39,6 @@ def store(self, request: Request, mail_manager: MailManager): Returns: masonite.request.Request -- The Masonite request class. """ - from masonite.auth.MustVerifyEmail import MustVerifyEmail password = bcrypt_password(request.input('password')) From 5de8998629e534f5f6098f4ca8fc51e52ccaa0fa Mon Sep 17 00:00:00 2001 From: Mitchell Dennett Date: Thu, 27 Sep 2018 19:49:15 -0400 Subject: [PATCH 17/20] Tests for Verify Email Feature --- .../auth/controllers/ConfirmController.py | 14 +++- resources/templates/auth/confirm.html | 1 + resources/templates/auth/error.html | 1 + tests/test_auth.py | 84 +++++++++++++++++++ 4 files changed, 99 insertions(+), 1 deletion(-) create mode 100644 resources/templates/auth/confirm.html create mode 100644 resources/templates/auth/error.html diff --git a/masonite/snippets/auth/controllers/ConfirmController.py b/masonite/snippets/auth/controllers/ConfirmController.py index 91474e1a3..9e2d2a4df 100644 --- a/masonite/snippets/auth/controllers/ConfirmController.py +++ b/masonite/snippets/auth/controllers/ConfirmController.py @@ -50,7 +50,7 @@ def confirm_email(self, request: Request, view: View): tokenParts = token.split("::") if len(tokenParts) > 1: id = tokenParts[0] - user = User.find(id) + user = self.get_user(id) if user.verified_at is None: timestamp = datetime.datetime.fromtimestamp(float(tokenParts[1])) @@ -65,6 +65,18 @@ def confirm_email(self, request: Request, view: View): return view.render('auth/error', {'app': request.app().make('Application'), 'Auth': Auth(request)}) + def get_user(self, id): + """Get the user from the database + + Arguments: + id {str} -- The user id + + Returns: + [User] -- [User model] + """ + + return User.find(id) + def send_verify_email(self, request: Request): user = request.user() diff --git a/resources/templates/auth/confirm.html b/resources/templates/auth/confirm.html new file mode 100644 index 000000000..9b29cca86 --- /dev/null +++ b/resources/templates/auth/confirm.html @@ -0,0 +1 @@ +confirm \ No newline at end of file diff --git a/resources/templates/auth/error.html b/resources/templates/auth/error.html new file mode 100644 index 000000000..760589cb5 --- /dev/null +++ b/resources/templates/auth/error.html @@ -0,0 +1 @@ +error \ No newline at end of file diff --git a/tests/test_auth.py b/tests/test_auth.py index ba6ebab03..f04e8191b 100644 --- a/tests/test_auth.py +++ b/tests/test_auth.py @@ -1,6 +1,16 @@ +import time +import datetime + +from masonite.view import View from masonite.auth import Auth from masonite.request import Request from masonite.testsuite.TestSuite import generate_wsgi +from masonite.auth import MustVerifyEmail +from masonite.app import App +from masonite.auth import Sign +from masonite.helpers.routes import get +from masonite.snippets.auth.controllers.ConfirmController import ConfirmController +from config import application class MockUser(): @@ -25,11 +35,24 @@ def find(self, id): return False +class MockVerifyUser(MockUser, MustVerifyEmail): + verified_at = None + pass + + class TestAuth: def setup_method(self): + self.container = App() + self.app = self.container + view = View(self.container) self.request = Request(generate_wsgi()) + self.auth = Auth(self.request, MockUser()) + self.container.bind('View', view.render) + self.container.bind('ViewClass', view) + self.app.bind('Application', application) + def reset_method(self): self.auth = Auth(self.request, MockUser()) def test_auth(self): @@ -67,3 +90,64 @@ def test_login_by_id(self): def test_login_once_does_not_set_cookie(self): assert isinstance(self.auth.once().login_by_id(1), MockUser) assert self.request.get_cookie('token') is None + + def test_user_is_mustverify_instance(self): + self.auth = Auth(self.request, MockVerifyUser()) + assert isinstance(self.auth.once().login_by_id(1), MustVerifyEmail) + self.reset_method() + assert not isinstance(self.auth.once().login_by_id(1), MustVerifyEmail) + + def get_user(self, id): + return MockVerifyUser() + + def test_confirm_controller_success(self): + self.auth = Auth(self.request, MockVerifyUser()) + params = {'id': Sign().sign('{0}::{1}'.format(1, time.time()))} + self.request.set_params(params) + user = self.auth.once().login_by_id(1) + self.request.set_user(user) + + self.app.bind('Request', self.request) + self.app.make('Request').load_app(self.app) + + # Create the route + route = get('/email/verify/@id', ConfirmController.confirm_email) + + ConfirmController.get_user = self.get_user + + # Resolve the controller constructor + controller = self.app.resolve(route.controller) + + # Resolve the method + response = self.app.resolve(getattr(controller, route.controller_method)) + self.reset_method() + + assert response.rendered_template == 'confirm' + + def test_confirm_controller_failure(self): + self.auth = Auth(self.request, MockVerifyUser()) + + timestamp_plus_11 = datetime.datetime.now() - datetime.timedelta(minutes=11) + print(timestamp_plus_11.timestamp()) + + params = {'id': Sign().sign('{0}::{1}'.format(1, timestamp_plus_11.timestamp()))} + self.request.set_params(params) + user = self.auth.once().login_by_id(1) + self.request.set_user(user) + + self.app.bind('Request', self.request) + self.app.make('Request').load_app(self.app) + + # Create the route + route = get('/email/verify/@id', ConfirmController.confirm_email) + + ConfirmController.get_user = self.get_user + + # Resolve the controller constructor + controller = self.app.resolve(route.controller) + + # Resolve the method + response = self.app.resolve(getattr(controller, route.controller_method)) + self.reset_method() + + assert response.rendered_template == 'error' From d7de87acd36213738518978e94aadda91aa18e39 Mon Sep 17 00:00:00 2001 From: Joseph Mancuso Date: Sat, 29 Sep 2018 13:38:39 -0400 Subject: [PATCH 18/20] added better exception handling to match routes --- masonite/exceptions.py | 4 ++++ masonite/routes.py | 8 ++++++-- tests/test_routes.py | 9 ++++++++- 3 files changed, 18 insertions(+), 3 deletions(-) diff --git a/masonite/exceptions.py b/masonite/exceptions.py index fb4a7f355..ad54d5f19 100644 --- a/masonite/exceptions.py +++ b/masonite/exceptions.py @@ -60,3 +60,7 @@ class StrictContainerException(Exception): class InvalidRouteCompileException(Exception): pass + + +class RouteException(Exception): + pass diff --git a/masonite/routes.py b/masonite/routes.py index 1b76aafb9..a18566097 100644 --- a/masonite/routes.py +++ b/masonite/routes.py @@ -5,7 +5,7 @@ import importlib import json -from masonite.exceptions import RouteMiddlewareNotFound, InvalidRouteCompileException +from masonite.exceptions import RouteMiddlewareNotFound, InvalidRouteCompileException, RouteException from masonite.view import View @@ -401,7 +401,11 @@ def __init__(self, method_type=['GET']): """Post constructor """ - self.method_type = method_type + if not isinstance(method_type, list): + raise RouteException("Method type needs to be a list. Got '{}'".format(method_type)) + + # Make all method types in list uppercase + self.method_type = [x.upper() for x in method_type] self.list_middleware = [] diff --git a/tests/test_routes.py b/tests/test_routes.py index 69f327d13..988772c8e 100644 --- a/tests/test_routes.py +++ b/tests/test_routes.py @@ -3,7 +3,7 @@ from masonite.routes import Get, Post, Put, Patch, Delete, RouteGroup, Match from masonite.helpers.routes import group, flatten_routes from masonite.testsuite.TestSuite import generate_wsgi -from masonite.exceptions import InvalidRouteCompileException +from masonite.exceptions import InvalidRouteCompileException, RouteException import pytest @@ -67,6 +67,13 @@ def test_route_doesnt_break_on_incorrect_controller(self): def test_route_can_have_multiple_routes(self): assert Match(['GET', 'POST']).route('test/url', 'TestController@show').method_type == ['GET', 'POST'] + def test_match_routes_convert_lowercase_to_uppercase(self): + assert Match(['Get', 'Post']).route('test/url', 'TestController@show').method_type == ['GET', 'POST'] + + def test_match_routes_raises_exception_with_non_list_method_types(self): + with pytest.raises(RouteException): + assert Match('get').route('test/url', 'TestController@show').method_type == ['GET', 'POST'] + def test_group_route(self): routes = group('/example', [ Get().route('/test/1', 'TestController@show'), From 3b8f0ba2508e6be57cd3b34a0f174870f4bd9c70 Mon Sep 17 00:00:00 2001 From: Joseph Mancuso Date: Sat, 29 Sep 2018 15:21:53 -0400 Subject: [PATCH 19/20] fixed pep --- masonite/helpers/routes.py | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/masonite/helpers/routes.py b/masonite/helpers/routes.py index 84e115124..ad3d0cb0e 100644 --- a/masonite/helpers/routes.py +++ b/masonite/helpers/routes.py @@ -37,6 +37,7 @@ def get(url, controller): """ from masonite.routes import Get + return Get().route(url, controller) def match(method_type, url, controller): @@ -50,9 +51,9 @@ def match(method_type, url, controller): Returns: masonite.routes.Get -- The Masonite Get class. """ - from masonite.routes import Match + return Match(method_type).route(url, controller) @@ -66,9 +67,9 @@ def post(url, controller): Returns: masonite.routes.Post -- The Masonite Post class. """ - from masonite.routes import Post + return Post().route(url, controller) @@ -82,9 +83,9 @@ def delete(url, controller): Returns: masonite.routes.Delete -- The Masonite Delete class. """ - from masonite.routes import Delete + return Delete().route(url, controller) @@ -100,6 +101,7 @@ def put(url, controller): """ from masonite.routes import Put + return Put().route(url, controller) @@ -113,9 +115,9 @@ def patch(url, controller): Returns: masonite.routes.Patch -- The Masonite Patch class. """ - from masonite.routes import Patch + return Patch().route(url, controller) From a85ad0979805b782517f2ef3c954b212164c2380 Mon Sep 17 00:00:00 2001 From: Joseph Mancuso Date: Sat, 29 Sep 2018 15:26:03 -0400 Subject: [PATCH 20/20] fixed pep --- masonite/helpers/routes.py | 7 +------ 1 file changed, 1 insertion(+), 6 deletions(-) diff --git a/masonite/helpers/routes.py b/masonite/helpers/routes.py index ad3d0cb0e..a57a4673d 100644 --- a/masonite/helpers/routes.py +++ b/masonite/helpers/routes.py @@ -37,9 +37,9 @@ def get(url, controller): """ from masonite.routes import Get - return Get().route(url, controller) + def match(method_type, url, controller): """Shortcut for Match HTTP class. @@ -53,7 +53,6 @@ def match(method_type, url, controller): """ from masonite.routes import Match - return Match(method_type).route(url, controller) @@ -69,7 +68,6 @@ def post(url, controller): """ from masonite.routes import Post - return Post().route(url, controller) @@ -85,7 +83,6 @@ def delete(url, controller): """ from masonite.routes import Delete - return Delete().route(url, controller) @@ -101,7 +98,6 @@ def put(url, controller): """ from masonite.routes import Put - return Put().route(url, controller) @@ -117,7 +113,6 @@ def patch(url, controller): """ from masonite.routes import Patch - return Patch().route(url, controller)