toulouse-maelis: accéder aux données nécessaires pour l'inscription extra-scolaire et loisir (#73648) #59

Merged
nroche merged 1 commits from wip/73648-parsifal-get-person-unit-info into main 2023-02-02 11:15:33 +01:00
5 changed files with 628 additions and 0 deletions

View File

@ -24,6 +24,7 @@ from django.contrib.postgres.fields import JSONField
from django.core.serializers.json import DjangoJSONEncoder
from django.db import models
from django.utils import dateformat
from django.utils.dateparse import parse_date
from django.utils.timezone import now
from zeep.helpers import serialize_object
from zeep.wsse.username import UsernameToken
@ -2433,6 +2434,58 @@ class ToulouseMaelis(BaseResource, HTTPResource):
def read_ape_indicators_list(self, request):
return {'data': self.get_referential('ApeIndicator')}
@endpoint(
display_category='Inscriptions',
description="Informations pour s'inscrire puis réserver sur l'extra-scolaire ou le loisir",
name='get-person-subscription-info',
perm='can_access',
fpeters marked this conversation as resolved Outdated

activité, singulier.

activité, singulier.
parameters={
'person_id': {'description': "Numéro du responsale légal ou de l'enfant"},
'activity_id': {'description': "Numéro de l'activité"},
'unit_id': {'description': "Numéro de l'unité"},
'place_id': {'description': "Numéro du lieu"},
'NameID': {'description': 'Publik NameID'},
'family_id': {'description': 'Numéro de DUI'},
'ref_date': {'description': 'Date du début du calcul'},
},
)
def get_person_subscription_info(
self,
request,
person_id,
activity_id,
unit_id,
place_id,
NameID=None,
family_id=None,
ref_date=None,
):
family_id = family_id or self.get_link(NameID).family_id
if ref_date:
try:
ref_date = parse_date(ref_date)
except ValueError:
raise APIError('%s is not a valid date' % ref_date, err_code='bad-request', http_status=400)
if not ref_date:
raise APIError(
'bad date format, should be YYYY-MM-DD', err_code='bad-request', http_status=400
)
ref_date = ref_date.strftime(utils.json_date_format)

Il me semblerait plus opportun que l'adaptation au format soit effectuée dans la méthode appelée, plutôt qu'avoir à être répétée dans tous les appelants.

Il me semblerait plus opportun que l'adaptation au format soit effectuée dans la méthode appelée, plutôt qu'avoir à être répétée dans tous les appelants.

Il ne me semble pas que ça ait été compris; ci-dessus je notais que la gestion u format du paramètre ref_date aurait à gagner à être géré dans la méthode appelée (get_person_unit_info_raw). Dans la branche actualisée ça n'est toujours pas le cas, l'appelant (get_person_subscribing_info) contient toujours un code d'interprétation de ref_date (curieusement encore plus long qu'avant).

Il ne me semble pas que ça ait été compris; ci-dessus je notais que la gestion u format du paramètre ref_date aurait à gagner à être géré dans la méthode appelée (get_person_unit_info_raw). Dans la branche actualisée ça n'est toujours pas le cas, l'appelant (get_person_subscribing_info) contient toujours un code d'interprétation de ref_date (curieusement encore plus long qu'avant).

Oui, j'ai anticipé la factorisation de l'appel au WS maélis, ce qui n'était pas une bonne idée. Il n'y a plus d'appelé.
(Concernant la taille du code d'interprétation de ref_date, voir la réponse au commentaire ci-dessous.)

Oui, j'ai anticipé la factorisation de l'appel au WS maélis, ce qui n'était pas une bonne idée. Il n'y a plus d'appelé. (Concernant la taille du code d'interprétation de ref_date, voir la réponse au commentaire ci-dessous.)
params = {
'numDossier': family_id,
'numPerson': person_id,
'activityUnitPlace': {
'idActivity': activity_id,
'idUnit': unit_id,
'idPlace': place_id,
},
'dateRef': ref_date,
}
response = self.call('Activity', 'getPersonUnitInfo', getPersonUnitInfoRequestBean=params)
data = serialize_object(response)
return {'data': data}
class Link(models.Model):
resource = models.ForeignKey(ToulouseMaelis, on_delete=models.CASCADE)

View File

@ -0,0 +1,89 @@
<soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<soap:Body>
<ns2:getPersonUnitInfoResponse xmlns:ns2="activity.ws.maelis.sigec.com" xmlns:ns3="bean.persistence.activity.ws.maelis.sigec.com">
<getPersonUnitInfoResponseBean>
<controlResult>
<controlOK>false</controlOK>
<message>E1019 : Il existe déjà une inscription à cette unité</message>
</controlResult>
<personInfo>
<idMaelis>S10053182024</idMaelis>
<num>246423</num>
<lastname>SIMPSON</lastname>
<firstname>BART</firstname>
<dateBirth>2014-04-01T00:00:00+02:00</dateBirth>
<sexe>M</sexe>
</personInfo>
<activity>
<idActivity>A10051141965</idActivity>
<libelle1>Vitrail Fusing 1/2 Je Adultes 2022/2023 - Mardi 14h-17h</libelle1>
<libelle2>Activité modèle</libelle2>
<activityType>
<code>LOI_ADU</code>
<libelle>Loisirs Adultes</libelle>
<natureSpec>
<code>P</code>
<libelle>Loisirs</libelle>
</natureSpec>
</activityType>
<typInsPortal>I</typInsPortal>
<paiementPortal>I</paiementPortal>
</activity>
<calendarGeneration>
<code>FORBIDDEN</code>
<value>I</value>
</calendarGeneration>
<weeklyCalendarActivity>
<dayWeekInfoList>
<dayNum>1</dayNum>
<isOpen>false</isOpen>
</dayWeekInfoList>
<dayWeekInfoList>
<dayNum>2</dayNum>
<isOpen>true</isOpen>
</dayWeekInfoList>
<dayWeekInfoList>
<dayNum>3</dayNum>
<isOpen>true</isOpen>
</dayWeekInfoList>
<dayWeekInfoList>
<dayNum>4</dayNum>
<isOpen>true</isOpen>
</dayWeekInfoList>
<dayWeekInfoList>
<dayNum>5</dayNum>
<isOpen>false</isOpen>
</dayWeekInfoList>
<dayWeekInfoList>
<dayNum>6</dayNum>
<isOpen>false</isOpen>
</dayWeekInfoList>
<dayWeekInfoList>
<dayNum>7</dayNum>
<isOpen>false</isOpen>
</dayWeekInfoList>
</weeklyCalendarActivity>
<openDayList>
<day>2023-01-24T00:00:00+01:00</day>
<hasPlace>true</hasPlace>
</openDayList>
<openDayList>
<day>2023-01-31T00:00:00+01:00</day>
<hasPlace>true</hasPlace>
</openDayList>
<unit>
<idUnit>A10051141990</idUnit>
<libelle>Inscription 1er semestre</libelle>
<dateStart>2022-09-01T00:00:00+02:00</dateStart>
<dateEnd>2023-01-31T00:00:00+01:00</dateEnd>
</unit>
<place>
<idPlace>A10053179226</idPlace>
<lib1>Centre Culturel ALBAN MINVILLE</lib1>
</place>
<billingInformation/>
<action>ADD_SUBSCRIBE</action>
</getPersonUnitInfoResponseBean>
</ns2:getPersonUnitInfoResponse>
</soap:Body>
</soap:Envelope>

View File

@ -0,0 +1,79 @@
<soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<soap:Body>
<ns2:getPersonUnitInfoResponse xmlns:ns2="activity.ws.maelis.sigec.com" xmlns:ns3="bean.persistence.activity.ws.maelis.sigec.com">
<getPersonUnitInfoResponseBean>
<controlResult>
<controlOK>true</controlOK>
</controlResult>
<personInfo>
<idMaelis>S10053182024</idMaelis>
<num>246423</num>
<lastname>SIMPSON</lastname>
<firstname>BART</firstname>
<dateBirth>2014-04-01T00:00:00+02:00</dateBirth>
<sexe>M</sexe>
</personInfo>
<activity>
<idActivity>A10053187087</idActivity>
<libelle1>Vacances Ete 2023</libelle1>
<activityType>
<code>LOI_VAC</code>
<libelle>Loisirs - Vacances</libelle>
<natureSpec>
<code>V</code>
<libelle>Vacances Enfants</libelle>
</natureSpec>
</activityType>
<typInsPortal>I</typInsPortal>
<paiementPortal>I</paiementPortal>
</activity>
<calendarGeneration>
<code>FORBIDDEN</code>
<value>I</value>
</calendarGeneration>
<weeklyCalendarActivity>
<dayWeekInfoList>
<dayNum>1</dayNum>
<isOpen>true</isOpen>
</dayWeekInfoList>
<dayWeekInfoList>
<dayNum>2</dayNum>
<isOpen>true</isOpen>
</dayWeekInfoList>
<dayWeekInfoList>
<dayNum>3</dayNum>
<isOpen>true</isOpen>
</dayWeekInfoList>
<dayWeekInfoList>
<dayNum>4</dayNum>
<isOpen>true</isOpen>
</dayWeekInfoList>
<dayWeekInfoList>
<dayNum>5</dayNum>
<isOpen>true</isOpen>
</dayWeekInfoList>
<dayWeekInfoList>
<dayNum>6</dayNum>
<isOpen>false</isOpen>
</dayWeekInfoList>
<dayWeekInfoList>
<dayNum>7</dayNum>
<isOpen>false</isOpen>
</dayWeekInfoList>
</weeklyCalendarActivity>
<unit>
<idUnit>A10053187241</idUnit>
<libelle>Juillet</libelle>
<dateStart>2023-07-10T00:00:00+02:00</dateStart>
<dateEnd>2023-07-31T00:00:00+02:00</dateEnd>
</unit>
<place>
<idPlace>A10053179604</idPlace>
<lib1>ALEX JANY</lib1>
</place>
<billingInformation/>
<action>ADD_SUBSCRIBE</action>
</getPersonUnitInfoResponseBean>
</ns2:getPersonUnitInfoResponse>
</soap:Body>
</soap:Envelope>

View File

@ -0,0 +1,88 @@
<soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<soap:Body>
<ns2:getPersonUnitInfoResponse xmlns:ns2="activity.ws.maelis.sigec.com" xmlns:ns3="bean.persistence.activity.ws.maelis.sigec.com">
<getPersonUnitInfoResponseBean>
<controlResult>
<controlOK>true</controlOK>
</controlResult>
<personInfo>
<idMaelis>S10053182024</idMaelis>
<num>246423</num>
<lastname>SIMPSON</lastname>
<firstname>BART</firstname>
<dateBirth>2014-04-01T00:00:00+02:00</dateBirth>
<sexe>M</sexe>
</personInfo>
<activity>
<idActivity>A10051141965</idActivity>
<libelle1>Vitrail Fusing 1/2 Je Adultes 2022/2023 - Mardi 14h-17h</libelle1>
<libelle2>Activité modèle</libelle2>
<activityType>
<code>LOI_ADU</code>
<libelle>Loisirs Adultes</libelle>
<natureSpec>
<code>P</code>
<libelle>Loisirs</libelle>
</natureSpec>
</activityType>
<typInsPortal>I</typInsPortal>
<paiementPortal>I</paiementPortal>
</activity>
<calendarGeneration>
<code>FORBIDDEN</code>
<value>I</value>
</calendarGeneration>
<weeklyCalendarActivity>
<dayWeekInfoList>
<dayNum>1</dayNum>
<isOpen>false</isOpen>
</dayWeekInfoList>
<dayWeekInfoList>
<dayNum>2</dayNum>
<isOpen>true</isOpen>
</dayWeekInfoList>
<dayWeekInfoList>
<dayNum>3</dayNum>
<isOpen>true</isOpen>
</dayWeekInfoList>
<dayWeekInfoList>
<dayNum>4</dayNum>
<isOpen>true</isOpen>
</dayWeekInfoList>
<dayWeekInfoList>
<dayNum>5</dayNum>
<isOpen>false</isOpen>
</dayWeekInfoList>
<dayWeekInfoList>
<dayNum>6</dayNum>
<isOpen>false</isOpen>
</dayWeekInfoList>
<dayWeekInfoList>
<dayNum>7</dayNum>
<isOpen>false</isOpen>
</dayWeekInfoList>
</weeklyCalendarActivity>
<openDayList>
<day>2023-01-24T00:00:00+01:00</day>
<hasPlace>true</hasPlace>
</openDayList>
<openDayList>
<day>2023-01-31T00:00:00+01:00</day>
<hasPlace>true</hasPlace>
</openDayList>
<unit>
<idUnit>A10051141990</idUnit>
<libelle>Inscription 1er semestre</libelle>
<dateStart>2022-09-01T00:00:00+02:00</dateStart>
<dateEnd>2023-01-31T00:00:00+01:00</dateEnd>
</unit>
<place>
<idPlace>A10053179226</idPlace>
<lib1>Centre Culturel ALBAN MINVILLE</lib1>
</place>
<billingInformation/>
<action>ADD_SUBSCRIBE</action>
</getPersonUnitInfoResponseBean>
</ns2:getPersonUnitInfoResponse>
</soap:Body>
</soap:Envelope>

View File

@ -5320,3 +5320,322 @@ def test_read_ape_indicator_list(con, app):
for item in resp.json['data']:
assert 'id' in item
assert 'text' in item
def test_get_person_subscription_info_extra_scolaire(activity_service, con, app):
activity_service.add_soap_response(
'getPersonUnitInfo',
get_xml_file('R_get_person_unit_info_extra_scolaire.xml'),
)
url = get_endpoint('get-person-subscription-info')
params = {
'NameID': '',
'family_id': '311323',
'person_id': '246423',
'activity_id': 'A10053187087',
'unit_id': 'A10053187241',
'place_id': 'A10053179604',
'ref_date': '2023-01-22',
}
resp = app.get(url, params=params)
assert resp.json['err'] == 0
Link.objects.create(resource=con, family_id='311323', name_id='local')
params['NameID'] = 'local'
params['family_id'] = ''
resp = app.get(url, params=params)
assert resp.json['err'] == 0
assert resp.json['data'] == {
'controlResult': {'controlOK': True, 'message': None},
'personInfo': {
'idMaelis': 'S10053182024',
'num': 246423,
'lastname': 'SIMPSON',
'firstname': 'BART',
'dateBirth': '2014-04-01T00:00:00+02:00',
'sexe': 'M',
},
'activity': {
'idActivity': 'A10053187087',
'libelle1': 'Vacances Ete 2023',
'libelle2': None,
'activityType': {
'code': 'LOI_VAC',
'libelle': 'Loisirs - Vacances',
'natureSpec': {'code': 'V', 'libelle': 'Vacances Enfants'},
},
'typInsPortal': 'I',
'paiementPortal': 'I',
},
'calendarGeneration': {'code': 'FORBIDDEN', 'value': 'I'},
'weeklyCalendarActivity': {
'dayWeekInfoList': [
{'dayNum': 1, 'isOpen': True},
{'dayNum': 2, 'isOpen': True},
{'dayNum': 3, 'isOpen': True},
{'dayNum': 4, 'isOpen': True},
{'dayNum': 5, 'isOpen': True},
{'dayNum': 6, 'isOpen': False},
{'dayNum': 7, 'isOpen': False},
]
},

Il est bien plus facile depuis w.c.s. de passer un paramètre vide que de ne pas passer de paramètre, pourquoi ce comportement contraire ?

Il est bien plus facile depuis w.c.s. de passer un paramètre vide que de ne pas passer de paramètre, pourquoi ce comportement contraire ?

C'était pour utiliser le type date sur ce paramètre pour ne pas à avoir à gérer les cas d'erreur, mais c'était une mauvaise idée, parce ce type ne fonctionne pas avec un paramètre optionnel.

C'était pour utiliser le type date sur ce paramètre pour ne pas à avoir à gérer les cas d'erreur, mais c'était une mauvaise idée, parce ce type ne fonctionne pas avec un paramètre optionnel.

C'est #72641

C'est #72641
'openDayList': [],
'unit': {
'idUnit': 'A10053187241',
'libelle': 'Juillet',
'dateStart': '2023-07-10T00:00:00+02:00',
'dateEnd': '2023-07-31T00:00:00+02:00',
'placeInfoList': [],
'idIns': None,
},
'place': {
'idPlace': 'A10053179604',
'lib1': 'ALEX JANY',
'lib2': None,
'idIns': None,
'etatIns': None,
'ageStart': None,
'ageEnd': None,
'ctrlPlaces': None,
'listBlocNoteBean': [],
'longitude': None,
'latitude': None,
},
'billingInformation': None,
'action': 'ADD_SUBSCRIBE',
'indicatorList': [],
}
# no date provided
del params['ref_date']
resp = app.get(url, params=params)
assert resp.json['err'] == 0
# passing an empty date
params['ref_date'] = ''
resp = app.get(url, params=params)
assert resp.json['err'] == 0
def test_get_person_subscription_info_loisir(activity_service, con, app):
activity_service.add_soap_response(
'getPersonUnitInfo',
get_xml_file('R_get_person_unit_info_loisir.xml'),
)
url = get_endpoint('get-person-subscription-info')
params = {
'NameID': '',
'family_id': '311323',
'person_id': '246423',
'activity_id': 'A10053187087',
'unit_id': 'A10053187241',
'place_id': 'A10053179604',
'ref_date': '2023-01-22',
}
resp = app.get(url, params=params)
assert resp.json['err'] == 0
Link.objects.create(resource=con, family_id='311323', name_id='local')
params['NameID'] = 'local'
params['family_id'] = ''
resp = app.get(url, params=params)
assert resp.json['err'] == 0
assert resp.json['data'] == {
'controlResult': {'controlOK': True, 'message': None},
'personInfo': {
'idMaelis': 'S10053182024',
'num': 246423,
'lastname': 'SIMPSON',
'firstname': 'BART',
'dateBirth': '2014-04-01T00:00:00+02:00',
'sexe': 'M',
},
'activity': {
'idActivity': 'A10051141965',
'libelle1': 'Vitrail Fusing 1/2 Je Adultes 2022/2023 - Mardi 14h-17h',
'libelle2': 'Activité modèle',
'activityType': {
'code': 'LOI_ADU',
'libelle': 'Loisirs Adultes',
'natureSpec': {'code': 'P', 'libelle': 'Loisirs'},
},
'typInsPortal': 'I',
'paiementPortal': 'I',
},
'calendarGeneration': {'code': 'FORBIDDEN', 'value': 'I'},
'weeklyCalendarActivity': {
'dayWeekInfoList': [
{'dayNum': 1, 'isOpen': False},
{'dayNum': 2, 'isOpen': True},
{'dayNum': 3, 'isOpen': True},
{'dayNum': 4, 'isOpen': True},
{'dayNum': 5, 'isOpen': False},
{'dayNum': 6, 'isOpen': False},
{'dayNum': 7, 'isOpen': False},
]
},
'openDayList': [
{'day': '2023-01-24T00:00:00+01:00', 'hasPlace': True},
{'day': '2023-01-31T00:00:00+01:00', 'hasPlace': True},
],
'unit': {
'idUnit': 'A10051141990',
'libelle': 'Inscription 1er semestre',
'dateStart': '2022-09-01T00:00:00+02:00',
'dateEnd': '2023-01-31T00:00:00+01:00',
'placeInfoList': [],
'idIns': None,
},
'place': {
'idPlace': 'A10053179226',
'lib1': 'Centre Culturel ALBAN MINVILLE',
'lib2': None,
'idIns': None,
'etatIns': None,
'ageStart': None,
'ageEnd': None,
'ctrlPlaces': None,
'listBlocNoteBean': [],
'longitude': None,
'latitude': None,
},
'billingInformation': None,
'action': 'ADD_SUBSCRIBE',
'indicatorList': [],
}
# no date provided
del params['ref_date']
resp = app.get(url, params=params)
assert resp.json['err'] == 0
# passing an empty date
params['ref_date'] = ''
resp = app.get(url, params=params)
assert resp.json['err'] == 0
def test_get_person_subscription_info_error(activity_service, con, app):
activity_service.add_soap_response(
'getPersonUnitInfo',
get_xml_file('R_get_person_unit_info_error.xml'),
)
url = get_endpoint('get-person-subscription-info')
params = {
'NameID': '',
'family_id': '311323',
'person_id': '246423',
'activity_id': 'A10053187087',
'unit_id': 'A10053187241',
'place_id': 'A10053179604',
'ref_date': '2023-01-22',
}
resp = app.get(url, params=params)
assert resp.json['err'] == 0
assert resp.json['data'] == {
'controlResult': {
'controlOK': False,
'message': 'E1019 : Il existe déjà une inscription à cette unité',
},
'personInfo': {
'idMaelis': 'S10053182024',
'num': 246423,
'lastname': 'SIMPSON',
'firstname': 'BART',
'dateBirth': '2014-04-01T00:00:00+02:00',
'sexe': 'M',
},
'activity': {
'idActivity': 'A10051141965',
'libelle1': 'Vitrail Fusing 1/2 Je Adultes 2022/2023 - Mardi 14h-17h',
'libelle2': 'Activité modèle',
'activityType': {
'code': 'LOI_ADU',
'libelle': 'Loisirs Adultes',
'natureSpec': {'code': 'P', 'libelle': 'Loisirs'},
},
'typInsPortal': 'I',
'paiementPortal': 'I',
},
'calendarGeneration': {'code': 'FORBIDDEN', 'value': 'I'},
'weeklyCalendarActivity': {
'dayWeekInfoList': [
{'dayNum': 1, 'isOpen': False},
{'dayNum': 2, 'isOpen': True},
{'dayNum': 3, 'isOpen': True},
{'dayNum': 4, 'isOpen': True},
{'dayNum': 5, 'isOpen': False},
{'dayNum': 6, 'isOpen': False},
{'dayNum': 7, 'isOpen': False},
]
},
'openDayList': [
{'day': '2023-01-24T00:00:00+01:00', 'hasPlace': True},
{'day': '2023-01-31T00:00:00+01:00', 'hasPlace': True},
],
'unit': {
'idUnit': 'A10051141990',
'libelle': 'Inscription 1er semestre',
'dateStart': '2022-09-01T00:00:00+02:00',
'dateEnd': '2023-01-31T00:00:00+01:00',
'placeInfoList': [],
'idIns': None,
},
'place': {
'idPlace': 'A10053179226',
'lib1': 'Centre Culturel ALBAN MINVILLE',
'lib2': None,
'idIns': None,
'etatIns': None,
'ageStart': None,
'ageEnd': None,
'ctrlPlaces': None,
'listBlocNoteBean': [],
'longitude': None,
'latitude': None,
},
'billingInformation': None,
'action': 'ADD_SUBSCRIBE',
'indicatorList': [],
}
def test_get_person_subscription_info_loisir_not_linked_error(con, app):
url = get_endpoint('get-person-subscription-info')
params = {
'NameID': 'local',
'family_id': '',
'person_id': '246423',
'activity_id': 'A10053187087',
'unit_id': 'A10053187241',
'place_id': 'A10053179604',
'ref_date': '2023-01-22',
}
resp = app.get(url, params=params)
assert resp.json['err'] == 'not-linked'
assert resp.json['err_desc'] == 'User not linked to family'
def test_get_person_subscription_info_loisir_date_error(con, app):
url = get_endpoint('get-person-subscription-info')
params = {
'NameID': '',
'family_id': '311323',
'person_id': '246423',
'activity_id': 'A10053187087',
'unit_id': 'A10053187241',
'place_id': 'A10053179604',
'ref_date': '22/01/2023',
}
resp = app.get(url, params=params, status=400)
assert resp.json['err'] == 'bad-request'
assert resp.json['err_desc'] == 'bad date format, should be YYYY-MM-DD'
params['ref_date'] = '2023-02-29'
resp = app.get(url, params=params, status=400)
assert resp.json['err'] == 'bad-request'
assert resp.json['err_desc'] == '2023-02-29 is not a valid date'