如何在 Prisma GraphQL 中向模型添加字段?

3

我按照 DigitalOcean 的教程学习了如何创建一个 Prisma GraphQL API。 https://www.digitalocean.com/community/tutorials/how-to-build-a-graphql-api-with-prisma-and-deploy-to-digitalocean-s-app-platform

该应用程序正在访问托管在 digitalOcean 上的 PostgreSQL 数据库,并且一切正常。 现在我想向“Post”模型添加字段“test”: TypeDefs:

  type Post {
    content: String
    id: ID!
    published: Boolean!
    title: String!
    author: User
    test: String

  }

解析器:

Mutation: {
    createMeme: (parent, args) => {
      return prisma.post.create({
        data: {
          title: args.title,
          content: args.content,
          published: args.published,
          author: args.authorEmail && {
            connect: { email: args.authorEmail },
          },
          test: args.test,
          
        },
      })
    },

变异:
  type Mutation {
    createMeme(authorEmail: String, content: String, title: String!, published: Boolean, test: String): Post!
  }

模型在 schema.prisma 文件中:

model Post {
  id        Int     @id @default(autoincrement())
  title     String
  content   String?
  published Boolean @default(false)
  author    User?   @relation(fields: [authorId], references: [id])
  authorId  Int?
  test      String?
}

当我将它迁移到托管在 Docker 上的本地 PostgreSQL 数据库时,它可以正常工作,以下是我的操作步骤:
  1. 更改.env文件中的DATABASE_URL为本地数据库
  2. 执行:“npm prisma migrate dev”
  3. “npm start”
当我现在尝试将DATABASE_URL更改为托管在DigitalOcean上的PostgreSQL数据库时,我会执行以下操作:
  1. “git add .”
  2. “git commit -m“test field added””
  3. “git push”
  4. “npx prisma migrate deploy”
在这种情况下,我得到了以下错误: Error: P3018
一个迁移无法应用。在从错误中恢复之前,不能应用新的迁移。了解有关如何解决生产数据库中的迁移问题的更多信息:
我通过“npx prisma migrate reset”修复了它。
当我现在尝试针对托管在Digital Ocean上的PostgreSQL数据库执行以下查询时:
mutation{
  createMeme(title: "Help", content: "Hellp", published: true, test: "Test") {
    id
    title
    content
    published
    test
  }
}

我收到以下错误:
  {"errors": [
    {
      "message": "\nInvalid `prisma.post.create()` invocation in\n/workspace/src/schema.js:61:26\n\n   58 },\n   59 Mutation: {\n   60   createMeme: (parent, args) => {\n→  61     return prisma.post.create({\n            data: {\n              title: 'Help',\n              content: 'Hellp',\n              published: true,\n              author: undefined,\n              test: 'Test'\n              ~~~~\n            }\n          })\n\nUnknown arg `test` in data.test for type PostCreateInput. Did you mean `title`? Available args:\ntype PostCreateInput {\n  title: String\n  content?: String | Null\n  published?: Boolean\n  author?: UserCreateNestedOneWithoutPostsInput\n}\n\n",
      "locations": [
        {
          "line": 2,
          "column": 3
        }
      ],
      "path": [
        "createMeme"
      ],
      "extensions": {
        "code": "INTERNAL_SERVER_ERROR",
        "exception": {
          "clientVersion": "3.6.0",
          "stacktrace": [
            "Error: ",
            "Invalid `prisma.post.create()` invocation in",
            "/workspace/src/schema.js:61:26",
            "",
            "   58 },",
            "   59 Mutation: {",
            "   60   createMeme: (parent, args) => {",
            "→  61     return prisma.post.create({",
            "            data: {",
            "              title: 'Help',",
            "              content: 'Hellp',",
            "              published: true,",
            "              author: undefined,",
            "              test: 'Test'",
            "              ~~~~",
            "            }",
            "          })",
            "",
            "Unknown arg `test` in data.test for type PostCreateInput. Did you mean `title`? Available args:",
            "type PostCreateInput {",
            "  title: String",
            "  content?: String | Null",
            "  published?: Boolean",
            "  author?: UserCreateNestedOneWithoutPostsInput",
            "}",
            "",
            "",
            "    at Object.validate (/workspace/node_modules/@prisma/client/runtime/index.js:34750:20)",
            "    at PrismaClient._executeRequest (/workspace/node_modules/@prisma/client/runtime/index.js:39729:17)",
            "    at consumer (/workspace/node_modules/@prisma/client/runtime/index.js:39670:23)",
            "    at /workspace/node_modules/@prisma/client/runtime/index.js:39674:49",
            "    at AsyncResource.runInAsyncScope (async_hooks.js:189:9)",
            "    at PrismaClient._request (/workspace/node_modules/@prisma/client/runtime/index.js:39674:27)",
            "    at request (/workspace/node_modules/@prisma/client/runtime/index.js:39779:77)",
            "    at _callback (/workspace/node_modules/@prisma/client/runtime/index.js:39987:14)",
            "    at PrismaPromise.then (/workspace/node_modules/@prisma/client/runtime/index.js:39994:23)",
            "    at resolveField (/workspace/node_modules/graphql/execution/execute.js:468:26)"
          ]
        }
      }
    }
  ],
  "data": null
}

这是一个奇怪的行为,为什么在我的本地主机上可以运行,但在DigitalOcean托管的数据库上却不能工作? 我在终端中漏掉了一些步骤吗?也许需要执行一些命令?
这是完整的schema.js文件,包括所有解析器、typeDefs等:
    const { gql } = require('apollo-server')
const { prisma } = require('./db')

const typeDefs = gql`
  type User {
    email: String!
    id: ID!
    name: String
    posts: [Post!]!
  }

  type Post {
    content: String
    id: ID!
    published: Boolean!
    title: String!
    author: User
    test: String

  }

  type Query {
    feed: [Post!]!
    post(id: ID!): Post
  }

  type Mutation {
    createUser(data: UserCreateInput!): User!
    createMeme(authorEmail: String, content: String, title: String!, published: Boolean, test: String): Post!
    publish(id: ID!): Post
  }

  input UserCreateInput {
    email: String!
    name: String
    posts: [PostCreateWithoutAuthorInput!]
  }

  input PostCreateWithoutAuthorInput {
    content: String
    published: Boolean
    title: String!
  }
`

const resolvers = {
  Query: {
    feed: (parent, args) => {
      return prisma.post.findMany({
        where: { published: true },
      })
    },
    post: (parent, args) => {
      return prisma.post.findOne({
        where: { id: Number(args.id) },
      })
    },
  },
  Mutation: {
    createMeme: (parent, args) => {
      return prisma.post.create({
        data: {
          title: args.title,
          content: args.content,
          published: args.published,
          author: args.authorEmail && {
            connect: { email: args.authorEmail },
          },
          test: args.test,
          
        },
      })
    },
    publish: (parent, args) => {
      return prisma.post.update({
        where: { id: Number(args.id) },
        data: {
          published: true,
        },
      })
    },
    createUser: (parent, args) => {
      return prisma.user.create({
        data: {
          email: args.data.email,
          name: args.data.name,
          posts: {
            create: args.data.posts,
          },
        },
      })
    },
  },
  User: {
    posts: (parent, args) => {
      return prisma.user
        .findOne({
          where: { id: parent.id },
        })
        .posts()
    },
  },
  Post: {
    author: (parent, args) => {
      return prisma.post
        .findOne({
          where: { id: parent.id },
        })
        .author()
    },
  },
}

module.exports = {
  resolvers,
  typeDefs,
}

这是GitHub上的项目: https://github.com/DaFaack/prisma-graphql.git

我在.gitignore文件中只忽略了node_modules和.env两个文件。


你能分享一下你的PostCreateInput文件吗?因为我在日志中看到了错误。 - Laxmikanta Nayak
我将整个schema.js文件添加了进来,包括所有的解析器和类型定义。 我的文件树中没有名为PostCreateInput的文件。 - HavanaSun
如果在本地添加了新字段“test”后可以正常工作,则尝试从@prisma/client导入PostCreateInput并查看它是否具有该字段。 - Laxmikanta Nayak
我该如何导入它?只需在我的schema.js文件顶部键入“import { PostCreateInput } from "@prisma/client"”即可。 - HavanaSun
我认为这与你的.env文件有关。请检查你是否在本地和部署/生产应用程序中使用了正确的.env文件。 - ArchNoob
2个回答

0

在我看来,您使用的客户端与您刚刚在模式中进行的更改不匹配,因此您需要生成客户端以使其与 npx prisma generate 同步。


我尝试过了,但它不起作用,prisma已经安装好了。 这是项目链接:https://github.com/DaFaack/prisma-graphql.git - HavanaSun

0

嗨,我已经检查了你的代码,我可以看到我能够创建变异。就像你在下面的截图中看到的那样。

enter image description here

运行的命令:
npm i
npx prisma migrate dev
npm run start


是的,就像我说的那样,这段代码在我的本地主机上也能正常工作。但是一旦我尝试连接托管在DigitalOcean上的PostgreSQL数据库,它就停止工作了。 - HavanaSun
你在部署到DigitalOcean之后是否运行了“npx prisma migrate deploy”命令,以便在你的DigitalOcean数据库中运行迁移。 - Laxmikanta Nayak
是的,我已经这样做了,并且还连接了pgAdmin,看到“test”列已成功创建。 因此迁移有效,但可能有其他问题。 此外,我的GitHub存储库拥有所需的一切。 只是不明白为什么它不起作用。 - HavanaSun

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接