diff --git a/core/authentication/api_v2.py b/core/authentication/api_v2.py index 019a0fd..cebb344 100644 --- a/core/authentication/api_v2.py +++ b/core/authentication/api_v2.py @@ -14,9 +14,21 @@ from authentication.models import ExtendedUser class UserSerializer(serializers.ModelSerializer): + permissions = serializers.SerializerMethodField() + class Meta: model = ExtendedUser - fields = ('id', 'username', 'email', 'first_name', 'last_name') + fields = ('id', 'username', 'email', 'first_name', 'last_name', 'permissions') + read_only_fields = ('id', 'username', 'email', 'first_name', 'last_name', 'permissions') + + def collect_permissions(self, obj): + for permission in obj.get_all_permissions(): + yield "*:" + permission + for permission in obj.event_permissions.all(): + yield permission.event.slug + ":" + permission.permission.codename + + def get_permissions(self, obj): + return list(self.collect_permissions(obj)) @receiver(post_save, sender=ExtendedUser) @@ -30,7 +42,7 @@ class UserViewSet(viewsets.ModelViewSet): serializer_class = UserSerializer -@api_view(['POST']) +@api_view(['GET']) @permission_classes([IsAuthenticated]) def selfUser(request): serializer = UserSerializer(request.user) diff --git a/core/authentication/tests/v2/test_permissions.py b/core/authentication/tests/v2/test_permissions.py index bb184cf..0a00fcd 100644 --- a/core/authentication/tests/v2/test_permissions.py +++ b/core/authentication/tests/v2/test_permissions.py @@ -65,7 +65,6 @@ class PermissionsTestCase(TestCase): user.event_permissions.create(permission=Permission.objects.get(codename='view_item'), event=Event.objects.get(slug='testevent2')) user.event_permissions.create(permission=Permission.objects.get(codename='add_item'), event=Event.objects.get(slug='testevent1')) user.save() - print(user.get_all_permissions()) #self.assertTrue(user.has_perm('inventory.view_event', Event.objects.get(slug='testevent1'))) #self.assertTrue(user.has_perm('inventory.view_event', Event.objects.get(slug='testevent2'))) #self.assertFalse(user.has_perm('inventory.add_event', Event.objects.get(slug='testevent1'))) diff --git a/core/authentication/tests/v2/test_users.py b/core/authentication/tests/v2/test_users.py index 6838e64..de979ed 100644 --- a/core/authentication/tests/v2/test_users.py +++ b/core/authentication/tests/v2/test_users.py @@ -1,17 +1,30 @@ from django.test import TestCase, Client -from django.contrib.auth.models import Permission +from django.contrib.auth.models import Permission, Group from knox.models import AuthToken -from authentication.models import ExtendedUser +from authentication.models import ExtendedUser, EventPermission from core import settings +from inventory.models import Event class UserApiTest(TestCase): def setUp(self): + self.event = Event.objects.create(name='testevent', slug='testevent') + self.group1 = Group.objects.create(name='testgroup1') + self.group2 = Group.objects.create(name='testgroup2') + self.group1.permissions.add(Permission.objects.get(codename='add_item')) + self.group1.permissions.add(Permission.objects.get(codename='view_item')) + self.group2.permissions.add(Permission.objects.get(codename='view_event')) + self.group2.permissions.add(Permission.objects.get(codename='view_item')) self.user = ExtendedUser.objects.create_user('testuser', 'test', 'test') - self.user.user_permissions.add(*Permission.objects.all()) + self.user.user_permissions.add(Permission.objects.get(codename='add_event')) + self.user.groups.add(self.group1) + self.user.groups.add(self.group2) + self.user.save() + EventPermission.objects.create(event=self.event, user=self.user, + permission=Permission.objects.get(codename='delete_item')) self.user.save() self.token = AuthToken.objects.create(user=self.user) self.client = Client(headers={'Authorization': 'Token ' + self.token[1]}) @@ -31,12 +44,14 @@ class UserApiTest(TestCase): self.assertEqual(response.json()[1]['last_name'], '') def test_self_user(self): - response = self.client.post('/api/2/self/') + response = self.client.get('/api/2/self/') self.assertEqual(response.status_code, 200) self.assertEqual(response.json()['username'], 'testuser') self.assertEqual(response.json()['email'], 'test') self.assertEqual(response.json()['first_name'], '') self.assertEqual(response.json()['last_name'], '') + permissions = response.json()['permissions'] + self.assertEqual(len(permissions), 5) def test_register_user(self): anonymous = Client() diff --git a/web/src/store/index.js b/web/src/store/index.js index 2edd9ff..49eeb49 100644 --- a/web/src/store/index.js +++ b/web/src/store/index.js @@ -63,6 +63,7 @@ const store = new Vuex.Store({ events: [], layout: 'cards', loadedItems: [], + itemCache: {}, loadedBoxes: [], toasts: [], tickets: [], @@ -111,6 +112,9 @@ const store = new Vuex.Store({ replaceLoadedItems(state, newItems) { state.loadedItems = newItems; }, + setItemCache(state, {slug, items}) { + state.itemCache[slug] = items; + }, setLayout(state, layout) { state.layout = layout; }, @@ -213,20 +217,24 @@ const store = new Vuex.Store({ router.push('/login'); }, async afterLogin({dispatch}) { - await dispatch('loadBoxes'); - await dispatch('loadEventItems'); - await dispatch('loadTickets'); + const boxes = dispatch('loadBoxes'); + const items = dispatch('loadEventItems'); + const tickets = dispatch('loadTickets'); + const user = dispatch('loadUserInfo'); }, async fetchImage({state}, url) { return await fetch(url, {headers: {'Authorization': `Token ${state.token}`}}); }, + async loadUserInfo({commit}) { + const {data} = await axios.get('/2/self/'); + commit('setUser', data.username); + }, async loadEvents({commit}) { const {data} = await axios.get('/2/events/'); commit('replaceEvents', data); }, changeEvent({dispatch, getters, commit}, eventName) { router.push({path: `/${eventName.slug}/${getters.getActiveView}/`}); - commit('replaceLoadedItems', []); dispatch('loadEventItems'); }, changeView({getters}, link) { @@ -235,10 +243,16 @@ const store = new Vuex.Store({ showBoxContent({getters}, box) { router.push({path: `/${getters.getEventSlug}/items/`, query: {box}}); }, - async loadEventItems({commit, getters}) { + async loadEventItems({commit, getters, state}) { try { - const {data} = await axios.get(`/2/${getters.getEventSlug}/items/`); + commit('replaceLoadedItems', []); + const slug = getters.getEventSlug; + if( slug in state.itemCache ) { + commit('replaceLoadedItems', state.itemCache[slug]); + } + const {data} = await axios.get(`/2/${slug}/items/`); commit('replaceLoadedItems', data); + commit('setItemCache', {slug, items: data}); } catch (e) { console.error("Error loading items"); }