• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

zopefoundation / Products.GenericSetup / 9927778353

12 Jun 2024 06:30AM UTC coverage: 93.296% (+0.06%) from 93.233%
9927778353

push

github

web-flow
- Add support for Python 3.12.  - Drop support for Python 3.7. (#130)

1806 of 2123 branches covered (85.07%)

Branch coverage included in aggregate %.

127 of 134 new or added lines in 4 files covered. (94.78%)

2 existing lines in 2 files now uncovered.

9285 of 9765 relevant lines covered (95.08%)

0.95 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

98.22
/src/Products/GenericSetup/tests/test_components.py
1
##############################################################################
2
#
3
# Copyright (c) 2006 Zope Foundation and Contributors.
4
#
5
# This software is subject to the provisions of the Zope Public License,
6
# Version 2.1 (ZPL).  A copy of the ZPL should accompany this distribution.
7
# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
8
# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
9
# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
10
# FOR A PARTICULAR PURPOSE.
11
#
12
##############################################################################
13
"""Component registry export / import support unit tests.
14
"""
15

16
import unittest
1✔
17

18
from AccessControl.class_init import InitializeClass
1✔
19
from AccessControl.SecurityInfo import ClassSecurityInfo
1✔
20
from Acquisition import aq_base
1✔
21
from OFS.Folder import Folder
1✔
22
from OFS.SimpleItem import SimpleItem
1✔
23
from Products.Five.component import enableSite
1✔
24
from Products.Five.component.interfaces import IObjectManagerSite
1✔
25
from zope.component import getGlobalSiteManager
1✔
26
from zope.component import getMultiAdapter
1✔
27
from zope.component import getSiteManager
1✔
28
from zope.component import handle
1✔
29
from zope.component import queryAdapter
1✔
30
from zope.component import queryUtility
1✔
31
from zope.component import subscribers
1✔
32
from zope.component.globalregistry import base
1✔
33
from zope.component.hooks import clearSite
1✔
34
from zope.component.hooks import setHooks
1✔
35
from zope.component.hooks import setSite
1✔
36
from zope.interface import Interface
1✔
37
from zope.interface import implementer
1✔
38

39
from ..interfaces import IBody
1✔
40
from ..interfaces import IComponentsHandlerBlacklist
1✔
41
from ..testing import BodyAdapterTestCase
1✔
42
from ..testing import DummySetupEnviron
1✔
43
from ..testing import ExportImportZCMLLayer
1✔
44
from ..tests.common import DummyImportContext
1✔
45

46

47
try:
1✔
48
    from five.localsitemanager.registry import PersistentComponents
1✔
NEW
49
except ModuleNotFoundError:
×
50
    # Avoid generating a spurious dependency
UNCOV
51
    PersistentComponents = None
×
52

53

54
def createComponentRegistry(context):
1✔
55
    enableSite(context, iface=IObjectManagerSite)
1✔
56

57
    components = PersistentComponents('++etc++site')
1✔
58
    components.__bases__ = (base, )
1✔
59
    components.__parent__ = aq_base(context)
1✔
60
    # Make sure calls to getSiteManager on me return myself
61
    # necessary because OFS.ObjectManager.getSiteManager expects _components
62
    components._components = components
1✔
63
    context.setSiteManager(components)
1✔
64

65

66
class IDummyInterface(Interface):
1✔
67
    """A dummy interface."""
68

69
    def verify():
1✔
70
        """Returns True."""
71

72

73
class IDummyInterface2(Interface):
1✔
74
    """A second dummy interface."""
75

76
    def verify():
1✔
77
        """Returns True."""
78

79

80
@implementer(IDummyInterface)
1✔
81
class DummyUtility:
1✔
82
    """A dummy utility."""
83

84
    def verify(self):
1✔
85
        return True
1✔
86

87

88
class IAnotherDummy(Interface):
1✔
89
    """A third dummy interface."""
90

91
    def inc():
1✔
92
        """Increments handle count"""
93

94

95
class IAnotherDummy2(Interface):
1✔
96
    """A second dummy interface."""
97

98
    def verify():
1✔
99
        """Returns True."""
100

101

102
@implementer(IAnotherDummy)
1✔
103
class DummyObject:
1✔
104
    """A dummy object to pass to the handler."""
105

106
    handled = 0
1✔
107

108
    def inc(self):
1✔
109
        self.handled += 1
1✔
110

111

112
@implementer(IAnotherDummy2)
1✔
113
class DummyAdapter:
1✔
114
    """A dummy adapter."""
115

116
    def __init__(self, context):
1✔
117
        pass
1✔
118

119
    def verify(self):
1✔
120
        return True
1✔
121

122

123
def dummy_handler(context):
1✔
124
    """A dummy event handler."""
125

126
    context.inc()
1✔
127

128

129
@implementer(IDummyInterface)
1✔
130
class DummyTool(SimpleItem):
1✔
131
    """A dummy tool."""
132

133
    id = 'dummy_tool'
1✔
134
    meta_type = 'dummy tool'
1✔
135
    security = ClassSecurityInfo()
1✔
136

137
    @security.public
1✔
138
    def verify(self):
1✔
139
        return True
1✔
140

141

142
InitializeClass(DummyTool)
1✔
143

144

145
@implementer(IDummyInterface2)
1✔
146
class DummyTool2(SimpleItem):
1✔
147
    """A second dummy tool."""
148

149
    id = 'dummy_tool2'
1✔
150
    meta_type = 'dummy tool2'
1✔
151
    security = ClassSecurityInfo()
1✔
152

153
    @security.public
1✔
154
    def verify(self):
1✔
155
        return True
1✔
156

157

158
InitializeClass(DummyTool2)
1✔
159

160

161
@implementer(IComponentsHandlerBlacklist)
1✔
162
class DummyBlacklist:
1✔
163
    """A blacklist."""
164

165
    def getExcludedInterfaces(self):
1✔
166
        return (IDummyInterface, )
1✔
167

168

169
_COMPONENTS_BODY = b"""\
1✔
170
<?xml version="1.0" encoding="utf-8"?>
171
<componentregistry>
172
 <adapters>
173
  <adapter factory="Products.GenericSetup.tests.test_components.DummyAdapter"
174
     for="zope.interface.Interface"
175
     provides="Products.GenericSetup.tests.test_components.IAnotherDummy2"/>
176
  <adapter name="foo"
177
     factory="Products.GenericSetup.tests.test_components.DummyAdapter"
178
     for="zope.interface.Interface"
179
     provides="Products.GenericSetup.tests.test_components.IAnotherDummy2"/>
180
 </adapters>
181
 <subscribers>
182
  <subscriber
183
     factory="Products.GenericSetup.tests.test_components.DummyAdapter"
184
     for="Products.GenericSetup.tests.test_components.IAnotherDummy"
185
     provides="Products.GenericSetup.tests.test_components.IAnotherDummy2"/>
186
  <subscriber for="Products.GenericSetup.tests.test_components.IAnotherDummy"
187
     handler="Products.GenericSetup.tests.test_components.dummy_handler"/>
188
 </subscribers>
189
 <utilities>
190
  <utility factory="Products.GenericSetup.tests.test_components.DummyUtility"
191
     id="dummy_utility"
192
     interface="Products.GenericSetup.tests.test_components.IDummyInterface"/>
193
  <utility name="dummy tool name"
194
     interface="Products.GenericSetup.tests.test_components.IDummyInterface"
195
     object="dummy_tool"/>
196
  <utility name="dummy tool name2"
197
     interface="Products.GenericSetup.tests.test_components.IDummyInterface2"
198
     object="dummy_tool2"/>
199
  <utility name="foo"
200
     factory="Products.GenericSetup.tests.test_components.DummyUtility"
201
     interface="Products.GenericSetup.tests.test_components.IDummyInterface2"/>
202
 </utilities>
203
</componentregistry>
204
"""
205

206
_REMOVE_IMPORT = b"""\
1✔
207
<?xml version="1.0" encoding="utf-8"?>
208
<componentregistry>
209
 <adapters>
210
  <adapter factory="Products.GenericSetup.tests.test_components.DummyAdapter"
211
     provides="Products.GenericSetup.tests.test_components.IAnotherDummy2"
212
     for="*" remove="True"/>
213
 </adapters>
214
 <subscribers>
215
  <subscriber
216
     factory="Products.GenericSetup.tests.test_components.DummyAdapter"
217
     for="Products.GenericSetup.tests.test_components.IAnotherDummy"
218
     provides="Products.GenericSetup.tests.test_components.IAnotherDummy2"
219
     remove="True"/>
220
  <subscriber
221
     for="Products.GenericSetup.tests.test_components.IAnotherDummy"
222
     handler="Products.GenericSetup.tests.test_components.dummy_handler"
223
     remove="True"/>
224
 </subscribers>
225
 <utilities>
226
  <utility id="dummy_utility"
227
     factory="Products.GenericSetup.tests.test_components.DummyUtility"
228
     interface="Products.GenericSetup.tests.test_components.IDummyInterface"
229
     remove="True"/>
230
  <utility name="dummy tool name"
231
     interface="Products.GenericSetup.tests.test_components.IDummyInterface"
232
     object="dummy_tool" remove="True"/>
233
  <utility name="foo"
234
     factory="Products.GenericSetup.tests.test_components.DummyUtility"
235
     interface="Products.GenericSetup.tests.test_components.IDummyInterface2"
236
     remove="True"/>
237
 </utilities>
238
</componentregistry>
239
"""
240

241
_INTERFACE_COMPONENT = b"""\
1✔
242
<?xml version="1.0" encoding="utf-8"?>
243
<componentregistry>
244
 <adapters/>
245
 <subscribers/>
246
 <utilities>
247
  <utility name="test_interface"
248
     component="Products.GenericSetup.tests.test_components.ITestInterface"
249
     interface="Products.GenericSetup.tests.test_components.ITestInterfaceType"/>
250
 </utilities>
251
</componentregistry>
252
"""
253

254

255
class ComponentRegistryXMLAdapterTests(BodyAdapterTestCase, unittest.TestCase):
1✔
256

257
    layer = ExportImportZCMLLayer
1✔
258

259
    def _getTargetClass(self):
1✔
260
        from Products.GenericSetup.components import \
1✔
261
            ComponentRegistryXMLAdapter
262
        return ComponentRegistryXMLAdapter
1✔
263

264
    def _populate(self, obj):
1✔
265
        obj.registerAdapter(DummyAdapter, required=(None, ))
1✔
266
        obj.registerAdapter(DummyAdapter, required=(None, ), name='foo')
1✔
267

268
        obj.registerSubscriptionAdapter(DummyAdapter,
1✔
269
                                        required=(IAnotherDummy, ))
270
        obj.registerHandler(dummy_handler, required=(IAnotherDummy, ))
1✔
271

272
        util = DummyUtility()
1✔
273
        name = 'dummy_utility'
1✔
274
        util.__name__ = name
1✔
275
        util.__parent__ = aq_base(obj)
1✔
276
        obj._setObject(name,
1✔
277
                       aq_base(util),
278
                       set_owner=False,
279
                       suppress_events=True)
280
        obj.registerUtility(aq_base(obj[name]), IDummyInterface)
1✔
281

282
        util = DummyUtility()
1✔
283
        name = ('Products.GenericSetup.tests.test_components.'
1✔
284
                'IDummyInterface2-foo')
285
        util.__name__ = name
1✔
286
        util.__parent__ = aq_base(obj)
1✔
287
        obj._setObject(name,
1✔
288
                       aq_base(util),
289
                       set_owner=False,
290
                       suppress_events=True)
291
        obj.registerUtility(aq_base(obj[name]), IDummyInterface2, name='foo')
1✔
292

293
        tool = aq_base(obj.aq_parent['dummy_tool'])
1✔
294
        obj.registerUtility(tool, IDummyInterface, name='dummy tool name')
1✔
295

296
        tool2 = aq_base(obj.aq_parent['dummy_tool2'])
1✔
297
        obj.registerUtility(tool2, IDummyInterface2, name='dummy tool name2')
1✔
298

299
    def _verifyImport(self, obj):
1✔
300
        adapted = queryAdapter(object(), IAnotherDummy2)
1✔
301
        self.assertTrue(IAnotherDummy2.providedBy(adapted))
1✔
302
        self.assertTrue(adapted.verify())
1✔
303

304
        adapted = queryAdapter(object(), IAnotherDummy2, name='foo')
1✔
305
        self.assertTrue(IAnotherDummy2.providedBy(adapted))
1✔
306
        self.assertTrue(adapted.verify())
1✔
307

308
        dummy = DummyObject()
1✔
309
        results = [
1✔
310
            adap.verify() for adap in subscribers([dummy], IAnotherDummy2)
311
        ]
312
        self.assertEqual(results, [True])
1✔
313

314
        dummy = DummyObject()
1✔
315
        handle(dummy)
1✔
316
        self.assertEqual(dummy.handled, 1)
1✔
317

318
        util = queryUtility(IDummyInterface2, name='foo')
1✔
319
        self.assertTrue(IDummyInterface.providedBy(util))
1✔
320
        self.assertTrue(util.verify())
1✔
321
        self.assertTrue(util.__parent__ == obj)
1✔
322
        name = ('Products.GenericSetup.tests.test_components.'
1✔
323
                'IDummyInterface2-foo')
324
        self.assertEqual(util.__name__, name)
1✔
325
        self.assertTrue(name in obj.objectIds())
1✔
326

327
        util = queryUtility(IDummyInterface)
1✔
328
        self.assertTrue(IDummyInterface.providedBy(util))
1✔
329
        self.assertTrue(util.verify())
1✔
330
        self.assertTrue(util.__parent__ == obj)
1✔
331
        name = 'dummy_utility'
1✔
332
        self.assertEqual(util.__name__, name)
1✔
333
        self.assertTrue(name in obj.objectIds())
1✔
334

335
        util = queryUtility(IDummyInterface, name='dummy tool name')
1✔
336
        self.assertTrue(IDummyInterface.providedBy(util))
1✔
337
        self.assertTrue(util.verify())
1✔
338
        self.assertEqual(util.meta_type, 'dummy tool')
1✔
339

340
        # make sure we can get the tool by normal means
341
        tool = getattr(obj.aq_parent, 'dummy_tool')
1✔
342
        self.assertEqual(tool.meta_type, 'dummy tool')
1✔
343
        self.assertEqual(repr(aq_base(util)), repr(aq_base(tool)))
1✔
344

345
        util = queryUtility(IDummyInterface2, name='dummy tool name2')
1✔
346
        self.assertTrue(IDummyInterface2.providedBy(util))
1✔
347
        self.assertTrue(util.verify())
1✔
348
        self.assertEqual(util.meta_type, 'dummy tool2')
1✔
349

350
        # make sure we can get the tool by normal means
351
        tool = getattr(obj.aq_parent, 'dummy_tool2')
1✔
352
        self.assertEqual(tool.meta_type, 'dummy tool2')
1✔
353
        self.assertEqual(repr(aq_base(util)), repr(aq_base(tool)))
1✔
354

355
    def test_blacklist_get(self):
1✔
356
        obj = self._obj
1✔
357
        self._populate(obj)
1✔
358

359
        # Register our blacklist
360
        gsm = getGlobalSiteManager()
1✔
361
        gsm.registerUtility(DummyBlacklist(),
1✔
362
                            IComponentsHandlerBlacklist,
363
                            name='dummy')
364

365
        context = DummySetupEnviron()
1✔
366
        adapted = getMultiAdapter((obj, context), IBody)
1✔
367

368
        body = adapted.body
1✔
369
        self.assertFalse(b'IComponentsHandlerBlacklist' in body)
1✔
370
        self.assertFalse(b'test_components.IDummyInterface"' in body)
1✔
371

372
    def test_blacklist_set(self):
1✔
373
        obj = self._obj
1✔
374
        # Register our blacklist
375
        gsm = getGlobalSiteManager()
1✔
376
        gsm.registerUtility(DummyBlacklist(),
1✔
377
                            IComponentsHandlerBlacklist,
378
                            name='dummy')
379

380
        context = DummySetupEnviron()
1✔
381
        adapted = getMultiAdapter((obj, context), IBody)
1✔
382
        adapted.body = self._BODY
1✔
383

384
        util = queryUtility(IDummyInterface2, name='foo')
1✔
385
        self.assertTrue(IDummyInterface.providedBy(util))
1✔
386
        self.assertTrue(util.verify())
1✔
387
        util = queryUtility(IDummyInterface)
1✔
388
        self.assertTrue(util is None)
1✔
389

390
        # now in update mode
391
        context._should_purge = False
1✔
392
        adapted = getMultiAdapter((obj, context), IBody)
1✔
393
        adapted.body = self._BODY
1✔
394

395
        util = queryUtility(IDummyInterface2, name='foo')
1✔
396
        self.assertTrue(IDummyInterface.providedBy(util))
1✔
397
        self.assertTrue(util.verify())
1✔
398
        util = queryUtility(IDummyInterface)
1✔
399
        self.assertTrue(util is None)
1✔
400

401
        # and again in update mode
402
        adapted = getMultiAdapter((obj, context), IBody)
1✔
403
        adapted.body = self._BODY
1✔
404

405
        util = queryUtility(IDummyInterface2, name='foo')
1✔
406
        self.assertTrue(IDummyInterface.providedBy(util))
1✔
407
        self.assertTrue(util.verify())
1✔
408
        util = queryUtility(IDummyInterface)
1✔
409
        self.assertTrue(util is None)
1✔
410

411
    def test_remove_components(self):
1✔
412
        from ..components import importComponentRegistry
1✔
413

414
        obj = self._obj
1✔
415
        self._populate(obj)
1✔
416
        self._verifyImport(obj)
1✔
417

418
        context = DummyImportContext(obj, False)
1✔
419
        context._files['componentregistry.xml'] = _REMOVE_IMPORT
1✔
420
        importComponentRegistry(context)
1✔
421

422
        adapted = queryAdapter(object(), IAnotherDummy2)
1✔
423
        self.assertTrue(adapted is None)
1✔
424

425
        # This one should still exist
426
        adapted = queryAdapter(object(), IAnotherDummy2, name='foo')
1✔
427
        self.assertFalse(adapted is None)
1✔
428

429
        dummy = DummyObject()
1✔
430
        results = [
1✔
431
            adap.verify() for adap in subscribers([dummy], IAnotherDummy2)
432
        ]
433
        self.assertEqual(results, [])
1✔
434

435
        dummy = DummyObject()
1✔
436
        handle(dummy)
1✔
437
        self.assertEqual(dummy.handled, 0)
1✔
438

439
        util = queryUtility(IDummyInterface2, name='foo')
1✔
440
        name = ('Products.GenericSetup.tests.test_components.'
1✔
441
                'IDummyInterface2-foo')
442
        self.assertTrue(util is None)
1✔
443
        self.assertFalse(name in obj.objectIds())
1✔
444

445
        util = queryUtility(IDummyInterface)
1✔
446
        self.assertTrue(util is None)
1✔
447
        self.assertFalse('dummy_utility' in obj.objectIds())
1✔
448

449
        util = queryUtility(IDummyInterface, name='dummy tool name')
1✔
450
        self.assertTrue(util is None)
1✔
451

452
        # This one should still exist
453
        util = queryUtility(IDummyInterface2, name='dummy tool name2')
1✔
454
        self.assertFalse(util is None)
1✔
455

456
    def test_export_interface_component(self):
1✔
457
        sm = self._obj
1✔
458
        sm.registerUtility(ITestInterface, ITestInterfaceType,
1✔
459
                           "test_interface")
460
        context = DummySetupEnviron()
1✔
461
        adapted = getMultiAdapter((sm, context), IBody)
1✔
462
        body = adapted.body
1✔
463
        self.assertEqual(body, _INTERFACE_COMPONENT)
1✔
464

465
    def test_import_interface_component(self):
1✔
466
        from ..components import importComponentRegistry
1✔
467
        sm = self._obj
1✔
468
        context = DummyImportContext(sm, False)
1✔
469
        context._files['componentregistry.xml'] = _INTERFACE_COMPONENT
1✔
470
        importComponentRegistry(context)
1✔
471
        self.assertIs(
1✔
472
            sm.queryUtility(ITestInterfaceType, name="test_interface"),
473
            ITestInterface)
474

475
    def setUp(self):
1✔
476
        # Create and enable a local component registry
477
        site = Folder()
1✔
478
        createComponentRegistry(site)
1✔
479
        setHooks()
1✔
480
        setSite(site)
1✔
481
        sm = getSiteManager()
1✔
482

483
        tool = DummyTool()
1✔
484
        site._setObject(tool.id, tool)
1✔
485

486
        tool2 = DummyTool2()
1✔
487
        site._setObject(tool2.id, tool2)
1✔
488

489
        self._obj = sm
1✔
490
        self._BODY = _COMPONENTS_BODY
1✔
491

492
    def tearDown(self):
1✔
493
        clearSite()
1✔
494
        # Make sure our global utility is gone again
495
        gsm = getGlobalSiteManager()
1✔
496
        gsm.unregisterUtility(provided=IComponentsHandlerBlacklist,
1✔
497
                              name='dummy')
498

499

500
class ITestInterface(Interface):
1✔
501
    """interface registered as utility."""
502

503

504
class ITestInterfaceType(Interface):
1✔
505
    """interface provided by ``ITestInterface``."""
506

507

508
if PersistentComponents is not None:
1!
509

510
    def test_suite():
1✔
511
        # reimport to make sure tests are run from Products
512
        from ..tests.test_components import ComponentRegistryXMLAdapterTests
1✔
513

514
        return unittest.TestSuite(
1✔
515
            (unittest.defaultTestLoader.loadTestsFromTestCase(
516
                ComponentRegistryXMLAdapterTests), ))
517
else:
518

519
    def test_suite():
×
520
        return unittest.TestSuite()
×
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2025 Coveralls, Inc