Projet

Général

Profil

0001-api-extend-form-card-roles-support-in-applification-.patch

Frédéric Péters, 24 septembre 2022 14:13

Télécharger (8,75 ko)

Voir les différences:

Subject: [PATCH] api: extend form/card roles support in applification API
 (#69252)

 tests/api/test_export_import.py | 45 +++++++++++++++++++++++++++++----
 wcs/api_export_import.py        | 24 +++++-------------
 wcs/formdef.py                  |  5 ++++
 3 files changed, 51 insertions(+), 23 deletions(-)
tests/api/test_export_import.py
95 95
def test_export_import_dependencies(pub):
96 96
    role = pub.role_class(name='Test role')
97 97
    role.store()
98
    role2 = pub.role_class(name='Second role')
99
    role2.store()
100
    role3 = pub.role_class(name='Third role')
101
    role3.store()
98 102

  
99 103
    formdef = FormDef()
100 104
    formdef.name = 'Test'
......
104 108
    resp = get_app(pub).get(sign_uri(resp.json['data'][0]['urls']['dependencies']))
105 109
    assert not resp.json['data']
106 110

  
111
    formdef.roles = ['logged-users']
112
    formdef.backoffice_submission_roles = [role2.id]
113
    formdef.workflow_roles = {'_receiver': role3.id}
114
    formdef.store()
115

  
107 116
    block = BlockDef(name='test')
108 117
    block.store()
109 118

  
......
144 153

  
145 154
    resp = get_app(pub).get(sign_uri('/api/export-import/forms/'))
146 155
    resp = get_app(pub).get(sign_uri(resp.json['data'][0]['urls']['dependencies']))
147
    assert {(x['id'], x['type']) for x in resp.json['data']} == {('test', 'workflows'), ('test', 'blocks')}
156
    assert {(x['id'], x['type']) for x in resp.json['data']} == {
157
        ('test', 'workflows'),
158
        ('test', 'blocks'),
159
        ('second-role', 'roles'),
160
        ('third-role', 'roles'),
161
    }
148 162
    for dependency in resp.json['data']:
149 163
        get_app(pub).get(sign_uri(dependency['urls']['export']))
150 164

  
......
238 252
            'elements': [
239 253
                {'type': 'forms', 'slug': 'test', 'name': 'test'},
240 254
                {'type': 'blocks', 'slug': 'test', 'name': 'test'},
255
                {'type': 'roles', 'slug': 'test', 'name': 'test'},
241 256
                {'type': 'workflows', 'slug': 'test', 'name': 'test'},
242 257
                {'type': 'forms-categories', 'slug': 'test', 'name': 'test'},
243 258
                {'type': 'mail-templates-categories', 'slug': 'test', 'name': 'test'},
......
253 268

  
254 269
        for (path, obj) in args:
255 270
            tarinfo = tarfile.TarInfo(path)
256
            xml_export = ET.tostring(obj.export_to_xml(include_id=True))
257
            tarinfo.size = len(xml_export)
258
            tar.addfile(tarinfo, fileobj=io.BytesIO(xml_export))
271
            if hasattr(obj, 'export_for_application'):
272
                export, _ = obj.export_for_application()
273
                export = export.encode()
274
            else:
275
                export = ET.tostring(obj.export_to_xml(include_id=True))
276
            tarinfo.size = len(export)
277
            tar.addfile(tarinfo, fileobj=io.BytesIO(export))
259 278

  
260 279
    return tar_io.getvalue()
261 280

  
262 281

  
263 282
def test_export_import_bundle_import(pub):
264 283
    workflow = Workflow(name='test')
284
    workflow.roles = {'_receiver': 'Receiver'}
265 285
    workflow.store()
266 286

  
267 287
    block = BlockDef(name='test')
268 288
    block.store()
269 289

  
290
    role = pub.role_class(name='test')
291
    role.store()
292

  
270 293
    formdef = FormDef()
271 294
    formdef.name = 'Test'
272 295
    formdef.fields = [
273 296
        BlockField(id='1', label='test', type='block:test'),
274 297
    ]
275 298
    formdef.workflow = workflow
299
    formdef.workflow_roles = {'_receiver': role.id}
276 300
    formdef.disabled = False
277 301
    formdef.store()
278 302

  
......
306 330
        ('data-sources-categories/test', ds_category),
307 331
        ('mail-templates/test', mail_template),
308 332
        ('mail-templates-categories/test', mail_template_category),
333
        ('roles/test', role),
309 334
    )
310 335
    Category.wipe()
311 336
    FormDef.wipe()
......
315 340
    MailTemplateCategory.wipe()
316 341
    NamedDataSource.wipe()
317 342
    DataSourceCategory.wipe()
343
    pub.role_class.wipe()
318 344
    pub.custom_view_class.wipe()
319 345

  
346
    # roles will be created beforehand with authentic provisionning
347
    extra_role = pub.role_class(name='not this one')
348
    extra_role.store()
349
    role = pub.role_class(name='test')
350
    role.store()
351

  
320 352
    resp = get_app(pub).put(sign_uri('/api/export-import/bundle-import/'), bundle)
321 353
    afterjob_url = resp.json['url']
322 354
    resp = get_app(pub).put(sign_uri(afterjob_url))
......
333 365
    assert DataSourceCategory.count() == 1
334 366
    assert FormDef.select()[0].fields[0].type == 'block:test'
335 367
    assert pub.custom_view_class().count() == 1
368
    assert FormDef.select()[0].workflow_roles == {'_receiver': role.id}
336 369

  
337 370
    # run new import to check it doesn't duplicate objects
338 371
    resp = get_app(pub).put(sign_uri('/api/export-import/bundle-import/'), bundle)
......
350 383
    assert DataSourceCategory.count() == 1
351 384
    assert pub.custom_view_class().count() == 1
352 385

  
353
    # change immutable attribute and check it's not reset
386
    # change immutable attributes and check they are not reset
354 387
    formdef = FormDef.select()[0]
388
    formdef.workflow_roles = {'_receiver': extra_role.id}
355 389
    formdef.disabled = True
356 390
    formdef.store()
357 391

  
......
362 396

  
363 397
    formdef = FormDef.select()[0]
364 398
    assert formdef.disabled is True
399
    assert formdef.workflow_roles == {'_receiver': extra_role.id}
wcs/api_export_import.py
204 204
        self.tar_content = tar_content
205 205

  
206 206
    def execute(self):
207
        object_types = [x for x in klasses if x != 'roles']
208

  
207 209
        tar_io = io.BytesIO(self.tar_content)
208 210
        with tarfile.open(fileobj=tar_io) as self.tar:
209 211
            manifest = json.loads(self.tar.extractfile('manifest.json').read().decode())
......
218 220
                    if x.get('type') in ('forms', 'cards', 'blocks', 'workflows')
219 221
                ]
220 222
            )
221
            self.total_count += len(manifest.get('elements'))
223
            self.total_count += len([x for x in manifest.get('elements') if x.get('type') in object_types])
222 224

  
223 225
            # first pass on formdef/carddef/blockdef/workflows to create them empty
224 226
            # (name and slug); so they can be found for sure in import pass
......
226 228
                self.pre_install([x for x in manifest.get('elements') if x.get('type') == type])
227 229

  
228 230
            # real installation pass
229
            for type in (
230
                'blocks-categories',
231
                'cards-categories',
232
                'forms-categories',
233
                'workflows-categories',
234
                'mail-templates-categories',
235
                'data-sources-categories',
236
                'data-sources',
237
                'wscalls',
238
                'mail-templates',
239
                'forms',
240
                'cards',
241
                'blocks',
242
                'workflows',
243
            ):
231
            for type in object_types:
244 232
                self.install([x for x in manifest.get('elements') if x.get('type') == type])
245 233

  
246 234
    def pre_install(self, elements):
......
283 271
                continue
284 272
            # replace
285 273
            new_object.id = existing_object.id
286
            if element['type'] in ('forms', 'cards'):
287
                # keep some settings
274
            if element['type'] in ('forms', 'cards') and not existing_object.name.startswith('[pre-import]'):
275
                # keep some settings when updating
288 276
                for attr in (
289 277
                    'workflow_options',
290 278
                    'workflow_roles',
wcs/formdef.py
691 691
            yield self.workflow
692 692
        for field in self.fields or []:
693 693
            yield from field.get_dependencies()
694
        role_class = get_publisher().role_class
695
        for role_id in itertools.chain(self.roles or [], self.backoffice_submission_roles or []):
696
            yield role_class.get(role_id, ignore_errors=True)
697
        for role_id in (self.workflow_roles or {}).values():
698
            yield role_class.get(role_id, ignore_errors=True)
694 699

  
695 700
    @property
696 701
    def keywords_list(self):
697
-