You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Deno连接MongoDB报错:Deno.openPlugin is not a function 求助

问题与解决方案

我的数据库连接代码

import { MongoClient, Database } from "https://deno.land/x/mongo@v0.8.0/mod.ts";

let db: Database;

export function connect() {
  const client = new MongoClient();
  client.connectWithUri(
    "mongodb+srv://mahdi:<password>@cluster0.dzbrnoa.mongodb.net/?retryWrites=true&w=majority"
  );

  db = client.database("todo-app");
}

export function getDb() {
  return db;
}

我的路由文件代码

import { Router } from 'https://deno.land/x/oak/mod.ts';
import { ObjectId } from 'https://deno.land/x/mongo@v0.8.0/mod.ts';

import { getDb } from '../helpers/db_client.ts';

const router = new Router();

interface Todo {
  id?: string;
  text: string;
}

let todos: Todo[] = [];

router.get('/todos', async (ctx) => {
  const todos = await getDb().collection('todos').find(); // { _id: ObjectId(), text: '...' }[]
  const transformedTodos = todos.map(
    (todo: { _id: ObjectId; text: string }) => {
      return { id: todo._id.$oid, text: todo.text };
    }
  );
  ctx.response.body = { todos: transformedTodos };
});

router.post('/todos', async (ctx) => {
  const data = await ctx.request.body().value;
  const newTodo: Todo = {
    // id: new Date().toISOString(),
    text: data.text,
  };

  const id = await getDb().collection('todos').insertOne(newTodo);

  newTodo.id = id.$oid;

  ctx.response.body = { message: 'Created todo!', todo: newTodo };
});

router.put('/todos/:todoId', async (ctx) => {
  const tid = ctx.params.todoId;
  const data = await ctx.request.body().value;
  const todoIndex = todos.findIndex((todo) => {
    return todo.id === tid;
  });
  todos[todoIndex] = { id: todos[todoIndex].id, text: data.text };
  ctx.response.body = { message: 'Updated todo' };
});

router.delete('/todos/:todoId', (ctx) => {
  const tid = ctx.params.todoId;
  todos = todos.filter((todo) => todo.id !== tid);
  ctx.response.body = { message: 'Deleted todo' };
});

export default router;

遇到的错误

Uncaught (in promise) TypeError: Deno.openPlugin is not a function
return Deno.openPlugin(localPath);

已尝试使用--unstable和--allow-plugin参数,但--unstable已被弃用,寻求解决方法。


解决方法

1. 核心原因

你使用的deno.land/x/mongo@v0.8.0是老旧版本,它依赖的Deno.openPlugin API已在Deno 1.10+版本中被彻底移除,同时--allow-plugin和旧--unstable参数也不再适用。新版deno_mongo已改用纯TypeScript实现,完全不需要插件支持。

2. 升级deno_mongo版本并修改代码

将mongo依赖替换为最新稳定版(示例用v0.32.0,可按需调整),同时适配新的连接逻辑:

修改后的数据库连接代码

import { MongoClient, Database } from "https://deno.land/x/mongo@v0.32.0/mod.ts";

let db: Database;

export async function connect() {
  const client = new MongoClient();
  // 新版本需要await连接操作
  await client.connect(
    "mongodb+srv://mahdi:<password>@cluster0.dzbrnoa.mongodb.net/?retryWrites=true&w=majority"
  );

  db = client.database("todo-app");
}

export function getDb() {
  return db;
}

调整路由文件

  • 替换mongo依赖导入:
import { ObjectId } from 'https://deno.land/x/mongo@v0.32.0/mod.ts';
  • 新版ObjectId不再有$oid属性,改用toString()方法转换ID:
// 原转换逻辑
// return { id: todo._id.$oid, text: todo.text };
// 修改为
return { id: todo._id.toString(), text: todo.text };
  • 修复put/delete路由的内存操作问题,改为直接操作数据库:
// 修改后的put路由
router.put('/todos/:todoId', async (ctx) => {
  const tid = ctx.params.todoId;
  const data = await ctx.request.body().value;
  
  await getDb().collection('todos').updateOne(
    { _id: new ObjectId(tid) },
    { $set: { text: data.text } }
  );

  ctx.response.body = { message: 'Updated todo' };
});

// 修改后的delete路由
router.delete('/todos/:todoId', async (ctx) => {
  const tid = ctx.params.todoId;
  
  await getDb().collection('todos').deleteOne({ _id: new ObjectId(tid) });

  ctx.response.body = { message: 'Deleted todo' };
});

3. 调整运行命令

不再需要--unstable和--allow-plugin,使用以下权限参数运行:

deno run --allow-net --allow-env 你的入口文件.ts
  • --allow-net:允许网络连接(连接MongoDB必需)
  • --allow-env:若连接字符串从环境变量读取则需要,否则可省略

内容的提问来源于stack exchange,提问作者Mahdi Zolfaghari

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.19 09:08:27