{pkgs, ...}: let inherit (builtins) elemAt isList isString mapAttrs match ; inherit (pkgs.lib) fix mkOption splitString types ; wrapArray = value: if isList value then value else [value]; hasMatch = pattern: str: isList (match pattern str); coerceToEvent = event: let part = elemAt (splitString " " event); value = if ! isString event then event else if ! hasMatch ".* .*" event then {name = event;} else { name = part 0; pattern = part 1; }; in mapAttrs (_: wrapArray) value; coerceToListOfEvent = events: if isList events then map coerceToEvent events else [(coerceToEvent events)]; typeOrListOf = t: with types; coercedTo t (e: [e]) (listOf t); in fix (self: { module = types.submodule { options = { name = mkOption { type = typeOrListOf types.str; default = "n"; example = "v"; description = '' The name of the event ''; }; pattern = mkOption { type = typeOrListOf types.str; example = ""; description = '' The pattern of the event ''; }; }; }; option = mkOption { type = with types; coercedTo (either str (listOf str)) coerceToListOfEvent (listOf self.module); default = []; description = '' List of events on which the plugin should be loaded ''; }; })