It looks like `create_filter` will always return a new filter and that callers should not be creating their own?  Should this not be an opaque struct?