lunr-module icon indicating copy to clipboard operation
lunr-module copied to clipboard

Where `nuxt.callHook` should be called on?

Open tonywei92 opened this issue 4 years ago • 5 comments

The guide isn't stating where this code should sit on:

nuxt.callHook('lunr:document', ({ locale: 'af', // optional, default en document, meta // optional })

Can I call it on asyncData? Any Example? thanks

tonywei92 avatar Feb 09 '21 05:02 tonywei92

You can take a look at this example @tonywei92 : https://github.com/nuxt-community/lunr-module/blob/master/example/nuxt.config.js

I think @pimlie may be the best to answer how to use it properly

atinux avatar Feb 09 '21 10:02 atinux

@tonywei92 Where you have to call the lunr:document hook isnt documented because it depends on your implementation / use-case.

Note that creating the search index is done at build time, not during runtime. Ie you build the index during build, and the index is then added to your project so it can be used during runtime.

pimlie avatar Feb 10 '21 11:02 pimlie

I'm trying this module out today and I am very confused as well. I have been using Nuxt a long time now but hooks are still new to me.

I am trying to add the documents that the build process discovers to a search index. That seems to be the default case we are talking about here.

The example does not add this module to the nuxt modules. It also provides a set of documents that occur outside of the generate process. I find this very confusing. How do I get access to the documents that are accessed during the build process (crawl)?

I'm going to try some things and will report back what I uncover. Just wanted to let you know my first thoughts on this module as I am working with it for the first time. Thanks.

ryanweal avatar Mar 22 '21 17:03 ryanweal

Yup, there are ways to setup your asyncData handler so that certain actions, e.g., adding Lunr documents, are only done during the generate process. This allows you to execute API calls in the same manner as the rest of your app and during the generate. Relying on a callHook in the config file requires you to setup API handlers that are outside of the normal app lifecycle.

I think the way around this is to take the nuxt.hook('lunr:document' handler and extract it to a function that is also injected into the context, at least for the "server", i.e., in a lunr.server.plugin.js. This would allow rapid iteration during development and testing when combined with asyncData handler. If setup correctly it'll only run on the server side and will be run during generation.

https://github.com/nuxt-community/lunr-module/blob/master/lib/module.js#L102

Example usage:

  async asyncData(ctx) {
    const { $lunr, $api, req, store } = ctx;
    // $lunr and $api are injected via a server plugin, so aren't available in the client
    if (!($api && $lunr)) {
      return;
    }
    const documents = await $api.getTheThingsIWantToIndexAndDisplay({ req })
    store.commit("things/INSERT", documents);
    Object.values(documents).forEach((d) => {
      $lunr.addDoc({ id: d.id, ...normalize(d) })
    })
  },
  computed: {
    // provide the things For SSR or client side navigation
    things() {
      return this.$store.getters["things/all"]
    }
  }

gruis avatar Mar 22 '21 23:03 gruis

@gruis Although your approach could work, I wouldn't recommend it personally cause I think adding the lunr/indexing logic into your page components could be confusing. Instead I would recommend to add a nuxtServerInit to preload your store and load the docs from your api in a build before hook:

// nuxt.config
  hooks: {
    'build:before'(nuxt) {
      // preload all docs from your API and save to disk or global obj
    },
    ready(nuxt) {
      // add docs to lunr
    }
  }

// ~/store/index.js
actions: {
  nuxtServerInit ({ commit }, { req }) {
    const documents = // load from disk or global obj
    commit("things/INSERT", documents);
  }
}

If you really need / want to use asyncData to load/index specific documents then please note that maybe nuxt/content is more suited to your needs.

pimlie avatar Mar 28 '21 11:03 pimlie