)]}'
{"api-ref/source/v3/parameters.yaml":[{"author":{"_account_id":8482,"name":"Colleen Murphy","email":"colleen@gazlene.net","username":"krinkle"},"change_message_id":"218cc15529b3d9124dd8ba9b011c4574ac93bbd5","unresolved":false,"context_lines":[{"line_number":1244,"context_line":"  in: body"},{"line_number":1245,"context_line":"  required: true"},{"line_number":1246,"context_line":"  type: object"},{"line_number":1247,"context_line":"membership_expires_at:"},{"line_number":1248,"context_line":"  description: |"},{"line_number":1249,"context_line":"    The date and time when the group membership expires."},{"line_number":1250,"context_line":""}],"source_content_type":"text/x-yaml","patch_set":11,"id":"df33271e_56f5a4ec","line":1247,"range":{"start_line":1247,"start_character":0,"end_line":1247,"end_character":21},"updated":"2020-04-07 19:30:08.000000000","message":"this needs to be added to groups.inc","commit_id":"daac4020902bda182635f9e60a81ac07cf107594"},{"author":{"_account_id":8482,"name":"Colleen Murphy","email":"colleen@gazlene.net","username":"krinkle"},"change_message_id":"218cc15529b3d9124dd8ba9b011c4574ac93bbd5","unresolved":false,"context_lines":[{"line_number":1244,"context_line":"  in: body"},{"line_number":1245,"context_line":"  required: true"},{"line_number":1246,"context_line":"  type: object"},{"line_number":1247,"context_line":"membership_expires_at:"},{"line_number":1248,"context_line":"  description: |"},{"line_number":1249,"context_line":"    The date and time when the group membership expires."},{"line_number":1250,"context_line":""}],"source_content_type":"text/x-yaml","patch_set":11,"id":"df33271e_d6e09429","line":1247,"range":{"start_line":1247,"start_character":0,"end_line":1247,"end_character":21},"updated":"2020-04-07 19:30:08.000000000","message":"we started trying to use the more descriptive naming convention we discussed a while ago https://etherpad.openstack.org/p/queens-ptg-keystone-doc-cleanup","commit_id":"daac4020902bda182635f9e60a81ac07cf107594"},{"author":{"_account_id":8482,"name":"Colleen Murphy","email":"colleen@gazlene.net","username":"krinkle"},"change_message_id":"218cc15529b3d9124dd8ba9b011c4574ac93bbd5","unresolved":false,"context_lines":[{"line_number":1248,"context_line":"  description: |"},{"line_number":1249,"context_line":"    The date and time when the group membership expires."},{"line_number":1250,"context_line":""},{"line_number":1251,"context_line":"    This is a response object attribute; not valid for requests."},{"line_number":1252,"context_line":"    A ``null`` value indicates that the membership never expires."},{"line_number":1253,"context_line":"  in: body"},{"line_number":1254,"context_line":"  required: true"}],"source_content_type":"text/x-yaml","patch_set":11,"id":"df33271e_b6db507b","line":1251,"range":{"start_line":1251,"start_character":4,"end_line":1251,"end_character":64},"updated":"2020-04-07 19:30:08.000000000","message":"you don\u0027t need to say this, groups.inc will only include it in the response","commit_id":"daac4020902bda182635f9e60a81ac07cf107594"}],"api-ref/source/v3/samples/admin/user-groups-list-response.json":[{"author":{"_account_id":8482,"name":"Colleen Murphy","email":"colleen@gazlene.net","username":"krinkle"},"change_message_id":"6699b58192ae8df42efc0709762180c1d0f5e462","unresolved":false,"context_lines":[{"line_number":7,"context_line":"            \"links\": {"},{"line_number":8,"context_line":"                \"self\": \"https://example.com/identity/v3/groups/ea167b\""},{"line_number":9,"context_line":"            },"},{"line_number":10,"context_line":"            \"membership_expires_at\": null,"},{"line_number":11,"context_line":"            \"name\": \"Developers\""},{"line_number":12,"context_line":"        },"},{"line_number":13,"context_line":"        {"}],"source_content_type":"application/json","patch_set":8,"id":"df33271e_9813e4b8","line":10,"updated":"2020-04-07 13:37:05.000000000","message":"This should be documented in paramaters.yaml too","commit_id":"7170bb0a28b2d28412666d0cca8d1307e7d252a3"}],"keystone/identity/backends/sql.py":[{"author":{"_account_id":8482,"name":"Colleen Murphy","email":"colleen@gazlene.net","username":"krinkle"},"change_message_id":"dac16583cd35ad354944e10e20724ec5e0f92e60","unresolved":false,"context_lines":[{"line_number":346,"context_line":"            # Note(knikolla): We must use the ExpiringGroupMembership model"},{"line_number":347,"context_line":"            # so that we can access the expired property."},{"line_number":348,"context_line":"            query \u003d session.query(model.ExpiringUserGroupMembership)"},{"line_number":349,"context_line":"            query \u003d query.filter(model.UserGroupMembership.user_id \u003d\u003d user_id)"},{"line_number":350,"context_line":"            query \u003d sql.filter_limit_query("},{"line_number":351,"context_line":"                model.UserGroupMembership, query, hints)"},{"line_number":352,"context_line":"            expiring_groups \u003d [row_to_group_dict(r) for r in query.all()"}],"source_content_type":"text/x-python","patch_set":5,"id":"df33271e_a055e252","line":349,"range":{"start_line":349,"start_character":39,"end_line":349,"end_character":58},"updated":"2020-03-24 23:15:35.000000000","message":"isn\u0027t this the wrong model?","commit_id":"f8b3c61c746e399bb23cc82599d98c70fa5e5b3c"},{"author":{"_account_id":16465,"name":"Kristi Nikolla","email":"knikolla@bu.edu","username":"knikolla"},"change_message_id":"97d349533ebfb172a57392a55d220ca25a3d284b","unresolved":false,"context_lines":[{"line_number":346,"context_line":"            # Note(knikolla): We must use the ExpiringGroupMembership model"},{"line_number":347,"context_line":"            # so that we can access the expired property."},{"line_number":348,"context_line":"            query \u003d session.query(model.ExpiringUserGroupMembership)"},{"line_number":349,"context_line":"            query \u003d query.filter(model.UserGroupMembership.user_id \u003d\u003d user_id)"},{"line_number":350,"context_line":"            query \u003d sql.filter_limit_query("},{"line_number":351,"context_line":"                model.UserGroupMembership, query, hints)"},{"line_number":352,"context_line":"            expiring_groups \u003d [row_to_group_dict(r) for r in query.all()"}],"source_content_type":"text/x-python","patch_set":5,"id":"df33271e_cd09312d","line":349,"range":{"start_line":349,"start_character":39,"end_line":349,"end_character":58},"in_reply_to":"df33271e_a055e252","updated":"2020-03-25 14:31:13.000000000","message":"Thank you, good catch. It is. I\u0027m assuming Python\u0027s duck typing made it work since both tables have that identical column.","commit_id":"f8b3c61c746e399bb23cc82599d98c70fa5e5b3c"},{"author":{"_account_id":8482,"name":"Colleen Murphy","email":"colleen@gazlene.net","username":"krinkle"},"change_message_id":"887497c7fc8c6b18f6fc237ca24630c0c66fa0eb","unresolved":false,"context_lines":[{"line_number":359,"context_line":"            # query, therefore we have to apply the limits here again."},{"line_number":360,"context_line":"            return self._apply_limits_to_list(groups + expiring_groups, hints)"},{"line_number":361,"context_line":""},{"line_number":362,"context_line":"    def list_users_in_group(self, group_id, hints):"},{"line_number":363,"context_line":"        with sql.session_for_read() as session:"},{"line_number":364,"context_line":"            self.get_group(group_id)"},{"line_number":365,"context_line":"            query \u003d session.query(model.User).outerjoin(model.LocalUser)"}],"source_content_type":"text/x-python","patch_set":6,"id":"df33271e_8d44841d","line":362,"updated":"2020-04-03 18:16:42.000000000","message":"should we add support to this as well?","commit_id":"37462a3037ab9d229188f591c3df9e26e65e4c62"},{"author":{"_account_id":16465,"name":"Kristi Nikolla","email":"knikolla@bu.edu","username":"knikolla"},"change_message_id":"c669b8af4f7e45350260bd3f3bd573f3d81ae3a5","unresolved":false,"context_lines":[{"line_number":359,"context_line":"            # query, therefore we have to apply the limits here again."},{"line_number":360,"context_line":"            return self._apply_limits_to_list(groups + expiring_groups, hints)"},{"line_number":361,"context_line":""},{"line_number":362,"context_line":"    def list_users_in_group(self, group_id, hints):"},{"line_number":363,"context_line":"        with sql.session_for_read() as session:"},{"line_number":364,"context_line":"            self.get_group(group_id)"},{"line_number":365,"context_line":"            query \u003d session.query(model.User).outerjoin(model.LocalUser)"}],"source_content_type":"text/x-python","patch_set":6,"id":"df33271e_34275cb9","line":362,"in_reply_to":"df33271e_2beffb87","updated":"2020-04-06 16:30:30.000000000","message":"If a user has been assigned a group, and they also carry the group membership from mapping, the listing will have both entries, the normal one and the expiring one.","commit_id":"37462a3037ab9d229188f591c3df9e26e65e4c62"},{"author":{"_account_id":16465,"name":"Kristi Nikolla","email":"knikolla@bu.edu","username":"knikolla"},"change_message_id":"e14cfd56e779fce2f4f0598ad3c2e299b9cdedef","unresolved":false,"context_lines":[{"line_number":359,"context_line":"            # query, therefore we have to apply the limits here again."},{"line_number":360,"context_line":"            return self._apply_limits_to_list(groups + expiring_groups, hints)"},{"line_number":361,"context_line":""},{"line_number":362,"context_line":"    def list_users_in_group(self, group_id, hints):"},{"line_number":363,"context_line":"        with sql.session_for_read() as session:"},{"line_number":364,"context_line":"            self.get_group(group_id)"},{"line_number":365,"context_line":"            query \u003d session.query(model.User).outerjoin(model.LocalUser)"}],"source_content_type":"text/x-python","patch_set":6,"id":"df33271e_a09df867","line":362,"in_reply_to":"df33271e_8d44841d","updated":"2020-04-05 18:06:33.000000000","message":"Sure thing. One thing of note that I realized just now, is the possibility of returning multiple entries with the same user and group going to cause issues with clients? Thinking out loud.","commit_id":"37462a3037ab9d229188f591c3df9e26e65e4c62"},{"author":{"_account_id":8482,"name":"Colleen Murphy","email":"colleen@gazlene.net","username":"krinkle"},"change_message_id":"aa61409066cf0c03921d7fb4dde2db07524a4356","unresolved":false,"context_lines":[{"line_number":359,"context_line":"            # query, therefore we have to apply the limits here again."},{"line_number":360,"context_line":"            return self._apply_limits_to_list(groups + expiring_groups, hints)"},{"line_number":361,"context_line":""},{"line_number":362,"context_line":"    def list_users_in_group(self, group_id, hints):"},{"line_number":363,"context_line":"        with sql.session_for_read() as session:"},{"line_number":364,"context_line":"            self.get_group(group_id)"},{"line_number":365,"context_line":"            query \u003d session.query(model.User).outerjoin(model.LocalUser)"}],"source_content_type":"text/x-python","patch_set":6,"id":"df33271e_2beffb87","line":362,"in_reply_to":"df33271e_a09df867","updated":"2020-04-06 15:02:58.000000000","message":"\u003e is the\n \u003e possibility of returning multiple entries with the same user and\n \u003e group going to cause issues with clients? \n\nI\u0027m not exactly sure what this means. If it\u0027s going to be too complex, we can defer it for now.","commit_id":"37462a3037ab9d229188f591c3df9e26e65e4c62"},{"author":{"_account_id":16465,"name":"Kristi Nikolla","email":"knikolla@bu.edu","username":"knikolla"},"change_message_id":"13082584c73ff49b0c6913ba13320a176051d382","unresolved":false,"context_lines":[{"line_number":359,"context_line":"            # query, therefore we have to apply the limits here again."},{"line_number":360,"context_line":"            return self._apply_limits_to_list(groups + expiring_groups, hints)"},{"line_number":361,"context_line":""},{"line_number":362,"context_line":"    def list_users_in_group(self, group_id, hints):"},{"line_number":363,"context_line":"        with sql.session_for_read() as session:"},{"line_number":364,"context_line":"            self.get_group(group_id)"},{"line_number":365,"context_line":"            query \u003d session.query(model.User).outerjoin(model.LocalUser)"}],"source_content_type":"text/x-python","patch_set":6,"id":"df33271e_e3354aaa","line":362,"in_reply_to":"df33271e_a09df867","updated":"2020-04-05 19:15:09.000000000","message":"This is going to be a bit more complex and I will try to get it done this Monday.","commit_id":"37462a3037ab9d229188f591c3df9e26e65e4c62"}],"keystone/identity/core.py":[{"author":{"_account_id":8482,"name":"Colleen Murphy","email":"colleen@gazlene.net","username":"krinkle"},"change_message_id":"887497c7fc8c6b18f6fc237ca24630c0c66fa0eb","unresolved":false,"context_lines":[{"line_number":1311,"context_line":"        ref_list \u003d driver.list_groups_for_user(entity_id, hints)"},{"line_number":1312,"context_line":"        for ref in ref_list:"},{"line_number":1313,"context_line":"            if \u0027expires\u0027 not in ref:"},{"line_number":1314,"context_line":"                ref[\u0027expires\u0027] \u003d None"},{"line_number":1315,"context_line":"        return self._set_domain_id_and_mapping("},{"line_number":1316,"context_line":"            ref_list, domain_id, driver, mapping.EntityType.GROUP)"},{"line_number":1317,"context_line":""}],"source_content_type":"text/x-python","patch_set":6,"id":"df33271e_8d5da4eb","line":1314,"updated":"2020-04-03 18:16:42.000000000","message":"Is this necessary? would it be okay to just omit this and have the non-existence of the expires key imply that there is no expiry?","commit_id":"37462a3037ab9d229188f591c3df9e26e65e4c62"},{"author":{"_account_id":16465,"name":"Kristi Nikolla","email":"knikolla@bu.edu","username":"knikolla"},"change_message_id":"9ca3ccac0fd44dc860cb0a83da10ae0e1127c6f6","unresolved":false,"context_lines":[{"line_number":1311,"context_line":"        ref_list \u003d driver.list_groups_for_user(entity_id, hints)"},{"line_number":1312,"context_line":"        for ref in ref_list:"},{"line_number":1313,"context_line":"            if \u0027expires\u0027 not in ref:"},{"line_number":1314,"context_line":"                ref[\u0027expires\u0027] \u003d None"},{"line_number":1315,"context_line":"        return self._set_domain_id_and_mapping("},{"line_number":1316,"context_line":"            ref_list, domain_id, driver, mapping.EntityType.GROUP)"},{"line_number":1317,"context_line":""}],"source_content_type":"text/x-python","patch_set":6,"id":"df33271e_205ba887","line":1314,"in_reply_to":"df33271e_8d5da4eb","updated":"2020-04-05 18:17:37.000000000","message":"I\u0027m not sure about the answer to this question. I skimmed the api-wg and they don\u0027t seem to provide guidelines for that. I check on other usage of ours, specifically \u0027password_expires_at\u0027 and that is present and null/None when password for a user do not expire. For now I\u0027m keeping it, and renaming it to `membership_expires_at` to be more descriptive of what is actually expiring. We can talk about this during the meeting if it is okay to ommit entirely and I will be happy to update.","commit_id":"37462a3037ab9d229188f591c3df9e26e65e4c62"}],"keystone/identity/shadow_backends/sql.py":[{"author":{"_account_id":8482,"name":"Colleen Murphy","email":"colleen@gazlene.net","username":"krinkle"},"change_message_id":"dac16583cd35ad354944e10e20724ec5e0f92e60","unresolved":false,"context_lines":[{"line_number":196,"context_line":"                                                   hints)"},{"line_number":197,"context_line":"            return [x.to_dict() for x in fed_user_refs]"},{"line_number":198,"context_line":""},{"line_number":199,"context_line":"    def add_user_to_group_expires(self, user_id, group_id):"},{"line_number":200,"context_line":"        def get_federated_user():"},{"line_number":201,"context_line":"            with sql.session_for_read() as session:"},{"line_number":202,"context_line":"                query \u003d session.query(model.FederatedUser)"}],"source_content_type":"text/x-python","patch_set":5,"id":"df33271e_20c71215","line":199,"range":{"start_line":199,"start_character":8,"end_line":199,"end_character":33},"updated":"2020-03-24 23:15:35.000000000","message":"suggest instead \"add_user_to_expiring_group\"","commit_id":"f8b3c61c746e399bb23cc82599d98c70fa5e5b3c"},{"author":{"_account_id":16465,"name":"Kristi Nikolla","email":"knikolla@bu.edu","username":"knikolla"},"change_message_id":"97d349533ebfb172a57392a55d220ca25a3d284b","unresolved":false,"context_lines":[{"line_number":196,"context_line":"                                                   hints)"},{"line_number":197,"context_line":"            return [x.to_dict() for x in fed_user_refs]"},{"line_number":198,"context_line":""},{"line_number":199,"context_line":"    def add_user_to_group_expires(self, user_id, group_id):"},{"line_number":200,"context_line":"        def get_federated_user():"},{"line_number":201,"context_line":"            with sql.session_for_read() as session:"},{"line_number":202,"context_line":"                query \u003d session.query(model.FederatedUser)"}],"source_content_type":"text/x-python","patch_set":5,"id":"df33271e_6d50e50b","line":199,"range":{"start_line":199,"start_character":8,"end_line":199,"end_character":33},"in_reply_to":"df33271e_20c71215","updated":"2020-03-25 14:31:13.000000000","message":"Sure, can rename. I was trying to avoid the implication that the group itself is expiring rather than the membership.","commit_id":"f8b3c61c746e399bb23cc82599d98c70fa5e5b3c"},{"author":{"_account_id":8482,"name":"Colleen Murphy","email":"colleen@gazlene.net","username":"krinkle"},"change_message_id":"dac16583cd35ad354944e10e20724ec5e0f92e60","unresolved":false,"context_lines":[{"line_number":201,"context_line":"            with sql.session_for_read() as session:"},{"line_number":202,"context_line":"                query \u003d session.query(model.FederatedUser)"},{"line_number":203,"context_line":"                query \u003d query.filter_by(user_id\u003duser_id)"},{"line_number":204,"context_line":"                rv \u003d query.first()"},{"line_number":205,"context_line":"                if not rv:"},{"line_number":206,"context_line":"                    # Note(knikolla): This shouldn\u0027t really ever happen, since"},{"line_number":207,"context_line":"                    # this requires the user to already be logged in."}],"source_content_type":"text/x-python","patch_set":5,"id":"df33271e_a0da02e6","line":204,"range":{"start_line":204,"start_character":16,"end_line":204,"end_character":18},"updated":"2020-03-24 23:15:35.000000000","message":"suggest using a more descriptive variable name","commit_id":"f8b3c61c746e399bb23cc82599d98c70fa5e5b3c"},{"author":{"_account_id":16465,"name":"Kristi Nikolla","email":"knikolla@bu.edu","username":"knikolla"},"change_message_id":"97d349533ebfb172a57392a55d220ca25a3d284b","unresolved":false,"context_lines":[{"line_number":201,"context_line":"            with sql.session_for_read() as session:"},{"line_number":202,"context_line":"                query \u003d session.query(model.FederatedUser)"},{"line_number":203,"context_line":"                query \u003d query.filter_by(user_id\u003duser_id)"},{"line_number":204,"context_line":"                rv \u003d query.first()"},{"line_number":205,"context_line":"                if not rv:"},{"line_number":206,"context_line":"                    # Note(knikolla): This shouldn\u0027t really ever happen, since"},{"line_number":207,"context_line":"                    # this requires the user to already be logged in."}],"source_content_type":"text/x-python","patch_set":5,"id":"df33271e_0d41593a","line":204,"range":{"start_line":204,"start_character":16,"end_line":204,"end_character":18},"in_reply_to":"df33271e_a0da02e6","updated":"2020-03-25 14:31:13.000000000","message":"Will do.","commit_id":"f8b3c61c746e399bb23cc82599d98c70fa5e5b3c"}],"keystone/tests/unit/test_backend_sql.py":[{"author":{"_account_id":27621,"name":"Vishakha Agarwal","email":"agarwalvishakha18@gmail.com","username":"Vishakha"},"change_message_id":"9b84cbc8813b12b2e1e10b8477fcf4a372ecdd4e","unresolved":false,"context_lines":[{"line_number":758,"context_line":"            frozen_time.tick(tick)"},{"line_number":759,"context_line":"            groups \u003d PROVIDERS.identity_api.list_groups_for_user("},{"line_number":760,"context_line":"                new_user[\u0027id\u0027])"},{"line_number":761,"context_line":"            self.assertEqual(len(groups), 1)"},{"line_number":762,"context_line":""},{"line_number":763,"context_line":"    def test_storing_null_domain_id_in_project_ref(self):"},{"line_number":764,"context_line":"        \"\"\"Test the special storage of domain_id\u003dNone in sql resource driver."}],"source_content_type":"text/x-python","patch_set":8,"id":"df33271e_1704e87a","line":761,"range":{"start_line":761,"start_character":12,"end_line":761,"end_character":44},"updated":"2020-04-06 07:26:58.000000000","message":"Would it be more helpful to match the group ids too?","commit_id":"7170bb0a28b2d28412666d0cca8d1307e7d252a3"}]}
