public function defines(array $defines): self
    {
        if (!$defines) {
            return $this;
        }

        $dup_keys = array_intersect_key($this->defines, $defines);
        if ($dup_keys) {
            throw new \InvalidArgumentException(
                "Cannot redefine defines: " . join(', ', array_keys($dup_keys))
            );
        }

        $copy = clone $this;
        $copy->defines += $defines;
        return $copy;
    }