)]}'
{"/COMMIT_MSG":[{"author":{"_account_id":6486,"name":"Brant Knudson","email":"blk@acm.org","username":"blk-u"},"change_message_id":"de222a04a1f7955fbf2a379d7c066bc0d29f3a56","unresolved":false,"context_lines":[{"line_number":16,"context_line":"The enforcement levels should allow us to start putting warnings on"},{"line_number":17,"context_line":"existing functions and strict enforcement on new functions, and the"},{"line_number":18,"context_line":"default value will mean that we should be able to do stricter default"},{"line_number":19,"context_line":"enforcement (for example in testing)"},{"line_number":20,"context_line":""},{"line_number":21,"context_line":"Change-Id: Ic0a196874930e7be8362df50594471ab8037c5b2"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":3,"id":"AAAAWH%2F%2F6gk%3D","line":19,"updated":"2014-03-13 00:24:54.000000000","message":"I think we\u0027re going to need this documented in the developer docs, where you\u0027re supposed to use it and where not.","commit_id":"2272c21798282e6587807fee20108ff7038322d8"},{"author":{"_account_id":6486,"name":"Brant Knudson","email":"blk@acm.org","username":"blk-u"},"change_message_id":"14fa81d8aa4e0427df851b4e255d8e9c5c7e1346","unresolved":false,"context_lines":[{"line_number":6,"context_line":""},{"line_number":7,"context_line":"Add a positional decorator"},{"line_number":8,"context_line":""},{"line_number":9,"context_line":"This decorator allow us to define that certain parameters are strictly"},{"line_number":10,"context_line":"keyword arguments only, without sacrificing the convenience of having"},{"line_number":11,"context_line":"those arguments listed in the function definition."},{"line_number":12,"context_line":""}],"source_content_type":"text/x-gerrit-commit-message","patch_set":6,"id":"AAAAWH%2F%2B3Jo%3D","line":9,"updated":"2014-03-22 16:00:16.000000000","message":"change \"allow\" to \"allows\"","commit_id":"bdecbf9d6d43b228f00527f7304e853cc81cd929"},{"author":{"_account_id":6486,"name":"Brant Knudson","email":"blk@acm.org","username":"blk-u"},"change_message_id":"40d1384c6151a84bcc64ffcd6c4fa77484b61fe2","unresolved":false,"context_lines":[{"line_number":6,"context_line":""},{"line_number":7,"context_line":"Add a positional decorator"},{"line_number":8,"context_line":""},{"line_number":9,"context_line":"This decorator allow us to define that certain parameters are strictly"},{"line_number":10,"context_line":"keyword arguments only, without sacrificing the convenience of having"},{"line_number":11,"context_line":"those arguments listed in the function definition."},{"line_number":12,"context_line":""}],"source_content_type":"text/x-gerrit-commit-message","patch_set":7,"id":"AAAAWH%2F%2BsYQ%3D","line":9,"updated":"2014-03-25 01:32:10.000000000","message":"change \"allow\" to \"allows\"","commit_id":"67e99991d52bc788a1380e8cb5fa1ffa27a484c8"}],"keystoneclient/tests/test_utils.py":[{"author":{"_account_id":9101,"name":"wanghong","email":"reviewwanghong@126.com","username":"wanghong"},"change_message_id":"1b89eedea7a683e30d265dc634bc495e843eccaa","unresolved":false,"context_lines":[{"line_number":136,"context_line":""},{"line_number":137,"context_line":"class TestPositional(test_utils.TestCase):"},{"line_number":138,"context_line":""},{"line_number":139,"context_line":"    RETURNED \u003d \u0027success\u0027"},{"line_number":140,"context_line":""},{"line_number":141,"context_line":"    @utils.positional(1)"},{"line_number":142,"context_line":"    def no_vars(self):"}],"source_content_type":"text/x-python","patch_set":2,"id":"AAAAVn%2F%2ByVI%3D","line":139,"updated":"2014-03-12 07:03:16.000000000","message":"Looks like this variable is unused.","commit_id":"feb4e4867cc2f6bbe64d57236e17cd2cf8434005"},{"author":{"_account_id":7191,"name":"Jamie Lennox","email":"jamielennox@gmail.com","username":"jamielennox"},"change_message_id":"c956e3f3552ccd1cdd4f51320fd7bd4e586e7a06","unresolved":false,"context_lines":[{"line_number":136,"context_line":""},{"line_number":137,"context_line":"class TestPositional(test_utils.TestCase):"},{"line_number":138,"context_line":""},{"line_number":139,"context_line":"    RETURNED \u003d \u0027success\u0027"},{"line_number":140,"context_line":""},{"line_number":141,"context_line":"    @utils.positional(1)"},{"line_number":142,"context_line":"    def no_vars(self):"}],"source_content_type":"text/x-python","patch_set":2,"id":"AAAAWH%2F%2F6y4%3D","line":139,"in_reply_to":"AAAAVn%2F%2Bx6k%3D","updated":"2014-03-12 23:18:02.000000000","message":"Done","commit_id":"feb4e4867cc2f6bbe64d57236e17cd2cf8434005"},{"author":{"_account_id":2903,"name":"Morgan Fainberg","email":"morgan.fainberg@gmail.com","username":"mdrnstm"},"change_message_id":"16cd7e316b22ec57a67a891273020c37e0142d66","unresolved":false,"context_lines":[{"line_number":136,"context_line":""},{"line_number":137,"context_line":"class TestPositional(test_utils.TestCase):"},{"line_number":138,"context_line":""},{"line_number":139,"context_line":"    RETURNED \u003d \u0027success\u0027"},{"line_number":140,"context_line":""},{"line_number":141,"context_line":"    @utils.positional(1)"},{"line_number":142,"context_line":"    def no_vars(self):"}],"source_content_type":"text/x-python","patch_set":2,"id":"AAAAVn%2F%2Bx6k%3D","line":139,"in_reply_to":"AAAAVn%2F%2ByVI%3D","updated":"2014-03-12 07:58:54.000000000","message":"++","commit_id":"feb4e4867cc2f6bbe64d57236e17cd2cf8434005"},{"author":{"_account_id":6486,"name":"Brant Knudson","email":"blk@acm.org","username":"blk-u"},"change_message_id":"de222a04a1f7955fbf2a379d7c066bc0d29f3a56","unresolved":false,"context_lines":[{"line_number":137,"context_line":"class TestPositional(test_utils.TestCase):"},{"line_number":138,"context_line":""},{"line_number":139,"context_line":"    @utils.positional(1)"},{"line_number":140,"context_line":"    def no_vars(self):"},{"line_number":141,"context_line":"        return True"},{"line_number":142,"context_line":""},{"line_number":143,"context_line":"    @utils.positional(3, utils.POSITIONAL_EXCEPT)"}],"source_content_type":"text/x-python","patch_set":3,"id":"AAAAWH%2F%2F6gQ%3D","line":140,"updated":"2014-03-13 00:24:54.000000000","message":"this seems to be an antipattern, since the function already enforces its arguments... suggest add a comment that this is an example for testing and not recommended.","commit_id":"2272c21798282e6587807fee20108ff7038322d8"},{"author":{"_account_id":6486,"name":"Brant Knudson","email":"blk@acm.org","username":"blk-u"},"change_message_id":"de222a04a1f7955fbf2a379d7c066bc0d29f3a56","unresolved":false,"context_lines":[{"line_number":140,"context_line":"    def no_vars(self):"},{"line_number":141,"context_line":"        return True"},{"line_number":142,"context_line":""},{"line_number":143,"context_line":"    @utils.positional(3, utils.POSITIONAL_EXCEPT)"},{"line_number":144,"context_line":"    def mixed_except(self, arg, kwarg1\u003dNone, kwarg2\u003dNone):"},{"line_number":145,"context_line":"        return (arg, kwarg1, kwarg2)"},{"line_number":146,"context_line":""}],"source_content_type":"text/x-python","patch_set":3,"id":"AAAAWH%2F%2F6eE%3D","line":143,"updated":"2014-03-13 00:24:54.000000000","message":"these tests would be useful documentation if there were some comments saying what this accomplishes.","commit_id":"2272c21798282e6587807fee20108ff7038322d8"},{"author":{"_account_id":6486,"name":"Brant Knudson","email":"blk@acm.org","username":"blk-u"},"change_message_id":"de222a04a1f7955fbf2a379d7c066bc0d29f3a56","unresolved":false,"context_lines":[{"line_number":152,"context_line":"        self.assertTrue(self.no_vars())"},{"line_number":153,"context_line":""},{"line_number":154,"context_line":"    def test_mixed_except(self):"},{"line_number":155,"context_line":"        self.assertEqual(self.mixed_except(1, 2, kwarg2\u003d3), (1, 2, 3))"},{"line_number":156,"context_line":"        self.assertEqual(self.mixed_except(1, kwarg1\u003d2, kwarg2\u003d3), (1, 2, 3))"},{"line_number":157,"context_line":"        self.assertEqual(self.mixed_except(1), (1, None, None))"},{"line_number":158,"context_line":"        self.assertRaises(TypeError, self.mixed_except, 1, 2, 3)"}],"source_content_type":"text/x-python","patch_set":3,"id":"AAAAWH%2F%2F6ds%3D","line":155,"updated":"2014-03-13 00:24:54.000000000","message":"(nit) the argumens to assertEqual are (expected, actual), so should reverse the order of all these.","commit_id":"2272c21798282e6587807fee20108ff7038322d8"},{"author":{"_account_id":6486,"name":"Brant Knudson","email":"blk@acm.org","username":"blk-u"},"change_message_id":"14fa81d8aa4e0427df851b4e255d8e9c5c7e1346","unresolved":false,"context_lines":[{"line_number":149,"context_line":"    @utils.positional(3, utils.positional.WARN)"},{"line_number":150,"context_line":"    def mixed_warn(self, arg, kwarg1\u003dNone, kwarg2\u003dNone):"},{"line_number":151,"context_line":"        # self, arg, and kwarg1 may be passed positionally, only a warning"},{"line_number":152,"context_line":"        # is emmitted"},{"line_number":153,"context_line":"        return (arg, kwarg1, kwarg2)"},{"line_number":154,"context_line":""},{"line_number":155,"context_line":"    def test_nothing(self):"}],"source_content_type":"text/x-python","patch_set":6,"id":"AAAAWH%2F%2B3JI%3D","line":152,"updated":"2014-03-22 16:00:16.000000000","message":"emitted","commit_id":"bdecbf9d6d43b228f00527f7304e853cc81cd929"}],"keystoneclient/utils.py":[{"author":{"_account_id":7725,"name":"David Stanek","email":"dstanek@dstanek.com","username":"dstanek"},"change_message_id":"d2b32cc8d68d027b9d9f8286fdafc86921704e04","unresolved":false,"context_lines":[{"line_number":171,"context_line":"positional_enforcement \u003d POSITIONAL_WARN"},{"line_number":172,"context_line":""},{"line_number":173,"context_line":""},{"line_number":174,"context_line":"def positional(max_positional_args, enforcement\u003dNone):"},{"line_number":175,"context_line":"    \"\"\"A decorator which enforces only some args may be passed positionally."},{"line_number":176,"context_line":""},{"line_number":177,"context_line":"    This idea and some of the code was taken from the oauth2 client of the"}],"source_content_type":"text/x-python","patch_set":1,"id":"AAAAVn%2F%2FOQQ%3D","line":174,"updated":"2014-03-07 14:28:04.000000000","message":"Have you thought about implementing with inspect? If you did you wouldn\u0027t have to pass in the max_positional_args value.  Example:\n\n  spec \u003d inspect.getargspec(func)\n  max_positional_args \u003d len(spec.args) - len(spec.defaults)","commit_id":"f0097ea40f489ad59d1f6ac101690b5375afaa50"},{"author":{"_account_id":5046,"name":"Lance Bragstad","email":"lbragstad@redhat.com","username":"ldbragst"},"change_message_id":"9c2b52c0a49de68197e91ffcc739ed07a735824e","unresolved":false,"context_lines":[{"line_number":210,"context_line":"        fn(required_kw\u003d10)  # Ok."},{"line_number":211,"context_line":""},{"line_number":212,"context_line":"      When defining instance or class methods always remember to account for"},{"line_number":213,"context_line":"      \u0027self\u0027 and \u0027cls\u0027:"},{"line_number":214,"context_line":""},{"line_number":215,"context_line":"        class MyClass(object):"},{"line_number":216,"context_line":""}],"source_content_type":"text/x-python","patch_set":2,"id":"AAAAVn%2F%2BzdA%3D","line":213,"updated":"2014-03-12 02:35:22.000000000","message":"So, this would be similar to accessing the args if they were in a list? \n\nEx: \n\n    args[3] \n\nwould be the 4th argument, right?","commit_id":"feb4e4867cc2f6bbe64d57236e17cd2cf8434005"},{"author":{"_account_id":7191,"name":"Jamie Lennox","email":"jamielennox@gmail.com","username":"jamielennox"},"change_message_id":"c956e3f3552ccd1cdd4f51320fd7bd4e586e7a06","unresolved":false,"context_lines":[{"line_number":210,"context_line":"        fn(required_kw\u003d10)  # Ok."},{"line_number":211,"context_line":""},{"line_number":212,"context_line":"      When defining instance or class methods always remember to account for"},{"line_number":213,"context_line":"      \u0027self\u0027 and \u0027cls\u0027:"},{"line_number":214,"context_line":""},{"line_number":215,"context_line":"        class MyClass(object):"},{"line_number":216,"context_line":""}],"source_content_type":"text/x-python","patch_set":2,"id":"AAAAWH%2F%2F63w%3D","line":213,"in_reply_to":"AAAAVn%2F%2BzdA%3D","updated":"2014-03-12 23:18:02.000000000","message":"more that for bound methods self or cls is always passed as the first positional argument eg below so to make the decorator work the same way for bound vs unbound you just have to remember that self is a positional arg as well","commit_id":"feb4e4867cc2f6bbe64d57236e17cd2cf8434005"},{"author":{"_account_id":2903,"name":"Morgan Fainberg","email":"morgan.fainberg@gmail.com","username":"mdrnstm"},"change_message_id":"e8c1194f52eeaa69a7b6cfed010a5b6c342dbe29","unresolved":false,"context_lines":[{"line_number":214,"context_line":""},{"line_number":215,"context_line":"        class MyClass(object):"},{"line_number":216,"context_line":""},{"line_number":217,"context_line":"          @positional(2)"},{"line_number":218,"context_line":"          def my_method(self, pos1, kwonly1\u003dNone):"},{"line_number":219,"context_line":"            ..."},{"line_number":220,"context_line":""}],"source_content_type":"text/x-python","patch_set":2,"id":"AAAAVn%2F%2Bx34%3D","line":217,"updated":"2014-03-12 08:02:08.000000000","message":"It seems like you should make \"self\" a special case if possible and allow that to use an @positional(0).","commit_id":"feb4e4867cc2f6bbe64d57236e17cd2cf8434005"},{"author":{"_account_id":7191,"name":"Jamie Lennox","email":"jamielennox@gmail.com","username":"jamielennox"},"change_message_id":"c956e3f3552ccd1cdd4f51320fd7bd4e586e7a06","unresolved":false,"context_lines":[{"line_number":214,"context_line":""},{"line_number":215,"context_line":"        class MyClass(object):"},{"line_number":216,"context_line":""},{"line_number":217,"context_line":"          @positional(2)"},{"line_number":218,"context_line":"          def my_method(self, pos1, kwonly1\u003dNone):"},{"line_number":219,"context_line":"            ..."},{"line_number":220,"context_line":""}],"source_content_type":"text/x-python","patch_set":2,"id":"AAAAWH%2F%2F63c%3D","line":217,"in_reply_to":"AAAAVn%2F%2Bx34%3D","updated":"2014-03-12 23:18:02.000000000","message":"I would think that makes it more confusing rather than less for anyone that has done much python. It\u0027s a quirk of the language that self is the first positional arg and it gets caught when you do a *args. I think I would prefer to keep it as 2 and document the difference than do checks for a self object. \n\nAny one else want to way in?","commit_id":"feb4e4867cc2f6bbe64d57236e17cd2cf8434005"},{"author":{"_account_id":2903,"name":"Morgan Fainberg","email":"morgan.fainberg@gmail.com","username":"mdrnstm"},"change_message_id":"16cd7e316b22ec57a67a891273020c37e0142d66","unresolved":false,"context_lines":[{"line_number":240,"context_line":"            # NOTE(jamielennox): these need to be set to a local variable as"},{"line_number":241,"context_line":"            # you can\u0027t assign to a value outside of the inner function scope"},{"line_number":242,"context_line":"            enforce \u003d enforcement or positional_enforcement"},{"line_number":243,"context_line":"            arg_length \u003d max_positional_args"},{"line_number":244,"context_line":""},{"line_number":245,"context_line":"            if arg_length is None:"},{"line_number":246,"context_line":"                spec \u003d inspect.getargspec(func)"}],"source_content_type":"text/x-python","patch_set":2,"id":"AAAAVn%2F%2Bx8k%3D","line":243,"updated":"2014-03-12 07:58:54.000000000","message":"Suggest moving all of the logic for arg_length and enforce into the wrapper, which would ensure that you don\u0027t need to make any assignments to the variables inside the inner scope. These values don\u0027t change at runtime and therefore don\u0027t need to be calculated on each method/function invocation.\n\nThis has the added benefit of avoiding the need to rebind the values.","commit_id":"feb4e4867cc2f6bbe64d57236e17cd2cf8434005"},{"author":{"_account_id":7191,"name":"Jamie Lennox","email":"jamielennox@gmail.com","username":"jamielennox"},"change_message_id":"c956e3f3552ccd1cdd4f51320fd7bd4e586e7a06","unresolved":false,"context_lines":[{"line_number":240,"context_line":"            # NOTE(jamielennox): these need to be set to a local variable as"},{"line_number":241,"context_line":"            # you can\u0027t assign to a value outside of the inner function scope"},{"line_number":242,"context_line":"            enforce \u003d enforcement or positional_enforcement"},{"line_number":243,"context_line":"            arg_length \u003d max_positional_args"},{"line_number":244,"context_line":""},{"line_number":245,"context_line":"            if arg_length is None:"},{"line_number":246,"context_line":"                spec \u003d inspect.getargspec(func)"}],"source_content_type":"text/x-python","patch_set":2,"id":"AAAAWH%2F%2F61U%3D","line":243,"in_reply_to":"AAAAVn%2F%2Bx8k%3D","updated":"2014-03-12 23:18:02.000000000","message":"agree on arg_length. I\u0027m not sure about enforcement. \n\nIt will depend on when you expect the value of positional_enforcement to be set. If you can set it first thing then it won\u0027t change but if you define a couple of functions and then change the value of positional_enforcement those won\u0027t get picked up for the functions already defined.","commit_id":"feb4e4867cc2f6bbe64d57236e17cd2cf8434005"},{"author":{"_account_id":2903,"name":"Morgan Fainberg","email":"morgan.fainberg@gmail.com","username":"mdrnstm"},"change_message_id":"16cd7e316b22ec57a67a891273020c37e0142d66","unresolved":false,"context_lines":[{"line_number":243,"context_line":"            arg_length \u003d max_positional_args"},{"line_number":244,"context_line":""},{"line_number":245,"context_line":"            if arg_length is None:"},{"line_number":246,"context_line":"                spec \u003d inspect.getargspec(func)"},{"line_number":247,"context_line":"                arg_length \u003d len(spec.args) - len(spec.defaults)"},{"line_number":248,"context_line":""},{"line_number":249,"context_line":"            if len(args) \u003e arg_length:"}],"source_content_type":"text/x-python","patch_set":2,"id":"AAAAVn%2F%2Bx%2B0%3D","line":246,"updated":"2014-03-12 07:58:54.000000000","message":"suggest moving the inspect into the wrapper (out of inner) function, the argspect should not change durning runtime. See above comment (ln: 243)","commit_id":"feb4e4867cc2f6bbe64d57236e17cd2cf8434005"},{"author":{"_account_id":7191,"name":"Jamie Lennox","email":"jamielennox@gmail.com","username":"jamielennox"},"change_message_id":"c956e3f3552ccd1cdd4f51320fd7bd4e586e7a06","unresolved":false,"context_lines":[{"line_number":243,"context_line":"            arg_length \u003d max_positional_args"},{"line_number":244,"context_line":""},{"line_number":245,"context_line":"            if arg_length is None:"},{"line_number":246,"context_line":"                spec \u003d inspect.getargspec(func)"},{"line_number":247,"context_line":"                arg_length \u003d len(spec.args) - len(spec.defaults)"},{"line_number":248,"context_line":""},{"line_number":249,"context_line":"            if len(args) \u003e arg_length:"}],"source_content_type":"text/x-python","patch_set":2,"id":"AAAAWH%2F%2F6zc%3D","line":246,"in_reply_to":"AAAAVn%2F%2Bx%2B0%3D","updated":"2014-03-12 23:18:02.000000000","message":"Done","commit_id":"feb4e4867cc2f6bbe64d57236e17cd2cf8434005"},{"author":{"_account_id":2903,"name":"Morgan Fainberg","email":"morgan.fainberg@gmail.com","username":"mdrnstm"},"change_message_id":"16cd7e316b22ec57a67a891273020c37e0142d66","unresolved":false,"context_lines":[{"line_number":247,"context_line":"                arg_length \u003d len(spec.args) - len(spec.defaults)"},{"line_number":248,"context_line":""},{"line_number":249,"context_line":"            if len(args) \u003e arg_length:"},{"line_number":250,"context_line":"                plural \u003d \u0027s\u0027 if len(args) \u003e 1 else \u0027\u0027"},{"line_number":251,"context_line":"                message \u003d (\u0027%(name)s takes at most %(max)d positional \u0027"},{"line_number":252,"context_line":"                           \u0027argument%(plural)s (%(given)d given)\u0027 %"},{"line_number":253,"context_line":"                           {\u0027name\u0027: func.__name__,"}],"source_content_type":"text/x-python","patch_set":2,"id":"AAAAVn%2F%2Bx6w%3D","line":250,"updated":"2014-03-12 07:58:54.000000000","message":"This looks like you mean:\n    plural \u003d \u0027s\u0027 if len(arg_length) \u003e 1 else \u0027\u0027\n\nThis can also be moved (if it is meant to look at arg_length) up into wrapper (and out of inner) since it shouldn\u0027t change.","commit_id":"feb4e4867cc2f6bbe64d57236e17cd2cf8434005"},{"author":{"_account_id":2903,"name":"Morgan Fainberg","email":"morgan.fainberg@gmail.com","username":"mdrnstm"},"change_message_id":"16cd7e316b22ec57a67a891273020c37e0142d66","unresolved":false,"context_lines":[{"line_number":250,"context_line":"                plural \u003d \u0027s\u0027 if len(args) \u003e 1 else \u0027\u0027"},{"line_number":251,"context_line":"                message \u003d (\u0027%(name)s takes at most %(max)d positional \u0027"},{"line_number":252,"context_line":"                           \u0027argument%(plural)s (%(given)d given)\u0027 %"},{"line_number":253,"context_line":"                           {\u0027name\u0027: func.__name__,"},{"line_number":254,"context_line":"                            \u0027max\u0027: arg_length,"},{"line_number":255,"context_line":"                            \u0027given\u0027: len(args),"},{"line_number":256,"context_line":"                            \u0027plural\u0027: plural})"}],"source_content_type":"text/x-python","patch_set":2,"id":"AAAAVn%2F%2Bx7c%3D","line":253,"updated":"2014-03-12 07:58:54.000000000","message":"suggest giving more specific value to the name not just func.__name__ but include the entire path if possible (e.g. keystoneclient.utils.positional) this can also be moved up into the wrapper function","commit_id":"feb4e4867cc2f6bbe64d57236e17cd2cf8434005"},{"author":{"_account_id":7191,"name":"Jamie Lennox","email":"jamielennox@gmail.com","username":"jamielennox"},"change_message_id":"c956e3f3552ccd1cdd4f51320fd7bd4e586e7a06","unresolved":false,"context_lines":[{"line_number":250,"context_line":"                plural \u003d \u0027s\u0027 if len(args) \u003e 1 else \u0027\u0027"},{"line_number":251,"context_line":"                message \u003d (\u0027%(name)s takes at most %(max)d positional \u0027"},{"line_number":252,"context_line":"                           \u0027argument%(plural)s (%(given)d given)\u0027 %"},{"line_number":253,"context_line":"                           {\u0027name\u0027: func.__name__,"},{"line_number":254,"context_line":"                            \u0027max\u0027: arg_length,"},{"line_number":255,"context_line":"                            \u0027given\u0027: len(args),"},{"line_number":256,"context_line":"                            \u0027plural\u0027: plural})"}],"source_content_type":"text/x-python","patch_set":2,"id":"AAAAWH%2F%2F600%3D","line":253,"in_reply_to":"AAAAVn%2F%2Bx7c%3D","updated":"2014-03-12 23:18:02.000000000","message":"\u0027given\u0027 still needs to be computed on the inner call. I guess i could save the template in the outer and just replace given on the inner - but i don\u0027t see that as a benefit.\n\nAlso i\u0027m not aware of a way to do the full path of a method that works across py2 and py3.","commit_id":"feb4e4867cc2f6bbe64d57236e17cd2cf8434005"},{"author":{"_account_id":2903,"name":"Morgan Fainberg","email":"morgan.fainberg@gmail.com","username":"mdrnstm"},"change_message_id":"16cd7e316b22ec57a67a891273020c37e0142d66","unresolved":false,"context_lines":[{"line_number":258,"context_line":"                if enforce \u003d\u003d POSITIONAL_EXCEPT:"},{"line_number":259,"context_line":"                    raise TypeError(message)"},{"line_number":260,"context_line":"                elif enforce \u003d\u003d POSITIONAL_WARN:"},{"line_number":261,"context_line":"                    logger.warn(message)"},{"line_number":262,"context_line":""},{"line_number":263,"context_line":"            return func(*args, **kwargs)"},{"line_number":264,"context_line":""}],"source_content_type":"text/x-python","patch_set":2,"id":"AAAAVn%2F%2Bx48%3D","line":261,"updated":"2014-03-12 07:58:54.000000000","message":"Not sure if warning is correct.\n\nI\u0027m also not sure if we should omit warning if we\u0027re raising an exception.","commit_id":"feb4e4867cc2f6bbe64d57236e17cd2cf8434005"},{"author":{"_account_id":7191,"name":"Jamie Lennox","email":"jamielennox@gmail.com","username":"jamielennox"},"change_message_id":"c956e3f3552ccd1cdd4f51320fd7bd4e586e7a06","unresolved":false,"context_lines":[{"line_number":258,"context_line":"                if enforce \u003d\u003d POSITIONAL_EXCEPT:"},{"line_number":259,"context_line":"                    raise TypeError(message)"},{"line_number":260,"context_line":"                elif enforce \u003d\u003d POSITIONAL_WARN:"},{"line_number":261,"context_line":"                    logger.warn(message)"},{"line_number":262,"context_line":""},{"line_number":263,"context_line":"            return func(*args, **kwargs)"},{"line_number":264,"context_line":""}],"source_content_type":"text/x-python","patch_set":2,"id":"AAAAWH%2F%2F6zk%3D","line":261,"in_reply_to":"AAAAVn%2F%2Bx48%3D","updated":"2014-03-12 23:18:02.000000000","message":"What else should it be if not warn? I consider that if you are hitting this you are purposefully using the API in a way that we don\u0027t consider stable. \n\nHaving said that i expect new functionality to override with POSITIONAL_EXCEPT because then there is no fear of breaking compatibility.","commit_id":"feb4e4867cc2f6bbe64d57236e17cd2cf8434005"},{"author":{"_account_id":6486,"name":"Brant Knudson","email":"blk@acm.org","username":"blk-u"},"change_message_id":"de222a04a1f7955fbf2a379d7c066bc0d29f3a56","unresolved":false,"context_lines":[{"line_number":165,"context_line":"            return"},{"line_number":166,"context_line":""},{"line_number":167,"context_line":""},{"line_number":168,"context_line":"POSITIONAL_EXCEPT \u003d \u0027strict\u0027"},{"line_number":169,"context_line":"POSITIONAL_WARN \u003d \u0027warn\u0027"},{"line_number":170,"context_line":"POSITIONAL_NONE \u003d \u0027none\u0027"},{"line_number":171,"context_line":""}],"source_content_type":"text/x-python","patch_set":3,"id":"AAAAWH%2F%2F6dM%3D","line":168,"updated":"2014-03-13 00:24:54.000000000","message":"These need documentation on where each should be used.\n\nAlso, suggest have the string be the same as the name (e.g., change \u0027strict\u0027 to \u0027except\u0027\n\nAlso, suggest put these in a class so don\u0027t need copy the name:\n\nclass Positional:\n   EXCEPT \u003d \u0027strict\u0027\n   WARN \u003d \u0027warn\u0027\n   NONE \u003d \u0027none\u0027\n\nThen make it the wrapper...\n\n @utils.Positional(3,Positional.EXCEPT)\n def f(whatever...","commit_id":"2272c21798282e6587807fee20108ff7038322d8"},{"author":{"_account_id":6486,"name":"Brant Knudson","email":"blk@acm.org","username":"blk-u"},"change_message_id":"de222a04a1f7955fbf2a379d7c066bc0d29f3a56","unresolved":false,"context_lines":[{"line_number":179,"context_line":"    google-api client."},{"line_number":180,"context_line":""},{"line_number":181,"context_line":"    This decorator makes it easy to support Python 3 style key-word only"},{"line_number":182,"context_line":"    parameters. For example, in Python 3 it is possible to write:"},{"line_number":183,"context_line":""},{"line_number":184,"context_line":"      def fn(pos1, *, kwonly1\u003dNone, kwonly1\u003dNone):"},{"line_number":185,"context_line":"        ..."}],"source_content_type":"text/x-python","patch_set":3,"id":"AAAAWH%2F%2F6Z0%3D","line":182,"updated":"2014-03-13 00:24:54.000000000","message":"do :: and add a blank line for rst.","commit_id":"2272c21798282e6587807fee20108ff7038322d8"},{"author":{"_account_id":6486,"name":"Brant Knudson","email":"blk@acm.org","username":"blk-u"},"change_message_id":"de222a04a1f7955fbf2a379d7c066bc0d29f3a56","unresolved":false,"context_lines":[{"line_number":184,"context_line":"      def fn(pos1, *, kwonly1\u003dNone, kwonly1\u003dNone):"},{"line_number":185,"context_line":"        ..."},{"line_number":186,"context_line":""},{"line_number":187,"context_line":"    All named parameters after * must be a keyword:"},{"line_number":188,"context_line":""},{"line_number":189,"context_line":"      fn(10, \u0027kw1\u0027, \u0027kw2\u0027)  # Raises exception."},{"line_number":190,"context_line":"      fn(10, kwonly1\u003d\u0027kw1\u0027)  # Ok."}],"source_content_type":"text/x-python","patch_set":3,"id":"AAAAWH%2F%2F6Z4%3D","line":187,"updated":"2014-03-13 00:24:54.000000000","message":"do :: and add a blank line for rst.","commit_id":"2272c21798282e6587807fee20108ff7038322d8"},{"author":{"_account_id":6486,"name":"Brant Knudson","email":"blk@acm.org","username":"blk-u"},"change_message_id":"de222a04a1f7955fbf2a379d7c066bc0d29f3a56","unresolved":false,"context_lines":[{"line_number":190,"context_line":"      fn(10, kwonly1\u003d\u0027kw1\u0027)  # Ok."},{"line_number":191,"context_line":""},{"line_number":192,"context_line":"    Example:"},{"line_number":193,"context_line":"      To define a function like above, do:"},{"line_number":194,"context_line":""},{"line_number":195,"context_line":"        @positional(1)"},{"line_number":196,"context_line":"        def fn(pos1, kwonly1\u003dNone, kwonly2\u003dNone):"}],"source_content_type":"text/x-python","patch_set":3,"id":"AAAAWH%2F%2F6Zg%3D","line":193,"updated":"2014-03-13 00:24:54.000000000","message":"do :: and add a blank line for rst.","commit_id":"2272c21798282e6587807fee20108ff7038322d8"},{"author":{"_account_id":6486,"name":"Brant Knudson","email":"blk@acm.org","username":"blk-u"},"change_message_id":"de222a04a1f7955fbf2a379d7c066bc0d29f3a56","unresolved":false,"context_lines":[{"line_number":197,"context_line":"          ..."},{"line_number":198,"context_line":""},{"line_number":199,"context_line":"      If no default value is provided to a keyword argument, it becomes a"},{"line_number":200,"context_line":"      required keyword argument:"},{"line_number":201,"context_line":""},{"line_number":202,"context_line":"        @positional(0)"},{"line_number":203,"context_line":"        def fn(required_kw):"}],"source_content_type":"text/x-python","patch_set":3,"id":"AAAAWH%2F%2F6Zs%3D","line":200,"updated":"2014-03-13 00:24:54.000000000","message":"do :: and add a blank line for rst. this applies throughout the docstring.","commit_id":"2272c21798282e6587807fee20108ff7038322d8"},{"author":{"_account_id":6486,"name":"Brant Knudson","email":"blk@acm.org","username":"blk-u"},"change_message_id":"de222a04a1f7955fbf2a379d7c066bc0d29f3a56","unresolved":false,"context_lines":[{"line_number":210,"context_line":"        fn(required_kw\u003d10)  # Ok."},{"line_number":211,"context_line":""},{"line_number":212,"context_line":"      When defining instance or class methods always remember to account for"},{"line_number":213,"context_line":"      \u0027self\u0027 and \u0027cls\u0027:"},{"line_number":214,"context_line":""},{"line_number":215,"context_line":"        class MyClass(object):"},{"line_number":216,"context_line":""}],"source_content_type":"text/x-python","patch_set":3,"id":"AAAAWH%2F%2F6bM%3D","line":213,"updated":"2014-03-13 00:24:54.000000000","message":"suggest provide a positional.method and positional.class_method that can be used for methods and class methods.  positional.classmethod could automatically add @classmethod, too?","commit_id":"2272c21798282e6587807fee20108ff7038322d8"},{"author":{"_account_id":6486,"name":"Brant Knudson","email":"blk@acm.org","username":"blk-u"},"change_message_id":"14fa81d8aa4e0427df851b4e255d8e9c5c7e1346","unresolved":false,"context_lines":[{"line_number":208,"context_line":""},{"line_number":209,"context_line":"        class MyClass(object):"},{"line_number":210,"context_line":""},{"line_number":211,"context_line":"            @positional(2)"},{"line_number":212,"context_line":"            def my_method(self, pos1, kwonly1\u003dNone):"},{"line_number":213,"context_line":"                ..."},{"line_number":214,"context_line":""}],"source_content_type":"text/x-python","patch_set":6,"id":"AAAAWH%2F%2B3Ic%3D","line":211,"updated":"2014-03-22 16:00:16.000000000","message":"how about provide a positional.method() that just adds 1 to the input.","commit_id":"bdecbf9d6d43b228f00527f7304e853cc81cd929"},{"author":{"_account_id":6486,"name":"Brant Knudson","email":"blk@acm.org","username":"blk-u"},"change_message_id":"14fa81d8aa4e0427df851b4e255d8e9c5c7e1346","unresolved":false,"context_lines":[{"line_number":213,"context_line":"                ..."},{"line_number":214,"context_line":""},{"line_number":215,"context_line":"            @classmethod"},{"line_number":216,"context_line":"            @positional(2)"},{"line_number":217,"context_line":"            def my_method(cls, pos1, kwonly1\u003dNone):"},{"line_number":218,"context_line":"                ..."},{"line_number":219,"context_line":""}],"source_content_type":"text/x-python","patch_set":6,"id":"AAAAWH%2F%2B3IU%3D","line":216,"updated":"2014-03-22 16:00:16.000000000","message":"how about provide a positional.classmethod() that adds 1 and automatically wraps in classmethod?","commit_id":"bdecbf9d6d43b228f00527f7304e853cc81cd929"},{"author":{"_account_id":6486,"name":"Brant Knudson","email":"blk@acm.org","username":"blk-u"},"change_message_id":"14fa81d8aa4e0427df851b4e255d8e9c5c7e1346","unresolved":false,"context_lines":[{"line_number":229,"context_line":"        fn(10, kwonly1\u003d20)  # Ok."},{"line_number":230,"context_line":""},{"line_number":231,"context_line":"    For compatibility reasons you may wish to not always raise an exception so"},{"line_number":232,"context_line":"    a WARN mode is available. Rather than throw an exception a warning message"},{"line_number":233,"context_line":"    will be logged::"},{"line_number":234,"context_line":""},{"line_number":235,"context_line":"        @positional(1, enforcement\u003dpositional.WARN):"}],"source_content_type":"text/x-python","patch_set":6,"id":"AAAAWH%2F%2B3IM%3D","line":232,"updated":"2014-03-22 16:00:16.000000000","message":"change \"throw\" to \"raise\"","commit_id":"bdecbf9d6d43b228f00527f7304e853cc81cd929"},{"author":{"_account_id":6486,"name":"Brant Knudson","email":"blk@acm.org","username":"blk-u"},"change_message_id":"14fa81d8aa4e0427df851b4e255d8e9c5c7e1346","unresolved":false,"context_lines":[{"line_number":240,"context_line":""},{"line_number":241,"context_line":"    - positional.EXCEPT - the default, raise an exception."},{"line_number":242,"context_line":"    - positional.WARN - log a warning on mistake."},{"line_number":243,"context_line":"    - positional.NONE - do nothing."},{"line_number":244,"context_line":"    \"\"\""},{"line_number":245,"context_line":""},{"line_number":246,"context_line":"    EXCEPT \u003d \u0027except\u0027"}],"source_content_type":"text/x-python","patch_set":6,"id":"AAAAWH%2F%2B3II%3D","line":243,"updated":"2014-03-22 16:00:16.000000000","message":"what\u0027s the point of NONE? Just don\u0027t use the wrapper.","commit_id":"bdecbf9d6d43b228f00527f7304e853cc81cd929"}]}
