Skip to content

Commit

Permalink
feat!: expose orama API (#161)
Browse files Browse the repository at this point in the history
* feat: expose all the orama apis

* feat: expose orama internals

* Update README.md
  • Loading branch information
Eomm authored Sep 14, 2023
1 parent 63855d0 commit 3911f6d
Show file tree
Hide file tree
Showing 6 changed files with 162 additions and 17 deletions.
36 changes: 30 additions & 6 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ npm install fastify-orama
## Usage

This plugin adds the `orama` decorator to your Fastify application.
The decorator exposes all the methods that [the Orama class exposes](https://docs.oramasearch.com/usage/create).

The `options` object is passed directly to the `Orama.create` constructor,
so it supports [all the options that Orama supports](https://docs.oramasearch.com/usage/create).
Expand Down Expand Up @@ -56,9 +57,9 @@ This plugin supports data persistence out of the box.
You need to pass the `persistence` option to the plugin registration!

This plugin uses [`@oramasearch/plugin-data-persistence`](https://docs.oramasearch.com/plugins/plugin-data-persistence)
under the hood to allow users to `load` or `save` database instances.
under the hood to allow users to `load` or `persist` database instances.

Turning on the `persistence` option will add the `fastify.orama.save()` method to your Fastify application.
Turning on the `persistence` option will add the `fastify.orama.persist()` method to your Fastify application.
You must call this method to save the database instance to the persistence layer, otherwise your data will be lost.

### PersistenceInFile
Expand Down Expand Up @@ -103,8 +104,8 @@ app.post('/quotes', async function (req, reply) {
return { success: true }
})

app.addHook('onClose', async function save (app) {
const path = await app.orama.save()
app.addHook('onClose', async function persist (app) {
const path = await app.orama.persist()
app.log.info(`Database saved to ${path}`)
})

Expand Down Expand Up @@ -137,7 +138,7 @@ await appOne.orama.insert({
author: 'Mateo Nunez'
})

const inMemoryDb = await appOne.orama.save()
const inMemoryDb = await appOne.orama.persist()

// Close the Fastify application
await appOne.close()
Expand Down Expand Up @@ -169,7 +170,7 @@ const customPersistance = {

persist: async function persist (db) {
// Persist the database instance to the persistence layer
// Whatever this method returns will be passed to the `app.orama.save()` method
// Whatever this method returns will be passed to the `app.orama.persist()` method
}

await fastify.register(fastifyOrama, {
Expand All @@ -178,6 +179,29 @@ await fastify.register(fastifyOrama, {
})
```
## Orama Internals
Do you need to access the [Orama internals utilities](https://docs.oramasearch.com/internals/utilities)?
No problem!
```js
import { fastifyOrama, oramaInternals } from 'fastify-orama'

const app = Fastify()

// The database must exists to load it in your Fastify application
app.register(fastifyOrama, {
schema: {
quote: "string",
author: "string"
}
})

app.get('/genId', async function handler (req, reply) {
return { newId: await oramaInternals.uniqueId() }
})
```
## License
fastifyOrama is licensed under the [MIT](LICENSE) license.
2 changes: 1 addition & 1 deletion index.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ declare module 'fastify' {
orama: {
insert: (document: Document) => Promise<string>,
search: (params: SearchParams) => Promise<Results>,
save?: () => Promise<any>,
persist?: () => Promise<any>,
}
}
}
Expand Down
26 changes: 19 additions & 7 deletions index.js
Original file line number Diff line number Diff line change
@@ -1,9 +1,15 @@
import fp from 'fastify-plugin'
import { create, insert, search } from '@orama/orama' // todo we are limiting the api to the server side
import * as Orama from '@orama/orama'

import PersistenceInMemory from './lib/persistence/in-memory.js'
import PersistenceInFile from './lib/persistence/in-file.js'

const SKIP_METHODS = [
'create'
]

const oramaInternals = Orama.internals

async function fastifyOrama (fastify, options) {
if (fastify.orama) {
throw new Error('fastify-orama is already registered')
Expand All @@ -17,15 +23,20 @@ async function fastifyOrama (fastify, options) {
let db

const oramaApi = {
insert: (...args) => insert(db, ...args),
search: (...args) => search(db, ...args),
save: undefined
persist: undefined // custom
}

const oramaProxyKeys = Object.keys(Orama)
.filter((key) => typeof Orama[key] === 'function' && !SKIP_METHODS.includes(key))

for (const key of oramaProxyKeys) {
oramaApi[key] = (...args) => Orama[key](db, ...args)
}

if (persistence) {
db = await persistence.restore()

oramaApi.save = /* async */ function save () {
oramaApi.persist = /* async */ function persist () {
return persistence.persist(db)
}
}
Expand All @@ -35,7 +46,7 @@ async function fastifyOrama (fastify, options) {
throw new Error('You must provide a schema to create a new database')
}

db = await create(oramaOptions)
db = await Orama.create(oramaOptions)
}

fastify.decorate('orama', oramaApi)
Expand All @@ -49,5 +60,6 @@ export default fp(fastifyOrama, {
export {
fastifyOrama,
PersistenceInMemory,
PersistenceInFile
PersistenceInFile,
oramaInternals
}
2 changes: 1 addition & 1 deletion test/fastify-orama.test.js → test/index.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ it('Should register correctly fastifyOrama plugin', async () => {
})

ok(fastify.orama)
ok(fastify.orama.save === undefined)
ok(fastify.orama.persist === undefined)
})

it('Should insert and retrieve data using Orama', async () => {
Expand Down
109 changes: 109 additions & 0 deletions test/orama-proxy.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,109 @@
'use strict'

import { it } from 'node:test'
import { ok, strictEqual } from 'node:assert'
import Fastify from 'fastify'
import { fastifyOrama, oramaInternals } from '../index.js'

it('Should expose all the Orama APIs', async () => {
const fastify = Fastify()

await fastify.register(fastifyOrama, {
id: 'my-orama-instance',
schema: {
title: 'string',
director: 'string',
plot: 'string',
year: 'number',
isFavorite: 'boolean'
}
})

const harryPotterId = await fastify.orama.insert({
title: 'Harry Potter and the Philosopher\'s Stone',
director: 'Chris Columbus',
plot: 'Harry Potter, an eleven-year-old orphan, discovers that he is a wizard and is invited to study at Hogwarts. Even as he escapes a dreary life and enters a world of magic, he finds trouble awaiting him.',
year: 2001,
isFavorite: false
})
ok(harryPotterId, 'the id is returned')

const docs = [
{
title: 'The prestige',
director: 'Christopher Nolan',
plot: 'Two friends and fellow magicians become bitter enemies after a sudden tragedy. As they devote themselves to this rivalry, they make sacrifices that bring them fame but with terrible consequences.',
year: 2006,
isFavorite: true
},
{
title: 'Big Fish',
director: 'Tim Burton',
plot: 'Will Bloom returns home to care for his dying father, who had a penchant for telling unbelievable stories. After he passes away, Will tries to find out if his tales were really true.',
year: 2004,
isFavorite: true
}
]

const docIds = await fastify.orama.insertMultiple(docs, 500)
ok(docIds.length === 2, 'the ids are returned')

const thePrestige = await fastify.orama.getByID(docIds[0])
strictEqual(thePrestige.title, 'The prestige')

const docNumber = await fastify.orama.count()
strictEqual(docNumber, 3)

const del = await fastify.orama.remove(harryPotterId)
ok(del, 'the document was deleted')

const docNumberUpdated = await fastify.orama.count()
strictEqual(docNumberUpdated, 2)

const delMultiple = await fastify.orama.removeMultiple(docIds, 500)
strictEqual(delMultiple, 2, 'the documents were deleted')

const docEmpty = await fastify.orama.count()
strictEqual(docEmpty, 0)
})

it('Should not expose some Orama APIs', async () => {
const fastify = Fastify()

await fastify.register(fastifyOrama, {
id: 'my-orama-instance',
schema: {
title: 'string',
director: 'string',
plot: 'string',
year: 'number',
isFavorite: 'boolean'
}
})

ok(fastify.orama.create === undefined)
})

it('Should not expose Orama internals', async () => {
const fastify = Fastify()

fastify.register(fastifyOrama, {
id: 'my-orama-instance',
schema: {
title: 'string',
director: 'string',
plot: 'string',
year: 'number',
isFavorite: 'boolean'
}
})

fastify.get('/genId', async function handler () {
return { newId: await oramaInternals.uniqueId() }
})

const response = await fastify.inject('/genId')
strictEqual(response.statusCode, 200)
ok(response.json().newId, 'the id is returned')
ok(typeof response.json().newId === 'string', 'the id is a string')
})
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,7 @@ describe('PersistenceInFile', () => {
author: 'Mateo Nunez'
})

const path = await fastify.orama.save()
const path = await fastify.orama.persist()
strictEqual(path, opts.filePath)

{
Expand Down Expand Up @@ -156,7 +156,7 @@ describe('PersistenceInMemory', () => {
author: 'Mateo Nunez'
})

const inMemoryDb = await fastifyOne.orama.save()
const inMemoryDb = await fastifyOne.orama.persist()

{
const results = await fastifyOne.orama.search({ term: 'Mateo Nunez' })
Expand Down

0 comments on commit 3911f6d

Please sign in to comment.