Установщик Windows не очень подходит для сценария, который вы описываете, по крайней мере, если вы не потратите время на предотвращение использования неправильно установленных файлов с какой-либо технологией лицензирования. Вы можете иметь свою dll для проверки серийного номера, а также установить свойство, от которого зависят различные функции или компоненты, однако преобразование может легко обойти это. Если вы не потратили (или не можете потратить) время на проверку лицензии, лучше всего поддерживать отдельные сборки (по одной на каждый набор разрешенных файлов). Однако вы можете объединить их в один проект.
В зависимости от того, что именно отличается между сборками, я думаю, что есть два взаимодополняющих подхода, которые дают вам ваши отдельные SKU. Первый наиболее легко указывается для каждого выпуска, и вы можете выбрать, какой выпуск создать, например. из командной строки. Вторая не зависит от выпуска и может быть обновлена вручную или может быть переопределена в сборке командной строки.
Флаги выпуска
Вы можете разделить группы элементов на дополнительные функции (возможно, скрытые, чтобы они не загромождали диалоговое окно выбора функций), а затем использовать флаги выпуска для каждого выпуска, чтобы включать или исключать эти файлы во время сборки. Это, вероятно, будет работать лучше, если вы изменяете файлы содержимого, но продолжаете использовать одну и ту же библиотеку пользовательских действий в разных SKU.
Переменные пути
Путь к вашей библиотеке пользовательских действий можно указать с помощью переменной пути, которую затем можно использовать для переопределения исходного местоположения файла. Убедитесь, что соответствующая запись (вероятно, в таблице «Файл» или «Двоичная таблица») использует свою собственную переменную в угловых скобках, а затем вы можете поменять ее отдельно во время сборки. Это имеет смысл, если вам нужно изменить свою DLL пользовательского действия, и может использоваться вместе с флагами выпуска.