| 1439 | on_setattr = setters.pipe(*on_setattr) |
| 1440 | |
| 1441 | def wrap(cls): |
| 1442 | nonlocal hash |
| 1443 | is_frozen = frozen or _has_frozen_base_class(cls) |
| 1444 | is_exc = auto_exc is True and issubclass(cls, BaseException) |
| 1445 | has_own_setattr = auto_detect and _has_own_attribute( |
| 1446 | cls, "__setattr__" |
| 1447 | ) |
| 1448 | |
| 1449 | if has_own_setattr and is_frozen: |
| 1450 | msg = "Can't freeze a class with a custom __setattr__." |
| 1451 | raise ValueError(msg) |
| 1452 | |
| 1453 | eq = not is_exc and _determine_whether_to_implement( |
| 1454 | cls, eq_, auto_detect, ("__eq__", "__ne__") |
| 1455 | ) |
| 1456 | |
| 1457 | Hashability = ClassProps.Hashability |
| 1458 | |
| 1459 | if is_exc: |
| 1460 | hashability = Hashability.LEAVE_ALONE |
| 1461 | elif hash is True: |
| 1462 | hashability = ( |
| 1463 | Hashability.HASHABLE_CACHED |
| 1464 | if cache_hash |
| 1465 | else Hashability.HASHABLE |
| 1466 | ) |
| 1467 | elif hash is False: |
| 1468 | hashability = Hashability.LEAVE_ALONE |
| 1469 | elif hash is None: |
| 1470 | if auto_detect is True and _has_own_attribute(cls, "__hash__"): |
| 1471 | hashability = Hashability.LEAVE_ALONE |
| 1472 | elif eq is True and is_frozen is True: |
| 1473 | hashability = ( |
| 1474 | Hashability.HASHABLE_CACHED |
| 1475 | if cache_hash |
| 1476 | else Hashability.HASHABLE |
| 1477 | ) |
| 1478 | elif eq is False: |
| 1479 | hashability = Hashability.LEAVE_ALONE |
| 1480 | else: |
| 1481 | hashability = Hashability.UNHASHABLE |
| 1482 | else: |
| 1483 | msg = "Invalid value for hash. Must be True, False, or None." |
| 1484 | raise TypeError(msg) |
| 1485 | |
| 1486 | KeywordOnly = ClassProps.KeywordOnly |
| 1487 | if kw_only: |
| 1488 | kwo = KeywordOnly.FORCE if force_kw_only else KeywordOnly.YES |
| 1489 | else: |
| 1490 | kwo = KeywordOnly.NO |
| 1491 | |
| 1492 | props = ClassProps( |
| 1493 | is_exception=is_exc, |
| 1494 | is_frozen=is_frozen, |
| 1495 | is_slotted=slots, |
| 1496 | collected_fields_by_mro=collect_by_mro, |
| 1497 | added_init=_determine_whether_to_implement( |
| 1498 | cls, init, auto_detect, ("__init__",) |