飞雪团队

 找回密码
 立即注册
搜索
热搜: 活动 交友 discuz
查看: 12679|回复: 0

使用Hot Chocolate和.NET 6构建GraphQL应用(8) —— 实现Mutate添加数据 ...

[复制链接]

8032

主题

8120

帖子

2万

积分

管理员

Rank: 9Rank: 9Rank: 9

积分
26426
发表于 2022-2-12 14:35:41 | 显示全部楼层 |阅读模式
, C2 n/ [- B+ X3 z1 J
<h2 id="系列导航">系列导航</h2>) K- c$ o- m6 O5 s5 Z/ }
<p><a  href="https://www.cnblogs.com/code4nothing/p/graphql-net6-0.html">使用Hot Chocolate和.NET 6构建GraphQL应用文章索引</a></p>$ p% a- I6 t2 U: \
<h2 id="需求">需求</h2>
% i, E: c) u3 ~8 @, n0 @# C* u<p>在讨论完GraphQL中的查询需求后,这篇文章我们将演示如何实现GraphQL中的数据添加任务。</p>' R7 x( t7 m  c5 L
<h2 id="思路">思路</h2>: w. P0 f2 I6 [4 R3 l9 H. r  ]
<p>在GraphQL中,对数据进行查询使用<code>query</code>,而对于修改数据则需要使用<code>mutation</code>,包括新增和修改数据。Hot Chocolate在使用Mutation的逻辑上和使用Query的基本一致,但是需要根据需要定义用于创建或者更新的数据对象,所以我们直接进行实现。</p>5 @# H3 H9 ~+ y# L7 t. A, J
<h2 id="实现">实现</h2>
7 ?) D$ [+ t) `/ G' u<p>为了保持简单,我们先定义以下两个类型:</p>6 ?. N* a: O6 e' I3 ~. o! ?5 v1 n9 y
<pre><code class="language-c#">// 定义新增Post的参数
4 J& Z: e6 f5 [6 Upublic record AddPostInput(string Title, string Author);5 W& h1 S6 ?. z: D
; F  }! p2 D! O6 Z; r8 J6 g/ W
// 定义新增Post的返回对象& ~' N1 D% a7 o( E5 c' ?
public record AddPostPayload(Post Post);
0 H, s. v9 R$ w* D1 a& A</code></pre>( o- {" p5 ~  D. x5 H0 D- X! R/ b% p: K
<p>新建<code>Mutation.cs</code>用来定义相关接口:</p>
$ I, ?. {+ M8 ~' s( n& v<ul>& C$ T' }! R: @: v
<li><code>Mutation.cs</code></li>) ]  `9 h- ~9 w5 k7 X$ s; o
</ul>! E# _& ~5 Y5 I2 ?% o
<pre><code class="language-c#">namespace PostGraphi.Api.GraphQL;$ E: i- n' I" d7 R5 ~! ]

- F" `; j+ _- Opublic class Mutation# c0 k9 z+ }# Y9 \5 o1 ~6 Z7 `0 P
{  C& ?, z( Z9 I0 |  W9 b
    public async Task&lt;AddPostPayload&gt; AddPostAsync(AddPostInput input, [Service] IRepository&lt;Post&gt; repository)2 b; ~, N$ D% o+ ]/ d+ o) |
    {1 q2 U* K3 c. k7 Q0 y: x
        return new AddPostPayload(await repository.AddAsync(new Post. b; ]7 S" |, m7 h( y8 T2 V9 j2 U
        {
0 K. U" ]# e  g7 y& y            Title = input.Title,
( J" D0 n! P2 e; j  s! x) B2 W            Author = input.Author* t) m" }) _& v- a* r
        }));6 C5 U! N( c7 F0 R0 ~4 w
    }
. J+ n! P! {' j$ E8 r: O/ q8 ^; [}$ f$ j* O' P7 B. d" v9 O' f

- j4 p: |/ l" }* {' k( I0 s. A* }& J3 B& s</code></pre>
, @0 L0 z8 O8 E/ b- p7 a6 y: U: `<p>最后在注入服务的地方进行配置:</p>
' ]# [- O: O) ~- f<ul>2 L% D8 ]+ }' p" H
<li><code>ProgramExtensions.cs</code></li>  j5 G, Q+ K/ F6 f# S
</ul>
# N9 f3 P! X. b" n" k1 I3 M! n<pre><code class="language-c#">builder.Services0 M4 k+ ?- b5 I
    .AddGraphQLServer(). E6 [1 s8 M" q& r
    .SetPagingOptions(new PagingOptions
7 V0 I% A  ~& v3 K% l  {2 |7 l/ R/ T. q# ~    {& j; i" h0 X: Y( ]" d7 L
        MaxPageSize = 50,
& E' d# W6 l9 r/ P0 y        IncludeTotalCount = true' L! E9 N! O; a
    })* O& c4 `& z/ H) I! d
    .AddFiltering()6 P) V+ b" L9 X% Y2 p  [: Z& t4 c
    .AddProjections()
7 X3 f+ N7 D: h' H; c    .AddSorting()
4 T% o# p* }+ t1 |; F    .AddQueryType&lt;Query&gt;()
) I; h+ W2 }* q7 B$ a; |# Y; i* E    .AddMutationType&lt;Mutation&gt;()
% s- w; X4 t% a, y    .AddMutationConventions(new MutationConventionOptions
# @/ f: D, C+ v    {0 {' Q) f/ q* B$ H: u
        ApplyToAllMutations = true,) |0 W* d# Y* O6 B" `
        InputArgumentName = "input",$ b" P/ }: }  D8 f4 K
        InputTypeNamePattern = "{MutationName}Input",( m. m  W# Y" g7 ~
        PayloadTypeNamePattern = "{MutationName}Payload",$ z. [- q. v1 u8 ~3 U
        PayloadErrorTypeNamePattern = "{MutationName}Error",
' ^: B3 z$ z. i! c- A        PayloadErrorsFieldName = "errors"
9 x; R( C: C" |7 n$ y+ Q    })( ~) Q5 k# n) Q
    .AddType&lt;PostType&gt;();3 E3 \& P: t, g6 o
</code></pre>% h. }8 f( ^# M% Y4 ~
<p>这样就实现了新增Post的需求,下面我们来验证一下。</p>$ g8 B' b+ q. |7 q* C. W1 P
<h2 id="验证">验证</h2>* `9 @4 `. T6 F, R' ?
<p>启动<code>Api</code>项目,调用接口:</p>
( D2 U  p$ Y' E7 x  d  V' r<p><img src="https://img2022.cnblogs.com/blog/2487237/202202/2487237-20220211104544617-1400586374.png" ></p>! Z+ h, q8 X  `( Q' t# V2 N% {
<p>终端的日志输出如下:</p>9 j* H- K& e' i( [
<pre><code class="language-bash">[10:45:15 INF] Executed DbCommand (1ms) [Parameters=[@p0='?' (DbType = Guid), @p1='?', @p2='?' (Size = 13), @p3='?', @p4='?' (DbType = DateTime), @p5='?', @p6='?' (DbType = DateTime), @p7='?', @p8='?', @p9='?' (DbType = DateTime), @p10='?' (Size = 30)], CommandType='Text', CommandTimeout='30']
; `' }/ x% C! E( V6 T0 gINSERT INTO "Posts" ("Id", "Abstraction", "Author", "Content", "Created", "CreatedBy", "LastModified", "LastModifiedBy", "Link", "PublishedAt", "Title"): ^9 t  w" L0 Z( k; ?4 n
VALUES (@p0, @p1, @p2, @p3, @p4, @p5, @p6, @p7, @p8, @p9, @p10);" N* H: ^6 L. K3 ~- l
[10:45:15 INF] Executed endpoint 'Hot Chocolate GraphQL Pipeline', {% b$ Y: i  o7 D
</code></pre>
" r  A9 o+ s$ v2 H# }# n<p>可以看到新建的Post已经存储到数据库中了,我们可以通过查询接口来获取详情:</p>
5 H5 N% X  D/ p' O9 C. F<p><img src="https://img2022.cnblogs.com/blog/2487237/202202/2487237-20220211104851825-1533915064.png" ></p>" J  `: n* ~7 X- `
<h2 id="总结">总结</h2>" M  |% m& |& r5 w" T4 e4 s
<p>在本文中我们实现了简单的新增Post操作,这里还有一些涉及到错误处理的内容,我没有在文章中演示,可以参考官方文档 <a  href="https://chillicream.com/docs/hotchocolate/defining-a-schema/mutations/#errors">Errors</a>,在自定义异常对象后,有三种方式可以进行错误处理:直接返回异常;使用异常工厂方法;使用构造函数。甚至可以在<code>AggregateExceptions</code>中一次性返回多个异常。基本思路都是通过添加属性<code>[Error(typeof(SomeUserDefinedException))]</code>来实现的。</p>- U( C; n9 M( M1 j
<p>在下一篇文章中,我们通过<code>Mutation</code>对已有数据进行更新。</p>
5 J$ Z. L3 i, G$ _" f
3 a' k: e! b2 v# j& u
回复

使用道具 举报

懒得打字嘛,点击右侧快捷回复 【右侧内容,后台自定义】
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

手机版|飞雪团队

GMT+8, 2025-12-4 08:15 , Processed in 0.065702 second(s), 21 queries , Gzip On.

Powered by Discuz! X3.4

Copyright © 2001-2021, Tencent Cloud.

快速回复 返回顶部 返回列表