Today was my first day at Hacker School.
I learned about decorators from Erik Taubeneck.
Decorators can be seen as a way to wrap arbitrary functions. Decorating the method
foo with the decorator @bar is syntactically equivalent to
foo = bar(foo) — that is, redefining foo to always be passed through bar.
The reason you'd want to do this: you can abstract out a lot of boilerplate that might apply to many different functions. As a bonus that boilerplate doesn't have to be in one spot; it can be at the beginning and end of the functions you want to call. For instance, if you need to run authentication checks on lots of functions in your web app, you can decorate all those functions with an authentication decorator.
Then, when you define the decorator, it takes a function as an argument and returns that function depending on whatever logic you like. So for instance it would take your user operation, check for authentication, and return the operation if the user was authenticated (and the operation would then run normally), and return a redirect function if the user is not authenticated.