{"id":15394,"date":"2022-08-10T15:12:53","date_gmt":"2022-08-10T13:12:53","guid":{"rendered":"https:\/\/www.centigrade.de\/blog\/graphql-net-und-react-miteinander-verbinden-teil-iv-react-und-graphql-schnell-zusammenbringen-dank-apollo-client\/"},"modified":"2022-08-11T14:36:22","modified_gmt":"2022-08-11T12:36:22","slug":"how-to-engage-graphql-net-and-react-together-react-graphql-apollo-client","status":"publish","type":"blog","link":"https:\/\/www.centigrade.de\/en\/blog\/how-to-engage-graphql-net-and-react-together-react-graphql-apollo-client\/","title":{"rendered":"How to engage GraphQL, .Net and React together \u2013 Part IV: React, GraphQL and the amazing Apollo Client"},"content":{"rendered":"\r\n<p>Hello! \ud83d\ude42 I&#8217;m Ulrike, a media informatics student in my master&#8217;s degree and currently an intern at Centigrade. During my internship one of my tasks was finishing the VedaVersum app together with <a href=\"https:\/\/www.centigrade.de\/en\/company\/team\/#mikhail.shabanov\">Mikhail<\/a>. We wanted to create the application using .NET, GraphQL and React as a knowledge base where team members can log in and write, edit and delete articles (see <a href=\"https:\/\/www.centigrade.de\/en\/blog\/how-to-engage-graphql-net-and-react-together-part-i\/\">first blog article<\/a>). In this part of the series, I&#8217;d like to share my approach to link the frontend with the backend with you and briefly report how I fared as a React and GraphQL newbie.<!--more--><\/p>\r\n\r\n\r\n\r\n<h2 class=\"wp-block-heading\">Review: .NET, GraphQL und MongoDB<\/h2>\r\n\r\n\r\n\r\n<p><strong>Review: .NET, GraphQL and MongoDB<\/strong><\/p>\r\n<p>In the <a href=\"https:\/\/www.centigrade.de\/en\/blog\/how-to-engage-graphql-net-and-react-together-part-i\/\">first blog article<\/a>, Mikhail explained how to create a GraphQL API with .Net. He chose <a href=\"https:\/\/chillicream.com\/docs\/hotchocolate\">Hot Chocolate<\/a> from <a href=\"https:\/\/chillicream.com\/\">ChilliCream<\/a> as GraphQL server to support it. <a href=\"https:\/\/chillicream.com\/docs\/bananacakepop\">Banana Cake Pop<\/a>, a tool for checking GraphQL queries provided by ChilliCream, will also be of use later, when we test our queries in isolation from the frontend. In the <a href=\"https:\/\/www.centigrade.de\/en\/blog\/how-to-engage-graphql-net-and-react-together-part-ii-veda-versum-backend-authentication\/\">follow-up article<\/a>, we focused entirely on backend authentication using GitLab as an example, and in the <a href=\"https:\/\/www.centigrade.de\/en\/blog\/how-to-engage-graphql-net-and-react-together-part-iii-veda-versum-backend-authentication\/\">latest article<\/a> we added MongoDB to the backend for ensuring data persistence.<\/p>\r\n<p>In this article, we will write GraphQL queries in JavaScript and integrate them in our React frontend using Apollo Client Library.<\/p>\r\n<p>An important note about the code on <a href=\"https:\/\/github.com\/Centigrade\/vedaversum\">Github<\/a>: While we are writing this series of articles for our blog, we have been working continuously on VedaVersum. Accordingly, as it is usually the case when developing software ?, there are always major and minor restructurings and renames. For example, the <em>VedaVersumCard<\/em> has now become the <em>VedaVersumArticle<\/em>.<\/p>\r\n\r\n\r\n\r\n<h2 class=\"wp-block-heading\">Frontend with React, Tailwind CSS and Apollo Client<\/h2>\r\n\r\n\r\n\r\n<p>We use the following technologies for the implementation of the frontend:<\/p>\r\n<p><img loading=\"lazy\" decoding=\"async\" class=\"aligncenter size-full wp-image-15382\" src=\"https:\/\/www.centigrade.de\/wordpress\/wp-content\/uploads\/Logos.png\" alt=\"Logos React, tailwind, apollo\" width=\"682\" height=\"109\" srcset=\"https:\/\/www.centigrade.de\/wordpress\/wp-content\/uploads\/Logos.png 682w, https:\/\/www.centigrade.de\/wordpress\/wp-content\/uploads\/Logos-300x48.png 300w\" sizes=\"auto, (max-width: 682px) 100vw, 682px\" \/><\/p>\r\n\r\n\r\n\r\n<p>As described in detail in the <a href=\"https:\/\/www.centigrade.de\/en\/blog\/how-to-engage-graphql-net-and-react-together-part-i\/\">first blog article<\/a>, we chose <a href=\"https:\/\/reactjs.org\/\"><strong>React<\/strong><\/a> because it is more lightweight (User Interface <em>Library<\/em>) than Angular (User Interface <em>Framework<\/em>).<\/p>\r\n<p><a href=\"https:\/\/tailwindcss.com\/\"><strong>Tailwind CSS<\/strong><\/a> is a CSS framework that follows the &#8220;utility first&#8221; approach. A <a href=\"https:\/\/frontstuff.io\/in-defense-of-utility-first-css\">blog article<\/a> from <a href=\"https:\/\/frontstuff.io\">frontstuff.io<\/a> inspired us to look into this topic. We chose TailwindCSS for the following reasons: We didn&#8217;t want anything heavyweight like Bootstrap for our small application. In addition, the requirements for our application and therefore its design and layout are continuously revised. With Tailwind CSS it is possible to implement these changes quickly right in HTML.<br \/>Since a detailed discussion of the framework and &#8220;utility first&#8221; would go beyond the scope of this blog article, I&#8217;ll only briefly discuss it for completeness.<\/p>\r\n<p><a href=\"https:\/\/www.apollographql.com\/apollo-client\/\"><strong>Apollo Client<\/strong><\/a> is an open-source JavaScript library for data management with GraphQL. We chose this library for our project because Apollo Client is widely used, well documented and handles a lot of data request logic on its own. For example, errors in data retrieval don&#8217;t have to be implemented manually. Apollo Client sends them along directly and we only have to take care of what should happen in case of an error.<\/p>\r\n\r\n\r\n\r\n<h3 class=\"wp-block-heading\">VedaVersum &#8211; A React application communicating with the GraphQL backend via Apollo Client<\/h3>\r\n<p>After reviewing the requirements for the VedaVersum app for the publication of this article, the first &#8220;<a href=\"https:\/\/en.wikipedia.org\/wiki\/Minimum_viable_product\">Minimum Viable Product<\/a>&#8221; of the application contains the following features:<\/p>\r\n<ul>\r\n<li>On the home page, a list of all existing articles is shown to the users. As a user I can filter this list by the articles I have created. For this we need <strong><em>GraphQL queries<\/em><\/strong>.<\/li>\r\n<li>I can create articles, delete articles created by me and edit articles written by me as well as articles written by other users. For this we need<strong><em> GraphQL mutations<\/em><\/strong>.<\/li>\r\n<li>If other users create new articles or edit existing articles while I am logged in, I will be notified by the system. For this we need a <strong><em>GraphQL subscription<\/em><\/strong>.<\/li>\r\n<\/ul>\r\n<h2>Initializing Apollo Client in React<\/h2>\r\n\r\n\r\n\r\n<p>The <a href=\"https:\/\/www.apollographql.com\/docs\/react\/get-started\/\">Apollo Client Docs<\/a> describe very well how to integrate Apollo Client into a React project. However, since we implemented authentication in the previous articles, we need a bit more code for the initialization than the &#8220;Get started&#8221; from the docs. Accordingly, we outsourced this code to a separate file called &#8220;ApolloSetup.ts&#8221;. We import the Apollo client created in \u201cApolloSetup.ts\u201d into the &#8220;index.tsx&#8221; file and put it around our application. The framework then looks like this:<\/p>\r\n\r\n\r\n\r\n<p><em>ApolloSetup.ts<\/em><\/p>\r\n\r\n\r\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; title: ; notranslate\" title=\"\">\r\nexport const apolloClient = new ApolloClient({\r\n  ...\r\n});\r\n\r\n<\/pre><\/div>\r\n\r\n\r\n<p>&nbsp;<\/p>\r\n\r\n\r\n\r\n<p><em><br \/>index.tsx<\/em><\/p>\r\n\r\n\r\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; title: ; notranslate\" title=\"\">\r\nconst root = ReactDOM.createRoot(document.getElementById(&#039;root&#039;) as HTMLElement);\r\n\r\nroot.render(\r\n  &lt;ApolloProvider client={apolloClient}&gt;\r\n    ...\r\n  &lt;\/ApolloProvider&gt;,\r\n);\r\n\r\n<\/pre><\/div>\r\n\r\n\r\n<p><strong><br \/><\/strong>The basic implementations of GraphQL Queries, Mutations and Subscriptions are very similar to each other. Hence, in the following section I will describe GraphQL queries a bit more in-depth and keep the explanation short in the other sections.<\/p>\r\n\r\n\r\n\r\n<h2 class=\"wp-block-heading\">How to write GraphQL queries and use them in React via Apollo Client<\/h2>\r\n\r\n\r\n\r\n<p>GraphQL queries are utilized to read data from the database, which is why we use them often in our application. On the one hand, these queries can be called directly, for example to request all the items stored in the database. On the other hand, we can pass them parameters, e.g. to filter all stored articles by the articles of the logged-in user.<\/p>\r\n<p><em><u>Writing GraphQL queries in JavaScript<\/u><\/em><\/p>\r\n<p>To define a query as a GraphQL query in JavaScript, you have to use the keyword <em>gql<\/em> with backticks ( ` ` ). Between the backticks you write the query and store the entire expression in a constant:<\/p>\r\n\r\n\r\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; title: ; notranslate\" title=\"\">\r\nexport const ALL_ARTICLES_QUERY = gql`\r\n   ...\r\n`;\r\n\r\n<\/pre><\/div>\r\n\r\n\r\n<p>The GraphQL query itself looks like this: Introduced by the keyword <em>query<\/em> and the name of the query, you put the database query in curly brackets. It is important that the GraphQL query is named the same as the variable in which the result of the query is stored in the backend. Otherwise, the result cannot be assigned to the database query, and you will get an error message. How exactly to write a GraphQL query is described very well in the <a href=\"https:\/\/graphql.org\/learn\/queries\/\">GraphQL docs<\/a>.<\/p>\r\n<p>The completed query, which reads all information of all articles stored in the database, looks like this:<\/p>\r\n\r\n\r\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; title: ; notranslate\" title=\"\">\r\nexport const ALL_ARTICLES_QUERY = gql`\r\n  query GetAllArticles {\r\n    allArticles {\r\n      id\r\n      title\r\n      content\r\n      created\r\n      userCreated\r\n      relatedArticleIds\r\n      userUpdated\r\n      updatedAt\r\n      accessCounter\r\n    }\r\n  }\r\n`;\r\n\r\n<\/pre><\/div>\r\n\r\n\r\n<p>To make sure that the GraphQL query itself is executable and that the backend returns the desired result, we can test the query in Banana Cake Pop without the frontend. To do this, we simply copy the pure GraphQL query from the code and paste it into Banana Cake Pop (see also <a href=\"https:\/\/www.centigrade.de\/en\/blog\/how-to-engage-graphql-net-and-react-together-part-i\/\">first blog article<\/a>). If there is a syntax error in the query, the program fortunately points it out immediately. If the query is correct, Banana Cake Pop shows us the result from the backend:<\/p>\r\n<p><img loading=\"lazy\" decoding=\"async\" class=\"aligncenter size-full wp-image-15384\" src=\"https:\/\/www.centigrade.de\/wordpress\/wp-content\/uploads\/Gif1-Query.gif\" alt=\"Banana Cake Pop Ergebnis Backend\" width=\"1920\" height=\"1080\" \/><\/p>\r\n\r\n\r\n\r\n<p><em><u>Using GraphQL queries with Apollo Client in React<\/u><\/em><\/p>\r\n<p>Now, to execute the GraphQL query in our React application, we first need to import the React hook <em>useQuery<\/em> from Apollo Client. Then we create a constant where the result of our GraphQL Query will be stored. We know that database requests cannot always be successfully resolved, for example if the server where the data is stored is currently unavailable. Likewise, it may take longer to process the query. To enable good usability, we want to cover both cases, and therefore choose the following notation:<\/p>\r\n\r\n\r\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; title: ; notranslate\" title=\"\">\r\nconst {\r\n    error: errorAllArticles,\r\n    data: allArticlesData,\r\n    loading: loadingAllArticles,\r\n  } = ...\r\n\r\n<\/pre><\/div>\r\n\r\n\r\n<p>If the query is successfully resolved, the data is stored in the data variable (here renamed to &#8220;allArticlesData&#8221;). Later we can process the result in the JavaScript code or check it in the HTML section and display the corresponding UI component.<\/p>\r\n<p>But back to the query &#8211; to call the query, we now assign our constant the following expression as &#8220;value&#8221;:<\/p>\r\n\r\n\r\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; title: ; notranslate\" title=\"\">\r\nconst { ... } = useQuery(ALL_ARTICLES_QUERY);\r\n<\/pre><\/div>\r\n\r\n\r\n<p>In round brackets we provide <em>useQuery <\/em>with the parameters the query needs &#8211; in this case only the name of the GraphQL query we want to execute. The GraphQL query must be imported for this.<\/p>\r\n<p>In general, you can pass other parameters to <em>useQuery<\/em> besides the name. These parameters are &#8220;collected&#8221; in an object and sent with the name of the GraphQL query separated by a comma. An example of this is <em>fetchPolicy<\/em>, whose value specifies whether and how data is cached. For GraphQL queries that expect parameters, the variables are also listed here. But we&#8217;ll take a closer look at that below:<\/p>\r\n<p><em><u>Writing GraphQL queries with parameters in JavaScript<\/u><\/em><\/p>\r\n<p>GraphQL queries can expect parameters. We can take advantage of this e.g. if we want to read an article. Users do not always take the detour via the start page but save an article as a bookmark in the browser for example. In this case we don&#8217;t want to request all articles from the database but get directly only the information of the selected article. For this we write a GraphQL query that gets the ID of an article and then returns all database entries for exactly this article &#8211; provided the article exists. The whole query looks like this in the end:<\/p>\r\n\r\n\r\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; title: ; notranslate\" title=\"\">\r\nexport const ARTICLE_BY_ID_QUERY = gql`\r\n  query GetArticle($articleId: String!) {\r\n    article(articleId: $articleId) {\r\n      # database table fields\r\n    }\r\n  }\r\n`;\r\n\r\n<\/pre><\/div>\r\n\r\n\r\n<p>The GraphQL query expects an article ID of the type string, that is passed to the backend in the next line. It is important to note that the names of the parameters received by the GraphQL query must start with a dollar sign and are passed on in the same way.<\/p>\r\n<p>For testing, we can also execute this GraphQL query in Banana Cake Pop with the article ID of one of our saved articles. We don&#8217;t have to pass the article ID to the GraphQL query, but give it directly to the backend function:<\/p>\r\n<p><img loading=\"lazy\" decoding=\"async\" class=\"aligncenter size-full wp-image-15386\" src=\"https:\/\/www.centigrade.de\/wordpress\/wp-content\/uploads\/Gif2-QueryWithParameters.gif\" alt=\"Query With Parameters\" width=\"1920\" height=\"1080\" \/><\/p>\r\n\r\n\r\n\r\n<p>To successfully execute this GraphQL query in the frontend, we need to add an object with the field &#8220;variables&#8221; to the parameters of <em>useQuery<\/em>. This field also gets an object where we would list all the parameters if there were more than one. It is important that the fields of the &#8220;variables&#8221; object are named the same as the parameters the query expects. If not, GraphQL cannot process the values. In this case, we only have the article ID as a parameter, which we previously stored as &#8220;currentArticleId&#8221;. From the <em>useQuery<\/em> structure, the rest remains the same:<\/p>\r\n\r\n\r\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; title: ; notranslate\" title=\"\">\r\nconst { error, data, loading } = useQuery(ARTICLE_BY_ID_QUERY, {\r\n    variables: { articleId: currentArticleId },\r\n  });\r\n\r\n<\/pre><\/div>\r\n\r\n\r\n<h2 class=\"wp-block-heading\">How to write GraphQL mutations and use them in React via Apollo Client\u00a0<\/h2>\r\n\r\n\r\n\r\n<p>GraphQL mutations are used to add, modify or delete data in the database. Since our users can do just that, we need a mutation for each action. The mutations have different parameters, but otherwise have the same structure. We take a look at this by the &#8220;UpdateArticle&#8221; mutation.<\/p>\r\n<p><em><u>Writing GraphQL mutations in JavaScript<\/u><\/em><\/p>\r\n<p>The basic structure of a GraphQL mutation in JavaScript is the same as for a GraphQL query:<\/p>\r\n\r\n\r\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; title: ; notranslate\" title=\"\">\r\nexport const UPDATE_ARTICLE_MUTATION = gql`\r\n  mutation UpdateArticle($articleId: String!, $articleTitle: String!, $articleContent: String!) {\r\n    articleAction(action: UPDATE, articleId: $articleId, title: $articleTitle, content: $articleContent) {\r\n      # database table fields\r\n    }\r\n  }\r\n`;\r\n\r\n<\/pre><\/div>\r\n\r\n\r\n<p>There are two small differences: Since we have created a mutation, we also use <em>mutation<\/em> as a keyword instead of <em>query<\/em>. Furthermore, we have written a function in the backend that handles all article mutations (create &#8211; &#8220;CREATE&#8221;, edit &#8211; &#8220;UPDATE&#8221;, delete &#8211; &#8220;DELETE&#8221;). Accordingly, when calling this function, we need to pass the &#8220;action&#8221; as an additional parameter &#8211; for &#8220;UpdateArticle&#8221;, of course &#8220;UPDATE&#8221;.<\/p>\r\n<p>Mutations can be tested in Banana Cake Pop like GraphQL queries with parameters:<\/p>\r\n<p><img loading=\"lazy\" decoding=\"async\" class=\"aligncenter size-full wp-image-15388\" src=\"https:\/\/www.centigrade.de\/wordpress\/wp-content\/uploads\/Gif3-Mutation.gif\" alt=\"Mutation Test Banana Cake Pop\" width=\"1920\" height=\"1080\" \/><\/p>\r\n\r\n\r\n\r\n<p><em><u>Using GraphQL mutations with Apollo Client in React<\/u><\/em><\/p>\r\n<p>GraphQL mutations are included in React again via a React hook from Apollo Client, this time <em>useMutation<\/em>. The basic structure is the same as a query. But in detail they differ:<\/p>\r\n\r\n\r\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; title: ; notranslate\" title=\"\">\r\nconst &#x5B;updateArticle] = useMutation(UPDATE_ARTICLE_MUTATION, {\r\n    variables: { articleId: articleData?.id, articleTitle: title, articleContent: content },\r\n    onError: error =&gt; {\r\n      \/\/ error handling\r\n    },\r\n    onCompleted: data =&gt; {\r\n      \/\/ actions when successful\r\n    },\r\n  });\r\n\r\n<\/pre><\/div>\r\n\r\n\r\n<p>The various responses (error, data, loading) are not specified in the constant, but in the mutation itself. They are listed after the name of the mutation and the parameters as <em>onError<\/em> or <em>onCompleted<\/em> with the corresponding statements.<\/p>\r\n<p>Later in the code the mutation can be called like a normal function:<\/p>\r\n\r\n\r\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; title: ; notranslate\" title=\"\">\r\nif (editorSettings.type === &#039;create&#039;) {\r\n   insertArticle();\r\n} else if (editorSettings.type === &#039;edit&#039;) {\r\n   updateArticle();\r\n}\r\n\r\n<\/pre><\/div>\r\n\r\n\r\n<h2 class=\"wp-block-heading\">How to write GraphQL subscriptions and use them in React via Apollo Client<\/h2>\r\n\r\n\r\n\r\n<p>GraphQL Subscriptions are used when a client needs to receive messages from the server in real time. As Mikhail mentioned in the <a href=\"https:\/\/www.centigrade.de\/en\/blog\/how-to-engage-graphql-net-and-react-together-part-i\/\">first blog article<\/a>, subscriptions are one of THE features of GraphQL. What I&#8217;ve written so far about GraphQL queries and mutations at first sounds a lot like standard <a href=\"https:\/\/en.wikipedia.org\/wiki\/Representational_state_transfer\">REST<\/a> GET and POST commands. GraphQL implements them with normal HTTP methods. However, subscriptions are a different story: Even if you don&#8217;t notice anything on the surface, for <em>subscriptions<\/em> GraphQL works with websockets. That&#8217;s why we must integrate the corresponding library for Apollo Client into our project later on. The use case for a subscription at VedaVersum are the notifications that should be triggered on the server side: If someone creates a new article or edits an existing article, all users that are logged in get a notification and can view the corresponding articles directly.<\/p>\r\n<p><em><u>Writing GraphQL subscriptions in JavaScript<\/u><\/em><\/p>\r\n<p>A GraphQL subscription in JavaScript is structured in the same way as a GraphQL query without parameters:<\/p>\r\n\r\n\r\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; title: ; notranslate\" title=\"\">\r\nexport const ARTICLE_CHANGED_SUBSCRIPTION = gql`\r\n  subscription OnArticleChanged {\r\n    articleChanged {\r\n      action\r\n      vedaVersumArticle {\r\n        # database table fields\r\n      }\r\n    }\r\n  }\r\n`;\r\n\r\n<\/pre><\/div>\r\n\r\n\r\n<p>As the keyword here, we write <em>subscription<\/em> instead of <em>query<\/em>.<\/p>\r\n<p>Testing a subscription in Banana Cake Pop is a bit more complicated than testing a query or mutation:<\/p>\r\n\r\n\r\n\r\n<ol class=\"wp-block-list\">\r\n<li>We start the subscription in a tab. We can see if the subscription is active by the button we use to execute GraphQL statements. Where before it said &#8220;Run&#8221; with an arrow icon, now it should say &#8220;Cancel&#8221; and show a loading circle.<\/li>\r\n<li>We switch to a second tab, authenticate and edit an article.<\/li>\r\n<li>We go back to the first tab. There we should see in the right field the changed article with the &#8220;action&#8221; that was executed.<\/li>\r\n<\/ol>\r\n<p><img loading=\"lazy\" decoding=\"async\" class=\"aligncenter size-full wp-image-15390\" src=\"https:\/\/www.centigrade.de\/wordpress\/wp-content\/uploads\/Gif4-Subscription.gif\" alt=\"GraphQL Subscriptions mit Apollo Client in React verwenden\" width=\"1920\" height=\"1080\" \/><\/p>\r\n\r\n\r\n\r\n<p><em><u>Using GraphQL subscriptions with Apollo Client in React<\/u><\/em><\/p>\r\n<p>Before we can use our subscription in React, we first need a subscription library. Even though it is not recommended in the <a href=\"https:\/\/www.apollographql.com\/docs\/react\/data\/subscriptions\/\">Apollo Docs<\/a>, we need to take the deprecated <em>subscription-transport-ws<\/em> library. The reason for this is that Hot Chocolate, our GraphQL server, does not yet support the successor library <em>graphql-ws<\/em>. How exactly to integrate the library into your project is described in detail <a href=\"https:\/\/www.apollographql.com\/docs\/react\/data\/subscriptions\/#the-older-subscriptions-transport-ws-library\">at the end of the Apollo Docs entry<\/a>.<\/p>\r\n<p>If you have successfully set up the library, you can use the React hook <em>useSubscription<\/em> in the code just like <em>useQuery<\/em> without parameters:<\/p>\r\n\r\n\r\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; title: ; notranslate\" title=\"\">\r\nconst { data: subscriptionData } = useSubscription(ARTICLE_CHANGED_SUBSCRIPTION);\r\n<\/pre><\/div>\r\n\r\n\r\n<p>Now the client gets a notification from the server every time a new article is created, or an already existing article is edited or deleted. So far, so good. Only this is of no use to us yet. The idea was that users get a notification when the article table in the database has changed. To achieve this, we need to use the React hook <em>useEffect<\/em> to monitor the data that the subscription sends (here &#8220;subscriptionData&#8221;). As soon as they change, i.e. the client receives a &#8220;new&#8221; changed article from the server, the statements inside the <em>useEffect<\/em> hook are executed. In the code, it looks like this (simplified):<\/p>\r\n\r\n\r\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; title: ; notranslate\" title=\"\">\r\nuseEffect(() =&gt; {\r\n    if (subscriptionData) {\r\n      \/\/ instructions what to do every time\r\n      \/\/ a new change is sent by the server\r\n    }\r\n  }, &#x5B;subscriptionData]);\r\n\r\n<\/pre><\/div>\r\n\r\n\r\n<p>In the dependency array at the end, we will later write all variables or functions on which the statements inside the curly brackets depend. Now we just program the user notifications in the if statement, then this feature is ready, too \ud83d\ude42<\/p>\r\n\r\n\r\n\r\n<h2 class=\"wp-block-heading\">Conclusion and outlook<\/h2>\r\n\r\n\r\n\r\n<p>In this blog article, I told you about my approach and experience on how to connect a React frontend to a GraphQL backend using Apollo Client. We have learned what GraphQL queries, mutations, and subscriptions are used for and how to implement them in JavaScript in the React frontend. This also included how to call these GraphQL queries using Apollo Client in React and how to process their result in the code.<\/p>\r\n<p>Personally, I learned a lot in the project because React, GraphQL, and &#8220;utility-first&#8221; are all areas I&#8217;ve had little to no exposure to. In the following section, I give a brief conclusion for each technology used.<\/p>\r\n<p>I have found <strong>React<\/strong> to be not particularly beginner-friendly \u2013 in part because I originally came from Vue.js, which is very different from React. As a result, I had problems understanding the concepts compared to getting started (in parallel) with Angular. Also, it was sometimes difficult to find solutions to problems or error messages because many forum posts, etc. were still written using the older class syntax instead of the new function syntax.<\/p>\r\n<p>I could only make friends with<strong> Tailwind CSS<\/strong> to a limited extent. I understand the idea of writing less CSS declarations, which then also repeat less often in the stylesheets. However, if you solve the complete styling via the utility classes, you get very quickly a lot of class names, which in my opinion make the code confusing. For example, the following line in the code describes the styling for a button:<\/p>\r\n\r\n\r\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: css; title: ; notranslate\" title=\"\">\r\nclassName=&quot;hover:cursor-pointer outline outline-4 outline-transparent text-white text-base text-center rounded-lg font-white bg-primary py-2 px-3 mr-4 hover:outline-primary-light active:bg-primary-dark disabled:bg-primary-dark disabled:outline-transparent disabled:cursor-auto&quot;\r\n<\/pre><\/div>\r\n\r\n\r\n<p>Using<strong> Apollo Client<\/strong> was pretty relaxed, since the library catches and processes everything (load status, errors, etc.), so we could continue working directly with the responses of the queries. In addition, you can define many settings, e.g. how caching is done, in a way that suits the project best. Another big plus is that even beginners can integrate Apollo Client into projects very quickly and work with it directly.<\/p>\r\n<p>With <strong>GraphQL<\/strong> it was very interesting to use something other than SQL queries. Especially because GraphQL queries can be a lot of typing, but you can see exactly what you get back from the query as result. In this project, we unfortunately couldn&#8217;t present all features of GraphQL, e.g. server-side data transformations like unit conversion, but it was still exciting to deal with it.<\/p>\r\n<p>So, now we have a runnable web app, with minimal but working features. To use the application internally, all that&#8217;s really missing is a deployment. We decided to deploy VedaVersum to GitLab pages for now. Our DevOps engineers will show you how to do that in the next article of this series ?<\/p>\r\n<p>Thanks for reading and happy coding!<\/p>\r\n","protected":false},"author":70,"featured_media":0,"template":"","tags":[177,962,885,655,653,638,656,654],"class_list":["post-15394","blog","type-blog","status-publish","hentry","tag-net","tag-apollo-2","tag-graphql","tag-react-en-2","tag-react-en","tag-ux-engineering-en-2","tag-web-engineering-en-2","tag-web-engineering-en"],"acf":[],"_links":{"self":[{"href":"https:\/\/www.centigrade.de\/en\/wp-json\/wp\/v2\/blog\/15394","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.centigrade.de\/en\/wp-json\/wp\/v2\/blog"}],"about":[{"href":"https:\/\/www.centigrade.de\/en\/wp-json\/wp\/v2\/types\/blog"}],"author":[{"embeddable":true,"href":"https:\/\/www.centigrade.de\/en\/wp-json\/wp\/v2\/users\/70"}],"version-history":[{"count":6,"href":"https:\/\/www.centigrade.de\/en\/wp-json\/wp\/v2\/blog\/15394\/revisions"}],"predecessor-version":[{"id":15404,"href":"https:\/\/www.centigrade.de\/en\/wp-json\/wp\/v2\/blog\/15394\/revisions\/15404"}],"wp:attachment":[{"href":"https:\/\/www.centigrade.de\/en\/wp-json\/wp\/v2\/media?parent=15394"}],"wp:term":[{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.centigrade.de\/en\/wp-json\/wp\/v2\/tags?post=15394"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}