Легко упустить из виду, что такое концепция Спецификации, потому что в Интернете так много плохих статей.
Прежде чем вопрос был отредактирован, вы изначально написали:
А с другой стороны, DDD говорит, что это знание предметной области или логика должны быть внутри самой сущности.
Эм, нет. Сущности — не единственные элементы внутри модели предметной области, которые могут нести знания предметной области. Объекты-значения тоже могут, а объекты спецификации, как описано в книге Эвана DDD, являются объектами-значениями, в частности, объектами-значениями, которые несут логическую логику. Сущности вместе со связанными ценностными объектами образуют агрегаты, это места, где живут знания предметной области.
Я рекомендую улучшить ваше понимание, начав с этой статьи ~ 20-летней давности, написанной Мартином Фаулером и Эриком Эвансом о «Спецификации» в основном как о шаблоне анализа, но также с некоторыми предложениями по возможным реализациям.
В простых случаях объекты спецификации можно просто рассматривать как своего рода вспомогательные объекты. Они могут появиться, когда вы видите необходимость рефакторинга некоторой логической логики из объекта предметной области, например, потому что вы хотите бороться против того, чтобы объект стал «божественным объектом», или потому что вы видите возможность создать объект, в котором часть логики может быть протестирован самостоятельно. Тем не менее Спецификация сама по себе не имеет идентичности, она принадлежит какой-либо предметной области, даже если код не помещен в тот же класс. Это то, что в предыдущей статье называется «Жестко запрограммированная спецификация».
Логика может быть не полностью жестко запрограммирована, ее также можно заменить во время выполнения, реализуя объекты спецификации с использованием шаблона стратегии или просто вводя параметры (которые в статье называются «параметризованной спецификацией»).
Для более сложных случаев могут быть полезны такие реализации, как «Композитная спецификация». В этой статье Википедии показана возможная реализация. Одна запутанная часть здесь заключается в том, что он просто называет это «Шаблон спецификации». Этот заголовок определенно слишком общий, а сама статья слишком конкретная, поскольку она показывает только композитный подход. Еще одна запутанная часть заключается в том, что в ней представлено много кода для требуемой инфраструктуры, но цель Composite Specification не проясняется. Преимущество такого сложного подхода заключается в возможности свободно изменять определенные бизнес-правила во время выполнения. Следовательно, он может быть изменен вводом или конфигурацией какого-либо пользователя или какого-либо внешнего источника данных. Это преимущество достигается за счет необходимости создавать и использовать вокруг него мини-каркас из «композитных элементов».
«Композитная спецификация» — это, по сути, способ объединения предикатов (логических функций) стандартными условными операторами И, ИЛИ, НЕ во время выполнения. То, что вы правильно заметили: это действительно функциональная задача, и ее наверняка можно реализовать функциональными средствами с меньшим количеством кода и меньшими накладными расходами, чем с помощью чистых ООП-средств.
Тем не менее, создание объектов спецификации имеет смысл в контексте OO и/или DDD. Сегодня, 20 лет спустя, функциональные элементы становятся все более популярными в большинстве основных языков программирования. Поэтому я думаю, что должно быть легко использовать мультипарадигмальный подход и реализовывать спецификации в модели предметной области, используя функции или замыкания более высокого порядка вместо обычных объектов-значений. Всё-таки это будет DDD и OO (с некоторыми функциональными "плюшками"), не вижу в этом никакого противоречия.
Рекомендую посмотреть эти видео для лучшего погружения в вопрос: