dekimir / postgres-searchbox

Enables react-instantsearch to work directly on PostgreSQL tables
Other
15 stars 1 forks source link

Discussion: config #6

Open data-envoy opened 1 year ago

data-envoy commented 1 year ago

And the moment, it's zero-config. Which is really nice becaues the user can get started quickly.

Working on highlight it's starting to look like we should be asking the user for some kind of config, otherwize, we will be highlighting all text columns (like algolia do). And that seems like a waste of processing as aparently ts_headline can be slow https://stackoverflow.com/q/71355870/21643056

This is also related to how we select columns to return for the main search query. At the moment it's SELECT * with some js to remove the vector column https://github.com/dekimir/postgres-searchbox/pull/3#discussion_r1165980504

I think there are 2 ways that we could give config.

Pass some options to the handler

// pages/api/search.jsx
import { getSsearchHandler } from 'postgres-searchbox';
const searchHandler = getSsearchHandler({
  highlightColumns: ['title', 'description'],
  returnColumns:['id', 'title', 'description']
})
export default searchHandler;

Have config set on the client and validation on the handler.

// pages/index.js
const client = make_client('api/search', {
  highlightColumns: ['title', 'description'],
  returnColumns:['id', 'title', 'description']
});
// pages/api/search.jsx
import { getSsearchHandler } from 'postgres-searchbox';
// Use properties like validXyz, or some other technique.
const searchHandler = getSsearchHandler({
  validHighlightColumns: ['title', 'description', 'genre'], 
  validReturnColumns: ['id', 'title', 'description', 'image']
})
export default searchHandler;

Even futher

The method that we use should be capable when we add facet features. And should support different configs per table.

// pages/api/search.jsx
import { getSsearchHandler } from 'postgres-searchbox';
// Use properties like validXyz, or some other technique.
const searchHandler = getSsearchHandler([{
  tableName: 'postgres_searchbox_movies',
  validHighlightColumns: ['title', 'description', 'genre'], 
  validReturnColumns: ['id', 'title', 'description', 'image'],
  facets: {
    // Some facet config.
  }
}])
export default searchHandler;

What do you think?

Edit

As there is potential for XSS and perhaps exposing content of private columns, do you think we should also allow or document how a user could do their own validation in pages/api/search.jsx

// pages/api/search.jsx
import { searchHandler } from 'postgres-searchbox';
export default (req, res) => {
  const json = typeof req.body === 'string' ? JSON.parse(req.body) : req.body;
  // Do validation of the json here
  // ...
  // searchHandler doesn't need the full request, just the payload
  return searchHandler({ body: json }, res);
};
data-envoy commented 1 year ago

Maybe we should use the same syntax as Algolia API Reference / API Parameters / searchableAttribute

e.g.

searchableAttributes: [
  'attribute1',
  'attribute2, attribute3', // both attributes have the same priority
  '[unordered](https://www.algolia.com/doc/api-reference/api-parameters/searchableAttributes/#parameter-option-unordered)(attribute4)'
]