How to write swagger base on serializer class in django to if we change fields, no need to edit swagger manually
I have end point in Django and I use DRF. I want to swagger generate document base on serializer class but I dont know how to do that. I prompt with chat gpt but there is no solution that i can find and every time generate swagger code with OpenAPI with manual parameters. I give you guys some example of my codes and appreciate to help me. before this view, if I dont have serializer, I write manually with @swagger_auto_schema and give parameters and reponses code manual. please note that I'm new in web development. thanks.
class MemberListView(CustomPagedListView, ListAPIView):
"""
Provides the Organization Member list
"""
permission_classes = [UserIsOrganizationAdmin]
serializer_class = OrganizationMemberRawSerializer
page_size = 10
def get_queryset(self):
try:
query, include_contracts = self.create_query(self.request.GET)
sort_by = self.request.GET.get("sort", "name")
if include_contracts:
organization_members = (
OrganizationMember.existing_objects.prefetch_related(
"contracts"
).filter(query)
).distinct()
else:
organization_members = OrganizationMember.existing_objects.filter(
query
).distinct()
str_field = self.request.GET.get("query", "").lower()
rate = self.request.GET.get("rate", "").strip()
if str_field + rate == "":
return self.sort_data(organization_members, sort_by)
selected_organization_member_ids = []
for item in organization_members:
if (
str_field != ""
and rate != ""
and self.check_str_field_found(item, str_field)
and self.check_rate_filter(item, rate)
):
selected_organization_member_ids.append(item.id)
if (
str_field != ""
and rate == ""
and self.check_str_field_found(item, str_field)
):
selected_organization_member_ids.append(item.id)
if (
str_field == ""
and rate != ""
and self.check_rate_filter(item, rate)
):
selected_organization_member_ids.append(item.id)
return self.sort_data(
OrganizationMember.existing_objects.filter(
id__in=selected_organization_member_ids
),
sort_by,
)
except Exception as ex:
logger.error("*" * 152)
logger.error("MemberListView :: get_queryset " + str(ex))
logger.error("*" * 152)
raise ValidationError400(
{
"result": "false",
"message": MessagesEnum.GENERAL_LOAD_DATA_ERROR.value,
}
)
def check_str_field_found(self, item, str_field):
if (
str_field != ""
and str_field
not in item.first_name_e.lower()
+ " "
+ item.last_name_e.lower()
+ "|"
+ item.username_e.lower()
):
return False
return True
def check_rate_filter(self, item, rate):
can_append = True
item_last_rate = item.get_current_rate()
if rate != "" and item_last_rate == "":
return False
dec_rate = item_last_rate
if dec_rate == "":
return False
if (
rate != ""
and ">" not in rate
and "<" not in rate
and item_last_rate != ""
and int(dec_rate) != int(rate)
):
can_append = False
if (
">" in rate
and item_last_rate != ""
and float(dec_rate) < int(rate.replace(">", ""))
):
can_append = False
if (
"<" in rate
and item_last_rate != ""
and float(dec_rate) > int(rate.replace("<", ""))
):
can_append = False
return can_append
def sort_data(self, organization_members, sort_by):
mindate = datetime.date(datetime.MINYEAR, 1, 1)
for obj in organization_members:
obj.name = obj.first_name_e
obj.date_joined_str = obj.get_date_joined_str()
obj.rate = obj.get_current_rate()
obj.rate2 = obj.rate if obj.rate else 0
obj.contract_end_date = obj.get_current_contract_end_date()
obj.contract_end_date_str = obj.get_current_contract_end_date_str()
obj.working_time = obj.get_current_working_time()
if sort_by == "name":
organization_members = sorted(
organization_members, key=lambda obj: obj.name
)
if sort_by == "-name":
organization_members = sorted(
organization_members, key=lambda obj: obj.name, reverse=True
)
if sort_by == "status":
organization_members = sorted(
organization_members, key=lambda obj: obj.is_active, reverse=True
)
if sort_by == "-status":
organization_members = sorted(
organization_members, key=lambda obj: obj.is_active
)
if sort_by == "date_joined":
organization_members = sorted(
organization_members, key=lambda obj: obj.date_joined
)
if sort_by == "-date_joined":
organization_members = sorted(
organization_members, key=lambda obj: obj.date_joined, reverse=True
)
if sort_by == "rate":
organization_members = sorted(
organization_members, key=lambda obj: obj.rate2
)
if sort_by == "-rate":
organization_members = sorted(
organization_members, key=lambda obj: obj.rate2, reverse=True
)
if sort_by == "contract_date":
organization_members = sorted(
organization_members, key=lambda obj: obj.contract_end_date or mindate
)
if sort_by == "-contract_date":
organization_members = sorted(
organization_members,
key=lambda obj: obj.contract_end_date or mindate,
reverse=True,
)
if sort_by == "working_time":
organization_members = sorted(
organization_members, key=lambda obj: obj.working_time
)
if sort_by == "-working_time":
organization_members = sorted(
organization_members, key=lambda obj: obj.working_time, reverse=True
)
return organization_members
def create_query(self, params):
query = Q(organization_id=self.request.user.organization.id)
join_date_from = params.get("join-date-from")
join_date_to = params.get("join-date-to")
contract_from = params.get("contract-from")
contract_to = params.get("contract-to")
working_time = params.get("working-time", "").strip()
status = params.get("status", "all").lower()
include_contracts = False
if join_date_from:
join_date_from = datetime.datetime.strptime(
join_date_from, settings.API_PARAMS_DATE_FORMAT
)
query.add(Q(date_joined__gte=join_date_from), Q.AND)
if join_date_to:
join_date_to = datetime.datetime.strptime(
join_date_to, settings.API_PARAMS_DATE_FORMAT
) + datetime.timedelta(days=1)
query.add(Q(date_joined__lt=join_date_to), Q.AND)
if status != "all":
query.add(Q(is_active=(status == "active")), Q.AND)
if contract_from:
contract_from = datetime.datetime.strptime(
contract_from, settings.API_PARAMS_DATE_FORMAT
)
query.add(Q(contracts__contract_end_date__gte=contract_from), Q.AND)
include_contracts = True
if contract_to:
contract_to = datetime.datetime.strptime(
contract_to, settings.API_PARAMS_DATE_FORMAT
) + datetime.timedelta(days=1)
query.add(Q(contracts__contract_end_date__lt=contract_to), Q.AND)
include_contracts = True
if working_time != "" and ">" not in working_time and "<" not in working_time:
query.add(
Q(contracts__working_time=int(working_time)),
Q.AND,
)
include_contracts = True
if ">" in working_time:
query.add(
Q(contracts__working_time__gte=int(working_time.replace(">", ""))),
Q.AND,
)
include_contracts = True
if "<" in working_time:
query.add(
Q(contracts__working_time__lte=int(working_time.replace("<", ""))),
Q.AND,
)
include_contracts = True
if include_contracts:
query.add(
Q(contracts__contract_end_date__gt=datetime.datetime.today()),
Q.AND,
)
return query, include_contracts
and here is my serializer:
class OrganizationMemberRawSerializer(OrganizationMemberBaseSerializer):
first_name = serializers.CharField(source="first_name_e")
last_name = serializers.CharField(source="last_name_e")
username = serializers.CharField(source="username_e")
date_joined_str = serializers.CharField()
rate = serializers.CharField()
contract_end_date_str = serializers.CharField()
working_time = serializers.CharField()
class Meta:
model = OrganizationMember
fields = [
"uuid",
"first_name",
"last_name",
"email",
"username",
"first_name_e",
"last_name_e",
"username_e",
"photo",
"is_active",
"date_joined",
"date_joined_str",
"rate",
"contract_end_date_str",
"working_time",
]