<turbo-stream action="append" target="posts_list"><template>    <div class="postbit" id="287731" data-post-id="287731">
  <section>
    <div class="post-wrap">


					<div class="post-header">
		        <div class="user-avatar">
		          <img alt="code-shoily" src="https://forum.elixirforum.com/user_avatar/forum.elixirforum.com/code-shoily/120/8052_2.png" width="120" height="120" />
		        </div>
					
						<div class="user-details">
		          <div class="user-name">
		            <h3>
                  code-shoily
                  </h3>
		          </div>
						
						</div>
					
					</div>

	        <div class="thread-main">
	            <div class="post-body" data-turbo="false">
								<p>Looking into <code>live_path</code> will reveal the mystery. It being a macro doesn’t seem to be a straight forward code to investigate into.</p>
<p><a class="mention" href="/u/m4hi2" rel="nofollow">@m4hi2</a> could you downgrade the LiveView version to 0.17/0.16 and see if it persists?</p> 
	            </div>

	            <div class="base-line">
	                <div class="thread-counters">
	                    <span class="thread-count count-likes js-likers-trigger" title="Likes" data-post-id="287731" data-batch-url="/posts/batch_likers">
                        1
                      </span>
                      <!-- <span class="thread-count js-solved-indicator" title="Marked as solution"></span> -->
	                </div>
	                <div class="go-to-post">
	                  <a title="Go to post" alt="Go to post" href="https://forum.elixirforum.com/t/programming-phoenix-liveview-book-club/55604/22">Post #21</a>
	                </div>
	            </div>
              <div id="likers-container-287731" 
                   class="likers-container"
                   data-first-post="false"
                   data-batch-url="/posts/batch_likers">
                   <div class="likers-placeholder" 
                     data-likers-post-id="287731"
                     data-batch-url="/posts/batch_likers">
                  <div class="post-likers"></div>
                </div>
              </div>
	        </div>
			

    </div>

    <div class="triangle-top-right type-standard-post cat-standard-post" title="Post #21"></div>
  </section>
</div>
    <div class="postbit" id="288003" data-post-id="288003">
  <section>
    <div class="post-wrap">


					<div class="post-header">
		        <div class="user-avatar">
		          <img alt="Tbobbe" src="https://forum.elixirforum.com/user_avatar/forum.elixirforum.com/Tbobbe/120/29146_2.png" width="120" height="120" />
		        </div>
					
						<div class="user-details">
		          <div class="user-name">
		            <h3>
                  Tbobbe
                  </h3>
		          </div>
						
						</div>
					
					</div>

	        <div class="thread-main">
	            <div class="post-body" data-turbo="false">
								<p>In case you haven’t solved the issue yet:</p>
<p>If you are using a new version of LiveView, you are getting an error because the functions you are trying to use does not exist anymore, they have been deprecated. If we look at the <a href="https://hexdocs.pm/phoenix_live_view/0.18.0/Phoenix.LiveView.Helpers.html#live_patch/2" rel="noopener nofollow ugc">LiveView docs</a> we can see that <code>live_patch</code> was deprecated in version 0.18.0 (current version is 0.18.18). The functionality you should use instead is described in <a href="https://hexdocs.pm/phoenix_live_view/0.18.18/live-navigation.html" rel="noopener nofollow ugc">Live navigation</a> <img src="https://forum.elixirforum.com/images/emoji/apple/slight_smile.png?v=15" title=":slight_smile:" class="emoji" alt=":slight_smile:" loading="lazy" width="20" height="20"></p> 
	            </div>

	            <div class="base-line">
	                <div class="thread-counters">
	                    <span class="thread-count count-likes js-likers-trigger" title="Likes" data-post-id="288003" data-batch-url="/posts/batch_likers">
                        3
                      </span>
                      <!-- <span class="thread-count js-solved-indicator" title="Marked as solution"></span> -->
	                </div>
	                <div class="go-to-post">
	                  <a title="Go to post" alt="Go to post" href="https://forum.elixirforum.com/t/programming-phoenix-liveview-book-club/55604/23">Post #22</a>
	                </div>
	            </div>
              <div id="likers-container-288003" 
                   class="likers-container"
                   data-first-post="false"
                   data-batch-url="/posts/batch_likers">
                   <div class="likers-placeholder" 
                     data-likers-post-id="288003"
                     data-batch-url="/posts/batch_likers">
                  <div class="post-likers"></div>
                </div>
              </div>
	        </div>
			

    </div>

    <div class="triangle-top-right type-standard-post cat-standard-post" title="Post #22"></div>
  </section>
</div>
    <div class="postbit" id="288026" data-post-id="288026">
  <section>
    <div class="post-wrap">


					<div class="post-header">
		        <div class="user-avatar">
		          <img alt="Tbobbe" src="https://forum.elixirforum.com/user_avatar/forum.elixirforum.com/Tbobbe/120/29146_2.png" width="120" height="120" />
		        </div>
					
						<div class="user-details">
		          <div class="user-name">
		            <h3>
                  Tbobbe
                  </h3>
		          </div>
						
						</div>
					
					</div>

	        <div class="thread-main">
	            <div class="post-body" data-turbo="false">
								<p><strong>Chapter 1</strong></p>
<p>Not too much to say about this chapter. It’s a nice little introduction to LiveView and the philosophy behind it. The chapters give some insight into the building blocks of LiveView such as the <em>Socket</em> struct, Websockets and how diffs are used to minimize data sent over the network. And of course, the LiveView lifecycle and loop.</p>
<p>The chapter is also used to hype up the technology a bit with sentences such as “<em>As a result of these Elixir language features, users would find a pleasant, productive programming experience in Phoenix LiveView.</em>” and “<em>As a result, in LiveView, programmers would find a beautiful programming model based on tested concepts, …</em>”.</p>
<p>All in all, since I’ve used LiveView a bit before, it was not much that I hadn’t heard before.<br>
I have one question though. In the very last part of the <strong>Your Turn</strong> section where you are encouraged to use the <em>patch</em> functionality in order to restart the guessing game, is there some benefit in using <em>patch</em> and <em>handle_params</em> instead of sending an event and using a <em>handle_event</em> function? Or is it just a way of getting the reader aware of the <em>patch</em> functionality in LiveView?</p>
<p>Finally, there is an error here. The reference link to the (deprecated) <code>live_path</code> is broken. This error has already been reported though <img src="https://forum.elixirforum.com/images/emoji/apple/slight_smile.png?v=15" title=":slight_smile:" class="emoji" alt=":slight_smile:" loading="lazy" width="20" height="20"></p>
<p>Time to get started with the next chapter!</p> 
	            </div>

	            <div class="base-line">
	                <div class="thread-counters">
	                    <span class="thread-count count-likes js-likers-trigger" title="Likes" data-post-id="288026" data-batch-url="/posts/batch_likers">
                        5
                      </span>
                      <!-- <span class="thread-count js-solved-indicator" title="Marked as solution"></span> -->
	                </div>
	                <div class="go-to-post">
	                  <a title="Go to post" alt="Go to post" href="https://forum.elixirforum.com/t/programming-phoenix-liveview-book-club/55604/24">Post #23</a>
	                </div>
	            </div>
              <div id="likers-container-288026" 
                   class="likers-container"
                   data-first-post="false"
                   data-batch-url="/posts/batch_likers">
                   <div class="likers-placeholder" 
                     data-likers-post-id="288026"
                     data-batch-url="/posts/batch_likers">
                  <div class="post-likers"></div>
                </div>
              </div>
	        </div>
			

    </div>

    <div class="triangle-top-right type-standard-post cat-standard-post" title="Post #23"></div>
  </section>
</div>
    <div class="postbit" id="288199" data-post-id="288199">
  <section>
    <div class="post-wrap">


					<div class="post-header">
		        <div class="user-avatar">
		          <img alt="Tbobbe" src="https://forum.elixirforum.com/user_avatar/forum.elixirforum.com/Tbobbe/120/29146_2.png" width="120" height="120" />
		        </div>
					
						<div class="user-details">
		          <div class="user-name">
		            <h3>
                  Tbobbe
                  </h3>
		          </div>
						
						</div>
					
					</div>

	        <div class="thread-main">
	            <div class="post-body" data-turbo="false">
								<h2><a name="p-288199-chapter-2-1" class="anchor" href="#p-288199-chapter-2-1" aria-label="Heading link" rel="nofollow"></a>Chapter 2</h2>
<p>Now, this was a chapter that introduced a lot of concepts. Code generators, <code>Plug</code>, the <code>endpoint</code> and <code>router</code>, policies, scopes, routes, authentication etc. This is probably a chapter one should read through 2 times in order for everything to sink in.</p>
<p>The absolute biggest takeaway, for me, in this chapter was the concept of <strong>CRC</strong> (Constructors, Reducers, Converters). Somehow I have managed to avoid this mental model until now, but it just makes so much sense when trying to understand how to think about <em>plugs</em>.<br>
The idea of taking some sort of input (the request), parse it into a datatype (Conn struct), perform some functions on the data in a pipeline manner (plugs), and lastly convert it into an output (response) made it very clear to me what was going on. Something seemingly complex turned simple! <img src="https://forum.elixirforum.com/images/emoji/apple/smiley.png?v=15" title=":smiley:" class="emoji" alt=":smiley:" loading="lazy" width="20" height="20"></p>
<h3><a name="p-288199-exercises-2" class="anchor" href="#p-288199-exercises-2" aria-label="Heading link" rel="nofollow"></a>Exercises</h3>
<p><strong>Mailer:</strong> I don’t have a mailing service, but after looking into it, it seems like you only need to add some <code>Swoosh</code> config and it “just works”. Please correct me if I’m wrong.</p>
<p><strong>Username:</strong> I deleted the user I created going through the chapter so that I could enforce every user to have a username, hehe. Doing the migration, making the changes to <code>User</code> and adding the form input in the registration was not much code. But adding the “change username” functionality seemed to require quite a lot of code and steps, so I didn’t go that far.</p>
<p><strong>Redirect:</strong> A one row change to the <code>PageController</code>.</p>
<p><strong>Session id:</strong> A small change to the <code>on_mount</code> function.</p>
<h3><a name="p-288199-errata-3" class="anchor" href="#p-288199-errata-3" aria-label="Heading link" rel="nofollow"></a>Errata</h3>
<p>On page 56 the authors show you how to add a root layout to your <code>live_session</code>:<br>
<code>root_layout: {PentoWeb.LayoutView, :root}</code><br>
This will result in an error. What they meant was probably:<br>
<code>root_layout: {PentoWeb.Layouts, :root}</code></p>
<p>This error has already been reported <img src="https://forum.elixirforum.com/images/emoji/apple/slight_smile.png?v=15" title=":slight_smile:" class="emoji" alt=":slight_smile:" loading="lazy" width="20" height="20"></p>
<p>Looking forward to <strong>Chapter 3</strong> ^^</p> 
	            </div>

	            <div class="base-line">
	                <div class="thread-counters">
	                    <span class="thread-count count-likes js-likers-trigger" title="Likes" data-post-id="288199" data-batch-url="/posts/batch_likers">
                        6
                      </span>
                      <!-- <span class="thread-count js-solved-indicator" title="Marked as solution"></span> -->
	                </div>
	                <div class="go-to-post">
	                  <a title="Go to post" alt="Go to post" href="https://forum.elixirforum.com/t/programming-phoenix-liveview-book-club/55604/25">Post #24</a>
	                </div>
	            </div>
              <div id="likers-container-288199" 
                   class="likers-container"
                   data-first-post="false"
                   data-batch-url="/posts/batch_likers">
                   <div class="likers-placeholder" 
                     data-likers-post-id="288199"
                     data-batch-url="/posts/batch_likers">
                  <div class="post-likers"></div>
                </div>
              </div>
	        </div>
			

    </div>

    <div class="triangle-top-right type-standard-post cat-standard-post" title="Post #24"></div>
  </section>
</div>
    <div class="postbit" id="288242" data-post-id="288242">
  <section>
    <div class="post-wrap">


					<div class="post-header">
		        <div class="user-avatar">
		          <img alt="BartOtten" src="https://forum.elixirforum.com/user_avatar/forum.elixirforum.com/BartOtten/120/25440_2.png" width="120" height="120" />
		        </div>
					
						<div class="user-details">
		          <div class="user-name">
		            <h3>
                  BartOtten
                  </h3>
		          </div>
						
						</div>
					
					</div>

	        <div class="thread-main">
	            <div class="post-body" data-turbo="false">
								<p><strong>This book is amazing!</strong></p>
<p>I wanted to read it for start to end first and then a second time while posting about the chapters (to not have the same debacle as last book club I participated in). But I just <em>have to</em> post this roaring, premature conclusion.</p>
<p>Concepts are exceptionally well explained (such as the CRC as mentioned in the post above) and then referred to when you ‘see them again’.</p>
<p>Currently at page 218 and those were 218 pages of joy. I mark the “this is significant stuff” sections and already have about 60 marks, only 4 of them are “maybe change this” nitpicks (the other 56 I will post about later)</p>
<p>Page 121: typo: comment → common<br>
Page 121: better use the new :if directive<br>
Page 173: “Elixir will always use Ecto to transact against the database”. Seems a bit bold as if they are married.<br>
Page 198: LiveView now uses ‘stream’ in the generated code. Guess that is being updated before final.</p>
<p>4 out of 60 is a very impressive ratio.</p>
<p>Want a pleasant time? Go read this book <img src="https://forum.elixirforum.com/images/emoji/apple/slight_smile.png?v=15" title=":slight_smile:" class="emoji" alt=":slight_smile:" loading="lazy" width="20" height="20"></p> 
	            </div>

	            <div class="base-line">
	                <div class="thread-counters">
	                    <span class="thread-count count-likes js-likers-trigger" title="Likes" data-post-id="288242" data-batch-url="/posts/batch_likers">
                        6
                      </span>
                      <!-- <span class="thread-count js-solved-indicator" title="Marked as solution"></span> -->
	                </div>
	                <div class="go-to-post">
	                  <a title="Go to post" alt="Go to post" href="https://forum.elixirforum.com/t/programming-phoenix-liveview-book-club/55604/26">Post #25</a>
	                </div>
	            </div>
              <div id="likers-container-288242" 
                   class="likers-container"
                   data-first-post="false"
                   data-batch-url="/posts/batch_likers">
                   <div class="likers-placeholder" 
                     data-likers-post-id="288242"
                     data-batch-url="/posts/batch_likers">
                  <div class="post-likers"></div>
                </div>
              </div>
	        </div>
			

    </div>

    <div class="triangle-top-right type-standard-post cat-standard-post" title="Post #25"></div>
  </section>
</div>
    <div class="postbit" id="288266" data-post-id="288266">
  <section>
    <div class="post-wrap">


					<div class="post-header">
		        <div class="user-avatar">
		          <img alt="Tbobbe" src="https://forum.elixirforum.com/user_avatar/forum.elixirforum.com/Tbobbe/120/29146_2.png" width="120" height="120" />
		        </div>
					
						<div class="user-details">
		          <div class="user-name">
		            <h3>
                  Tbobbe
                  </h3>
		          </div>
						
						</div>
					
					</div>

	        <div class="thread-main">
	            <div class="post-body" data-turbo="false">
								<h2><a name="p-288266-chapter-3-1" class="anchor" href="#p-288266-chapter-3-1" aria-label="Heading link" rel="nofollow"></a>Chapter 3</h2>
<p>Fantastic chapter! It is basically a chapter about structuring Elixir software, and some very valuable concepts are introduced.</p>
<p>The most important takeaway for me from this chapter was the concept of the <strong>Context</strong> and the <strong>Core</strong> of a <em>resource</em>.</p>
<h3><a name="p-288266-the-context-2" class="anchor" href="#p-288266-the-context-2" aria-label="Heading link" rel="nofollow"></a>The Context</h3>
<p>The context is the API to the resource, every interaction with the resource goes through the context module (in this case the <strong>Products</strong> module). Every <em>unpure</em> function goes here (functions that can perform I/O, might fail, etc.). The <code>with</code> function can often be put to good use in the context.</p>
<h3><a name="p-288266-the-core-3" class="anchor" href="#p-288266-the-core-3" aria-label="Heading link" rel="nofollow"></a>The Core</h3>
<p>All <em>pure</em> functions go here. The schema, query builders, etc. Core functions are often suitable for piping.</p>
<p><strong>Best quotes of the chapter:</strong></p>
<ul>
<li><em>“The Context API is with-land”</em></li>
<li><em>“The Core is pipe-land”</em></li>
</ul>
<p>Now, in the code used so far, the context and the core is very easy to separate since it’s just the <code>Products</code> module and the <code>Product</code> module. I hope the book will keep referring to these concepts as the application grows.</p>
<p>Next up is the frontend in <strong>Chapter 4</strong> <img src="https://forum.elixirforum.com/images/emoji/apple/smiley.png?v=15" title=":smiley:" class="emoji" alt=":smiley:" loading="lazy" width="20" height="20"></p> 
	            </div>

	            <div class="base-line">
	                <div class="thread-counters">
	                    <span class="thread-count count-likes js-likers-trigger" title="Likes" data-post-id="288266" data-batch-url="/posts/batch_likers">
                        7
                      </span>
                      <!-- <span class="thread-count js-solved-indicator" title="Marked as solution"></span> -->
	                </div>
	                <div class="go-to-post">
	                  <a title="Go to post" alt="Go to post" href="https://forum.elixirforum.com/t/programming-phoenix-liveview-book-club/55604/27">Post #26</a>
	                </div>
	            </div>
              <div id="likers-container-288266" 
                   class="likers-container"
                   data-first-post="false"
                   data-batch-url="/posts/batch_likers">
                   <div class="likers-placeholder" 
                     data-likers-post-id="288266"
                     data-batch-url="/posts/batch_likers">
                  <div class="post-likers"></div>
                </div>
              </div>
	        </div>
			

    </div>

    <div class="triangle-top-right type-most-liked cat-most-liked" title="One of the top 3 liked posts in this thread!"></div>
  </section>
</div>
    <div class="postbit" id="288274" data-post-id="288274">
  <section>
    <div class="post-wrap">


					<div class="post-header">
		        <div class="user-avatar">
		          <img alt="BartOtten" src="https://forum.elixirforum.com/user_avatar/forum.elixirforum.com/BartOtten/120/25440_2.png" width="120" height="120" />
		        </div>
					
						<div class="user-details">
		          <div class="user-name">
		            <h3>
                  BartOtten
                  </h3>
		          </div>
						
						</div>
					
					</div>

	        <div class="thread-main">
	            <div class="post-body" data-turbo="false">
								<aside class="quote no-group" data-username="Tbobbe" data-post="27" data-topic="55604">
<div class="title">
<div class="quote-controls"></div>
<img alt="" width="24" height="24" src="https://forum.elixirforum.com/user_avatar/forum.elixirforum.com/tbobbe/48/29146_2.png" class="avatar"> Tbobbe:</div>
<blockquote>
<p><strong>Best quotes of the chapter:</strong></p>
<ul>
<li><em>“The Context API is with-land”</em></li>
<li><em>“The Core is pipe-land”</em></li>
</ul>
</blockquote>
</aside>
<p>Indeed. This chapter is gold, even for non-Phoenix projects. The pipe- &amp; with-land is very easy to remember and the explanation for the Context module is the best I read so far.</p> 
	            </div>

	            <div class="base-line">
	                <div class="thread-counters">
	                    <span class="thread-count count-likes js-likers-trigger" title="Likes" data-post-id="288274" data-batch-url="/posts/batch_likers">
                        4
                      </span>
                      <!-- <span class="thread-count js-solved-indicator" title="Marked as solution"></span> -->
	                </div>
	                <div class="go-to-post">
	                  <a title="Go to post" alt="Go to post" href="https://forum.elixirforum.com/t/programming-phoenix-liveview-book-club/55604/28">Post #27</a>
	                </div>
	            </div>
              <div id="likers-container-288274" 
                   class="likers-container"
                   data-first-post="false"
                   data-batch-url="/posts/batch_likers">
                   <div class="likers-placeholder" 
                     data-likers-post-id="288274"
                     data-batch-url="/posts/batch_likers">
                  <div class="post-likers"></div>
                </div>
              </div>
	        </div>
			

    </div>

    <div class="triangle-top-right type-standard-post cat-standard-post" title="Post #27"></div>
  </section>
</div>
    <div class="postbit" id="288299" data-post-id="288299">
  <section>
    <div class="post-wrap">


					<div class="post-header">
		        <div class="user-avatar">
		          <img alt="olivegarden" src="/assets/icons/user-9f439610.png" width="120" height="120" />
		        </div>
					
						<div class="user-details">
		          <div class="user-name">
		            <h3>
                  olivegarden
                  </h3>
		          </div>
						
						</div>
					
					</div>

	        <div class="thread-main">
	            <div class="post-body" data-turbo="false">
								<p>Hello all,</p>
<p>I’m new to Elixir and Phoenix.  I’m also early in my career as a developer.  I got the book a few weeks ago and this book club inspired me to really start cracking into it!</p>
<p>Here’s what I’ve got for Chapter 1 (B0.9.0)</p>
<p><img src="https://forum.elixirforum.com/images/emoji/apple/drum.png?v=15" title=":drum:" class="emoji" alt=":drum:" loading="lazy" width="20" height="20"> <img src="https://forum.elixirforum.com/images/emoji/apple/drum.png?v=15" title=":drum:" class="emoji" alt=":drum:" loading="lazy" width="20" height="20"> <img src="https://forum.elixirforum.com/images/emoji/apple/drum.png?v=15" title=":drum:" class="emoji" alt=":drum:" loading="lazy" width="20" height="20"> <img src="https://forum.elixirforum.com/images/emoji/apple/drum.png?v=15" title=":drum:" class="emoji" alt=":drum:" loading="lazy" width="20" height="20"> Chapter 1 Awards <img src="https://forum.elixirforum.com/images/emoji/apple/drum.png?v=15" title=":drum:" class="emoji" alt=":drum:" loading="lazy" width="20" height="20"> <img src="https://forum.elixirforum.com/images/emoji/apple/drum.png?v=15" title=":drum:" class="emoji" alt=":drum:" loading="lazy" width="20" height="20"> <img src="https://forum.elixirforum.com/images/emoji/apple/drum.png?v=15" title=":drum:" class="emoji" alt=":drum:" loading="lazy" width="20" height="20"> <img src="https://forum.elixirforum.com/images/emoji/apple/drum.png?v=15" title=":drum:" class="emoji" alt=":drum:" loading="lazy" width="20" height="20"></p>
<ul>
<li>
<p><img src="https://forum.elixirforum.com/images/emoji/apple/open_book.png?v=15" title=":open_book:" class="emoji" alt=":open_book:" loading="lazy" width="20" height="20"> <strong>Most Rereadable Section</strong> <img src="https://forum.elixirforum.com/images/emoji/apple/open_book.png?v=15" title=":open_book:" class="emoji" alt=":open_book:" loading="lazy" width="20" height="20"><br>
<em><strong>Build a Simple Live View</strong></em> <em>(pp. 15-23)</em><br>
As a relatively new Phoenix/Elixir user, it was helpful for me to read this section several times.  The subsection titled <code>Understand the LiveView Loop</code> was most valuable to me.  It removed some of the magic and gave me a better understanding of the importance of event handlers.  I’m sure that some of the other sections will become more valuable for me to reread as I continue to learn.</p>
</li>
<li>
<p><img src="https://forum.elixirforum.com/images/emoji/apple/rabbit2.png?v=15" title=":rabbit2:" class="emoji" alt=":rabbit2:" loading="lazy" width="20" height="20"> <strong>Most Likely to Send You Down The Rabbit Hole</strong> <img src="https://forum.elixirforum.com/images/emoji/apple/rabbit2.png?v=15" title=":rabbit2:" class="emoji" alt=":rabbit2:" loading="lazy" width="20" height="20"><br>
<em><strong>Examine Network Traffic</strong></em> <em>(pp. 24-25)</em><br>
This section got me excited to learn about the data diffs being sent over the wire.  I really liked how it encouraged you to actually open up your browser tools and look at the small footprint of the traffic.  I read a previous forum post[1] and the the <code>Phoenix.Socket.Message</code> API[2] to help me dig deeper into understanding the network traffic.</p>
<pre data-code-wrap="elixir"><code class="lang-elixir">["4","5","lv:phx-1YfONAIF",
"event",{"type":"click","event":"guess",
"value":{"number":"8"}}]
</code></pre>
<p>Where I believe that:</p>
<ul>
<li>“4” is the <code>join_ref</code></li>
<li>“5” is the <code>ref</code></li>
<li>“lv:phx-1Y…” is the <code>topic</code></li>
</ul>
</li>
</ul>
<p>Great book and thank you for hosting this club!</p>
<p>[1] <a href="https://forum.elixirforum.com/t/shape-of-phoenix-channel-socket-messages/45632/2" class="inline-onebox" rel="nofollow">Shape of Phoenix Channel socket messages - #2 by kartheek</a><br>
[2] <a href="https://hexdocs.pm/phoenix/Phoenix.Socket.Message.html" class="inline-onebox" rel="noopener nofollow ugc">Phoenix.Socket.Message — Phoenix v1.8.8</a></p> 
	            </div>

	            <div class="base-line">
	                <div class="thread-counters">
	                    <span class="thread-count count-likes js-likers-trigger" title="Likes" data-post-id="288299" data-batch-url="/posts/batch_likers">
                        5
                      </span>
                      <!-- <span class="thread-count js-solved-indicator" title="Marked as solution"></span> -->
	                </div>
	                <div class="go-to-post">
	                  <a title="Go to post" alt="Go to post" href="https://forum.elixirforum.com/t/programming-phoenix-liveview-book-club/55604/29">Post #28</a>
	                </div>
	            </div>
              <div id="likers-container-288299" 
                   class="likers-container"
                   data-first-post="false"
                   data-batch-url="/posts/batch_likers">
                   <div class="likers-placeholder" 
                     data-likers-post-id="288299"
                     data-batch-url="/posts/batch_likers">
                  <div class="post-likers"></div>
                </div>
              </div>
	        </div>
			

    </div>

    <div class="triangle-top-right type-standard-post cat-standard-post" title="Post #28"></div>
  </section>
</div>
    <div class="postbit" id="288300" data-post-id="288300">
  <section>
    <div class="post-wrap">


					<div class="post-header">
		        <div class="user-avatar">
		          <img alt="code-shoily" src="https://forum.elixirforum.com/user_avatar/forum.elixirforum.com/code-shoily/120/8052_2.png" width="120" height="120" />
		        </div>
					
						<div class="user-details">
		          <div class="user-name">
		            <h3>
                  code-shoily
                  </h3>
		          </div>
						
						</div>
					
					</div>

	        <div class="thread-main">
	            <div class="post-body" data-turbo="false">
								<p>Thank you <a class="mention" href="/u/tbobbe" rel="nofollow">@Tbobbe</a> and <a class="mention" href="/u/olivegarden" rel="nofollow">@olivegarden</a> … some very interesting pointers on your reviews. It’ll certainly help us late readers</p> 
	            </div>

	            <div class="base-line">
	                <div class="thread-counters">
	                    <span class="thread-count count-likes js-likers-trigger" title="Likes" data-post-id="288300" data-batch-url="/posts/batch_likers">
                        4
                      </span>
                      <!-- <span class="thread-count js-solved-indicator" title="Marked as solution"></span> -->
	                </div>
	                <div class="go-to-post">
	                  <a title="Go to post" alt="Go to post" href="https://forum.elixirforum.com/t/programming-phoenix-liveview-book-club/55604/30">Post #29</a>
	                </div>
	            </div>
              <div id="likers-container-288300" 
                   class="likers-container"
                   data-first-post="false"
                   data-batch-url="/posts/batch_likers">
                   <div class="likers-placeholder" 
                     data-likers-post-id="288300"
                     data-batch-url="/posts/batch_likers">
                  <div class="post-likers"></div>
                </div>
              </div>
	        </div>
			

    </div>

    <div class="triangle-top-right type-standard-post cat-standard-post" title="Post #29"></div>
  </section>
</div>
    <div class="postbit" id="288647" data-post-id="288647">
  <section>
    <div class="post-wrap">


					<div class="post-header">
		        <div class="user-avatar">
		          <img alt="Tbobbe" src="https://forum.elixirforum.com/user_avatar/forum.elixirforum.com/Tbobbe/120/29146_2.png" width="120" height="120" />
		        </div>
					
						<div class="user-details">
		          <div class="user-name">
		            <h3>
                  Tbobbe
                  </h3>
		          </div>
						
						</div>
					
					</div>

	        <div class="thread-main">
	            <div class="post-body" data-turbo="false">
								<h2><a name="p-288647-chapter-4-1" class="anchor" href="#p-288647-chapter-4-1" aria-label="Heading link" rel="nofollow"></a>Chapter 4</h2>
<p>Time to dive into the generated code for the frontend. There is quite a lot to take in from this chapter, so I will try to list my main takeaways:</p>
<ul>
<li><code>handle_params(params, url, socket)</code>: This is the function that runs after <code>mount</code>. It is used to handle URL <em>named parameters</em> and <em>live actions</em>.</li>
<li><em>live actions</em>: Used when one want to have a single live view handle multiple page states. In this case, listing, editing and creating product.</li>
<li><code>CoreComponents</code>: A module with some fancy premade components ready to be used and/or modified. Learn the available core components for your own benefit! <img src="https://forum.elixirforum.com/images/emoji/apple/smiley.png?v=15" title=":smiley:" class="emoji" alt=":smiley:" loading="lazy" width="20" height="20"></li>
<li><em>Attributes</em>: Acts as named variables for your components, they are put inside the tag. Can be defined above the component definition using the <code>attr</code> macro.</li>
<li><em>Slots</em>: Can be named or default to <code>@inner_block</code>. They are markup you put between the opening and closing tag of your component. Can be defined using the <code>slot</code> macro.</li>
<li><em>patch link</em>: Changes the URL path and re-routes, but without changing the live view process. Perfect and effective when one want to move to a new <em>live action</em> within the same live view. Since no <em>GET</em> request is actually fired, <code>mount</code> will not be called, but we will get to <code>handle_params</code> instead.</li>
<li><em>Forms</em>: When you see a form, think of changing data, which mean, think about <em>Changesets</em>. We use the validations defined in the <em>Changeset</em> to validate the form input! Smart!</li>
</ul>
<p>I didn’t touch on <em>functional components</em> and <em>live components</em> since my list is already quite long, and they will get their own chapters.</p>
<h3><a name="p-288647-indexhtmlheex-2" class="anchor" href="#p-288647-indexhtmlheex-2" aria-label="Heading link" rel="nofollow"></a>Index.html.heex</h3>
<p>I was actually quite surprised when I opened up the <em>index.html.heex</em>, and could not see a single normal HTML tag (actually, I later found one hiding in the table component). Now, all these concepts with components, attributes, slots etc. are great and super powerful, but at the same time I could see it feeling a bit daunting if you have done some HTML/CS/JS and some standard Elixir before, then you open up this file, and suddenly you can’t recognize a single thing.<br>
This is not a criticism at all, just a thought about the experience of learning a new framework/DSL.</p>
<h3><a name="p-288647-outdated-form-3" class="anchor" href="#p-288647-outdated-form-3" aria-label="Heading link" rel="nofollow"></a>Outdated form</h3>
<p>Unfortunately, the last part of the chapter regarding creating a new product using the form is a bit outdated. Not only syntax wise, but the logic has changed too.</p>
<p>In the book, they describe that the following happens when a product is saved: If the new product is successfully saved to the DB, we will <em>navigate</em> back to the product index page. This will trigger the <code>mount</code> function that will make a call to the DB, fetching <em>all</em> product in order to display the new one in the list.</p>
<p>The new generated code is much more efficient!<br>
When the product is successfully sent to the DB, we will send the new product in a message to the parent using the <code>notify_parent</code> helper function. In the parent, this event is handled using a <code>handle_info</code> function (see <em>index.ex</em>). Since the list of products is implemented using a <em>stream</em> (also different from the book), the function simply inserts the new product into the stream. After this, we do a <em>patch</em> navigation to the product index page.</p>
<p>This results in 3 major gains (from what I can see):</p>
<ol>
<li>Since we use a stream, no data from the list of products is stored on the server, leading to gains in memory efficiency. This might not mean much in this small case, but think about the case when a list might contain thousands of items, and you have thousands of users using the site at the same time. Suddenly there is a lot of memory to be saved.</li>
<li>Since we use <em>patch</em> instead of <em>navigate</em>, we don’t have to do a slow, pesky GET request. <img src="https://forum.elixirforum.com/images/emoji/apple/smiley.png?v=15" title=":smiley:" class="emoji" alt=":smiley:" loading="lazy" width="20" height="20"></li>
<li>Since we send the product from the child component to the parent directly, we don’t have to read a single entry from the database! (Once again, imagine if there were tens of thousands of products in the DB).</li>
</ol>
<p>I’m sure the outdated code will be fixed for the final revision of the book. ^^</p>
<p>Overall, a great chapter which also makes multiple references to the CRC pattern. But you will probably have to go through it a couple of times in order to pick up on all the new information presented. Sorry for the long post <img src="https://forum.elixirforum.com/images/emoji/apple/sweat_smile.png?v=15" title=":sweat_smile:" class="emoji" alt=":sweat_smile:" loading="lazy" width="20" height="20">.</p> 
	            </div>

	            <div class="base-line">
	                <div class="thread-counters">
	                    <span class="thread-count count-likes js-likers-trigger" title="Likes" data-post-id="288647" data-batch-url="/posts/batch_likers">
                        6
                      </span>
                      <!-- <span class="thread-count js-solved-indicator" title="Marked as solution"></span> -->
	                </div>
	                <div class="go-to-post">
	                  <a title="Go to post" alt="Go to post" href="https://forum.elixirforum.com/t/programming-phoenix-liveview-book-club/55604/31">Post #30</a>
	                </div>
	            </div>
              <div id="likers-container-288647" 
                   class="likers-container"
                   data-first-post="false"
                   data-batch-url="/posts/batch_likers">
                   <div class="likers-placeholder" 
                     data-likers-post-id="288647"
                     data-batch-url="/posts/batch_likers">
                  <div class="post-likers"></div>
                </div>
              </div>
	        </div>
			

    </div>

    <div class="triangle-top-right type-standard-post cat-standard-post" title="Post #30"></div>
  </section>
</div>
</template></turbo-stream><turbo-stream action="replace" target="load-more-container"><template><div id="load-more-container" class="load-more-container">
    <a class="load-more-button" data-turbo-stream="true" href="/topics/55604/load_more?page=4">Load more posts (41 remaining)</a>
</div></template></turbo-stream>