Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Idf2 #509

Merged
merged 8 commits into from
Dec 10, 2023
2 changes: 2 additions & 0 deletions backend/settings.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,8 @@
DEBUG = True

ALLOWED_HOSTS = ['*']
CORS_ORIGIN_WHITELIST = ['https://www.insti.app','https://api.insti.app', 'https://gymkhana.iitb.ac.in', 'http://10.105.177.175', 'http://localhost:4200', 'http://10.198.49.175']
CORS_ALLOW_CREDENTIALS = True

# SSO Config
SSO_TOKEN_URL = 'https://gymkhana.iitb.ac.in/sso/oauth/token/'
Expand Down
1 change: 1 addition & 0 deletions community/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
from uuid import uuid4
from django.db import models
from helpers.misc import get_url_friendly
from users.models import UserProfile

class Community(models.Model):
id = models.UUIDField(primary_key=True, default=uuid4, editable=False)
Expand Down
15 changes: 14 additions & 1 deletion community/serializer_min.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
from achievements.serializers import InterestSerializer
from bodies.serializer_min import BodySerializerMin
from community.models import Community, CommunityPost
from users.models import UserProfile
from users.serializers import UserProfileSerializer

class CommunitySerializerMin(serializers.ModelSerializer):
Expand Down Expand Up @@ -36,7 +37,8 @@ class CommunityPostSerializerMin(serializers.ModelSerializer):
reactions_count = serializers.SerializerMethodField()
user_reaction = serializers.SerializerMethodField()
comments_count = serializers.SerializerMethodField()
posted_by = UserProfileSerializer(read_only=True)
# posted_by = UserProfileSerializer(read_only=True)
posted_by = serializers.SerializerMethodField()
image_url = serializers.SerializerMethodField()
most_liked_comment = serializers.SerializerMethodField()
community = CommunitySerializerMin(read_only=True)
Expand All @@ -45,6 +47,17 @@ class CommunityPostSerializerMin(serializers.ModelSerializer):
interests = InterestSerializer(read_only=True, many=True)
has_user_reported = serializers.SerializerMethodField()

def get_posted_by(self, obj):
pb = UserProfile.objects.get(id=obj.posted_by.id)
if(obj.anonymous and "return_for_mod" in self.context and not self.context["return_for_mod"]):
pb.name = "Anonymous"
pb.id = "null"
pb.ldap_id = "null"
pb.profile_pic = "https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcSM9q9XJKxlskry5gXTz1OXUyem5Ap59lcEGg&usqp=CAU"
elif(obj.anonymous and "return_for_mod" in self.context and self.context["return_for_mod"]):
pb.name += " (Anon)"
return UserProfileSerializer(pb).data

def get_most_liked_comment(self, obj):
"""Get the most liked comment of the community post """
queryset = obj.comments.filter(deleted=False, status=1)
Expand Down
13 changes: 13 additions & 0 deletions community/serializers.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
from roles.serializers import RoleSerializerMin
from users.models import UserProfile
from bodies.models import Body
from users.serializers import UserProfileSerializer

class CommunitySerializers(serializers.ModelSerializer):

Expand Down Expand Up @@ -57,10 +58,22 @@ def setup_eager_loading(queryset, request):

class CommunityPostSerializers(CommunityPostSerializerMin):
comments = serializers.SerializerMethodField()
posted_by = serializers.SerializerMethodField()

def get_comments(self, obj):
comments = obj.comments.filter(deleted=False, status=1)
return CommunityPostSerializerMin(comments, many=True).data

def get_posted_by(self, obj):
pb = UserProfile.objects.get(id=obj.posted_by.id)
if(obj.anonymous and "return_for_mod" in self.context and not self.context["return_for_mod"]):
pb.name = "Anonymous"
pb.id = "null"
pb.ldap_id = "null"
pb.profile_pic = "https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcSM9q9XJKxlskry5gXTz1OXUyem5Ap59lcEGg&usqp=CAU"
elif(obj.anonymous and "return_for_mod" in self.context and self.context["return_for_mod"]):
pb.name += " (Anon)"
return UserProfileSerializer(pb).data

class Meta:
model = CommunityPost
Expand Down
1 change: 1 addition & 0 deletions community/urls.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
urlpatterns = [
path('communities', CommunityViewSet.as_view({
'get': 'list',
'post': 'create'
})), # viewing the list of communities

path('communities/<pk>', CommunityViewSet.as_view({
Expand Down
34 changes: 28 additions & 6 deletions community/views.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
from roles.helpers import forbidden_no_privileges
from helpers.misc import query_from_num
from helpers.misc import query_search

from users.models import UserProfile
class ModeratorViewSet(viewsets.ModelViewSet):
queryset = CommunityPost.objects
serializer_class = CommunityPostSerializers
Expand Down Expand Up @@ -62,7 +62,10 @@ def retrieve_full(self, request, pk):

self.queryset = CommunityPostSerializers.setup_eager_loading(self.queryset, request)
post = self.get_community_post(pk)
serialized = CommunityPostSerializers(post, context={'request': request}).data
return_for_mod = False
if(user_has_privilege(request.user.profile, post.community.body.id, "AppP")):
return_for_mod = True
serialized = CommunityPostSerializers(post, context={'return_for_mod': return_for_mod}).data

return Response(serialized)

Expand All @@ -73,24 +76,32 @@ def list(self, request):

# Check for time and date filtered query params
status = request.GET.get("status")
comm_id = request.GET.get("community")
if comm_id is None:
return Response({"message": "comm_id is required"}, status=400)
community = get_object_or_404(Community.objects, id=comm_id)

# If your posts
if status is None:
queryset = CommunityPost.objects.filter(thread_rank=1, posted_by=request.user
queryset = CommunityPost.objects.filter(thread_rank=1, community=community, posted_by=request.user
.profile).order_by("-time_of_modification")
else:
# If reported posts
if status == "3":
queryset = CommunityPost.objects.filter(status=status, deleted=False).order_by("-time_of_modification")
queryset = CommunityPost.objects.filter(
status=status, community=community, deleted=False).order_by("-time_of_modification")
# queryset = CommunityPost.objects.all()

else:
queryset = CommunityPost.objects.filter(
status=status, deleted=False, thread_rank=1).order_by("-time_of_modification")
status=status, community=community, deleted=False, thread_rank=1).order_by("-time_of_modification")
queryset = query_search(request, 3, queryset, ['content'], 'posts')
queryset = query_from_num(request, 20, queryset)
return_for_mod = False
if(user_has_privilege(request.user.profile, community.body.id, "AppP")):
return_for_mod = True

serializer = CommunityPostSerializerMin(queryset, many=True, context={'request': request})
serializer = CommunityPostSerializerMin(queryset, many=True, context={'return_for_mod': return_for_mod})
data = serializer.data

return Response({'count': len(data), 'data': data})
Expand All @@ -103,6 +114,7 @@ def create(self, request):
if 'community' not in request.data or not request.data['community']:
return forbidden_no_privileges()

user, created = UserProfile.objects.get_or_create(user=request.user)
return super().create(request)

@login_required_ajax
Expand Down Expand Up @@ -203,3 +215,13 @@ def get_community(self, pk):
return get_object_or_404(self.queryset, id=pk)
except ValueError:
return get_object_or_404(self.queryset, str_id=pk)

@login_required_ajax
def create(self, request):
name = request.data['name']
user, created = UserProfile.objects.get_or_create(user=request.user)
if not Community.objects.all().filter(name=name).exists():
super().create(request)
return Response({"message": "Community created"})

return Response({"message": "Community already exists"}, status=400)
5 changes: 3 additions & 2 deletions other/tasks.py
Original file line number Diff line number Diff line change
Expand Up @@ -78,8 +78,9 @@ def notify_new_commpost(pk):

for interest in instance.interests.all():
users = User.objects.filter(
id__in=UserInterest.filter(title=interest.title).user.filter(active=True).values('user_id')
)

id__in=UserInterest.objects.filter(title=interest.title)).filter(is_active=True).values('id')

notify.send(
instance,
recipient=users,
Expand Down
1 change: 1 addition & 0 deletions roles/admin.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ class BodyRoleAdmin(admin.ModelAdmin):
list_display = ('name', 'body', 'permissions')
search_fields = ('body__name', 'name')


class InstittuteRoleAdmin(admin.ModelAdmin):
list_display = ('name', 'permissions')
search_fields = ['name']
Expand Down
2 changes: 2 additions & 0 deletions roles/helpers.py
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,8 @@ def user_has_community_privilege(profile, communityid, privilege):
return True
return False



def user_has_insti_privilege(profile, privilege):
"""Returns true if UserProfile has the institute privilege."""
return check_roles(profile.institute_roles.all(), privilege)
Expand Down
36 changes: 36 additions & 0 deletions roles/migrations/0020_communityrole.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
# Generated by Django 3.2.16 on 2023-07-07 14:40

from django.db import migrations, models
import django.db.models.deletion
import multiselectfield.db.fields
import uuid


class Migration(migrations.Migration):

dependencies = [
('community', '0028_auto_20221003_2130'),
('roles', '0019_alter_bodyrole_permissions'),
]

operations = [
migrations.CreateModel(
name='CommunityRole',
fields=[
('id', models.UUIDField(default=uuid.uuid4, editable=False, primary_key=True, serialize=False)),
('time_of_creation', models.DateTimeField(auto_now_add=True)),
('name', models.CharField(max_length=50)),
('inheritable', models.BooleanField(default=False)),
('permissions', multiselectfield.db.fields.MultiSelectField(choices=[('AddE', 'Add Event'), ('UpdE', 'Update Event'), ('DelE', 'Delete Event'), ('UpdB', 'Update Body'), ('Role', 'Modify Roles'), ('VerA', 'Verify Achievements'), ('AppP', 'Moderate Post'), ('ModC', 'Moderate Comment')], max_length=39)),
('priority', models.IntegerField(default=0)),
('official_post', models.BooleanField(default=True)),
('permanent', models.BooleanField(default=False)),
('community', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='roles', to='community.community')),
],
options={
'verbose_name': 'Community Role',
'verbose_name_plural': 'Community Roles',
'ordering': ('community__name', 'priority'),
},
),
]
17 changes: 17 additions & 0 deletions roles/migrations/0021_delete_communityrole.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
# Generated by Django 3.2.16 on 2023-07-22 13:35

from django.db import migrations


class Migration(migrations.Migration):

dependencies = [
('users', '0043_remove_userprofile_community_roles'),
('roles', '0020_communityrole'),
]

operations = [
migrations.DeleteModel(
name='CommunityRole',
),
]
25 changes: 25 additions & 0 deletions roles/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,31 @@ class Meta:

def __str__(self):
return self.body.name + " " + self.name

'''
Added Community Role Model : To allow to have various communities in a single body and have different roles for each community.
Ditched For Now
'''
# class CommunityRole(models.Model):
# """A role for a bodywhich can be granted to multiple users."""

# id = models.UUIDField(primary_key=True, default=uuid4, editable=False)
# time_of_creation = models.DateTimeField(auto_now_add=True)
# name = models.CharField(max_length=50)
# community = models.ForeignKey('community.Community', on_delete=models.CASCADE, related_name='roles')
# inheritable = models.BooleanField(default=False)
# permissions = MultiSelectField(choices=PERMISSION_CHOICES)
# priority = models.IntegerField(default=0)
# official_post = models.BooleanField(default=True)
# permanent = models.BooleanField(default=False)

# class Meta:
# verbose_name = "Community Role"
# verbose_name_plural = "Community Roles"
# ordering = ("community__name", "priority")

# def __str__(self):
# return self.community.name + " " + self.name


INSTITUTE_PERMISSION_CHOICES = (
Expand Down
19 changes: 19 additions & 0 deletions users/migrations/0041_userprofile_community_roles.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
# Generated by Django 3.2.16 on 2023-07-07 14:40

from django.db import migrations, models


class Migration(migrations.Migration):

dependencies = [
('roles', '0020_communityrole'),
('users', '0040_remove_userprofile_followed_communities'),
]

operations = [
migrations.AddField(
model_name='userprofile',
name='community_roles',
field=models.ManyToManyField(blank=True, related_name='users', to='roles.CommunityRole'),
),
]
19 changes: 19 additions & 0 deletions users/migrations/0042_userprofile_followed_communities.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
# Generated by Django 3.2.16 on 2023-07-07 23:27

from django.db import migrations, models


class Migration(migrations.Migration):

dependencies = [
('community', '0028_auto_20221003_2130'),
('users', '0041_userprofile_community_roles'),
]

operations = [
migrations.AddField(
model_name='userprofile',
name='followed_communities',
field=models.ManyToManyField(blank=True, related_name='community_followers', to='community.Community'),
),
]
17 changes: 17 additions & 0 deletions users/migrations/0043_remove_userprofile_community_roles.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
# Generated by Django 3.2.16 on 2023-07-22 13:35

from django.db import migrations


class Migration(migrations.Migration):

dependencies = [
('users', '0042_userprofile_followed_communities'),
]

operations = [
migrations.RemoveField(
model_name='userprofile',
name='community_roles',
),
]
17 changes: 17 additions & 0 deletions users/migrations/0044_remove_userprofile_followed_communities.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
# Generated by Django 3.2.16 on 2023-07-24 18:08

from django.db import migrations


class Migration(migrations.Migration):

dependencies = [
('users', '0043_remove_userprofile_community_roles'),
]

operations = [
migrations.RemoveField(
model_name='userprofile',
name='followed_communities',
),
]
3 changes: 2 additions & 1 deletion users/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -48,13 +48,14 @@ class UserProfile(models.Model):
# InstiApp feature fields
active = models.BooleanField(default=True)
followed_bodies = models.ManyToManyField('bodies.Body', related_name='followers', blank=True)

# InstiApp roles
roles = models.ManyToManyField('roles.BodyRole', related_name='users', blank=True)
former_roles = models.ManyToManyField(
'roles.BodyRole', related_name='former_users', blank=True, through='UserFormerRole')
institute_roles = models.ManyToManyField(
'roles.InstituteRole', related_name='users', blank=True)

# community_roles = models.ManyToManyField('roles.CommunityRole', related_name='users', blank=True)
# User exposed fields
show_contact_no = models.BooleanField(default=False)
fcm_id = models.CharField(max_length=200, null=True, blank=True)
Expand Down