Refactor to allow generic matching and a nice client API
The more generic version