{"id":4476,"date":"2017-04-27T18:33:35","date_gmt":"2017-04-27T18:33:35","guid":{"rendered":"https:\/\/cheesecakelabs.com\/blog\/?p=4476"},"modified":"2024-03-14T13:05:50","modified_gmt":"2024-03-14T13:05:50","slug":"simple-chat-architecture-mvp","status":"publish","type":"post","link":"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/","title":{"rendered":"A simple chat architecture for your MVP"},"content":{"rendered":"\n<p>When we think about the process of developing an <a href=\"https:\/\/cheesecakelabs.com\/blog\/mvp-meaning\/\" target=\"_blank\" rel=\"noreferrer noopener\">MVP<\/a>, what we have in mind is to create great value in a short time, avoiding complexities and solving problems in the simplest way possible.<\/p>\n\n\n\n<p>Then, on a beautiful sunny summer day, the Project Manager comes up and says:<\/p>\n\n\n\n<p class=\"has-text-align-center\"><em>&#8220;We need to create an MVP for a chat system in just one month!&#8221;<\/em><\/p>\n\n\n\n<p><span style=\"font-weight: 400;\">It\u2019s chaos! It seems to be something very complex for only a month of work. Some questions begin to emerge: <\/span><\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li><span style=\"font-weight: 400;\">What are the requirements?<\/span><\/li>\n\n\n\n<li><span style=\"font-weight: 400;\">How to estimate the effort?<\/span><\/li>\n\n\n\n<li><span style=\"font-weight: 400;\">How to build a simple chat app that aggregates value?<\/span><\/li>\n<\/ul>\n\n\n\n<p><span style=\"font-weight: 400;\">After brainstorming a bit, developers start to think about various open-source alternatives, like <\/span><a href=\"https:\/\/github.com\/jsxc\/jsxc\"><i><span style=\"font-weight: 400;\">jsxc<\/span><\/i><\/a><span style=\"font-weight: 400;\"> and <\/span><a href=\"https:\/\/github.com\/Jajcus\/pyxmpp\"><i><span style=\"font-weight: 400;\">pyxmpp<\/span><\/i><\/a><span style=\"font-weight: 400;\">, that could fit the business model and the project&#8217;s needs.<\/span><\/p>\n\n\n\n<p><span style=\"font-weight: 400;\">In this case, the alternatives found didn\u2019t meet the application requirements perfectly, because the team would have to spend a lot of time learning a new library whose features would mostly not be needed for our MVP.<\/span><\/p>\n\n\n\n<p><span style=\"font-weight: 400;\">After extensive research and no solution, a voice from heaven says:<\/span><\/p>\n\n\n\n<p class=\"has-text-align-center\"><i><span style=\"font-weight: 400;\">\u201cWhy not create your own architecture?\u201d<\/span><\/i><\/p>\n\n\n\n<p><span style=\"font-weight: 400;\">It\u2019s just an MVP! We need to test the project before we think about scalability, right? It was then that we decided to implement this architecture with WebSockets. Here&#8217;s the breakdown of what we came up with.<\/span><\/p>\n\n\n\n<h2 class=\"wp-block-heading\">The Project<\/h2>\n\n\n\n<p><span style=\"font-weight: 400;\">Our starting point was a basic architecture, composed by a Back-end with Python and Django, using PostgreSQL database and ReactJS and Redux on the Front-end.&nbsp;<\/span><span style=\"font-weight: 400;\">With baby steps in mind, we thought about creating a chat system without real-time operations, in other words, just a CRUD of messages.&nbsp;<\/span><span style=\"font-weight: 400;\">After the database modeling, we ended up with only two tables: <\/span><b>Chat<\/b><span style=\"font-weight: 400;\"> and <\/span><b>Message<\/b><span style=\"font-weight: 400;\">. Simple!<\/span><\/p>\n\n\n<div class=\"wp-block-image wp-image-4477\">\n<figure class=\"aligncenter\"><img decoding=\"async\" width=\"1090\" height=\"458\" src=\"https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2017\/04\/Screen-Shot-2017-04-26-at-18.33.01.png\" alt=\"Database Models for Chat and Messages\" class=\"wp-image-4477\" srcset=\"https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2017\/04\/Screen-Shot-2017-04-26-at-18.33.01.png 1090w, https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2017\/04\/Screen-Shot-2017-04-26-at-18.33.01-768x323.png 768w\" sizes=\"(max-width: 1090px) 100vw, 1090px\" \/><figcaption class=\"wp-element-caption\"><center><em>Database Models<\/em><\/center><\/figcaption><\/figure>\n<\/div>\n\n\n<p><span style=\"font-weight: 400;\">With the database ready, we created all the endpoints needed to communicate with the Front-end. Our API became very simple, just two endpoints: <\/span><span style=\"font-weight: 400;\"><code>\/chats<\/code><\/span><span style=\"font-weight: 400;\"> and <\/span><span style=\"font-weight: 400;\"><code>\/chats\/:idChat\/messages<\/code>, <\/span><span style=\"font-weight: 400;\">having the following HTTP actions:<\/span><\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li><b>POST: \/api\/v1\/chats\/<\/b><span style=\"font-weight: 400;\"> \u2014 Creates a new chat between two users.<\/span><\/li>\n\n\n\n<li><b>GET: \/api\/v1\/chats\/<\/b><span style=\"font-weight: 400;\"> \u2014 Lists all chats the logged-in user belongs to.<\/span><\/li>\n\n\n\n<li><b>POST: \/api\/v1\/chats\/:idChat\/messages\/&nbsp;<\/b><span style=\"font-weight: 400;\">\u2014 Adds a new message to a specific chat.<\/span><\/li>\n\n\n\n<li><b>GET: \/api\/v1\/chats\/:idChat\/messages\/<\/b><span style=\"font-weight: 400;\"> \u2014 Lists all interactions between users on a specific chat.<\/span><\/li>\n<\/ul>\n\n\n\n<p><span style=\"font-weight: 400;\">In the Front-end we created, with the Redux, two stores: one for the chats and another for the messages, reflecting exactly what was being received from the API. For the communication between the Reducers, four actions were necessary:<\/span><\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li><b>CREATE_CHAT<\/b><span style=\"font-weight: 400;\">: sends a POST call to <\/span><i><span style=\"font-weight: 400;\">\/chats\/<\/span><\/i><span style=\"font-weight: 400;\"> and merges the new chat in the store.<\/span><\/li>\n\n\n\n<li><b>GET_ALL_CHATS: <\/b><span style=\"font-weight: 400;\">sends a GET call to <\/span><i><span style=\"font-weight: 400;\">\/chats\/<\/span><\/i><span style=\"font-weight: 400;\"> and adds the returned chats in the store.<\/span><\/li>\n\n\n\n<li><b>SEND_MESSAGE: <\/b><span style=\"font-weight: 400;\">sends a POST call to <\/span><i><span style=\"font-weight: 400;\">\/chats\/:idChat\/messages\/<\/span><\/i><span style=\"font-weight: 400;\"> and adds the new message to the store.<\/span><\/li>\n\n\n\n<li><b>GET_ALL_MESSAGES<\/b><span style=\"font-weight: 400;\">: sends a GET call to <\/span><i><span style=\"font-weight: 400;\">\/chats\/:idChat\/messages\/<\/span><\/i><span style=\"font-weight: 400;\"> and adds the returned messages in the store.<\/span><\/li>\n<\/ul>\n\n\n<div class=\"wp-block-image wp-image-4478\">\n<figure class=\"aligncenter\"><img decoding=\"async\" width=\"418\" height=\"842\" src=\"https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2017\/04\/Screen-Shot-2017-04-26-at-20.27.54.png\" alt=\"Diagram showing the communication between database, webserver and the user.\" class=\"wp-image-4478\"\/><figcaption class=\"wp-element-caption\"><center><em>Simple Chat Architecture<\/em><\/center><\/figcaption><\/figure>\n<\/div>\n\n\n<p><span style=\"font-weight: 400;\">The image above represents the implementation after the first phase of the project. With this, we could already carry out conversations between two users. However, we needed to refresh the page to receive new messages. <\/span><\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Thinking about real-time<\/h2>\n\n\n\n<p><span style=\"font-weight: 400;\">To evolve the application into a real-time architecture, we needed to add two key pieces: a data structure featuring publish\/subscription and a WebSocket server.<\/span><\/p>\n\n\n\n<p><span style=\"font-weight: 400;\">For Pub\/Sub, we chose Redis \u2013 an open source (BSD licensed), in-memory data structure store, used as a database, cache and message broker \u2013 \u00a0as our team was very familiar with it. This tool has the utmost importance for the operation of our new architecture, allowing messages to almost instantaneously published without harming our web service performance.<\/span><\/p>\n\n\n\n<p><span style=\"font-weight: 400;\">To listen to the Redis publications and create a WebSocket server, we decided to create a microservice using NodeJS. When initialized, it creates a WebSocket using the <a href=\"https:\/\/github.com\/socketio\/socket.io\">socket.io<\/a> library, subscribing as a Redis listener.<\/span><\/p>\n\n\n\n<p><span style=\"font-weight: 400;\">The microservice works like a messaging router. After receiving messages from Redis, it checks if the recipient is connected via WebSockets and forwards the content. Messages sent to unconnected recipients are discarded, but, when users log in to chat, they will receive messages through HTTP requests.<\/span><\/p>\n\n\n\n<p><span style=\"font-weight: 400;\">After adding these two pieces, our architecture looks like this:<\/span><\/p>\n\n\n<div class=\"wp-block-image wp-image-4479\">\n<figure class=\"aligncenter\"><img decoding=\"async\" width=\"812\" height=\"836\" src=\"https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2017\/04\/Screen-Shot-2017-04-26-at-18.40.42.png\" alt=\"Diagram showing the communication between the database, Redis, WebSocket, webserver and the user.\" class=\"wp-image-4479\" srcset=\"https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2017\/04\/Screen-Shot-2017-04-26-at-18.40.42.png 812w, https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2017\/04\/Screen-Shot-2017-04-26-at-18.40.42-768x791.png 768w\" sizes=\"(max-width: 812px) 100vw, 812px\" \/><figcaption class=\"wp-element-caption\"><center><em>Real-Time Chat Architecture<\/em><\/center><\/figcaption><\/figure>\n<\/div>\n\n\n<p><span style=\"font-weight: 400;\">Now it\u2019s time to fix the page <\/span><i><span style=\"font-weight: 400;\">refresh <\/span><\/i><span style=\"font-weight: 400;\">issue, making our conversation more fluid. For this, we needed a bidirectional communication between the server and the client. <\/span><span style=\"font-weight: 400;\">According to our architecture, now we just need to add the <a href=\"https:\/\/socket.io\/\">socket.io<\/a> library on the Front-end side and connect it to <strong>microservice<\/strong>. With this, we were able to have a permanent connection between the client and the server, allowing them to receive and send messages at any moment.<\/span><\/p>\n\n\n\n<p><span style=\"font-weight: 400;\">In the Back-end side, we added two things: the connection with Redis and the publication of the message after it has been saved in the database.&nbsp;<\/span><span style=\"font-weight: 400;\">For the Front-end structure, we just created a new action called&nbsp;<\/span><i><span style=\"font-weight: 400;\"><code>ADD_MESSAGE_FROM_SOCKET<\/code><\/span><\/i><span style=\"font-weight: 400;\"> and the &nbsp;<\/span><i><span style=\"font-weight: 400;\"><code>&lt;WebSocket \/&gt;<\/code><\/span><\/i><span style=\"font-weight: 400;\"> component. <\/span><\/p>\n\n\n\n<p><span style=\"font-weight: 400;\">The action has the simple responsibility of adding the messages received in the correct store. The component took the role of creating\/removing the connection to the WebSocket and listening to the port. When it receives a new message via the WebSocket, it just calls the action <\/span><i><span style=\"font-weight: 400;\"><code>ADD_MESSAGE_FROM_SOCKET<\/code><\/span><\/i><span style=\"font-weight: 400;\">.<\/span><\/p>\n\n\n\n<p><span style=\"font-weight: 400;\">Some important decisions were made:<\/span><\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li><span style=\"font-weight: 400;\">The connection from the WebSocket to the Client should not be responsibility of the web server.<\/span><\/li>\n\n\n\n<li><span style=\"font-weight: 400;\">The messages should be saved in PostgreSQL and published in Redis.<\/span><\/li>\n\n\n\n<li><span style=\"font-weight: 400;\">The client could only receive new messages via WebSockets, the insertion of new messages would still occur&nbsp;via HTTP.<\/span><\/li>\n<\/ul>\n\n\n\n<p><span style=\"font-weight: 400;\">Using this simple approach, we were able to transform our CRUD-only chat in real-time fluent conversations.<\/span><\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Wrapping up<\/h2>\n\n\n\n<p><span style=\"font-weight: 400;\">Through this solution, we created a simple and maintainable chat application for our MVP. Also, we managed to prove that, for an MVP, this solution is extremely feasible. However, we have to keep in mind that as the project grows, some concerns should be raised, such as scalability and maintainability.<\/span><\/p>\n","protected":false},"excerpt":{"rendered":"<p>When we think about the process of developing an MVP, what we have in mind is to create great value in a short time, avoiding complexities and solving problems in the simplest way possible. Then, on a beautiful sunny summer day, the Project Manager comes up and says: &#8220;We need to create an MVP for [&hellip;]<\/p>\n","protected":false},"author":65,"featured_media":4482,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[432],"tags":[350,303,400,302],"class_list":["post-4476","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-engineering","tag-tag-django","tag-tag-frontend","tag-tag-javascript","tag-tag-reactjs"],"yoast_head":"<!-- This site is optimized with the Yoast SEO plugin v27.1.1 - https:\/\/yoast.com\/product\/yoast-seo-wordpress\/ -->\n<title>A simple chat architecture for your MVP<\/title>\n<meta name=\"description\" content=\"Using WebSockets, we created from scratch a simple and maintainable architecture for a chat application that perfectly fit an MVP project.\" \/>\n<meta name=\"robots\" content=\"index, follow, max-snippet:-1, max-image-preview:large, max-video-preview:-1\" \/>\n<link rel=\"canonical\" href=\"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/\" \/>\n<meta property=\"og:locale\" content=\"en_US\" \/>\n<meta property=\"og:type\" content=\"article\" \/>\n<meta property=\"og:title\" content=\"A simple chat architecture for your MVP\" \/>\n<meta property=\"og:description\" content=\"Using WebSockets, we created from scratch a simple and maintainable architecture for a chat application that perfectly fit an MVP project.\" \/>\n<meta property=\"og:url\" content=\"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/\" \/>\n<meta property=\"og:site_name\" content=\"Cheesecake Labs\" \/>\n<meta property=\"article:publisher\" content=\"https:\/\/www.facebook.com\/cheesecakelabs\" \/>\n<meta property=\"article:published_time\" content=\"2017-04-27T18:33:35+00:00\" \/>\n<meta property=\"article:modified_time\" content=\"2024-03-14T13:05:50+00:00\" \/>\n<meta property=\"og:image\" content=\"https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2017\/04\/Banner_chatapp.png\" \/>\n\t<meta property=\"og:image:width\" content=\"2000\" \/>\n\t<meta property=\"og:image:height\" content=\"720\" \/>\n\t<meta property=\"og:image:type\" content=\"image\/png\" \/>\n<meta name=\"author\" content=\"Cheesecake Labs\" \/>\n<meta name=\"twitter:card\" content=\"summary_large_image\" \/>\n<meta name=\"twitter:creator\" content=\"@cheesecakelabs\" \/>\n<meta name=\"twitter:site\" content=\"@cheesecakelabs\" \/>\n<meta name=\"twitter:label1\" content=\"Written by\" \/>\n\t<meta name=\"twitter:data1\" content=\"\" \/>\n\t<meta name=\"twitter:label2\" content=\"Est. reading time\" \/>\n\t<meta name=\"twitter:data2\" content=\"5 minutes\" \/>\n<script type=\"application\/ld+json\" class=\"yoast-schema-graph\">{\"@context\":\"https:\/\/schema.org\",\"@graph\":[{\"@type\":\"Article\",\"@id\":\"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/#article\",\"isPartOf\":{\"@id\":\"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/\"},\"author\":{\"name\":\"Daniel Leite\"},\"headline\":\"A simple chat architecture for your MVP\",\"datePublished\":\"2017-04-27T18:33:35+00:00\",\"dateModified\":\"2024-03-14T13:05:50+00:00\",\"mainEntityOfPage\":{\"@id\":\"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/\"},\"wordCount\":992,\"commentCount\":0,\"image\":{\"@id\":\"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/#primaryimage\"},\"thumbnailUrl\":\"https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2017\/04\/Banner_chatapp.png\",\"keywords\":[\"Django\",\"Front-end\",\"JavaScript\",\"ReactJS\"],\"articleSection\":[\"Engineering\"],\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"CommentAction\",\"name\":\"Comment\",\"target\":[\"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/#respond\"]}]},{\"@type\":\"WebPage\",\"@id\":\"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/\",\"url\":\"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/\",\"name\":\"A simple chat architecture for your MVP\",\"isPartOf\":{\"@id\":\"https:\/\/cheesecakelabs.com\/blog\/#website\"},\"primaryImageOfPage\":{\"@id\":\"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/#primaryimage\"},\"image\":{\"@id\":\"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/#primaryimage\"},\"thumbnailUrl\":\"https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2017\/04\/Banner_chatapp.png\",\"datePublished\":\"2017-04-27T18:33:35+00:00\",\"dateModified\":\"2024-03-14T13:05:50+00:00\",\"author\":{\"@type\":\"person\",\"name\":\"Daniel Leite\"},\"description\":\"Using WebSockets, we created from scratch a simple and maintainable architecture for a chat application that perfectly fit an MVP project.\",\"breadcrumb\":{\"@id\":\"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/#breadcrumb\"},\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"ReadAction\",\"target\":[\"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/\"]}]},{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/#primaryimage\",\"url\":\"https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2017\/04\/Banner_chatapp.png\",\"contentUrl\":\"https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2017\/04\/Banner_chatapp.png\",\"width\":2000,\"height\":720,\"caption\":\"Two smartphones communicating through a cloud.\"},{\"@type\":\"BreadcrumbList\",\"@id\":\"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/#breadcrumb\",\"itemListElement\":[{\"@type\":\"ListItem\",\"position\":1,\"name\":\"Home\",\"item\":\"https:\/\/cheesecakelabs.com\/blog\/\"},{\"@type\":\"ListItem\",\"position\":2,\"name\":\"A simple chat architecture for your MVP\"}]},{\"@type\":\"WebSite\",\"@id\":\"https:\/\/cheesecakelabs.com\/blog\/#website\",\"url\":\"https:\/\/cheesecakelabs.com\/blog\/\",\"name\":\"Cheesecake Labs\",\"description\":\"Nearshore outsourcing company for Web and Mobile design and engineering services, and staff augmentation for startups and enterprises..\",\"potentialAction\":[{\"@type\":\"SearchAction\",\"target\":{\"@type\":\"EntryPoint\",\"urlTemplate\":\"https:\/\/cheesecakelabs.com\/blog\/?s={search_term_string}\"},\"query-input\":{\"@type\":\"PropertyValueSpecification\",\"valueRequired\":true,\"valueName\":\"search_term_string\"}}],\"inLanguage\":\"en-US\"},{\"@type\":\"Person\",\"name\":\"Daniel Leite\",\"image\":{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\/\/cheesecakelabs.com\/blog\/#\/schema\/person\/image\/\",\"url\":\"https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2016\/11\/daniel-300x300.jpg\",\"contentUrl\":\"https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2016\/11\/daniel-300x300.jpg\",\"caption\":\"Daniel Leite\"},\"description\":\"10 years of experience in Marketing and Sales in the Technology sector. My main purpose is help, support and structure efficient operations and also develop independent and multidisciplinary teams.\",\"url\":\"https:\/\/cheesecakelabs.com\/blog\/autor\/dleitee\/\"}]}<\/script>\n<!-- \/ Yoast SEO plugin. -->","yoast_head_json":{"title":"A simple chat architecture for your MVP","description":"Using WebSockets, we created from scratch a simple and maintainable architecture for a chat application that perfectly fit an MVP project.","robots":{"index":"index","follow":"follow","max-snippet":"max-snippet:-1","max-image-preview":"max-image-preview:large","max-video-preview":"max-video-preview:-1"},"canonical":"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/","og_locale":"en_US","og_type":"article","og_title":"A simple chat architecture for your MVP","og_description":"Using WebSockets, we created from scratch a simple and maintainable architecture for a chat application that perfectly fit an MVP project.","og_url":"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/","og_site_name":"Cheesecake Labs","article_publisher":"https:\/\/www.facebook.com\/cheesecakelabs","article_published_time":"2017-04-27T18:33:35+00:00","article_modified_time":"2024-03-14T13:05:50+00:00","og_image":[{"width":2000,"height":720,"url":"https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2017\/04\/Banner_chatapp.png","type":"image\/png"}],"author":"Cheesecake Labs","twitter_card":"summary_large_image","twitter_creator":"@cheesecakelabs","twitter_site":"@cheesecakelabs","twitter_misc":{"Written by":null,"Est. reading time":"5 minutes"},"schema":{"@context":"https:\/\/schema.org","@graph":[{"@type":"Article","@id":"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/#article","isPartOf":{"@id":"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/"},"author":{"name":"Daniel Leite"},"headline":"A simple chat architecture for your MVP","datePublished":"2017-04-27T18:33:35+00:00","dateModified":"2024-03-14T13:05:50+00:00","mainEntityOfPage":{"@id":"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/"},"wordCount":992,"commentCount":0,"image":{"@id":"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/#primaryimage"},"thumbnailUrl":"https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2017\/04\/Banner_chatapp.png","keywords":["Django","Front-end","JavaScript","ReactJS"],"articleSection":["Engineering"],"inLanguage":"en-US","potentialAction":[{"@type":"CommentAction","name":"Comment","target":["https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/#respond"]}]},{"@type":"WebPage","@id":"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/","url":"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/","name":"A simple chat architecture for your MVP","isPartOf":{"@id":"https:\/\/cheesecakelabs.com\/blog\/#website"},"primaryImageOfPage":{"@id":"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/#primaryimage"},"image":{"@id":"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/#primaryimage"},"thumbnailUrl":"https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2017\/04\/Banner_chatapp.png","datePublished":"2017-04-27T18:33:35+00:00","dateModified":"2024-03-14T13:05:50+00:00","author":{"@type":"person","name":"Daniel Leite"},"description":"Using WebSockets, we created from scratch a simple and maintainable architecture for a chat application that perfectly fit an MVP project.","breadcrumb":{"@id":"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/#breadcrumb"},"inLanguage":"en-US","potentialAction":[{"@type":"ReadAction","target":["https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/"]}]},{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/#primaryimage","url":"https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2017\/04\/Banner_chatapp.png","contentUrl":"https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2017\/04\/Banner_chatapp.png","width":2000,"height":720,"caption":"Two smartphones communicating through a cloud."},{"@type":"BreadcrumbList","@id":"https:\/\/cheesecakelabs.com\/blog\/simple-chat-architecture-mvp\/#breadcrumb","itemListElement":[{"@type":"ListItem","position":1,"name":"Home","item":"https:\/\/cheesecakelabs.com\/blog\/"},{"@type":"ListItem","position":2,"name":"A simple chat architecture for your MVP"}]},{"@type":"WebSite","@id":"https:\/\/cheesecakelabs.com\/blog\/#website","url":"https:\/\/cheesecakelabs.com\/blog\/","name":"Cheesecake Labs","description":"Nearshore outsourcing company for Web and Mobile design and engineering services, and staff augmentation for startups and enterprises..","potentialAction":[{"@type":"SearchAction","target":{"@type":"EntryPoint","urlTemplate":"https:\/\/cheesecakelabs.com\/blog\/?s={search_term_string}"},"query-input":{"@type":"PropertyValueSpecification","valueRequired":true,"valueName":"search_term_string"}}],"inLanguage":"en-US"},{"@type":"Person","name":"Daniel Leite","image":{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/cheesecakelabs.com\/blog\/#\/schema\/person\/image\/","url":"https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2016\/11\/daniel-300x300.jpg","contentUrl":"https:\/\/ckl-website-static.s3.amazonaws.com\/wp-content\/uploads\/2016\/11\/daniel-300x300.jpg","caption":"Daniel Leite"},"description":"10 years of experience in Marketing and Sales in the Technology sector. My main purpose is help, support and structure efficient operations and also develop independent and multidisciplinary teams.","url":"https:\/\/cheesecakelabs.com\/blog\/autor\/dleitee\/"}]}},"_links":{"self":[{"href":"https:\/\/cheesecakelabs.com\/blog\/wp-json\/wp\/v2\/posts\/4476","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/cheesecakelabs.com\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/cheesecakelabs.com\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/cheesecakelabs.com\/blog\/wp-json\/wp\/v2\/users\/65"}],"replies":[{"embeddable":true,"href":"https:\/\/cheesecakelabs.com\/blog\/wp-json\/wp\/v2\/comments?post=4476"}],"version-history":[{"count":3,"href":"https:\/\/cheesecakelabs.com\/blog\/wp-json\/wp\/v2\/posts\/4476\/revisions"}],"predecessor-version":[{"id":11868,"href":"https:\/\/cheesecakelabs.com\/blog\/wp-json\/wp\/v2\/posts\/4476\/revisions\/11868"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/cheesecakelabs.com\/blog\/wp-json\/wp\/v2\/media\/4482"}],"wp:attachment":[{"href":"https:\/\/cheesecakelabs.com\/blog\/wp-json\/wp\/v2\/media?parent=4476"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/cheesecakelabs.com\/blog\/wp-json\/wp\/v2\/categories?post=4476"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/cheesecakelabs.com\/blog\/wp-json\/wp\/v2\/tags?post=4476"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}