Overview
Morph’s Rerank API improves search quality by reordering candidate results based on their relevance to a query. Unlike the Apply and Embedding endpoints, the Rerank API uses a custom endpoint specifically designed for reranking tasks.
Morph does not store file content by default.
API Endpoint
Model Versions
The current version is morph-rerank-v2
.
Example Request
Note that the top_n
request parameter is optional and will default to the length of the documents
field. Result documents will be sorted by relevance, and the index
property can be used to determine original order.
The request accepts the following parameters:
Parameter | Type | Required | Description |
---|
model | string | Yes | The model ID to use for reranking. Use morph-rerank-v1 . |
query | string | Yes | The search query to compare documents against. |
documents | array | No* | An array of document strings to be reranked. Required if embedding_ids is not provided. |
embedding_ids | array | No* | An array of embedding IDs to rerank. Required if documents is not provided. Remote content storage must be enabled. |
top_n | integer | No | Number of top results to return. Default is all documents. |
return_documents | boolean | No | Whether to include document texts in response. Default is true . |
* Either documents
or embedding_ids
must be provided.
Using Document Content
import requests
def rerank_results(query, documents, top_n=5):
response = requests.post(
"https://api.morphllm.com/v1/rerank",
headers={
"Authorization": f"Bearer your-morph-api-key",
"Content-Type": "application/json"
},
json={
"model": "morph-rerank-v1",
"query": query,
"documents": documents,
"top_n": top_n
}
)
return response.json()
query = "How to implement JWT authentication in Express"
documents = [
"""const jwt = require('jsonwebtoken');
const express = require('express');
function authenticateToken(req, res, next) {
const authHeader = req.headers['authorization'];
const token = authHeader && authHeader.split(' ')[1];
if (token == null) return res.sendStatus(401);
jwt.verify(token, process.env.ACCESS_TOKEN_SECRET, (err, user) => {
if (err) return res.sendStatus(403);
req.user = user;
next();
});
}""",
"""const express = require('express');
const app = express();
const port = 3000;
app.use(express.json());
app.get('/', (req, res) => {
res.send('Hello World!');
});
app.listen(port, () => {
console.log(`App listening at http://localhost:${port}`);
});""",
"""const jwt = require('jsonwebtoken');
const user = { id: 123, username: 'john_doe' };
const accessToken = jwt.sign(user, process.env.ACCESS_TOKEN_SECRET, { expiresIn: '15m' });
const refreshToken = jwt.sign(user, process.env.REFRESH_TOKEN_SECRET);
console.log('Access Token:', accessToken);""",
"""const express = require('express');
const router = express.Router();
router.get('/users', (req, res) => {
res.json([{ id: 1, name: 'John' }, { id: 2, name: 'Jane' }]);
});
router.post('/users', (req, res) => {
const { name } = req.body;
res.json({ id: 3, name });
});
module.exports = router;""",
"""const passport = require('passport');
const GoogleStrategy = require('passport-google-oauth20').Strategy;
passport.use(new GoogleStrategy({
clientID: process.env.GOOGLE_CLIENT_ID,
clientSecret: process.env.GOOGLE_CLIENT_SECRET,
callbackURL: "/auth/google/callback"
}, (accessToken, refreshToken, profile, done) => {
return done(null, profile);
}));""",
"""const express = require('express');
const passport = require('passport');
const JwtStrategy = require('passport-jwt').Strategy;
const ExtractJwt = require('passport-jwt').ExtractJwt;
passport.use(new JwtStrategy({
jwtFromRequest: ExtractJwt.fromAuthHeaderAsBearerToken(),
secretOrKey: process.env.JWT_SECRET
}, (payload, done) => {
User.findById(payload.sub, (err, user) => {
if (err) return done(err, false);
if (user) return done(null, user);
return done(null, false);
});
}));"""
]
results = rerank_results(query, documents, top_n=3)
print(results)
Using Embedding IDs
When you have previously generated embeddings and enabled remote content storage, you can rerank using embedding IDs:
cURL Examples
With Document Content
curl --request POST \
--url https://api.morphllm.com/v1/rerank \
--header 'Authorization: Bearer your-morph-api-key' \
--header 'Content-Type: application/json' \
--data '{
"model": "morph-rerank-v2",
"query": "How to implement JWT authentication in Express",
"documents": [
"const jwt = require(\"jsonwebtoken\");\nconst express = require(\"express\");\n\nfunction authenticateToken(req, res, next) {\n const authHeader = req.headers[\"authorization\"];\n const token = authHeader && authHeader.split(\" \")[1];\n \n if (token == null) return res.sendStatus(401);\n \n jwt.verify(token, process.env.ACCESS_TOKEN_SECRET, (err, user) => {\n if (err) return res.sendStatus(403);\n req.user = user;\n next();\n });\n}",
"const express = require(\"express\");\nconst app = express();\nconst port = 3000;\n\napp.use(express.json());\n\napp.get(\"/\", (req, res) => {\n res.send(\"Hello World!\");\n});\n\napp.listen(port, () => {\n console.log(`App listening at http://localhost:${port}`);\n});",
"const jwt = require(\"jsonwebtoken\");\n\nconst user = { id: 123, username: \"john_doe\" };\nconst accessToken = jwt.sign(user, process.env.ACCESS_TOKEN_SECRET, { expiresIn: \"15m\" });\nconst refreshToken = jwt.sign(user, process.env.REFRESH_TOKEN_SECRET);\n\nconsole.log(\"Access Token:\", accessToken);",
"const express = require(\"express\");\nconst router = express.Router();\n\nrouter.get(\"/users\", (req, res) => {\n res.json([{ id: 1, name: \"John\" }, { id: 2, name: \"Jane\" }]);\n});\n\nrouter.post(\"/users\", (req, res) => {\n const { name } = req.body;\n res.json({ id: 3, name });\n});\n\nmodule.exports = router;",
"const passport = require(\"passport\");\nconst GoogleStrategy = require(\"passport-google-oauth20\").Strategy;\n\npassport.use(new GoogleStrategy({\n clientID: process.env.GOOGLE_CLIENT_ID,\n clientSecret: process.env.GOOGLE_CLIENT_SECRET,\n callbackURL: \"/auth/google/callback\"\n}, (accessToken, refreshToken, profile, done) => {\n return done(null, profile);\n}));",
"const express = require(\"express\");\nconst passport = require(\"passport\");\nconst JwtStrategy = require(\"passport-jwt\").Strategy;\nconst ExtractJwt = require(\"passport-jwt\").ExtractJwt;\n\npassport.use(new JwtStrategy({\n jwtFromRequest: ExtractJwt.fromAuthHeaderAsBearerToken(),\n secretOrKey: process.env.JWT_SECRET\n}, (payload, done) => {\n User.findById(payload.sub, (err, user) => {\n if (err) return done(err, false);\n if (user) return done(null, user);\n return done(null, false);\n });\n}));"
],
"top_n": 3
}'
With Embedding IDs
When using embedding IDs, the response will include the document content if available and if return_documents
is set to true
.
Remote Content Storage
To use embedding IDs for reranking, you must enable remote content storage in your account settings. This allows Morph to retrieve the content associated with each embedding ID for reranking purposes. Without remote content storage enabled, you’ll need to pass in the document content directly.
Benefits of using embedding IDs:
- Reduced payload size for large document collections
- Improved security as content is stored in your account’s secure storage
- Ability to rerank content that was previously embedded
Integration with Search Systems
The Rerank API is typically used as a second-pass ranking system in a multi-stage retrieval pipeline:
This two-stage approach combines the efficiency of initial retrieval methods with the accuracy of deep neural reranking models.