飞雪团队

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

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

[复制链接]

7952

主题

8040

帖子

2万

积分

管理员

Rank: 9Rank: 9Rank: 9

积分
26186
发表于 2022-2-12 14:35:41 | 显示全部楼层 |阅读模式
& H- L, N4 Z+ b3 @
<h2 id="系列导航">系列导航</h2>
6 l2 o( O' W" c) a5 V0 F<p><a  href="https://www.cnblogs.com/code4nothing/p/graphql-net6-0.html">使用Hot Chocolate和.NET 6构建GraphQL应用文章索引</a></p>+ s# r8 i7 p5 S( q. B
<h2 id="需求">需求</h2>
- n$ z3 h( ?5 F4 N& e<p>在讨论完GraphQL中的查询需求后,这篇文章我们将演示如何实现GraphQL中的数据添加任务。</p>
" J2 }6 _) r; m2 W<h2 id="思路">思路</h2>, }! n6 ]. F! G  m9 L, d
<p>在GraphQL中,对数据进行查询使用<code>query</code>,而对于修改数据则需要使用<code>mutation</code>,包括新增和修改数据。Hot Chocolate在使用Mutation的逻辑上和使用Query的基本一致,但是需要根据需要定义用于创建或者更新的数据对象,所以我们直接进行实现。</p>
2 K1 S& W/ [: L; G4 ]# X/ G<h2 id="实现">实现</h2>
$ s% }$ P3 ^& R4 }) a<p>为了保持简单,我们先定义以下两个类型:</p>6 \1 x9 D4 q+ x+ B7 X9 U- J* ]8 a" x
<pre><code class="language-c#">// 定义新增Post的参数
6 O7 C/ k, ~/ x9 bpublic record AddPostInput(string Title, string Author);. e6 U, m1 T; Q1 U. ?) y+ a4 |8 c
$ d) T; K; X, k' H7 u$ p
// 定义新增Post的返回对象
: u( U  K0 }4 ^" a. Jpublic record AddPostPayload(Post Post);4 L6 o0 ?( d3 w: b8 v; u4 c7 W" {+ ~- k
</code></pre>/ o9 Z* H1 F3 Y" m0 ?+ f0 {
<p>新建<code>Mutation.cs</code>用来定义相关接口:</p>6 B6 S" A/ D  a% U) i0 B' A
<ul>
, i* j7 O3 |* H6 A8 k<li><code>Mutation.cs</code></li>" _* c0 ~3 i7 n, Q4 M
</ul>. t$ g! u$ H* c  V+ M- y) q2 I' o
<pre><code class="language-c#">namespace PostGraphi.Api.GraphQL;
" H1 ^: i& i8 ?! y- Z6 a0 v: L* v( [3 I8 ]" s+ D- ]9 ]8 I
public class Mutation2 E/ f! ]. [' O8 Q- n# g
{
4 D- Q; B& F8 d5 E7 S! v' s  _; N    public async Task&lt;AddPostPayload&gt; AddPostAsync(AddPostInput input, [Service] IRepository&lt;Post&gt; repository)
3 ^" {' s& j" W; p; B- b    {
1 q- Z. P( P  O  o% V3 {7 C        return new AddPostPayload(await repository.AddAsync(new Post
& i9 L4 g; i  p, e        {
! P$ l, Q2 y- b* h" J, Q* q            Title = input.Title,5 j, q) f/ J3 G/ a
            Author = input.Author
7 K/ Z2 N) d; k. G; y        }));( Z8 n% X3 u0 ~' ^
    }
4 Y4 u" w" q" d9 z$ s1 U}6 B! c% B+ z% R/ s6 r  K9 Y

* U8 S8 u) k  a+ y, T% ?</code></pre>6 f/ O7 w- W3 \7 X, l
<p>最后在注入服务的地方进行配置:</p>
4 v2 A' p( a/ J" p, v( r6 D<ul>
/ Q/ }& h( m. ?- |! b: x<li><code>ProgramExtensions.cs</code></li>* h& X; m9 d& L. A3 U6 Z
</ul>
( R  ?5 R+ w$ U& X) Z<pre><code class="language-c#">builder.Services
5 J3 }2 w: A- z) |9 f3 a/ i    .AddGraphQLServer()
) x( H5 u2 C2 }) a/ j; K    .SetPagingOptions(new PagingOptions
, |+ M( o( t9 C( Q+ k. u    {
' A: I' \9 c) u! S, _  _% o( ~        MaxPageSize = 50,* m( P  D% x! n  o; P9 v& y. i
        IncludeTotalCount = true
, @/ F  |- R9 t9 A9 Z) B, |    })) Y: Z' [  h4 \/ z5 a1 K
    .AddFiltering()
0 J4 v! r. j+ U6 c, s    .AddProjections()+ X1 [6 o' _' I
    .AddSorting()& q* N5 h* ~* s. w
    .AddQueryType&lt;Query&gt;()% A) v, [/ N$ J& C! S% R8 K% g# K! I- q' |
    .AddMutationType&lt;Mutation&gt;()* ~9 v! ^; I) v- `9 {( F  R6 Z: A
    .AddMutationConventions(new MutationConventionOptions
0 X& Z7 @8 C/ M1 g' X0 O    {0 F- z7 y  l, O  s/ a
        ApplyToAllMutations = true,' u. K& U) z4 F! t, z% p7 J* d
        InputArgumentName = "input",& C3 A- a7 F6 d* ]
        InputTypeNamePattern = "{MutationName}Input",# t0 ^# V& Y9 Y8 m  X, f( V7 U
        PayloadTypeNamePattern = "{MutationName}Payload",2 [$ g5 ^9 m7 E3 U5 g1 U
        PayloadErrorTypeNamePattern = "{MutationName}Error",
2 |2 K3 c0 E: M  h$ `* f, r        PayloadErrorsFieldName = "errors"
2 a/ }7 B4 U' o1 F    })- b7 @% u* D7 X' u. h3 f
    .AddType&lt;PostType&gt;();/ B+ _: e8 r7 T8 r9 Z. E' W
</code></pre>
8 N1 n- @2 N' l<p>这样就实现了新增Post的需求,下面我们来验证一下。</p>8 V( d- Z8 l/ m
<h2 id="验证">验证</h2>
- D2 s! F) l+ c<p>启动<code>Api</code>项目,调用接口:</p>
3 \5 j/ t4 k4 p; n<p><img src="https://img2022.cnblogs.com/blog/2487237/202202/2487237-20220211104544617-1400586374.png" ></p>3 C8 [' d5 o( v( ~; M, j
<p>终端的日志输出如下:</p>
$ J  a" n7 ]5 u3 ^3 B8 T8 k<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']$ d1 I% Y8 f) k! }6 s9 D
INSERT INTO "Posts" ("Id", "Abstraction", "Author", "Content", "Created", "CreatedBy", "LastModified", "LastModifiedBy", "Link", "PublishedAt", "Title")& |* [' [, m9 {& Q: f3 F8 C
VALUES (@p0, @p1, @p2, @p3, @p4, @p5, @p6, @p7, @p8, @p9, @p10);
: C0 C( `* f# |[10:45:15 INF] Executed endpoint 'Hot Chocolate GraphQL Pipeline'' m+ E5 Z7 b& s. e; t+ O7 E
</code></pre>3 k& d7 Y' m" ?3 Q. g1 \
<p>可以看到新建的Post已经存储到数据库中了,我们可以通过查询接口来获取详情:</p>
* a* o! i& b9 a2 d<p><img src="https://img2022.cnblogs.com/blog/2487237/202202/2487237-20220211104851825-1533915064.png" ></p>
% I1 L4 i. R% @" d( @! g<h2 id="总结">总结</h2>* u: U( x+ a3 C  @
<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>0 ~- n/ W% {+ K) a
<p>在下一篇文章中,我们通过<code>Mutation</code>对已有数据进行更新。</p>  I8 X* w9 e! b& S3 P
% g/ A1 z3 u- g9 s
回复

使用道具 举报

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

本版积分规则

手机版|飞雪团队

GMT+8, 2025-11-24 09:39 , Processed in 0.068535 second(s), 21 queries , Gzip On.

Powered by Discuz! X3.4

Copyright © 2001-2021, Tencent Cloud.

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