Projet

Général

Profil

0001-caluire-axel-child_activities_info-enpoint-53934.patch

Lauréline Guérin, 18 mai 2021 10:51

Télécharger (14,7 ko)

Voir les différences:

Subject: [PATCH] caluire-axel: child_activities_info enpoint (#53934)

 functests/caluire_axel/test_caluire_axel.py   |  13 ++
 passerelle/contrib/caluire_axel/models.py     |  48 +++++++-
 passerelle/contrib/caluire_axel/schemas.py    |   1 +
 .../caluire_axel/xsd/Q_GetListActivites.xsd   |  26 ++++
 .../caluire_axel/xsd/R_GetListActivites.xsd   |  49 ++++++++
 tests/data/caluire_axel/activities_info.xml   |  11 ++
 tests/test_caluire_axel.py                    | 112 ++++++++++++++++--
 7 files changed, 248 insertions(+), 12 deletions(-)
 create mode 100644 passerelle/contrib/caluire_axel/xsd/Q_GetListActivites.xsd
 create mode 100644 passerelle/contrib/caluire_axel/xsd/R_GetListActivites.xsd
 create mode 100644 tests/data/caluire_axel/activities_info.xml
functests/caluire_axel/test_caluire_axel.py
62 62
        assert res['err'] == 0
63 63
        print('\n')
64 64

  
65
        print("and GET activities info")
66
        url = conn + '/child_activities_info?NameID=%s&idpersonne=%s&schooling_date=%s' % (
67
            name_id,
68
            child['IDENT'],
69
            datetime.date.today().strftime('%Y-%m-%d'),
70
        )
71
        resp = requests.get(url)
72
        resp.raise_for_status()
73
        res = resp.json()
74
        pprint.pprint(res)
75
        assert res['err'] == 0
76
        print('\n')
77

  
65 78
    print("GET school list")
66 79
    url = conn + '/school_list'
67 80
    payload = {
passerelle/contrib/caluire_axel/models.py
220 220
            'street': {'description': _('Address: street')},
221 221
            'zipcode': {'description': _('Address: zipcode')},
222 222
            'city': {'description': _('Address: city')},
223
            'schooling_date': {'description': _('Booking date (to get reference year)')},
223
            'schooling_date': {'description': _('Schooling date (to get reference year)')},
224 224
            'school_level': {'description': _('Requested school level')},
225 225
        },
226 226
    )
......
269 269
        parameters={
270 270
            'NameID': {'description': _('Publik ID')},
271 271
            'idpersonne': {'description': _('Child ID')},
272
            'schooling_date': {'description': _('Booking date (to get reference year)')},
272
            'schooling_date': {'description': _('Schooling date (to get reference year)')},
273 273
        },
274 274
    )
275 275
    def child_schooling_info(self, request, NameID, idpersonne, schooling_date):
......
300 300

  
301 301
        return {'data': schooling_data}
302 302

  
303
    @endpoint(
304
        display_category=_('Schooling'),
305
        display_order=3,
306
        description=_("Get information about activities of a child for the year"),
307
        perm='can_access',
308
        parameters={
309
            'NameID': {'description': _('Publik ID')},
310
            'idpersonne': {'description': _('Child ID')},
311
            'schooling_date': {'description': _('Schooling date (to get reference year)')},
312
        },
313
    )
314
    def child_activities_info(self, request, NameID, idpersonne, schooling_date):
315
        link = self.get_link(NameID)
316
        try:
317
            schooling_date = datetime.datetime.strptime(schooling_date, axel.json_date_format)
318
        except ValueError:
319
            raise APIError('bad date format, should be YYYY-MM-DD', err_code='bad-request', http_status=400)
320

  
321
        child_data = self.get_child_data(link.family_id, idpersonne)
322
        if child_data is None:
323
            raise APIError('Child not found', err_code='not-found')
324

  
325
        reference_year = utils.get_reference_year_from_date(schooling_date)
326
        try:
327
            result = schemas.get_list_activites(
328
                self,
329
                {
330
                    'PORTAIL': {
331
                        'GETLISTACTIVITES': {'IDENTINDIVIDU': idpersonne, 'ANNEE': str(reference_year)}
332
                    }
333
                },
334
            )
335
        except axel.AxelError as e:
336
            raise APIError(
337
                'Axel error: %s' % e,
338
                err_code='error',
339
                data={'xml_request': e.xml_request, 'xml_response': e.xml_response},
340
            )
341

  
342
        activities_data = result.json_response['DATA']['PORTAIL']['GETLISTACTIVITES']
343
        print(result.xml_response)
344

  
345
        return {'data': activities_data}
346

  
303 347

  
304 348
class Link(models.Model):
305 349
    resource = models.ForeignKey(CaluireAxel, on_delete=models.CASCADE)
passerelle/contrib/caluire_axel/schemas.py
76 76
get_famille_individus = Operation('GetFamilleIndividus')
77 77
get_individu = Operation('GetIndividu')
78 78
get_list_ecole = Operation('GetListEcole')
79
get_list_activites = Operation('GetListActivites')
79 80

  
80 81

  
81 82
LINK_SCHEMA = copy.deepcopy(
passerelle/contrib/caluire_axel/xsd/Q_GetListActivites.xsd
1
<?xml version="1.0" encoding="utf-8" ?>
2
<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:all="urn:AllAxelTypes">
3
	
4
	<xsd:import schemaLocation="./AllAxelTypes.xsd" namespace="urn:AllAxelTypes"  />
5
	
6
	<xsd:complexType name="PORTAILType">
7
		<xsd:sequence>
8
			<xsd:element ref="GETLISTACTIVITES" minOccurs="0" maxOccurs="1"/>
9
		</xsd:sequence>  
10
	</xsd:complexType>
11
	
12
	<xsd:complexType name="GETLISTACTIVITESType">
13
		<xsd:sequence>
14
			<xsd:element ref="ANNEE" />
15
			<xsd:element ref="IDENTINDIVIDU" />
16
		</xsd:sequence> 
17
	</xsd:complexType>
18
	
19
	<xsd:element name="IDENTINDIVIDU" type="all:IDENTREQUIREDType"/>
20
	<xsd:element name="ANNEE" type="all:ANNEEType"/>
21
	
22
	<xsd:element name="GETLISTACTIVITES" type="GETLISTACTIVITESType"/>
23
	
24
	<xsd:element name="PORTAIL" type="PORTAILType"/>	
25
		
26
</xsd:schema>
passerelle/contrib/caluire_axel/xsd/R_GetListActivites.xsd
1
<?xml version="1.0" encoding="utf-8" ?>
2
<xsd:schema	xmlns:all="urn:AllAxelTypes" xmlns:ind="urn:Individu"  xmlns:xsd="http://www.w3.org/2001/XMLSchema" >
3
	
4
	<xsd:import schemaLocation="./AllAxelTypes.xsd" namespace="urn:AllAxelTypes" />
5
	
6
	<xsd:redefine schemaLocation="./R_ShemaResultat.xsd">
7
	    <xsd:simpleType name="TYPEType">
8
			<xsd:restriction base="TYPEType">
9
				<xsd:enumeration value="GetListActivites" />
10
			</xsd:restriction>
11
	    </xsd:simpleType>
12
		
13
		<xsd:complexType name="PORTAILType">
14
			<xsd:complexContent>
15
				<xsd:extension base="PORTAILType">
16
					<xsd:sequence>
17
							<xsd:element ref="GETLISTACTIVITES" minOccurs="0" maxOccurs="1"/>
18
					</xsd:sequence>
19
				</xsd:extension>
20
			 </xsd:complexContent>
21
		</xsd:complexType>
22
	</xsd:redefine>	
23
		
24
	<xsd:complexType name="ACTIVITEType">
25
		<xsd:sequence>
26
			<xsd:element ref="IDENTACTIVITE" />
27
			<xsd:element ref="LIBELLEACTIVITE"/>
28
			<xsd:element ref="ENTREE"/>
29
			<xsd:element ref="SORTIE"/>
30
		</xsd:sequence> 
31
	</xsd:complexType>
32
	
33
	<xsd:complexType name="GETLISTACTIVITESType">
34
		<xsd:sequence>
35
			<xsd:element ref="CODE" />
36
			<xsd:element ref="ACTIVITE" minOccurs="0" maxOccurs="unbounded" />
37
		</xsd:sequence> 
38
	</xsd:complexType>
39
	
40
	<xsd:element name="CODE" type="xsd:integer"/>	
41
	<xsd:element name="IDENTACTIVITE" type="all:IDREQUIREDType"/>
42
	<xsd:element name="LIBELLEACTIVITE" type="all:LIBELLE100Type"/>
43
	<xsd:element name="ENTREE" type="all:DATEType"/>
44
	<xsd:element name="SORTIE" type="all:DATEType"/>
45
	<xsd:element name="ACTIVITE" type="ACTIVITEType"/>
46
	
47
	<xsd:element name="GETLISTACTIVITES" type="GETLISTACTIVITESType"/>
48
		
49
</xsd:schema>
tests/data/caluire_axel/activities_info.xml
1
<PORTAIL>
2
  <GETLISTACTIVITES>
3
    <CODE>1</CODE>
4
    <ACTIVITE>
5
      <IDENTACTIVITE>ELEM</IDENTACTIVITE>
6
      <LIBELLEACTIVITE>Restaurant El&#233;mentaire </LIBELLEACTIVITE>
7
      <ENTREE>01/09/2020</ENTREE>
8
      <SORTIE>31/07/2021</SORTIE>
9
    </ACTIVITE>
10
  </GETLISTACTIVITES>
11
</PORTAIL>
tests/test_caluire_axel.py
180 180
            )
181 181

  
182 182

  
183
@pytest.mark.parametrize(
184
    'content',
185
    [
186
        '<PORTAIL><GETLISTECOLE/></PORTAIL>',
187
    ],
188
)
189
def test_operation_get_list_ecole(resource, content):
190
    with mock_getdata(content, 'GetListEcole'):
191
        with pytest.raises(AxelError):
192
            schemas.get_list_ecole(
193
                resource,
194
                {
195
                    'PORTAIL': {
196
                        'GETLISTECOLE': {
197
                            'NORUE': '42',
198
                            'ADRESSE1': 'rue Pasteur',
199
                            'CODEPOSTAL': '69300',
200
                            'VILLE': 'Caluire et Cuire',
201
                            'IDENTNIVEAU': '',
202
                            'ANNEE': '2021',
203
                        }
204
                    }
205
                },
206
            )
207

  
208

  
183 209
@pytest.mark.parametrize(
184 210
    'content',
185 211
    [
......
205 231
@pytest.mark.parametrize(
206 232
    'content',
207 233
    [
208
        '<PORTAIL><GETLISTECOLE/></PORTAIL>',
234
        '<PORTAIL><GETLISTACTIVITES/></PORTAIL>',
209 235
    ],
210 236
)
211
def test_operation_get_list_ecole(resource, content):
212
    with mock_getdata(content, 'GetListEcole'):
237
def test_operation_get_list_activites(resource, content):
238
    with mock_getdata(content, 'GetListActivites'):
213 239
        with pytest.raises(AxelError):
214
            schemas.get_list_ecole(
240
            schemas.get_list_activites(
215 241
                resource,
216 242
                {
217 243
                    'PORTAIL': {
218
                        'GETLISTECOLE': {
219
                            'NORUE': '42',
220
                            'ADRESSE1': 'rue Pasteur',
221
                            'CODEPOSTAL': '69300',
222
                            'VILLE': 'Caluire et Cuire',
223
                            'IDENTNIVEAU': '',
244
                        'GETLISTACTIVITES': {
245
                            'IDENTINDIVIDU': 'XXX',
224 246
                            'ANNEE': '2021',
225 247
                        }
226 248
                    }
......
696 718
            )
697 719
    assert resp.json['err'] == 0
698 720
    assert set(resp.json['data'].keys()) == set(['CODE', 'INDIVIDU', 'SCOLAIRE'])
721

  
722

  
723
def test_child_activities_info_endpoint_axel_error(app, resource):
724
    Link.objects.create(resource=resource, name_id='yyy', family_id='XXX', person_id='42')
725
    with mock.patch('passerelle.contrib.caluire_axel.schemas.get_famille_individus') as operation:
726
        operation.side_effect = AxelError('FooBar')
727
        resp = app.get(
728
            '/caluire-axel/test/child_activities_info?NameID=yyy&idpersonne=50632&schooling_date=2021-05-10'
729
        )
730
    assert resp.json['err_desc'] == "Axel error: FooBar"
731
    assert resp.json['err'] == 'error'
732

  
733
    filepath = os.path.join(os.path.dirname(__file__), 'data/caluire_axel/family_info.xml')
734
    with open(filepath) as xml:
735
        content = xml.read()
736
    with mock_getdata(content, 'GetFamilleIndividus'):
737
        with mock.patch('passerelle.contrib.caluire_axel.schemas.get_list_activites') as operation:
738
            operation.side_effect = AxelError('FooBar')
739
            resp = app.get(
740
                '/caluire-axel/test/child_activities_info?NameID=yyy&idpersonne=50632&schooling_date=2021-05-10'
741
            )
742
    assert resp.json['err_desc'] == "Axel error: FooBar"
743
    assert resp.json['err'] == 'error'
744

  
745

  
746
@pytest.mark.parametrize('value', ['foo', '20/01/2020', '2020'])
747
def test_child_activities_info_endpoint_bad_date_format(app, resource, value):
748
    Link.objects.create(resource=resource, name_id='yyy', family_id='XXX', person_id='42')
749
    resp = app.get(
750
        '/caluire-axel/test/child_activities_info?NameID=yyy&idpersonne=50632&schooling_date=%s' % value,
751
        status=400,
752
    )
753
    assert resp.json['err_desc'] == "bad date format, should be YYYY-MM-DD"
754
    assert resp.json['err'] == 'bad-request'
755

  
756

  
757
def test_child_activities_info_endpoint_no_result(app, resource):
758
    resp = app.get(
759
        '/caluire-axel/test/child_activities_info?NameID=yyy&idpersonne=50632&schooling_date=2021-05-10'
760
    )
761
    assert resp.json['err_desc'] == "Person not found"
762
    assert resp.json['err'] == 'not-found'
763

  
764
    Link.objects.create(resource=resource, name_id='yyy', family_id='XXX', person_id='42')
765
    filepath = os.path.join(os.path.dirname(__file__), 'data/caluire_axel/family_info.xml')
766
    with open(filepath) as xml:
767
        content = xml.read()
768
    with mock_getdata(content, 'GetFamilleIndividus'):
769
        resp = app.get(
770
            '/caluire-axel/test/child_activities_info?NameID=yyy&idpersonne=zzz&schooling_date=2021-05-10'
771
        )
772
    assert resp.json['err_desc'] == "Child not found"
773
    assert resp.json['err'] == 'not-found'
774

  
775

  
776
def test_child_activities_info(app, resource, family_data):
777
    Link.objects.create(resource=resource, name_id='yyy', family_id='XXX', person_id='42')
778
    filepath = os.path.join(os.path.dirname(__file__), 'data/caluire_axel/activities_info.xml')
779
    with open(filepath) as xml:
780
        content = xml.read()
781
    with mock_getdata(content, 'GetListActivites'):
782
        with mock.patch(
783
            'passerelle.contrib.caluire_axel.models.CaluireAxel.get_family_data',
784
            return_value=family_data,
785
        ):
786
            resp = app.get(
787
                '/caluire-axel/test/child_activities_info?NameID=yyy&idpersonne=50632&schooling_date=2021-05-10'
788
            )
789
    assert resp.json['err'] == 0
790
    assert set(resp.json['data'].keys()) == set(['CODE', 'ACTIVITE'])
699
-