<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Wonjin Cho</title>
    <description>The latest articles on DEV Community by Wonjin Cho (@cwonjin11).</description>
    <link>https://dev.to/cwonjin11</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F543631%2F063076d3-7c7e-4507-9d55-00d0508a6d10.jpeg</url>
      <title>DEV Community: Wonjin Cho</title>
      <link>https://dev.to/cwonjin11</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/cwonjin11"/>
    <language>en</language>
    <item>
      <title>React-Redux Terminology</title>
      <dc:creator>Wonjin Cho</dc:creator>
      <pubDate>Mon, 19 Jul 2021 17:40:55 +0000</pubDate>
      <link>https://dev.to/cwonjin11/react-redux-terminology-58fg</link>
      <guid>https://dev.to/cwonjin11/react-redux-terminology-58fg</guid>
      <description>&lt;p&gt;Learning new languages always requires to learn new terminology which are usually very strange.&lt;br&gt;
When we are talking about especially on React and Redux, a lot of new terminologies are involved. I hope this articles my help you to get some basic knowledges of strange definitions. These are my notes and brief summary of the React and Redux when I've built my last project of the Flatiron school.&lt;/p&gt;

&lt;p&gt;*** Redux vs React***&lt;br&gt;
We are utilizing Redux, our redux store is handling a lot of the data manipulation and communication with our api; whereas, our React application should be mainly for just to display our data.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--pnVjr4Ef--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://res.cloudinary.com/practicaldev/image/fetch/s--VtRaY29J--/c_limit%252Cf_auto%252Cfl_progressive%252Cq_auto%252Cw_880/https://thepracticaldev.s3.amazonaws.com/i/fewc8ez6r2e2agah717y.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--pnVjr4Ef--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://res.cloudinary.com/practicaldev/image/fetch/s--VtRaY29J--/c_limit%252Cf_auto%252Cfl_progressive%252Cq_auto%252Cw_880/https://thepracticaldev.s3.amazonaws.com/i/fewc8ez6r2e2agah717y.png" alt="Alt text of image"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;em&gt;ACTION CREATOR:&lt;/em&gt;&lt;/strong&gt;&lt;br&gt;
A function that creates an action&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;em&gt;ACTION:&lt;/em&gt;&lt;/strong&gt;&lt;br&gt;
An object that contains information about how we want to change some data within our central state&lt;/p&gt;

&lt;p&gt;action: { &lt;br&gt;
  type: [describes what change we want to make to our data], &lt;br&gt;
  payload: [context of what change we want to make] &lt;br&gt;
}&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;em&gt;DISPATCH:&lt;/em&gt;&lt;/strong&gt;&lt;br&gt;
A function that takes in an action, makes copies of the action, and sends them out to the reducers.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;em&gt;REDUCER:&lt;/em&gt;&lt;/strong&gt;&lt;br&gt;
A function that takes in an action and some existing data, changes the data according to the type and payload of the action, and then sends the updated data to the state.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;em&gt;STATE:&lt;/em&gt;&lt;/strong&gt;&lt;br&gt;
An object that serves as the central repository of all data from the reducers.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;em&gt;React-Redux&lt;/em&gt;&lt;/strong&gt;&lt;br&gt;
With React-Redux, we use some components and functions to tie React and Redux together: Store, Provider, and Connect.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;em&gt;STORE:&lt;/em&gt;&lt;/strong&gt;&lt;br&gt;
The Store contains the consolidated reducers and the state.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;em&gt;PROVIDER:&lt;/em&gt;&lt;/strong&gt;&lt;br&gt;
The Provider is a component that has a reference to the Store and provides the data from the Store to the component it wraps.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;em&gt;CONNECT:&lt;/em&gt;&lt;/strong&gt;&lt;br&gt;
Connect is a function communicates with the Provider. Whatever component we wrap with Connect, that component will be able to get changes in the Store state from the Provider.&lt;/p&gt;

&lt;p&gt;We can configure Connect to get just the part of the data we want from the Provider. Connect passes this down as props into the wrapped components.&lt;/p&gt;

&lt;p&gt;The flow with react-redux looks like this:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Create the Provider&lt;/li&gt;
&lt;li&gt;Pass it a reference to our Redux Store&lt;/li&gt;
&lt;li&gt;Wrap any component that needs to interact with the Store with Connect&lt;/li&gt;
&lt;li&gt;Connect passes down the different pieces of state and any action creators we need as props down to the wrapped component.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;&lt;strong&gt;&lt;em&gt;Configuring connect&lt;/em&gt;&lt;/strong&gt;&lt;br&gt;
Connect takes in several arguments, but we will only be concerned with the first two: mapStateToProps and mapDispatchToProps.&lt;/p&gt;

&lt;p&gt;*&lt;strong&gt;&lt;em&gt;Extracting data with mapStateToProps&lt;/em&gt;&lt;/strong&gt;*&lt;br&gt;
mapStateToProps is essentially extracting just the pieces of the state you want into your component as props. It is important to note that when you specify a function for this argument, you are subscribing the component to changes in that part of the state. If the component does not need to re-render based on changes in the state, you can pass in null or undefined as the argument instead.&lt;/p&gt;

&lt;p&gt;*&lt;strong&gt;&lt;em&gt;Dispatching actions with mapDispatchToProps&lt;/em&gt;&lt;/strong&gt;*&lt;br&gt;
mapDispatchToProps can be defined as an object of action creators (there's Redux magic behind the scenes but this is a nice shorthand) and binds the dispatch of the store to each of the action creators. This allows you to use the actions creators through props in the component as you would by passing down functional props from the parent without Redux.&lt;/p&gt;

</description>
    </item>
    <item>
      <title>Project #4 : Vanilla JS Frontend with RoR API backend</title>
      <dc:creator>Wonjin Cho</dc:creator>
      <pubDate>Sun, 20 Jun 2021 17:32:56 +0000</pubDate>
      <link>https://dev.to/cwonjin11/project-4-vanilla-js-frontend-with-ror-api-backend-55kk</link>
      <guid>https://dev.to/cwonjin11/project-4-vanilla-js-frontend-with-ror-api-backend-55kk</guid>
      <description>&lt;h3&gt;
  
  
  Intro
&lt;/h3&gt;

&lt;p&gt;My fourth project for Flatiron School was building a Single Page Application(SPA) using Javascript as a frontend and Rails API as a backend. &lt;/p&gt;

&lt;h3&gt;
  
  
  Project Description
&lt;/h3&gt;

&lt;p&gt;As always, for this time again, my 3 years old son gave me another idea what my project would be. It might be a little bit childish;however, I named my project "Dinosaur Flash Card" which will show the dinosaurs as cards and using CSS, flipping those cards to show the user to have brief details of the selected dinosaurs.&lt;/p&gt;

&lt;h3&gt;
  
  
  Backend Setup
&lt;/h3&gt;

&lt;p&gt;I added two model since "MesozoicEra" and "Dinosaur" with a relationship of has_many and belongs_to relatively.&lt;br&gt;
After migration and seeding data, by using rails scaffold for both models, backend was easily set up without having trouble. &lt;/p&gt;
&lt;h3&gt;
  
  
  Frontend challenges
&lt;/h3&gt;

&lt;p&gt;There were many difficulties and challenges when I worked on this project. Altering codes from Index.js file to each model folder's file in order to make my code DRY was the basic challenge;however, the most important part was understanding what JS code looked like since I am totally new in this city.&lt;br&gt;
For this project, 'fetching' and using 'addEventListner' method were the most useful method I had to use for several times.&lt;/p&gt;
&lt;h3&gt;
  
  
  Fetching
&lt;/h3&gt;

&lt;p&gt;I used 5 fetching method; render all dions, render all eras, render dinos by era, POST(creating a dino), DELETE dino.&lt;br&gt;
For this post, I would like to introduce how I fetched all dinosaurs and made them displayed on the webpage.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;class API {
    static ALL_DINOSAURS_URL = "http://localhost:3000/dinosaurs"

   static addDinosaurs() {
        fetch(this.ALL_DINOSAURS_URL)
        .then(response =&amp;gt; response.json())
        .then(dinosaurs =&amp;gt; {
              dinosaurs.forEach(dinosaur =&amp;gt; {
              const newDinosaur = new Dinosaur(dinosaur)
              newDinosaur.renderDinosaur(dinosaur)     
              Dinosaur.all.push(newDinosaur)
              })
        }) 
    }
}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Above code is the way how I fetched all dinosaurs as a class.&lt;br&gt;
In services folder, I've created API.js file and added API class to make my code as DRY as I could. Since this is just fetching process, I needed to add the below codes to actually display all dinosaurs on the web page.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;document.addEventListener("DOMContentLoaded", function() {
  API.addDinosaurs() };
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;I called 'addDinosaurs' function and invoked it to Index.js file with "DOMContentLaded" event listener so that it finally rendered and displayed all dinosaurs from the backend to the front. &lt;/p&gt;

&lt;h3&gt;
  
  
  Summary
&lt;/h3&gt;

&lt;p&gt;Throughout this basic fetching process, I felt much comfortable playing with Javascript. As a beginner of JS, all methods and functions do not look familiar just like when I learned RUBY as a first computer language. By practicing this simple fetching method and repeating those process to fetch other backend data, I finally ended up having better confidence than the beginning of this project.&lt;/p&gt;

</description>
      <category>rails</category>
      <category>javascript</category>
    </item>
    <item>
      <title>Rails Project - Rate My Hairstylist</title>
      <dc:creator>Wonjin Cho</dc:creator>
      <pubDate>Sun, 16 May 2021 08:27:04 +0000</pubDate>
      <link>https://dev.to/cwonjin11/rails-project-rate-my-hairstylist-29cp</link>
      <guid>https://dev.to/cwonjin11/rails-project-rate-my-hairstylist-29cp</guid>
      <description>&lt;h3&gt;
  
  
  Project Idea
&lt;/h3&gt;

&lt;p&gt;For my third project,  I decided to build rating and reviewing web application. &lt;/p&gt;

&lt;h3&gt;
  
  
  Relationship
&lt;/h3&gt;

&lt;p&gt;I created 3 models; User, UserStylist, Stylist.&lt;br&gt;
User will have many stylists and Stylist will have many User through user_stylists. UserStylist(which will be review/rating model) model will be a join of User and Stylist. It belongs to user and stylists.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--0orgTSxA--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/gdyeya403d54h95wbrvs.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--0orgTSxA--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/gdyeya403d54h95wbrvs.png" alt="Screen Shot 2021-05-16 at 3.51.48 AM"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  Data Migration
&lt;/h3&gt;

&lt;p&gt;By using rails g resource function, it was really easy to create migrations. Since this project requires omniauth log in function, I've added "uid" and "provider" as user's attributes. I'll user Google omniauth login for my project. &lt;/p&gt;

&lt;h3&gt;
  
  
  Rested routes
&lt;/h3&gt;

&lt;p&gt;Here are all the routes for this web application.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--m_vSoNXn--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/np0fr5tp7k4mh7nnlrhp.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--m_vSoNXn--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/np0fr5tp7k4mh7nnlrhp.png" alt="Screen Shot 2021-05-16 at 3.56.11 AM"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;There is a nested route for user_stylist. For example, "user/3/user_stylists/46" will be the review details page which is a show page of this user's review. &lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--xZBU54bS--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/vnecxka8kghc8t9kiuop.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--xZBU54bS--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/vnecxka8kghc8t9kiuop.png" alt="Screen Shot 2021-05-16 at 4.00.32 AM"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;A nested new route with form will be following.&lt;br&gt;
&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--KHi-p_j4--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/e0pes7ukdhhvmjie031z.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--KHi-p_j4--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/e0pes7ukdhhvmjie031z.png" alt="Screen Shot 2021-05-16 at 4.03.57 AM"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  scope method
&lt;/h3&gt;

&lt;p&gt;Rather than using native Ruby method, this time, I've added two scope method; Most Reviewed hairstylists and High-rated reviews. &lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--XiGlIRpr--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/omgwpvb2wqo25ab76nm2.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--XiGlIRpr--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/omgwpvb2wqo25ab76nm2.png" alt="Screen Shot 2021-05-16 at 4.10.44 AM"&gt;&lt;/a&gt;&lt;br&gt;
&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--ntQH3huG--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ycjgmmnyo7ahsy5vpbhu.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--ntQH3huG--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ycjgmmnyo7ahsy5vpbhu.png" alt="Screen Shot 2021-05-16 at 4.10.59 AM"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Those are my code for the two scope method. First one shows top 5 most reviewed hair stylists name. The second code is for rating scope that means each hairstylist has their reviews with star rating and by using that star attribute, I defined scope method to show only 5 stars reviews.&lt;/p&gt;

&lt;h3&gt;
  
  
  Conclusion
&lt;/h3&gt;

&lt;p&gt;By having the 'resources' keyword, rails sets up every 'RESTful' route associated with that model. The routes magic were the one that really shined for me. I had struggled a lot dealing with all of Rails server errors to get promptly worked this application; however, each time, I've learned more than one error since one error causes usually another error.   &lt;/p&gt;

</description>
    </item>
    <item>
      <title>Sinatra app basics - all you need to know before building up your project</title>
      <dc:creator>Wonjin Cho</dc:creator>
      <pubDate>Fri, 16 Apr 2021 02:14:51 +0000</pubDate>
      <link>https://dev.to/cwonjin11/sinatra-app-basics-all-you-need-to-know-before-building-up-your-project-2p05</link>
      <guid>https://dev.to/cwonjin11/sinatra-app-basics-all-you-need-to-know-before-building-up-your-project-2p05</guid>
      <description>&lt;h1&gt;
  
  
  Building a Sinatra web application
&lt;/h1&gt;

&lt;p&gt;From this blog posting, I am going to write down some basic key words and definitions to build a CRUD application using Sinatra.&lt;/p&gt;

&lt;h3&gt;
  
  
  Sinatra
&lt;/h3&gt;

&lt;p&gt;Sinatra is Domain Specific Language implemented in Ruby to build web applications. By using methods like , for instance, "get" and "post", it will instantly transform Ruby application into an application that can respond to HTTP requests.&lt;/p&gt;

&lt;h3&gt;
  
  
  ORM/ActiveRecord
&lt;/h3&gt;

&lt;p&gt;Object Relational Mapping :to map (or equate) ruby classes with database tables and the instances of those classes with the rows of the table. &lt;br&gt;
ActiveRecord : a Ruby library that connects classes to relational SQL Databases. Essentially ActiveRecord is an ORM that helps to deal with databases. &lt;/p&gt;

&lt;h3&gt;
  
  
  Rack
&lt;/h3&gt;

&lt;p&gt;a simple interface sits between web frameworks (Sinatra, Rails, etc) and web server&lt;/p&gt;

&lt;h3&gt;
  
  
  MVC
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;Models&lt;/strong&gt;: The 'logic' of a web application where data is manipulated and/or saved.&lt;br&gt;
&lt;strong&gt;Views&lt;/strong&gt;: The 'front-end' web application - this is the only part of the app that the user interacts with directly. Views generally consist of HTML, CSS, and Javascript.&lt;br&gt;
&lt;strong&gt;Controllers&lt;/strong&gt;: The go-between for models and views. The controller relays data from the browser to the application, and from the application to the browser.&lt;/p&gt;

&lt;h4&gt;
  
  
  naming conventions for an MVC folder structure
&lt;/h4&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--g976bP9w--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/focwmgo9ovq969efnjhq.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--g976bP9w--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/focwmgo9ovq969efnjhq.png" alt="Screen Shot 2021-02-17 at 11.27.31 PM"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  erb
&lt;/h3&gt;

&lt;p&gt;.erb file: contains HTML tags and embedded ruby(erb) tags(work with Ruby code); file names, by convention, should match with the action that renders them&lt;/p&gt;

&lt;h3&gt;
  
  
  controllers
&lt;/h3&gt;

&lt;p&gt;will contain all the necessary routes to help the user sign-in/sign-out, sign-up, and CRUD user's data from the web.&lt;/p&gt;

&lt;h3&gt;
  
  
  Application Controller
&lt;/h3&gt;

&lt;p&gt;Application Controller represents an instance of the web application when server is running; it is where configurations, routes and controller actions are implements; other controllers use it as an inheritance point to inherit all the defaults and behavior defined in ApplicationController (which inherits from Sinatra::Base)&lt;/p&gt;

&lt;h3&gt;
  
  
  Database Migrations
&lt;/h3&gt;

&lt;p&gt;by creating tables and schema by using "rake db:migrate" in db/migrate folder, SQLite is usable with seeds data.&lt;/p&gt;

&lt;h3&gt;
  
  
  shotgun
&lt;/h3&gt;

&lt;p&gt;a ruby Gem to test Rack-based Ruby web application and start Rack with auto code reloading&lt;/p&gt;

&lt;h3&gt;
  
  
  7 RESTful routes
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;Sinatra and ActiveRecord CRUD&lt;/strong&gt;&lt;br&gt;
&lt;strong&gt;CRUD&lt;/strong&gt;&lt;br&gt;
an acronym for Create, Read, Update, and Delete, these are the four basic functions of persistent storage.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Create&lt;/strong&gt; is implemented in Sinatra by building a route, or controller action, to render a form for creating a new instance of your model.&lt;br&gt;
&lt;em&gt;get '/models/new' -&amp;gt; new.erb -&amp;gt; post '/models'&lt;/em&gt;&lt;br&gt;
&lt;strong&gt;Read&lt;/strong&gt; read either all of the instances of a class or a specific instance of a class&lt;br&gt;
&lt;em&gt;get '/models' -&amp;gt; index.erb&lt;/em&gt; (to render all of the instances stored in the @models instance variable)&lt;br&gt;
&lt;em&gt;get '/models/:id' -&amp;gt; show.erb&lt;/em&gt; (to find the instance of the model with that id number and set it equal to an instance variable: @model = Model.find(params[:id]))&lt;br&gt;
&lt;strong&gt;Update&lt;/strong&gt; To implement the update action, we need a controller action that renders an update form, and we need a controller action to catch the post request sent by that form&lt;br&gt;
Add &lt;em&gt;"use Rack::MethodOverride"&lt;/em&gt; line in "config.ru" file to use the Sinatra Middleware that lets our app send patch requests&lt;br&gt;
&lt;em&gt;get '/models/:id/edit' -&amp;gt; edit.erb -&amp;gt; patch '/models/:id'&lt;/em&gt;&lt;br&gt;
&lt;strong&gt;Delete&lt;/strong&gt; does not get into its own view page but is implemented via a "delete" button on the show page of given instance&lt;br&gt;
&lt;em&gt;get '/models/:id -&amp;gt; show.erb -&amp;gt; post '/models/:id/delete'&lt;/em&gt;&lt;br&gt;
&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--hctjcnUH--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/j3nel24zwjrpti74r9lo.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--hctjcnUH--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/j3nel24zwjrpti74r9lo.png" alt="Screen Shot 2021-02-17 at 11.11.56 PM"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  bcrypt gem
&lt;/h3&gt;

&lt;p&gt;It will store a salted and hashed version of our user's passwords(not a plain text version of password) in our database in a column called "password_digest"&lt;/p&gt;

&lt;h3&gt;
  
  
  has_secure_password
&lt;/h3&gt;

&lt;p&gt;Active Record macro method that works in conjunction with 'bcrypt' gem. It encrypts the plain text version of the password and comes with .authenticate method to see the match of the salted and hashed password from the database.&lt;/p&gt;

&lt;h3&gt;
  
  
  Session vs cookie
&lt;/h3&gt;

&lt;p&gt;Cookies and Sessions are used to store information. Cookies are only stored on the client-side machine, while sessions get stored on the client as well as a server.&lt;/p&gt;

&lt;h3&gt;
  
  
  Session
&lt;/h3&gt;

&lt;p&gt;server-side use case for temporarily persisting data while a user browsers the server’s website. Session hash lives on server and web application can access session via any of the controllers at any point in time. &lt;/p&gt;

&lt;h3&gt;
  
  
  Cookies
&lt;/h3&gt;

&lt;p&gt;Text files stored on the client computer. Server sends a set of cookies to the browser; name, age, or ids etc. The browser stores this information on a local machine and when next time browser sends any request to web server, then it sends those cookies information to the server and server uses that information to identify the user.&lt;/p&gt;

&lt;h3&gt;
  
  
  Rendering
&lt;/h3&gt;

&lt;p&gt;Rendering allows us to pass instance variables through to the erb file. Rendering a file displays the view without submitting an additional  request to the server. &lt;/p&gt;

&lt;h3&gt;
  
  
  Redirecting
&lt;/h3&gt;

&lt;p&gt;It actually sends a new request to the server. For this reason, Since HTTP is a stateless protocol, we are not able to pass instance variables through a redirect, as those variables no longer exist once new request has been made. &lt;/p&gt;

&lt;h3&gt;
  
  
  helper method
&lt;/h3&gt;

&lt;p&gt;Helper methods is defined in the controller and can access to the views. It will help not only whether a user is logged in and who the current user is, but also make our code DRY.&lt;/p&gt;

&lt;h3&gt;
  
  
  rack::methodoverride
&lt;/h3&gt;

&lt;p&gt;The only HTTP methods that HTML form element should allow are "GET" and "POST". For this reason, Rack::MethodOverride is required in order for forms to have a "_method", allowing PUT, PATCH and DELETE actions to function. Don't forget to add the "use Rack::MethodOverride" to 'config.ru' file so that the application will know how to handle patch and delete requests. Put "use Rack::MethodOverride" above "run application_controller" so that the override method works properly throughout the app. &lt;/p&gt;

</description>
    </item>
    <item>
      <title> Sinatra app basics - all you need to know before building up your project</title>
      <dc:creator>Wonjin Cho</dc:creator>
      <pubDate>Thu, 18 Feb 2021 05:58:59 +0000</pubDate>
      <link>https://dev.to/cwonjin11/basic-knowledge-of-building-sinatra-crud-app-3051</link>
      <guid>https://dev.to/cwonjin11/basic-knowledge-of-building-sinatra-crud-app-3051</guid>
      <description>&lt;h1&gt;
  
  
  Building a Sinatra web application
&lt;/h1&gt;

&lt;p&gt;From this blog posting, I am going to write down some basic key words and definitions to build a CRUD application using Sinatra.&lt;/p&gt;

&lt;h3&gt;
  
  
  Sinatra
&lt;/h3&gt;

&lt;p&gt;Sinatra is Domain Specific Language implemented in Ruby to build web applications. By using methods like , for instance, "get" and "post", it will instantly transform Ruby application into an application that can respond to HTTP requests.&lt;/p&gt;

&lt;h3&gt;
  
  
  ORM/ActiveRecord
&lt;/h3&gt;

&lt;p&gt;Object Relational Mapping :to map (or equate) ruby classes with database tables and the instances of those classes with the rows of the table. &lt;br&gt;
ActiveRecord : a Ruby library that connects classes to relational SQL Databases. Essentially ActiveRecord is an ORM that helps to deal with databases. &lt;/p&gt;

&lt;h3&gt;
  
  
  Rack
&lt;/h3&gt;

&lt;p&gt;a simple interface sits between web frameworks (Sinatra, Rails, etc) and web server&lt;/p&gt;

&lt;h3&gt;
  
  
  MVC
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;Models&lt;/strong&gt;: The 'logic' of a web application where data is manipulated and/or saved.&lt;br&gt;
&lt;strong&gt;Views&lt;/strong&gt;: The 'front-end' web application - this is the only part of the app that the user interacts with directly. Views generally consist of HTML, CSS, and Javascript.&lt;br&gt;
&lt;strong&gt;Controllers&lt;/strong&gt;: The go-between for models and views. The controller relays data from the browser to the application, and from the application to the browser.&lt;/p&gt;

&lt;h4&gt;
  
  
  naming conventions for an MVC folder structure
&lt;/h4&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--g976bP9w--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/focwmgo9ovq969efnjhq.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--g976bP9w--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/focwmgo9ovq969efnjhq.png" alt="Screen Shot 2021-02-17 at 11.27.31 PM"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  erb
&lt;/h3&gt;

&lt;p&gt;.erb file: contains HTML tags and embedded ruby(erb) tags(work with Ruby code); file names, by convention, should match with the action that renders them&lt;/p&gt;

&lt;h3&gt;
  
  
  controllers
&lt;/h3&gt;

&lt;p&gt;will contain all the necessary routes to help the user sign-in/sign-out, sign-up, and CRUD user's data from the web.&lt;/p&gt;

&lt;h3&gt;
  
  
  Application Controller
&lt;/h3&gt;

&lt;p&gt;Application Controller represents an instance of the web application when server is running; it is where configurations, routes and controller actions are implements; other controllers use it as an inheritance point to inherit all the defaults and behavior defined in ApplicationController (which inherits from Sinatra::Base)&lt;/p&gt;

&lt;h3&gt;
  
  
  Database Migrations
&lt;/h3&gt;

&lt;p&gt;by creating tables and schema by using "rake db:migrate" in db/migrate folder, SQLite is usable with seeds data.&lt;/p&gt;

&lt;h3&gt;
  
  
  shotgun
&lt;/h3&gt;

&lt;p&gt;a ruby Gem to test Rack-based Ruby web application and start Rack with auto code reloading&lt;/p&gt;

&lt;h3&gt;
  
  
  7 RESTful routes
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;Sinatra and ActiveRecord CRUD&lt;/strong&gt;&lt;br&gt;
&lt;strong&gt;CRUD&lt;/strong&gt;&lt;br&gt;
an acronym for Create, Read, Update, and Delete, these are the four basic functions of persistent storage.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Create&lt;/strong&gt; is implemented in Sinatra by building a route, or controller action, to render a form for creating a new instance of your model.&lt;br&gt;
&lt;em&gt;get '/models/new' -&amp;gt; new.erb -&amp;gt; post '/models'&lt;/em&gt;&lt;br&gt;
&lt;strong&gt;Read&lt;/strong&gt; read either all of the instances of a class or a specific instance of a class&lt;br&gt;
&lt;em&gt;get '/models' -&amp;gt; index.erb&lt;/em&gt; (to render all of the instances stored in the @models instance variable)&lt;br&gt;
&lt;em&gt;get '/models/:id' -&amp;gt; show.erb&lt;/em&gt; (to find the instance of the model with that id number and set it equal to an instance variable: @model = Model.find(params[:id]))&lt;br&gt;
&lt;strong&gt;Update&lt;/strong&gt; To implement the update action, we need a controller action that renders an update form, and we need a controller action to catch the post request sent by that form&lt;br&gt;
Add &lt;em&gt;"use Rack::MethodOverride"&lt;/em&gt; line in "config.ru" file to use the Sinatra Middleware that lets our app send patch requests&lt;br&gt;
&lt;em&gt;get '/models/:id/edit' -&amp;gt; edit.erb -&amp;gt; patch '/models/:id'&lt;/em&gt;&lt;br&gt;
&lt;strong&gt;Delete&lt;/strong&gt; does not get into its own view page but is implemented via a "delete" button on the show page of given instance&lt;br&gt;
&lt;em&gt;get '/models/:id -&amp;gt; show.erb -&amp;gt; post '/models/:id/delete'&lt;/em&gt;&lt;br&gt;
&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--hctjcnUH--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/j3nel24zwjrpti74r9lo.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--hctjcnUH--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/j3nel24zwjrpti74r9lo.png" alt="Screen Shot 2021-02-17 at 11.11.56 PM"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  bcrypt gem
&lt;/h3&gt;

&lt;p&gt;It will store a salted and hashed version of our user's passwords(not a plain text version of password) in our database in a column called "password_digest"&lt;/p&gt;

&lt;h3&gt;
  
  
  has_secure_password
&lt;/h3&gt;

&lt;p&gt;Active Record macro method that works in conjunction with 'bcrypt' gem. It encrypts the plain text version of the password and comes with .authenticate method to see the match of the salted and hashed password from the database.&lt;/p&gt;

&lt;h3&gt;
  
  
  Session vs cookie
&lt;/h3&gt;

&lt;p&gt;Cookies and Sessions are used to store information. Cookies are only stored on the client-side machine, while sessions get stored on the client as well as a server.&lt;/p&gt;

&lt;h3&gt;
  
  
  Session
&lt;/h3&gt;

&lt;p&gt;server-side use case for temporarily persisting data while a user browsers the server’s website. Session hash lives on server and web application can access session via any of the controllers at any point in time. &lt;/p&gt;

&lt;h3&gt;
  
  
  Cookies
&lt;/h3&gt;

&lt;p&gt;Text files stored on the client computer. Server sends a set of cookies to the browser; name, age, or ids etc. The browser stores this information on a local machine and when next time browser sends any request to web server, then it sends those cookies information to the server and server uses that information to identify the user.&lt;/p&gt;

&lt;h3&gt;
  
  
  Rendering
&lt;/h3&gt;

&lt;p&gt;Rendering allows us to pass instance variables through to the erb file. Rendering a file displays the view without submitting an additional  request to the server. &lt;/p&gt;

&lt;h3&gt;
  
  
  Redirecting
&lt;/h3&gt;

&lt;p&gt;It actually sends a new request to the server. For this reason, Since HTTP is a stateless protocol, we are not able to pass instance variables through a redirect, as those variables no longer exist once new request has been made. &lt;/p&gt;

&lt;h3&gt;
  
  
  helper method
&lt;/h3&gt;

&lt;p&gt;Helper methods is defined in the controller and can access to the views. It will help not only whether a user is logged in and who the current user is, but also make our code DRY.&lt;/p&gt;

&lt;h3&gt;
  
  
  rack::methodoverride
&lt;/h3&gt;

&lt;p&gt;The only HTTP methods that HTML form element should allow are "GET" and "POST". For this reason, Rack::MethodOverride is required in order for forms to have a "_method", allowing PUT, PATCH and DELETE actions to function. Don't forget to add the "use Rack::MethodOverride" to 'config.ru' file so that the application will know how to handle patch and delete requests. Put "use Rack::MethodOverride" above "run application_controller" so that the override method works properly throughout the app. &lt;/p&gt;

</description>
    </item>
    <item>
      <title>First Project : Build a CLI app with External Data</title>
      <dc:creator>Wonjin Cho</dc:creator>
      <pubDate>Thu, 14 Jan 2021 15:24:19 +0000</pubDate>
      <link>https://dev.to/cwonjin11/first-project-build-a-cli-app-with-external-data-2k42</link>
      <guid>https://dev.to/cwonjin11/first-project-build-a-cli-app-with-external-data-2k42</guid>
      <description>&lt;p&gt;My first application ever before.Half success, half failure. But It was a precious project where I could learn a lot.&lt;/p&gt;

&lt;h3&gt;
  
  
  Brief introduction of the application:
&lt;/h3&gt;

&lt;p&gt;The CLI application I built for the first project at Flatiron is a very simple app that can list the menu of Dunkin' donut's espresso and coffee. By scraping the list of menu from the website, user can see more details about the menu chosen.&lt;/p&gt;

&lt;h3&gt;
  
  
  How I scrape the data?
&lt;/h3&gt;

&lt;p&gt;require 'nokogiri'&lt;br&gt;
require 'open-uri'&lt;br&gt;
URL = open("&lt;a href="https://www.webpage%22"&gt;https://www.webpage"&lt;/a&gt;) &lt;br&gt;
doc = Nokogiri::HTML(open(URL))&lt;br&gt;
doc.css("class").&lt;br&gt;
puts doc&lt;/p&gt;

&lt;p&gt;By this way, I could get messy data that is difficult to read. The problem has begun here. I misjudged the data and I believed I could scrape the text I want. Without analyzing the data in details, I started to code my project, enjoyed CLI time for several days. The problem occurred at last. There were data not "scrapable". All 'Ingredients', 'calories' and 'Allergens' text data were unable to scrape. I struggle with scraping the data for several days because it seemed like just normal text data. What i learned a few days later was that it happened because the web page used 'JavaScript' for the certain data: which I needed.&lt;/p&gt;

&lt;p&gt;I have not learnt JavaScript yet so I had to minimize and simplify my project finish up on time. As I mentioned before, there was actually a bigger plan than what this application I coded shows now. I should have scraped the data and see the details of it very carefully before I start to code. &lt;/p&gt;

&lt;p&gt;For this project, scraping external data might give more sources to build various applications. However, since the way 'scraping' has certain risk, for instance, each website may have different designs and use different languages with special styles, it will affect the application and someday the app will be no longer useful. &lt;/p&gt;

&lt;p&gt;So, next time? Definitely APIs rather than scraping web data.&lt;/p&gt;

&lt;h3&gt;
  
  
  What I learned from the first project
&lt;/h3&gt;

&lt;ol&gt;
&lt;li&gt;creating/ editing ruby project files using gems.&lt;/li&gt;
&lt;li&gt;Coding CLI class method and testing by bin/filename and binding.pry&lt;/li&gt;
&lt;li&gt;The use of web scraping and what risk it has. Also why programmers are more likely to use APIs &lt;/li&gt;
&lt;li&gt;How to use github&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;git status =&amp;gt; if I want to check the status&lt;br&gt;
  git add . = &amp;gt; add file&lt;br&gt;
  git commit -am "any commit message" =&amp;gt; to save my changes to the local repository. &lt;br&gt;
   -a &lt;br&gt;
     Includes all currently changed files in this commit&lt;br&gt;
   -m &lt;br&gt;
     Sets the commit's message&lt;br&gt;
  git push =&amp;gt; to upload local repository content to a my github repo&lt;/p&gt;

</description>
    </item>
    <item>
      <title>Why am I studying Software Engineering?</title>
      <dc:creator>Wonjin Cho</dc:creator>
      <pubDate>Sat, 19 Dec 2020 22:54:32 +0000</pubDate>
      <link>https://dev.to/cwonjin11/why-studying-software-engineering-5556</link>
      <guid>https://dev.to/cwonjin11/why-studying-software-engineering-5556</guid>
      <description>&lt;p&gt;When I worked for an airlines in Korea, I participated in numerous projects. One of the biggest projects was data migration from old system to new ERP. At that time, I had to spend a lot of time with software engineers as a financial analyst. &lt;/p&gt;

&lt;p&gt;My first motive has started there. They, the engineers, were always pursuing "efficiency". I was the one trying to tell them all the very and the finest details. However, they just collected only the most important parts of my words and transferred as data. Efficiency, conciseness and obviousness; every time when I worked, these were the first words that had come to my mind and that engineers were always dealing with those words.&lt;/p&gt;

&lt;p&gt;The second motive has started from a little personal. Here, I want to be a little honest. During the data migration project, I had to go to work on weekends as well; however, the engineers were alway at home! I felt so lonely and envious of them. They were working remotely and socializing each other. &lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--pp4ydWX_--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/0bw26c31yvmb5t8n0m2h.jpg" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--pp4ydWX_--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/0bw26c31yvmb5t8n0m2h.jpg" alt="Alt Text"&gt;&lt;/a&gt;&lt;br&gt;
   There are a lot of reason why I decided to change my career and to study a new field 'software engineering'. I have a three years old son and he is always the one who gives me the most powerful motivation. Whenever I carefully look at him, he makes me want to live a life just like as he lives now: Learning everyday new things, meeting and socializing with new people everyday, and for the last, being a creative painter(engineer). &lt;/p&gt;

</description>
    </item>
  </channel>
</rss>
