<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
    <channel>
        <title>
            Kamer&#39;s Personal Blog
        </title>
        <link>http://kamer.dev/</link>
        <description>Recent content on Kamer&#39;s Personal Blog</description>
        <generator>Hugo -- gohugo.io</generator>
        <language>en-us</language>
        
        
        <lastBuildDate>Sat, 02 May 2020 17:13:16 +0300</lastBuildDate>
        
        
        <atom:link href="http://kamer.dev/feed.xml" rel="self" type="application/rss+xml" />
        
        <item>
            <title>Java Optional Guide</title>
            <link>http://kamer.dev/java-optional-guide/</link>
            <pubDate>Sat, 02 May 2020 17:13:16 +0300</pubDate>
            
            <guid>http://kamer.dev/java-optional-guide/</guid>
            <description>&lt;div class=&#34;ox-hugo-toc toc&#34;&gt;
&lt;div&gt;&lt;/div&gt;
&lt;div class=&#34;heading&#34;&gt;Table of Contents&lt;/div&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;#1-dot-what-is-the-purpose-of-optional-class&#34;&gt;1. What is the purpose of Optional Class?&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-creating-optional-objects&#34;&gt;2. Creating Optional Objects&lt;/a&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-1-empty-optional--empty&#34;&gt;2.1 Empty Optional (&lt;code&gt;empty()&lt;/code&gt;)&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-2-optional-with-a-value--of&#34;&gt;2.2 Optional with a value (&lt;code&gt;of()&lt;/code&gt;)&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-3-optional-with-a-nullable-value--ofnullable&#34;&gt;2.3 Optional with a nullable value (&lt;code&gt;ofNullable()&lt;/code&gt;)&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#3-dot-checking-optionals&#34;&gt;3. Checking Optionals&lt;/a&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;#3-dot-1-checking-with-ispresent&#34;&gt;3.1 Checking with &lt;code&gt;isPresent();&lt;/code&gt;&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#3-dot-2-dot-checking-with-isempty&#34;&gt;3.2. Checking with &lt;code&gt;isEmpty();&lt;/code&gt;&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#4-dot-getting-value-from-optional&#34;&gt;4. Getting Value From Optional&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#5-dot-default-values-and-actions&#34;&gt;5. Default Values and Actions&lt;/a&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;#5-dot-1-get-a-default-value-with-orelse&#34;&gt;5.1 Get a default value with &lt;code&gt;orElse()&lt;/code&gt;&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#5-dot-2-throw-nosuchelementexception-with-orelsethrow&#34;&gt;5.2 Throw &lt;code&gt;NoSuchElementException&lt;/code&gt; with &lt;code&gt;orElseThrow()&lt;/code&gt;&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#5-dot-3-throw-any-exception-with-orelsethrow&#34;&gt;5.3 Throw any exception with &lt;code&gt;orElseThrow()&lt;/code&gt;&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#5-dot-4-get-a-default-value-with-a-supplier-with-orelseget&#34;&gt;5.4 Get a default value with a Supplier with &lt;code&gt;orElseGet()&lt;/code&gt;&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#5-dot-5-return-a-default-optional-with-or&#34;&gt;5.5 Return a default Optional with &lt;code&gt;or()&lt;/code&gt;&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#6-dot-conditional-actions-with-lambda-expressions&#34;&gt;6. Conditional Actions with Lambda Expressions&lt;/a&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;#6-dot-1-ifpresent&#34;&gt;6.1 &lt;code&gt;ifPresent()&lt;/code&gt;&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#6-dot-2-ifpresentorelse&#34;&gt;6.2 &lt;code&gt;ifPresentOrElse()&lt;/code&gt;&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#7-dot-filtering-the-value-with-filter&#34;&gt;7. Filtering the Value with &lt;code&gt;filter()&lt;/code&gt;&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#8-dot-mapping-values&#34;&gt;8. Mapping Values&lt;/a&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;#8-dot-1-map&#34;&gt;8.1 &lt;code&gt;map()&lt;/code&gt;&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#8-dot-2-flatmap&#34;&gt;8.2 &lt;code&gt;flatMap()&lt;/code&gt;&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#references&#34;&gt;References&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;
&lt;!--endtoc--&gt;
&lt;h2 id=&#34;1-dot-what-is-the-purpose-of-optional-class&#34;&gt;1. What is the purpose of Optional Class?&lt;/h2&gt;
&lt;p&gt;If you have been into coding for a while, you should have encountered Null Pointer Exception before. &lt;strong&gt;If you try to use a reference type that doesn&amp;rsquo;t point anything in the memory, you get &lt;code&gt;NullPointerException&lt;/code&gt;.&lt;/strong&gt; This sentence may be complicated, see the example below:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;String name &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;null&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;println&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;name&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;I declared a name variable that points to null and tried to print it. This will throw &lt;code&gt;NullPointerException&lt;/code&gt; since &lt;code&gt;name&lt;/code&gt; variable doesn&amp;rsquo;t show anywhere in the memory. Generally, you do not assign &lt;code&gt;null&lt;/code&gt; to a variable and print it. But there are many cases you may accidentally see this runtime exception. If you want to see all cases read &lt;a href=&#34;https://docs.oracle.com/javase/8/docs/api/java/lang/NullPointerException.html&#34;&gt;docs&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;Programmers are used to deal with this exceptions by null checking. (&lt;code&gt;if(name != null)&lt;/code&gt;). But this makes the code ugly and a programmer cannot be sure if there is a possibility of &lt;code&gt;null&lt;/code&gt; return from a method he/she called. Many of the programming languages have different methods to deal with Null Pointer Exception. Java Optional is one of them since Java 8. Optionals are objects that may have null or non-value inside. You can check an optional object whether the value is null or not and get the value if it is not. Returning an Optional from a method is simply saying &lt;strong&gt;&amp;ldquo;check the returning object since it can have null value.&amp;quot;&lt;/strong&gt;&lt;/p&gt;
&lt;h2 id=&#34;2-dot-creating-optional-objects&#34;&gt;2. Creating Optional Objects&lt;/h2&gt;
&lt;h3 id=&#34;2-dot-1-empty-optional--empty&#34;&gt;2.1 Empty Optional (&lt;code&gt;empty()&lt;/code&gt;)&lt;/h3&gt;
&lt;p&gt;Returning an empty optional is equivalent to returning null before Java 8. This can be done with the static &lt;code&gt;empty()&lt;/code&gt; method.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;Optional&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; optionalName &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; Optional&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;empty&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;block-note&#34;&gt;
  &lt;div&gt;&lt;/div&gt;
&lt;p&gt;Never check an optional if it is empty by comparing it &lt;code&gt;== Optional.empty();&lt;/code&gt; There are different methods to check an Optional.&lt;/p&gt;
&lt;/div&gt;
&lt;h3 id=&#34;2-dot-2-optional-with-a-value--of&#34;&gt;2.2 Optional with a value (&lt;code&gt;of()&lt;/code&gt;)&lt;/h3&gt;
&lt;p&gt;Returning an optional with a value inside it is equivalent to returning the object itself before Java 8.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;Optional&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; optionalString &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; Optional&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;of&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Kamer&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;block-note&#34;&gt;
  &lt;div&gt;&lt;/div&gt;
&lt;p&gt;&lt;code&gt;of()&lt;/code&gt; method is not nullable. If you pass null, you will get &lt;code&gt;NullPointerException&lt;/code&gt;.&lt;/p&gt;
&lt;/div&gt;
&lt;h3 id=&#34;2-dot-3-optional-with-a-nullable-value--ofnullable&#34;&gt;2.3 Optional with a nullable value (&lt;code&gt;ofNullable()&lt;/code&gt;)&lt;/h3&gt;
&lt;p&gt;This method is for nullable values. You can pass any value whether it is null or&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;Optional&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; optionalString &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; Optional&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;ofNullable&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;null&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

Optional&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; optionalString &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; Optional&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;ofNullable&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Kamer&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;3-dot-checking-optionals&#34;&gt;3. Checking Optionals&lt;/h2&gt;
&lt;h3 id=&#34;3-dot-1-checking-with-ispresent&#34;&gt;3.1 Checking with &lt;code&gt;isPresent();&lt;/code&gt;&lt;/h3&gt;
&lt;p&gt;It does what the name suggests. Returns boolean value.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;if&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;optionalName&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;isPresent&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()){&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;...&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;...&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;3-dot-2-dot-checking-with-isempty&#34;&gt;3.2. Checking with &lt;code&gt;isEmpty();&lt;/code&gt;&lt;/h3&gt;
&lt;p&gt;Opposite of &lt;code&gt;isPresent()&lt;/code&gt;. This method can be used since Java 11.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;if&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;optionalName&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;isEmpty&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()){&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;...&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;...&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;4-dot-getting-value-from-optional&#34;&gt;4. Getting Value From Optional&lt;/h2&gt;
&lt;p&gt;As you see, Optional is a container that holds some value.
After checking an Optional with the methods above, you can get the value with &lt;code&gt;get()&lt;/code&gt; method.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;if&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;optionalUser&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;isPresent&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()){&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; optionalUser&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;get&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;else&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;throw&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; UserNotFoundException&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;5-dot-default-values-and-actions&#34;&gt;5. Default Values and Actions&lt;/h2&gt;
&lt;p&gt;Sometimes we may return a default value, produce a value or do some actions in case of any empty Optional.&lt;/p&gt;
&lt;h3 id=&#34;5-dot-1-get-a-default-value-with-orelse&#34;&gt;5.1 Get a default value with &lt;code&gt;orElse()&lt;/code&gt;&lt;/h3&gt;
&lt;p&gt;It returns the value if optional has a value and returns the default value if not so.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;String userName &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; optionalUsername&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;orElse&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;admin&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;5-dot-2-throw-nosuchelementexception-with-orelsethrow&#34;&gt;5.2 Throw &lt;code&gt;NoSuchElementException&lt;/code&gt; with &lt;code&gt;orElseThrow()&lt;/code&gt;&lt;/h3&gt;
&lt;p&gt;Title is clear. This method is available since Java 10.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#666&#34;&gt;...&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; optionalUsername&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;orElseThrow&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;5-dot-3-throw-any-exception-with-orelsethrow&#34;&gt;5.3 Throw any exception with &lt;code&gt;orElseThrow()&lt;/code&gt;&lt;/h3&gt;
&lt;p&gt;You can throw any exception you want if Optional is empty.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#666&#34;&gt;...&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; optionalUsername&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;orElseThrow&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;UserNotFoundException&lt;span style=&#34;color:#666&#34;&gt;::&lt;/span&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#666&#34;&gt;...&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; optionalUsername&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;orElseThrow&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;-&amp;gt;&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; UserNotFoundException&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;...&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;5-dot-4-get-a-default-value-with-a-supplier-with-orelseget&#34;&gt;5.4 Get a default value with a Supplier with &lt;code&gt;orElseGet()&lt;/code&gt;&lt;/h3&gt;
&lt;p&gt;Supplier is the function that takes no value and produces a result. See &lt;code&gt;java.util.function.Supplier&lt;/code&gt;.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#666&#34;&gt;...&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; optionalUsername&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;orElseGet&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;::&lt;/span&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;5-dot-5-return-a-default-optional-with-or&#34;&gt;5.5 Return a default Optional with &lt;code&gt;or()&lt;/code&gt;&lt;/h3&gt;
&lt;p&gt;This function also takes Supplier function as parameter. &lt;code&gt;or()&lt;/code&gt; returns the Optional or the default Optional that supplier function produces. This method is available since Java 9.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#666&#34;&gt;...&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; optionalUsername&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;or&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;-&amp;gt;&lt;/span&gt; Optional&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;of&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;admin&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;6-dot-conditional-actions-with-lambda-expressions&#34;&gt;6. Conditional Actions with Lambda Expressions&lt;/h2&gt;
&lt;h3 id=&#34;6-dot-1-ifpresent&#34;&gt;6.1 &lt;code&gt;ifPresent()&lt;/code&gt;&lt;/h3&gt;
&lt;p&gt;This method takes &lt;code&gt;Consumer&amp;lt;? super T&amp;gt;&lt;/code&gt; as parameter. See &lt;code&gt;java.util.function.Consumer&lt;/code&gt;.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;optionalUsername&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;ifPresent&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;::&lt;/span&gt;println&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;6-dot-2-ifpresentorelse&#34;&gt;6.2 &lt;code&gt;ifPresentOrElse()&lt;/code&gt;&lt;/h3&gt;
&lt;p&gt;This method takes two parameters. &lt;code&gt;Consumer&amp;lt;? super T&amp;gt;&lt;/code&gt; and &lt;code&gt;Runnable&lt;/code&gt;. It is available since Java 9.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;optionalUsername&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;ifPresentOrElse&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;
    System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;::&lt;/span&gt;println&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;-&amp;gt;&lt;/span&gt; System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;println&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;No Username.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;7-dot-filtering-the-value-with-filter&#34;&gt;7. Filtering the Value with &lt;code&gt;filter()&lt;/code&gt;&lt;/h2&gt;
&lt;p&gt;This method takes a predicate and an Optional is returned based on the result of the predicate. If predicate returns true Optional has the value.  Otherwise, empty Optional is returned.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#666&#34;&gt;...&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; optionalUsername&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;filter&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;::&lt;/span&gt;isBlank&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;8-dot-mapping-values&#34;&gt;8. Mapping Values&lt;/h2&gt;
&lt;h3 id=&#34;8-dot-1-map&#34;&gt;8.1 &lt;code&gt;map()&lt;/code&gt;&lt;/h3&gt;
&lt;p&gt;It returns an Optional. If Optional is not  empty, it has the state after mapping function is applied.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;Optional&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; optionalUsername &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; optionalResult&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;map&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;::&lt;/span&gt;trim&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;8-dot-2-flatmap&#34;&gt;8.2 &lt;code&gt;flatMap()&lt;/code&gt;&lt;/h3&gt;
&lt;p&gt;It&amp;rsquo;s like &lt;code&gt;map()&lt;/code&gt; but this time the result is flattened. This means if there is more than one level nested Optional, it converts it to one-level. See the example.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;Optional&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; optionalUsername &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; Optional&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;ofNullable&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Kamer&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

Optional&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;Object&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; mapOptional
    &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; optionalUsername&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;map&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;username &lt;span style=&#34;color:#666&#34;&gt;-&amp;gt;&lt;/span&gt; Optional&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;of&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;username&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;toLowerCase&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;This &lt;code&gt;map()&lt;/code&gt; return will return the String inside an Optional which is inside another Optional. &lt;code&gt;Optional&amp;lt;Optional&amp;lt;String&amp;gt;&amp;gt;&lt;/code&gt;&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;Optional&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; optionalUsername &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; Optional&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;ofNullable&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Kamer&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

Optional&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;Object&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; flatMapOptional
    &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; optionalUsername&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;flatMap&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;s &lt;span style=&#34;color:#666&#34;&gt;-&amp;gt;&lt;/span&gt; Optional&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;of&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;s&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;toLowerCase&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;But &lt;code&gt;flatMap()&lt;/code&gt; flattens the result and it returns just &lt;code&gt;Optional&amp;lt;String&amp;gt;&lt;/code&gt;&lt;/p&gt;
&lt;h2 id=&#34;references&#34;&gt;References&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://docs.oracle.com/en/java/javase/11/docs/api/java.base/java/util/Optional.html&#34;&gt;https://docs.oracle.com/en/java/javase/11/docs/api/java.base/java/util/Optional.html&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.oracle.com/technical-resources/articles/java/java8-optional.html&#34;&gt;https://www.oracle.com/technical-resources/articles/java/java8-optional.html&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://docs.oracle.com/javase/8/docs/api/java/lang/NullPointerException.html&#34;&gt;https://docs.oracle.com/javase/8/docs/api/java/lang/NullPointerException.html&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
</description>
        </item>
        
        <item>
            <title>Spring Boot User Registration and Login</title>
            <link>http://kamer.dev/spring-boot-user-registration-and-login/</link>
            <pubDate>Sat, 21 Mar 2020 20:30:00 +0000</pubDate>
            
            <guid>http://kamer.dev/spring-boot-user-registration-and-login/</guid>
            <description>&lt;div class=&#34;block-plain&#34;&gt;
  &lt;div&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;Update 2020/05/02:&lt;/strong&gt; I removed useless &lt;code&gt;csrf().disabled()&lt;/code&gt; config and &lt;code&gt;CustomAuthenticatorProvider&lt;/code&gt; class. Also, I changed &lt;code&gt;Optional&lt;/code&gt; logic and used &lt;code&gt;orElseThrow()&lt;/code&gt; method. Thanks &lt;a href=&#34;https://twitter.com/gokcensedat&#34;&gt;@gokcensedat&lt;/a&gt; and &lt;a href=&#34;https://twitter.com/utkuozdemir&#34;&gt;@utkuozdemir&lt;/a&gt; for their valuable comments.&lt;/p&gt;
&lt;/div&gt;
&lt;p&gt;Hello! In this article, I’ll explain how to register users to your application, how to send confirmation mail and handle user logins. My main resource will be official docs and you can access Github repository at the end of the article. I will not explain exception handling parts since our main subject is different.&lt;/p&gt;
&lt;div class=&#34;ox-hugo-toc toc&#34;&gt;
&lt;div&gt;&lt;/div&gt;
&lt;div class=&#34;heading&#34;&gt;Table of Contents&lt;/div&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;#requirements&#34;&gt;Requirements&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#1-dot-creating-a-project-with-spring-initialzr&#34;&gt;1. Creating a project with Spring Initialzr&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-create-user-entity&#34;&gt;2. Create User entity&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#3-dot-create-userservice&#34;&gt;3. Create UserService&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#4-dot-create-confirmationtoken-class&#34;&gt;4. Create ConfirmationToken class&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#5-dot-user-registration-process&#34;&gt;5. User registration process&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#6-dot-create-confirmation-methods&#34;&gt;6. Create confirmation methods&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#7-dot-spring-mail-config&#34;&gt;7. Spring Mail config&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#8-dot-create-emailservice&#34;&gt;8. Create EmailService&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#9-dot-spring-security-configuration&#34;&gt;9. Spring Security Configuration&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#10-dot-create-controller-and-pages&#34;&gt;10. Create controller and pages&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#conclusion&#34;&gt;Conclusion&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;
&lt;!--endtoc--&gt;
&lt;h2 id=&#34;requirements&#34;&gt;Requirements&lt;/h2&gt;
&lt;p&gt;You need to know Java and must have developed at least one Spring project to understand this article.&lt;/p&gt;
&lt;h2 id=&#34;1-dot-creating-a-project-with-spring-initialzr&#34;&gt;1. Creating a project with Spring Initialzr&lt;/h2&gt;
&lt;p&gt;Create a project with &lt;strong&gt;Spring Web, Lombok, Thymeleaf, Spring Security, Java Mail Sender, H2&lt;/strong&gt; and &lt;strong&gt;Spring Data JPA&lt;/strong&gt; dependencies with Spring Initialzr. You can use your IDE’s plugin or &lt;a href=&#34;https://start.spring.io/&#34;&gt;https://start.spring.io/&lt;/a&gt;.&lt;/p&gt;
&lt;h2 id=&#34;2-dot-create-user-entity&#34;&gt;2. Create User entity&lt;/h2&gt;
&lt;p&gt;Create an &lt;code&gt;entity&lt;/code&gt; package and &lt;code&gt;UserRole&lt;/code&gt; enum inside the package. We will add ADMIN and USER values for now but you can add more according to your needs.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;enum&lt;/span&gt; UserRole &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    ADMIN&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; USER
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Now, create a &lt;code&gt;User&lt;/code&gt; class. This class has to implement &lt;code&gt;UserDetails&lt;/code&gt; interface. This interface has basic user methods. You can see an implementation in &lt;code&gt;org.springframework.security.core.userdetails.User&lt;/code&gt; class. You can also extend this class and add your own fields. I will not extend this class because I want to show the whole process. So, let’s create a few fields, implement the required methods and fill them.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Getter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Setter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Builder&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@EqualsAndHashCode&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@NoArgsConstructor&lt;/span&gt;&lt;span style=&#34;&#34;&gt;`&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@AllArgsConstructor&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Entity&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;name &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Users&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;User&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;implements&lt;/span&gt; UserDetails &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Id&lt;/span&gt;
    &lt;span style=&#34;color:#a2f&#34;&gt;@GeneratedValue&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;strategy &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; GenerationType&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;IDENTITY&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Long id&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String name&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String surname&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String email&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String password&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Builder.Default&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; UserRole userRole &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; UserRole&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;USER&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Builder.Default&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Boolean locked &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;false&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Builder.Default&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Boolean enabled &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;false&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; Collection&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;?&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;extends&lt;/span&gt; GrantedAuthority&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;getAuthorities&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; SimpleGrantedAuthority simpleGrantedAuthority &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; SimpleGrantedAuthority&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;userRole&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;name&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;());&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; Collections&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;singletonList&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;simpleGrantedAuthority&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; String &lt;span style=&#34;color:#00a000&#34;&gt;getPassword&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; password&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; String &lt;span style=&#34;color:#00a000&#34;&gt;getUsername&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; email&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;boolean&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;isAccountNonExpired&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;true&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;boolean&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;isAccountNonLocked&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;!&lt;/span&gt;locked&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;boolean&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;isCredentialsNonExpired&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;true&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;boolean&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;isEnabled&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; enabled&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;We will not use &lt;code&gt;expired&lt;/code&gt; field for this example, so always return &lt;code&gt;true&lt;/code&gt; and we will also use &lt;code&gt;email&lt;/code&gt; instead of &lt;code&gt;username&lt;/code&gt;. So return &lt;code&gt;email&lt;/code&gt; from &lt;code&gt;getUsername()&lt;/code&gt; method. You can deduce others from the names.&lt;/p&gt;
&lt;h2 id=&#34;3-dot-create-userservice&#34;&gt;3. Create UserService&lt;/h2&gt;
&lt;p&gt;Create a &lt;code&gt;user&lt;/code&gt; package and &lt;code&gt;UserService&lt;/code&gt; class inside the package. Then, implement &lt;code&gt;UserDetailsService&lt;/code&gt; which requires you to implement &lt;code&gt;loadByUsername()&lt;/code&gt;. But here’s important, we will use &lt;code&gt;email&lt;/code&gt; instead of &lt;code&gt;username&lt;/code&gt;. So, this method will take email as parameter and return the user. To achieve this, we need to interact with database, so we need a repository. Create a &lt;code&gt;UserRepository&lt;/code&gt; interface inside the same package and add &lt;code&gt;findByEmail()&lt;/code&gt; method.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;interface&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;UserRepository&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;extends&lt;/span&gt; CrudRepository&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;User&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; Long&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    Optional&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;User&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;findByEmail&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;String email&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Now, turn back to &lt;code&gt;UserService&lt;/code&gt;, add &lt;code&gt;UserRepository&lt;/code&gt; as a field and complete the method. &lt;code&gt;UserService&lt;/code&gt; will be as below.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Service&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@AllArgsConstructor&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;UserService&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;implements&lt;/span&gt; UserDetailsService &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; UserRepository userRepository&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; UserDetails &lt;span style=&#34;color:#00a000&#34;&gt;loadUserByUsername&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;String email&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;throws&lt;/span&gt; UsernameNotFoundException &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; Optional&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;User&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; optionalUser &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; userRepository&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;findByEmail&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;email&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;if&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;optionalUser&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;isPresent&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;())&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; optionalUser&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;get&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
	&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;else&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;throw&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; UsernameNotFoundException&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;MessageFormat&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;format&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;User with email {0} cannot be found.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; email&lt;span style=&#34;color:#666&#34;&gt;));&lt;/span&gt;
	&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;4-dot-create-confirmationtoken-class&#34;&gt;4. Create ConfirmationToken class&lt;/h2&gt;
&lt;p&gt;We will create a token and a unique link for every user registration and send them with email. Create a &lt;code&gt;ConfirmationToken&lt;/code&gt; class inside &lt;code&gt;user&lt;/code&gt; package and add these fields:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Entity&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Getter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Setter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@AllArgsConstructor&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@NoArgsConstructor&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;ConfirmationToken&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Id&lt;/span&gt;
    &lt;span style=&#34;color:#a2f&#34;&gt;@GeneratedValue&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;strategy &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; GenerationType&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;IDENTITY&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Long id&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String confirmationToken&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; LocalDate createdDate&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@OneToOne&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;targetEntity &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; User&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;class&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; fetch &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; FetchType&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;EAGER&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f&#34;&gt;@JoinColumn&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;nullable &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;false&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; name &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;user_id&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; User user&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    ConfirmationToken&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;User user&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;this&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;user&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; user&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;this&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;createdDate&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; LocalDate&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;now&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;this&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;confirmationToken&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; UUID&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;randomUUID&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;().&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;toString&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;This is a simple entity as you see. Since every user will have a single token, we create a &lt;strong&gt;OneToOne&lt;/strong&gt; relation. &lt;code&gt;createdDate&lt;/code&gt; field will be used to check if the token is expired or not.&lt;/p&gt;
&lt;h2 id=&#34;5-dot-user-registration-process&#34;&gt;5. User registration process&lt;/h2&gt;
&lt;p&gt;I want you to experience a real-like development process instead of writing all the methods and classes. So let’s think of the process step by step.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;Take user information with the registration form.&lt;/li&gt;
&lt;li&gt;Encode the password with &lt;code&gt;BCryptPasswordEncoder&lt;/code&gt; and create the user with &lt;code&gt;enabled=false&lt;/code&gt; value as we set default in &lt;code&gt;User&lt;/code&gt; class.&lt;/li&gt;
&lt;li&gt;Create a &lt;code&gt;ConfirmationToken&lt;/code&gt; and assign this token to the user.&lt;/li&gt;
&lt;li&gt;Create a unique url with this token and send it via email.&lt;/li&gt;
&lt;li&gt;When the user clicks the link change &lt;code&gt;enabled&lt;/code&gt; field to &lt;code&gt;true&lt;/code&gt; for that user.&lt;/li&gt;
&lt;li&gt;Delete the token.&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;So, we will create &lt;code&gt;ConfirmationTokenRepository&lt;/code&gt; and &lt;code&gt;ConfirmationTokenService&lt;/code&gt; before &lt;code&gt;signUpUser()&lt;/code&gt; method. Because we need this method in signing-up process.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Repository&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;interface&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;ConfirmationTokenRepository&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;extends&lt;/span&gt; CrudRepository&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;ConfirmationToken&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; Long&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Service&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@AllArgsConstructor&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;ConfirmationTokenService&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; ConfirmationTokenRepository confirmationTokenRepository&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;saveConfirmationToken&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;ConfirmationToken confirmationToken&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	confirmationTokenRepository&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;save&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;confirmationToken&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Now, go to &lt;code&gt;UserService&lt;/code&gt; class and create &lt;code&gt;signUpUser()&lt;/code&gt; method.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;signUpUser&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;User user&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; String encryptedPassword &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; bCryptPasswordEncoder&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;encode&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;user&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;getPassword&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;());&lt;/span&gt;

    user&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;setPassword&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;encryptedPassword&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; User createdUser &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; userRepository&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;save&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;user&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; ConfirmationToken confirmationToken &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; ConfirmationToken&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;user&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

    confirmationTokenService&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;saveConfirmationToken&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;confirmationToken&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;6-dot-create-confirmation-methods&#34;&gt;6. Create confirmation methods&lt;/h2&gt;
&lt;p&gt;We have user registration process. Now, we need confirmation process. First of all, create the method that will delete token after confirmation.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;deleteConfirmationToken&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;Long id&lt;span style=&#34;color:#666&#34;&gt;){&lt;/span&gt;

    confirmationTokenRepository&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;deleteById&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;id&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Then, create &lt;code&gt;confirmUser()&lt;/code&gt; method.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;confirmUser&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;ConfirmationToken confirmationToken&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; User user &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; confirmationToken&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;getUser&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;

    user&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;setEnabled&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;true&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

    userRepository&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;save&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;user&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

    confirmationTokenService&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;deleteConfirmationToken&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;confirmationToken&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;getId&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;());&lt;/span&gt;

&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;7-dot-spring-mail-config&#34;&gt;7. Spring Mail config&lt;/h2&gt;
&lt;p&gt;I use &lt;strong&gt;application.yml&lt;/strong&gt; instead of &lt;strong&gt;application.properties&lt;/strong&gt;. (see &lt;a href=&#34;https://docs.spring.io/spring-boot/docs/current/reference/html/spring-boot-features.html#boot-features-external-config-yaml&#34;&gt;this&lt;/a&gt;) Here’s the Spring Mail config for Gmail. If you use 2-factor, you have to create a password for application. (see &lt;a href=&#34;https://support.google.com/mail/answer/185833?hl=en&#34;&gt;this&lt;/a&gt;)&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-yaml&#34; data-lang=&#34;yaml&#34;&gt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;spring&lt;/span&gt;:&lt;span style=&#34;color:#bbb&#34;&gt;
&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;  &lt;/span&gt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;mail&lt;/span&gt;:&lt;span style=&#34;color:#bbb&#34;&gt;
&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;    &lt;/span&gt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;host&lt;/span&gt;:&lt;span style=&#34;color:#bbb&#34;&gt; &lt;/span&gt;smtp.gmail.com&lt;span style=&#34;color:#bbb&#34;&gt;
&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;    &lt;/span&gt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;port&lt;/span&gt;:&lt;span style=&#34;color:#bbb&#34;&gt; &lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;587&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;
&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;    &lt;/span&gt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;username&lt;/span&gt;:&lt;span style=&#34;color:#bbb&#34;&gt; &lt;/span&gt;&amp;lt;MAIL_ADDRESS&amp;gt;&lt;span style=&#34;color:#bbb&#34;&gt;
&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;    &lt;/span&gt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;password&lt;/span&gt;:&lt;span style=&#34;color:#bbb&#34;&gt; &lt;/span&gt;&amp;lt;PASSWORD&amp;gt;&lt;span style=&#34;color:#bbb&#34;&gt;
&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;    &lt;/span&gt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;properties&lt;/span&gt;:&lt;span style=&#34;color:#bbb&#34;&gt;
&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;      &lt;/span&gt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;mail&lt;/span&gt;:&lt;span style=&#34;color:#bbb&#34;&gt;
&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;	&lt;/span&gt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;smtp&lt;/span&gt;:&lt;span style=&#34;color:#bbb&#34;&gt;
&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;	  &lt;/span&gt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;auth&lt;/span&gt;:&lt;span style=&#34;color:#bbb&#34;&gt; &lt;/span&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;true&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;
&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;	  &lt;/span&gt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;starttls&lt;/span&gt;:&lt;span style=&#34;color:#bbb&#34;&gt;
&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;	    &lt;/span&gt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;enable&lt;/span&gt;:&lt;span style=&#34;color:#bbb&#34;&gt; &lt;/span&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;true&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;
&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;	  &lt;/span&gt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;connectiontimeout&lt;/span&gt;:&lt;span style=&#34;color:#bbb&#34;&gt; &lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;5000&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;
&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;	  &lt;/span&gt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;timeout&lt;/span&gt;:&lt;span style=&#34;color:#bbb&#34;&gt; &lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;3000&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;
&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;	  &lt;/span&gt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;writetimeout&lt;/span&gt;:&lt;span style=&#34;color:#bbb&#34;&gt; &lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;5000&lt;/span&gt;&lt;span style=&#34;color:#bbb&#34;&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;8-dot-create-emailservice&#34;&gt;8. Create EmailService&lt;/h2&gt;
&lt;p&gt;Create an &lt;code&gt;EmailService&lt;/code&gt; class inside user package and create &lt;code&gt;sendEmail()&lt;/code&gt; method inside it.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Service&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@AllArgsConstructor&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;EmailSenderService&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; JavaMailSender javaMailSender&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Async&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;sendEmail&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;SimpleMailMessage email&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	javaMailSender&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;send&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;email&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Now, create the &lt;code&gt;sendConfirmationMail()&lt;/code&gt; inside &lt;strong&gt;UserService&lt;/strong&gt;.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;sendConfirmationMail&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;String userMail&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; String token&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; SimpleMailMessage mailMessage &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; SimpleMailMessage&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
    mailMessage&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;setTo&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;userMail&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    mailMessage&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;setSubject&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Mail Confirmation Link!&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    mailMessage&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;setFrom&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;&amp;lt;MAIL&amp;gt;&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    mailMessage&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;setText&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;
	    &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Thank you for registering. Please click on the below link to activate your account.&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;http://localhost:8080/sign-up/confirm?token=&amp;#34;&lt;/span&gt;
		    &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; token&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

    emailSenderService&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;sendEmail&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;mailMessage&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;9-dot-spring-security-configuration&#34;&gt;9. Spring Security Configuration&lt;/h2&gt;
&lt;p&gt;We created the whole process related to Spring Security. Now we will set configuration for all. Create &lt;code&gt;WebSecurityConfig&lt;/code&gt; and &lt;code&gt;WebConfig&lt;/code&gt; inside &lt;strong&gt;config&lt;/strong&gt; package.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Configuration&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@AllArgsConstructor&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;WebSecurityConfig&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;extends&lt;/span&gt; WebSecurityConfigurerAdapter &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; UserService userService&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; BCryptPasswordEncoder bCryptPasswordEncoder&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;protected&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;configure&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;HttpSecurity http&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;throws&lt;/span&gt; Exception &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	http
	    &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;authorizeRequests&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt;
	    &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;antMatchers&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/sign-up/**&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/sign-in/**&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
	    &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;permitAll&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt;
	    &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;anyRequest&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt;
	    &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;authenticated&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt;
	    &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;and&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt;
	    &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;formLogin&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt;
	    &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;loginPage&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/sign-in&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
	    &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;permitAll&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Autowired&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;configureGlobal&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;AuthenticationManagerBuilder auth&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;throws&lt;/span&gt; Exception &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	auth&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;userDetailsService&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;userService&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
		&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;passwordEncoder&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;bCryptPasswordEncoder&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Configuration&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;WebConfig&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

      &lt;span style=&#34;color:#a2f&#34;&gt;@Bean&lt;/span&gt;
      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; BCryptPasswordEncoder &lt;span style=&#34;color:#00a000&#34;&gt;bCryptPasswordEncoder&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; BCryptPasswordEncoder&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
      &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;These configuration classes simply set sign-in and sign-up pages, set encoder and authentication provider. You can learn them with &lt;a href=&#34;https://spring.io/guides/topicals/spring-security-architecture&#34;&gt;this great article&lt;/a&gt;.&lt;/p&gt;
&lt;h2 id=&#34;10-dot-create-controller-and-pages&#34;&gt;10. Create controller and pages&lt;/h2&gt;
&lt;p&gt;We have all we need for an application except HTML pages. We will create those and make them accessible with controller.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&lt;span style=&#34;color:#080&#34;&gt;&amp;lt;!DOCTYPE html&amp;gt;&lt;/span&gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;html&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;xmlns:th&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;http://www.thymeleaf.org&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;lang&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;en&amp;#34;&lt;/span&gt;&amp;gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;head&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;title&lt;/span&gt;&amp;gt;Spring Boot User Authentication&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;title&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;head&lt;/span&gt;&amp;gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;body&lt;/span&gt;&amp;gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;form&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;role&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;form&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:action&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;@{/sign-in}&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:method&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;post&amp;#34;&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;label&lt;/span&gt;&amp;gt;Username&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;label&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;text&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;id&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;username&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;name&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;username&amp;#34;&lt;/span&gt;&amp;gt;

    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;label&lt;/span&gt;&amp;gt;Password&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;label&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;password&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;id&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;password&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;name&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;password&amp;#34;&lt;/span&gt;&amp;gt;

    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;submit&amp;#34;&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;form&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;body&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;html&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&lt;span style=&#34;color:#080&#34;&gt;&amp;lt;!DOCTYPE html&amp;gt;&lt;/span&gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;html&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;xmlns:th&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;http://www.thymeleaf.org&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;lang&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;en&amp;#34;&lt;/span&gt;&amp;gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;head&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;title&lt;/span&gt;&amp;gt;Spring Boot User Authentication&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;title&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;head&lt;/span&gt;&amp;gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;body&lt;/span&gt;&amp;gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;form&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;role&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;form&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:action&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;@{/sign-up}&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:method&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;post&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:object&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${user}&amp;#34;&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;label&lt;/span&gt;&amp;gt;Name&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;label&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;text&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;id&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;name&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;name&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;name&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:field&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;*{name}&amp;#34;&lt;/span&gt;&amp;gt;

    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;label&lt;/span&gt;&amp;gt;Surname&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;label&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;text&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;id&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;surname&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;name&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;surname&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:field&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;*{surname}&amp;#34;&lt;/span&gt;&amp;gt;

    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;label&lt;/span&gt;&amp;gt;Email&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;label&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;text&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;id&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;email&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;name&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;email&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:field&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;*{email}&amp;#34;&lt;/span&gt;&amp;gt;

    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;label&lt;/span&gt;&amp;gt;Password&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;label&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;password&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;id&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;password&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;name&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;password&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:field&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;*{password}&amp;#34;&lt;/span&gt;&amp;gt;

    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;submit&amp;#34;&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;form&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;body&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;html&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Controller&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@AllArgsConstructor&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;UserController&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; UserService userService&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; ConfirmationTokenService confirmationTokenService&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@GetMapping&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/sign-in&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    String &lt;span style=&#34;color:#00a000&#34;&gt;signIn&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;sign-in&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@GetMapping&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/sign-up&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    String &lt;span style=&#34;color:#00a000&#34;&gt;signUp&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;sign-up&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@PostMapping&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/sign-up&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    String &lt;span style=&#34;color:#00a000&#34;&gt;signUp&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;User user&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	userService&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;signUpUser&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;user&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;redirect:/sign-in&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@GetMapping&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/confirm&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    String &lt;span style=&#34;color:#00a000&#34;&gt;confirmMail&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@RequestParam&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;token&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; String token&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	Optional&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;ConfirmationToken&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; optionalConfirmationToken &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; confirmationTokenService&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;findConfirmationTokenByToken&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;token&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	optionalConfirmationToken&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;ifPresent&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;userService&lt;span style=&#34;color:#666&#34;&gt;::&lt;/span&gt;confirmUser&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/sign-in&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;conclusion&#34;&gt;Conclusion&lt;/h2&gt;
&lt;p&gt;If you have followed the article properly, you can go to &lt;a href=&#34;http://localhost:8080/sign-up&#34;&gt;http://localhost:8080/sign-up&lt;/a&gt; to sign up. But do not forget, it is not a production ready application since we didn’t create validations(&lt;strong&gt;including token expiration&lt;/strong&gt;) and provide proper exception handling. If you want to learn about validations you can see &lt;a href=&#34;https://medium.com/@kamer.dev/validations-in-spring-boot-4f15598c3d6a&#34;&gt;https://medium.com/@kamer.dev/validations-in-spring-boot-4f15598c3d6a&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Github Repository:&lt;/strong&gt; &lt;a href=&#34;https://github.com/kamer/spring-boot-user-registration&#34;&gt;https://github.com/kamer/spring-boot-user-registration&lt;/a&gt;&lt;/p&gt;
</description>
        </item>
        
        <item>
            <title>How to debug your code in IntelliJ</title>
            <link>http://kamer.dev/how-to-debug-your-code-in-intellij/</link>
            <pubDate>Sat, 21 Mar 2020 17:05:00 +0000</pubDate>
            
            <guid>http://kamer.dev/how-to-debug-your-code-in-intellij/</guid>
            <description>&lt;p&gt;Debugging code can be difficult sometimes for newbies but it is not as difficult as it seems. In this post I will explain IntelliJ Debugging interface starting from the basics. I will not cover all the features. They are the ones that I use most.&lt;/p&gt;
&lt;div class=&#34;ox-hugo-toc toc&#34;&gt;
&lt;div&gt;&lt;/div&gt;
&lt;div class=&#34;heading&#34;&gt;Table of Contents&lt;/div&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;#requirements&#34;&gt;Requirements&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#my-motivation&#34;&gt;My Motivation&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#1-dot-setting-breakpoints&#34;&gt;1. Setting breakpoints&lt;/a&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;#1-dot-1-line-breakpoint&#34;&gt;1.1 Line Breakpoint&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#1-dot-2-method-breakpoint&#34;&gt;1.2 Method Breakpoint&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#1-dot-3-dot-field-watchpoint&#34;&gt;1.3. Field Watchpoint&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#1-dot-4-dot-exception-breakpoint&#34;&gt;1.4. Exception Breakpoint&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#1-dot-5-conditional-breakpoint&#34;&gt;1.5 Conditional Breakpoint&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-debug-window&#34;&gt;2. Debug Window&lt;/a&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-1-step-functions&#34;&gt;2.1 Step Functions&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-2-debugger-control-buttons&#34;&gt;2.2 Debugger Control Buttons&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-3-tracing-variables&#34;&gt;2.3 Tracing Variables&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-4-evaluating-expressions-and-setting-values-manually&#34;&gt;2.4 Evaluating Expressions and Setting Values Manually&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;
&lt;!--endtoc--&gt;
&lt;h2 id=&#34;requirements&#34;&gt;Requirements&lt;/h2&gt;
&lt;p&gt;There is no requirements for this.&lt;/p&gt;
&lt;h2 id=&#34;my-motivation&#34;&gt;My Motivation&lt;/h2&gt;
&lt;p&gt;I used to debug my code with &lt;code&gt;System.out.println();&lt;/code&gt; and it was OK for me. I didn&amp;rsquo;t have any complaints about it because I thought using debugging interface does the same thing with a fancy label. Last year I did an internship and one day, I forgot to remove &lt;code&gt;System.out.println();&lt;/code&gt; in my pull request. It was rejected in the code review and my mentor taught me the basics of debugging. It was a good experience for me although I had difficulty giving up my bad habit. Now, I&amp;rsquo;ve completely quitted &lt;code&gt;System.out.println();&lt;/code&gt; and explored some much about debugging. It&amp;rsquo;s time to share what I&amp;rsquo;ve learnt.&lt;/p&gt;
&lt;h2 id=&#34;1-dot-setting-breakpoints&#34;&gt;1. Setting breakpoints&lt;/h2&gt;
&lt;p&gt;The most important part of debugging is &lt;strong&gt;breakpoints&lt;/strong&gt;. Breakpoint is the place where you want to pause your program for debugging purposes.
When your program pauses at somewhere, you can see many properties of your current scope. There are four types of breakpoints.&lt;/p&gt;
&lt;h3 id=&#34;1-dot-1-line-breakpoint&#34;&gt;1.1 Line Breakpoint&lt;/h3&gt;
&lt;p&gt;This is the most used one of all. It pauses your program before the marked line is executed. Just click on the gutter near line number to set your breakpoint. There is only one requirement, the line should be executable.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/how-to-debug-your-code-in-intellij/1-set-line-breakpoint.jpg&#34;/&gt;
&lt;/figure&gt;

&lt;h3 id=&#34;1-dot-2-method-breakpoint&#34;&gt;1.2 Method Breakpoint&lt;/h3&gt;
&lt;p&gt;You can pause the program to see the entering and exiting values of a method. This breakpoint pauses the program twice. Click the gutter where the method is declared. You can also click the class declaration to set breakpoint to the constructor.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/how-to-debug-your-code-in-intellij/2-set-method-breakpoint.jpg&#34;/&gt;
&lt;/figure&gt;

&lt;h3 id=&#34;1-dot-3-dot-field-watchpoint&#34;&gt;1.3. Field Watchpoint&lt;/h3&gt;
&lt;p&gt;This is used for tracking all interactions for a field. Set the breakpoint on the field declaration. Your program will pause every time you interact with that field.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/how-to-debug-your-code-in-intellij/3-set-field-watchpoint.jpg&#34;/&gt;
&lt;/figure&gt;

&lt;h3 id=&#34;1-dot-4-dot-exception-breakpoint&#34;&gt;1.4. Exception Breakpoint&lt;/h3&gt;
&lt;p&gt;When you set an &lt;strong&gt;exception breakpoint&lt;/strong&gt;, your program pauses whenever an exception is thrown. It&amp;rsquo;s global and not dependent on your source code. So, you don&amp;rsquo;t set it with gutter clicks like previous ones. Open &lt;strong&gt;View Breakpoints&lt;/strong&gt; window with &lt;strong&gt;Ctrl+Shift+F8&lt;/strong&gt; or &lt;strong&gt;View Breakpoints&lt;/strong&gt; button in Debug window. You can choose &lt;strong&gt;Any Exception&lt;/strong&gt; under &lt;strong&gt;Java Exception Breakpoints&lt;/strong&gt; or add a specific exception with the &lt;strong&gt;+&lt;/strong&gt; icon or &lt;strong&gt;Alt+Insert&lt;/strong&gt;.&lt;/p&gt;
&lt;div class=&#34;block-note&#34;&gt;
  &lt;div&gt;&lt;/div&gt;
&lt;p&gt;You can add all types of breakpoints in this window. But gutters are more convenient for others.&lt;/p&gt;
&lt;/div&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/how-to-debug-your-code-in-intellij/4-set-exception-breakpoint.jpg&#34;/&gt;
&lt;/figure&gt;

&lt;h3 id=&#34;1-dot-5-conditional-breakpoint&#34;&gt;1.5 Conditional Breakpoint&lt;/h3&gt;
&lt;p&gt;No need to explain, it does what the name says. After setting a breakpoint right click on the icon you will see basic condition input.
You can write a condition as if you are writing an &lt;code&gt;if&lt;/code&gt; condition. It will pause if the condition returns true.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/how-to-debug-your-code-in-intellij/8-basic-breakpoint-condition.jpg&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;IntelliJ provides different types of conditions and filters but I will not explain them. See &lt;a href=&#34;https://www.jetbrains.com/help/idea/using-breakpoints.html&#34;&gt;IntelliJ docs&lt;/a&gt;.&lt;/p&gt;
&lt;h2 id=&#34;2-dot-debug-window&#34;&gt;2. Debug Window&lt;/h2&gt;
&lt;h3 id=&#34;2-dot-1-step-functions&#34;&gt;2.1 Step Functions&lt;/h3&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/how-to-debug-your-code-in-intellij/5-debug-steps.jpg&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;You can see the step functions above. These buttons are taken from Debug window. You can use &lt;strong&gt;Alt+5&lt;/strong&gt; to open &lt;strong&gt;Debug&lt;/strong&gt; window if not visible. Let&amp;rsquo;s dive into the details of these step functions.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Step Over:&lt;/strong&gt; When you step over a line, you execute it and pause before the next line is executed.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Step Into:&lt;/strong&gt; If you step into a line, there are two possibilities. If there is a function call debugger go to that function and execute it step-by-step. Otherwise, it will behave like Step Over since there&amp;rsquo;s nothing to &lt;strong&gt;step into&lt;/strong&gt;.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Force Step Into:&lt;/strong&gt; In some cases debugger ignores the step into option and behaves like step over. You can force it to step into with it. For instance, debugger ignores stepping into `String string = new String(&amp;ldquo;Hello World!&amp;quot;);` but if you force, you will see String implementation.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Step Out:&lt;/strong&gt; You go back where you called the current function. To continue with the example above, when you click &lt;strong&gt;Step Out&lt;/strong&gt; inside String implementation then you go back where you call &lt;code&gt;new String();&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Drop Frame:&lt;/strong&gt; It&amp;rsquo;s going one step backward. As I stated before in this article, when your program pauses at some point, you see the current stack frame. You go to previous stack frame with it. But do not confuse, you don&amp;rsquo;t go back in time, you just go one step backward. It won&amp;rsquo;t undo your last operation.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Run to Cursor:&lt;/strong&gt; It will take the debugger where your cursor is regardless of the breakpoints.&lt;/p&gt;
&lt;h3 id=&#34;2-dot-2-debugger-control-buttons&#34;&gt;2.2 Debugger Control Buttons&lt;/h3&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/how-to-debug-your-code-in-intellij/6-debugger-control-buttons.jpg&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;These are debugger control buttons placed leftmost part of the debugger window.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Rerun:&lt;/strong&gt; It does what it says.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Resume Program:&lt;/strong&gt; It resumes the program from where it is paused until a breakpoint pauses it again.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Pause Program:&lt;/strong&gt;  It pauses the running program but does not provide you all the functionalities that breakpoints have.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Stop:&lt;/strong&gt; It stops the running program as you might guess.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/how-to-debug-your-code-in-intellij/9-debug-control-buttons.jpg&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;&lt;strong&gt;View Breakpoints:&lt;/strong&gt; It will show a window where you can see all set breakpoints, set/remove breakpoints and define conditions.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Mute Breakpoints:&lt;/strong&gt; It will deactivate all set breakpoints.&lt;/p&gt;
&lt;h3 id=&#34;2-dot-3-tracing-variables&#34;&gt;2.3 Tracing Variables&lt;/h3&gt;
&lt;p&gt;You write a method or any piece of code and expect it to work as you planned but things don&amp;rsquo;t go well. If you trust your algorithm, the best option is to trace every change in your code through the stack frame. Just set a breakpoint and see every change.&lt;/p&gt;
&lt;p&gt;Think of a method that you give a ticket date in String as parameter and it returns you whether the ticket is expired. You think something is wrong according and wanted to debug your method step by step. You might have parsed the String date wrong or made a mistake while calculating the days between two dates. Just put breakpoints in your method and inspect changes in variables. I created a simple dummy method and set the breakpoint at the end of the method to see all variables&#39; last state.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/how-to-debug-your-code-in-intellij/variables.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;You see &lt;code&gt;dateInput&lt;/code&gt; variable and it is parsed as &amp;ldquo;2019-03-10&amp;rdquo;. Then you check front-end and see that the date is actually sent as &amp;ldquo;dd-M-yyyy&amp;rdquo; but parsed like &amp;ldquo;M/dd/yyyy&amp;rdquo;. So the problem is solved quickly. This is a dummy example to see the basic purpose of tracing variables.
Real-life scenarios will be more useful.&lt;/p&gt;
&lt;h3 id=&#34;2-dot-4-evaluating-expressions-and-setting-values-manually&#34;&gt;2.4 Evaluating Expressions and Setting Values Manually&lt;/h3&gt;
&lt;p&gt;These are also good features. You can test your paused application with different values and take your inspection further. If you look at a variable and say &lt;strong&gt;&amp;ldquo;what would happen if it were &amp;hellip;?&amp;quot;&lt;/strong&gt;, this means you need one of these features. &lt;strong&gt;Evaluate Expression&lt;/strong&gt; also provides more than just setting values.&lt;/p&gt;
&lt;p&gt;To set a value basically, right-click on the variable, select &lt;strong&gt;Set Value (F2)&lt;/strong&gt; and write the new value.&lt;/p&gt;
&lt;p&gt;If you want to have more advanced capabilities or evaluate a Java expression, right-click on the variable and select &lt;strong&gt;Evaluate Expression (Alt+F8)&lt;/strong&gt;.
You can run your expression in that window.&lt;/p&gt;
&lt;p&gt;Think of the last dummy example above in &lt;a href=&#34;#2-dot-3-tracing-variables&#34;&gt;2.3 Tracing Variables&lt;/a&gt;. You wanted to see if your method would work correctly when you change your parser.
Change the date before logic and see what happens.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/how-to-debug-your-code-in-intellij/7-evaluate-expression.jpg&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;You can also declare a new variable and add it to your watches. Result is shown under the expression input as you see.&lt;/p&gt;
&lt;p&gt;My main resource is IntelliJ docs. You can check &lt;a href=&#34;https://www.jetbrains.com/help/idea/debugging-code.html&#34;&gt;this link&lt;/a&gt; for further information.&lt;/p&gt;
</description>
        </item>
        
        <item>
            <title>FasterXML/jackson Tips for JSON in Java</title>
            <link>http://kamer.dev/jackson-tips-for-json-in-java/</link>
            <pubDate>Fri, 06 Mar 2020 23:30:00 +0000</pubDate>
            
            <guid>http://kamer.dev/jackson-tips-for-json-in-java/</guid>
            <description>&lt;h2 id=&#34;introduction&#34;&gt;Introduction&lt;/h2&gt;
&lt;p&gt;All my examples will be in a Spring Boot project that has &lt;strong&gt;Web&lt;/strong&gt; and &lt;strong&gt;Lombok&lt;/strong&gt; dependencies. I will not list all features and explain them one by one like a documentation. Instead, I will ask some questions and answer them. I hope you will find your questions! If not so, you can ask me on &lt;a href=&#34;https://twitter.com/kamer%5Fee&#34;&gt;Twitter&lt;/a&gt; or &lt;a href=&#34;mailto:kamer@kamer.dev&#34;&gt;e-mail&lt;/a&gt;.&lt;/p&gt;
&lt;div class=&#34;ox-hugo-toc toc&#34;&gt;
&lt;div&gt;&lt;/div&gt;
&lt;div class=&#34;heading&#34;&gt;Table of Contents&lt;/div&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;#introduction&#34;&gt;Introduction&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#what-is-jackson&#34;&gt;What is Jackson?&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#q1-how-to-create-a-java-pojo-for-any-json-input&#34;&gt;Q1: How to create a Java POJO for any JSON input?&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#q2-how-to-use-different-field-names-in-pojo-to-map-json&#34;&gt;Q2: How to use different field names in POJO to map JSON?&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#q3-how-to-deserialize-nested-json-objects&#34;&gt;Q3: How to deserialize nested JSON objects?&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#q4-how-to-create-a-custom-deserializer&#34;&gt;Q4: How to create a custom deserializer?&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#q5-how-to-deserialize-enum-values&#34;&gt;Q5: How to deserialize enum values?&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#references&#34;&gt;References&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;
&lt;!--endtoc--&gt;
&lt;h2 id=&#34;what-is-jackson&#34;&gt;What is Jackson?&lt;/h2&gt;
&lt;p&gt;This article is not a &lt;strong&gt;zero-to-hero-like&lt;/strong&gt; article. So, I will not start from basics but introduce Jackson with a few words. Because you may have been using Jackson library without knowing you do so. Jackson is the most widely used JSON processing library for Java. It has 3 core modules (&lt;code&gt;jackson-core&lt;/code&gt;, &lt;code&gt;jackson-annotations&lt;/code&gt;, &lt;code&gt;jackson-databind&lt;/code&gt;), third-party modules for different integrations. You may have been using them because spring-boot-starter-web includes these three modules(and more) and Jackson is registered as default object mapper library. This is why you can produce JSON data by just returning Java object in your controller in your Spring application.&lt;/p&gt;
&lt;h2 id=&#34;q1-how-to-create-a-java-pojo-for-any-json-input&#34;&gt;Q1: How to create a Java POJO for any JSON input?&lt;/h2&gt;
&lt;p&gt;Perhaps, this is the simplest question that comes to mind. Let’s see an example JSON:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
  &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;title&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;2019-2020 Algorithms Final Exam&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt;
  &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;lecture&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Algorithms&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt;
  &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;examDate&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;2020-03-04T09:00:00.000Z&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt;
  &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;studentNumber&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;:&lt;/span&gt; 75&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt;
  &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;questions&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;[&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
      &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;questionNumber&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;:&lt;/span&gt; 1&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt;
  &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;question&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;What is an asymptotic notation?&amp;#34;&lt;/span&gt;
  &lt;span style=&#34;color:#666&#34;&gt;},&lt;/span&gt;
  &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
      &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;questionNumber&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;:&lt;/span&gt; 2&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt;
  &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;questions&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Find worst case for insertion sort?&amp;#34;&lt;/span&gt;
  &lt;span style=&#34;color:#666&#34;&gt;},&lt;/span&gt;
  &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
      &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;questionNumber&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;:&lt;/span&gt; 3&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt;
  &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;question&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Which algorithm would you choose to sort 1m numbers, why?&amp;#34;&lt;/span&gt;
  &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
  &lt;span style=&#34;color:#666&#34;&gt;]&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Let’s analyze this JSON. This is an object that has &lt;code&gt;title (string)&lt;/code&gt;, &lt;code&gt;lecture (string)&lt;/code&gt;, &lt;code&gt;examDate (date)&lt;/code&gt;, &lt;code&gt;studentNumber (numeric value, int is the best option for this case.)&lt;/code&gt; and &lt;code&gt;questions (array)&lt;/code&gt; fields. So, we should map this JSON to a Java object that has the same fields. All fields are OK but &lt;code&gt;questions&lt;/code&gt; array has an object type that has &lt;code&gt;questionNumber(numberic value, int)&lt;/code&gt; and &lt;code&gt;question (string)&lt;/code&gt; fields.&lt;/p&gt;
&lt;p&gt;First of all, create a &lt;code&gt;Question&lt;/code&gt; object as below:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Getter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Setter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@ToString&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;Question&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

   &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Integer questionNumber&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

   &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String question&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Then, create &lt;code&gt;Exam&lt;/code&gt; object.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Getter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Setter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@ToString&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;Exam&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

   &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String title&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

   &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String lecture&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

   &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; LocalDateTime examDate&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

   &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Integer studentNumber&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

   &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; List&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;Question&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; questions&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;That’s all. Finally, create a controller.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@PostMapping&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/question-one&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
ResponseEntity&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;Void&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;questionOne&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@RequestBody&lt;/span&gt; Exam exam&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
   log&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;info&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Parsed object: {}&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; exam&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
   &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; ResponseEntity&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;ok&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;().&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;build&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Now, send JSON with any method you like.&lt;/p&gt;
&lt;div class=&#34;block-note&#34;&gt;
  &lt;div&gt;&lt;/div&gt;
&lt;p&gt;We mapped JSON array as List in our POJO. This is not a must, we can also use Java Array (&lt;code&gt;Question[]&lt;/code&gt;), &lt;code&gt;Collection&amp;lt;&amp;gt;&lt;/code&gt;, &lt;code&gt;Set&amp;lt;&amp;gt;&lt;/code&gt;,  &lt;code&gt;Iterable&amp;lt;&amp;gt;&lt;/code&gt;  and any other type that implements &lt;code&gt;Iterable&amp;lt;&amp;gt;&lt;/code&gt;.&lt;/p&gt;
&lt;/div&gt;
&lt;h2 id=&#34;q2-how-to-use-different-field-names-in-pojo-to-map-json&#34;&gt;Q2: How to use different field names in POJO to map JSON?&lt;/h2&gt;
&lt;p&gt;In Q1 we named our fields according to given JSON. But this is not a must. We can use different names with many different options. But I will explain only two of them. So let’s create an example JSON:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-json&#34; data-lang=&#34;json&#34;&gt;{
  &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;productTitle&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;TWSBI ECO Fountain Pen White M Nib&amp;#34;&lt;/span&gt;,
  &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;productPrice&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;30.00&amp;#34;&lt;/span&gt;,
  &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;productCategoryId&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#666&#34;&gt;13&lt;/span&gt;,
  &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;productTagId&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#666&#34;&gt;235&lt;/span&gt;
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;As you see, there is a JSON object &lt;em&gt;-let’s call it product-&lt;/em&gt;  and it has 4 fields. Creating a POJO with the same field names are possible. But removing &lt;code&gt;product...&lt;/code&gt; prefix is better.&lt;/p&gt;
&lt;h3 id=&#34;option-1&#34;&gt;Option 1&lt;/h3&gt;
&lt;p&gt;Create a POJO as below:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Getter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Setter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@ToString&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;Q2ProductOptionOne&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@JsonAlias&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;productTitle&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String title&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@JsonAlias&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;productPrice&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String price&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@JsonAlias&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;productCategoryId&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Integer categoryId&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@JsonAlias&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;productTagId&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Integer tagId&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;&lt;code&gt;@JsonAlias&lt;/code&gt; annotation makes possible to define multiple options for a property. So &lt;code&gt;@JsonAlias(&amp;quot;productTitle&amp;quot;)&lt;/code&gt; annotation catches &lt;code&gt;productTitle&lt;/code&gt; key in JSON. But don&amp;rsquo;t forget, this annotation creates alternatives only. Actual property name doesn&amp;rsquo;t change.&lt;/p&gt;
&lt;p&gt;This option works perfectly but not the best option. Because what we want is to change the property name not to create alternatives.&lt;/p&gt;
&lt;h3 id=&#34;option-2&#34;&gt;Option 2&lt;/h3&gt;
&lt;p&gt;&lt;code&gt;@JsonProperty&lt;/code&gt; annotation is the other option. This will change the property name:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Getter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Setter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@ToString&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;Q2ProductOptionTwo&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@JsonProperty&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;productTitle&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String title&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@JsonProperty&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;productPrice&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String price&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@JsonProperty&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;productCategoryId&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Integer categoryId&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@JsonProperty&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;productTagId&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Integer tagId&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;block-tip&#34;&gt;
  &lt;div&gt;&lt;/div&gt;
&lt;p&gt;We can use these two annotations at the same time. &lt;code&gt;@JsonProperty&lt;/code&gt; will change the actual name and &lt;code&gt;@JsonAlias&lt;/code&gt; will add other options.&lt;/p&gt;
&lt;/div&gt;
&lt;div class=&#34;block-tip&#34;&gt;
  &lt;div&gt;&lt;/div&gt;
&lt;p&gt;You can set an &lt;code&gt;access&lt;/code&gt; option on &lt;code&gt;@JsonProperty&lt;/code&gt;. This will provide you some options such as changing the property name on deserialization/serialization/both.&lt;/p&gt;
&lt;/div&gt;
&lt;h2 id=&#34;q3-how-to-deserialize-nested-json-objects&#34;&gt;Q3: How to deserialize nested JSON objects?&lt;/h2&gt;
&lt;p&gt;In a standard JSON communication, you are likely to encounter nested objects inside JSON. In Q1 we deserialized a JSON input with multiple classes.
But there are other options.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-json&#34; data-lang=&#34;json&#34;&gt;{
    &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;title&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;TWSBI ECO Fountain Pen White M Nib&amp;#34;&lt;/span&gt;,
    &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;price&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;30.00&amp;#34;&lt;/span&gt;,
    &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;taxonomy&amp;#34;&lt;/span&gt;: {
	&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;categoryId&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#666&#34;&gt;13&lt;/span&gt;,
	&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;tagId&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#666&#34;&gt;235&lt;/span&gt;
    }
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;option-1&#34;&gt;Option 1&lt;/h3&gt;
&lt;p&gt;First option is to map nested object to a Map. This is very easy.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Getter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Setter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@ToString&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;Q3ProductOptionOne&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String title&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Float price&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Map&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; taxonomy&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Jackson will initialize this map with categoryId and tagId keys.&lt;/p&gt;
&lt;h3 id=&#34;option-2&#34;&gt;Option 2&lt;/h3&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Getter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Setter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@ToString&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;Q3ProductOptionTwo&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String title&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Float price&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Integer tagId&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Integer categoryId&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@JsonProperty&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;taxonomy&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f&#34;&gt;@SuppressWarnings&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;unchecked&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;taxonomyDeserializer&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;Map&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; Object&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; taxonomy&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;this&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;tagId&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;Integer&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; taxonomy&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;get&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;tagId&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;this&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;categoryId&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;Integer&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; taxonomy&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;get&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;categoryId&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;This option looks like the previous option. But it’s better I think. Because we does not use map class as nested object. Instead, we give this nested map to a private method annotated with &lt;code&gt;@JsonProperty&lt;/code&gt; and &lt;code&gt;@SuppressWarnings&lt;/code&gt;. Then extract values from map and set to fields.&lt;/p&gt;
&lt;h3 id=&#34;option-3&#34;&gt;Option 3&lt;/h3&gt;
&lt;p&gt;This option is a different question. So, check Q4 for this.&lt;/p&gt;
&lt;h2 id=&#34;q4-how-to-create-a-custom-deserializer&#34;&gt;Q4: How to create a custom deserializer?&lt;/h2&gt;
&lt;p&gt;There may be some cases that you don’t want to use annotations or these annotations are not enough for your development. So, you can create your own deserializer that you receive raw JSON and export POJO, then, register it to overwrite default deserializer. Let’s create a JSON that has nested objects.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-json&#34; data-lang=&#34;json&#34;&gt;{
    &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;applicant&amp;#34;&lt;/span&gt;: {
	&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;name&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Joss&amp;#34;&lt;/span&gt;,
	&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;surname&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Stone&amp;#34;&lt;/span&gt;
    },
    &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;application&amp;#34;&lt;/span&gt;: {
	&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;announcementId&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#666&#34;&gt;2&lt;/span&gt;,
	&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;givenInput&amp;#34;&lt;/span&gt;: {
	    &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;profileLink&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;&amp;lt;https://dummypage.com&amp;gt;&amp;#34;&lt;/span&gt;,
	    &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;cvFileName&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;myAwesomeCv.pdf&amp;#34;&lt;/span&gt;
	}
    }
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;We can deserialize it as it is explained in Q3. But creating a custom deserializer is another option.&lt;/p&gt;
&lt;p&gt;This is our POJO:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Getter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Setter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Builder&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@ToString&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;Application&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String applicationFullName&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Integer announcementId&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String applicantProfileLink&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String cvName&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;And this is deserializer:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;ApplicationDeserializer&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;extends&lt;/span&gt; StdDeserializer&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;Application&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;ApplicationDeserializer&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;this&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;null&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;ApplicationDeserializer&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;Class&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;?&amp;gt;&lt;/span&gt; vc&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;super&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;vc&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; Application &lt;span style=&#34;color:#00a000&#34;&gt;deserialize&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;JsonParser jp&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; DeserializationContext ctxt&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;throws&lt;/span&gt; IOException&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; JsonProcessingException &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; JsonNode jsonNode &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; jp&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;getCodec&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;().&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;readTree&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;jp&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; JsonNode applicantNode &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; jsonNode&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;get&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;applicant&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; JsonNode applicationNode &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; jsonNode&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;get&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;application&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; String name &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; applicantNode&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;get&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;name&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;).&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;asText&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; String surname &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; applicantNode&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;get&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;surname&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;).&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;asText&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; Integer announcementId &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; applicationNode&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;get&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;announcementId&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;).&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;asInt&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; JsonNode givenInputNode &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; applicationNode&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;get&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;givenInput&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; String profileLink &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; givenInputNode&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;get&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;profileLink&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;).&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;asText&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; String cvFileName &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; givenInputNode&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;get&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;cvFileName&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;).&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;asText&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; Application&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;builder&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt;
		      &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;applicationFullName&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;name &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34; &amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; surname&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
		      &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;announcementId&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;announcementId&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
		      &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;applicantProfileLink&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;profileLink&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
		      &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;cvName&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;cvFileName&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
		      &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;build&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;All elements are JsonNode in this deserialization process. If you chain a method such as &lt;code&gt;asText()&lt;/code&gt;, &lt;code&gt;asInt()&lt;/code&gt;, they are converted into desired form. Otherwise they are treated as JsonNode. You can perform all kinds of validations and manipulations also.&lt;/p&gt;
&lt;p&gt;Lastly, let’s register deserializer class in our POJO class with the annotation below:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@JsonDeserialize&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;using &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; ApplicationDeserializer&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;class&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;q5-how-to-deserialize-enum-values&#34;&gt;Q5: How to deserialize enum values?&lt;/h2&gt;
&lt;p&gt;Deserializing enum values is easy. You can do it without a tutorial. But there are different options. First of all, create an enum class.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;enum&lt;/span&gt; ContainerStatusOptionOne &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt; RUNNING&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; FAILED&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; PENDING&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; REMOVING &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Then, create a POJO that has this enum as a field.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Getter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Setter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@ToString&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;Container&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String containerTitle&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; ContainerStatus containerStatus&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;option-1&#34;&gt;Option 1&lt;/h3&gt;
&lt;p&gt;This is option is the first that comes to mind. Just send the name of the enum value.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-json&#34; data-lang=&#34;json&#34;&gt;{
    &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;containerTitle&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Stage&amp;#34;&lt;/span&gt;,
    &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;containerStatus&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;RUNNING&amp;#34;&lt;/span&gt;
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;But don’t forget, this option works case sensitive. If you send running as a value, you get &lt;code&gt;HttpMessageNotReadableException&lt;/code&gt;.&lt;/p&gt;
&lt;h3 id=&#34;option-2&#34;&gt;Option 2&lt;/h3&gt;
&lt;p&gt;This option is as easy as the first option but personally, I don’t find it useful. When you send numeric values for enum, Jackson deserializes it also. RUNNING is 0 for our example and REMOVING is 3. So:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-json&#34; data-lang=&#34;json&#34;&gt;{
    &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;containerTitle&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Stage&amp;#34;&lt;/span&gt;,
    &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;containerStatus&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#666&#34;&gt;0&lt;/span&gt;
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;is the same as the example above.&lt;/p&gt;
&lt;h3 id=&#34;option-3&#34;&gt;Option 3&lt;/h3&gt;
&lt;p&gt;There are some situations that you may work with 3rd party services and you cannot change your request body according to your POJO. For instance, 3rd party service sends lowercase values for enums. Jackson provides an annotation for this also. We need to change enum values as below:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;enum&lt;/span&gt; ContainerStatusOptionTwo &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
    &lt;span style=&#34;color:#a2f&#34;&gt;@JsonProperty&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;running&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; RUNNING&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt;
    &lt;span style=&#34;color:#a2f&#34;&gt;@JsonProperty&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;failed&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; FAILED&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt;
    &lt;span style=&#34;color:#a2f&#34;&gt;@JsonProperty&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;pending&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; PENDING&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt;
    &lt;span style=&#34;color:#a2f&#34;&gt;@JsonProperty&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;removing&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; REMOVING
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Now, Jackson will look for running, failed, pending and removing as input. So, sending the JSON below works:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-json&#34; data-lang=&#34;json&#34;&gt;
{
    &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;containerTitle&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Stage&amp;#34;&lt;/span&gt;,
    &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;containerStatus&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;running&amp;#34;&lt;/span&gt;
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;references&#34;&gt;References&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;Jackson Documentation&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.concretepage.com/jackson-api/jackson-jsonproperty-and-jsonalias-example&#34;&gt;https://www.concretepage.com/jackson-api/jackson-jsonproperty-and-jsonalias-example&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.baeldung.com/jackson-nested-values&#34;&gt;https://www.baeldung.com/jackson-nested-values&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;Github Repo:&lt;/strong&gt; &lt;a href=&#34;https://github.com/kamer/jackson-tips-for-json-in-java&#34;&gt;https://github.com/kamer/jackson-tips-for-json-in-java&lt;/a&gt;&lt;/p&gt;
</description>
        </item>
        
        <item>
            <title>Thymeleaf Crash Course</title>
            <link>http://kamer.dev/thymeleaf-crash-course/</link>
            <pubDate>Mon, 24 Feb 2020 20:45:00 +0000</pubDate>
            
            <guid>http://kamer.dev/thymeleaf-crash-course/</guid>
            <description>&lt;p&gt;Hello! In this article I will explain what &lt;strong&gt;template engine&lt;/strong&gt; is and give you a crash course about Thymeleaf with Spring Boot. My main resources are official documentations which are published under the title of &lt;a href=&#34;https://www.thymeleaf.org/doc/tutorials/3.0/usingthymeleaf.html&#34;&gt;Thymeleaf 3.0&lt;/a&gt; and &lt;a href=&#34;https://www.thymeleaf.org/doc/tutorials/3.0/thymeleafspring.html&#34;&gt;Thymeleaf+Spring&lt;/a&gt;.
Github repo is also available at the end of the article.&lt;/p&gt;
&lt;div class=&#34;ox-hugo-toc toc&#34;&gt;
&lt;div&gt;&lt;/div&gt;
&lt;div class=&#34;heading&#34;&gt;Table of Contents&lt;/div&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;#1-dot-theoretical&#34;&gt;1. Theoretical&lt;/a&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;#1-dot-1-what-is-thymeleaf&#34;&gt;1.1 What is Thymeleaf?&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#1-dot-2-thymeleaf-standart-dialect&#34;&gt;1.2 Thymeleaf Standart Dialect&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-practical&#34;&gt;2. Practical&lt;/a&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-1-folder-hierarchy&#34;&gt;2.1 Folder Hierarchy&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-2-syntax&#34;&gt;2.2 Syntax&lt;/a&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-2-dot-1-simple-expressions&#34;&gt;2.2.1 Simple Expressions&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-2-dot-2-constructing-texts&#34;&gt;2.2.2 Constructing Texts&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-2-dot-3-arithmetic-operations-comparators-and-equality&#34;&gt;2.2.3 Arithmetic Operations, Comparators and Equality&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-2-dot-4-th-if-th-unless-th-switch-th-case&#34;&gt;2.2.4 &lt;code&gt;th:if&lt;/code&gt;, &lt;code&gt;th:unless&lt;/code&gt;, &lt;code&gt;th:switch&lt;/code&gt;, &lt;code&gt;th:case&lt;/code&gt;&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-2-dot-5-loops-with-th-each&#34;&gt;2.2.5 Loops with &lt;code&gt;th:each&lt;/code&gt;&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-2-dot-6-ternary-and-elvis-operator&#34;&gt;2.2.6 Ternary and Elvis Operator&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-2-dot-7-th-attributes&#34;&gt;2.2.7 th:* Attributes&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-2-dot-8-general-attribute-modification&#34;&gt;2.2.8 General Attribute Modification&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-2-dot-9-local-variables&#34;&gt;2.2.9 Local Variables&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-2-dot-10-thymeleaf-comment-blocks&#34;&gt;2.2.10 Thymeleaf Comment Blocks&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-2-dot-11-expression-inlining&#34;&gt;2.2.11 Expression Inlining&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-3-expression-objects&#34;&gt;2.3 Expression Objects&lt;/a&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-3-dot-1-expression-basic-objects&#34;&gt;2.3.1 Expression Basic Objects&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#2-dot-3-dot-2-expression-utility-objects&#34;&gt;2.3.2 Expression Utility Objects&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#3-dot-a-few-words&#34;&gt;3. A Few Words&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;
&lt;!--endtoc--&gt;
&lt;h2 id=&#34;1-dot-theoretical&#34;&gt;1. Theoretical&lt;/h2&gt;
&lt;h3 id=&#34;1-dot-1-what-is-thymeleaf&#34;&gt;1.1 What is Thymeleaf?&lt;/h3&gt;
&lt;p&gt;You can find the shortest and &lt;strong&gt;-I think-&lt;/strong&gt; the best explanation at Thymeleaf&amp;rsquo;s docs:&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;Thymeleaf is a modern server-side Java template engine for…&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;Keywords are &lt;strong&gt;server-side&lt;/strong&gt; and &lt;strong&gt;Java template engine&lt;/strong&gt;. Rest of the definition is not important at this point. Let&amp;rsquo;s look at &lt;strong&gt;template engine&lt;/strong&gt;.&lt;/p&gt;
&lt;p&gt;Template engine is a language-independent software that processes given template and produces a result by filling it with data. There are several template engines for different languages. For instance, there is a page template for Jekyll below:&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/thymeleaf-crash-course/liquid.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Jekyll uses &lt;a href=&#34;https://shopify.github.io/liquid/&#34;&gt;Liquid&lt;/a&gt; template language. When you read the example, you can find out that &lt;code&gt;post&lt;/code&gt; is an object that has &lt;code&gt;title&lt;/code&gt;, &lt;code&gt;content&lt;/code&gt; and &lt;code&gt;tags[]&lt;/code&gt; fields. You can render this page in your mind.&lt;/p&gt;
&lt;p&gt;Once you have a clear definition of &lt;strong&gt;template&lt;/strong&gt; and &lt;strong&gt;template engine&lt;/strong&gt; you can comprehend the difference between &lt;strong&gt;client-side&lt;/strong&gt; and &lt;strong&gt;server-side&lt;/strong&gt; rendering. At &lt;strong&gt;client-side rendering,&lt;/strong&gt; client receives the template with some data(XML, JSON etc.) and renders them at the client-side. But when you use &lt;strong&gt;server-side templating,&lt;/strong&gt; template and the data is processed at the server-side and the final result is sent to client.&lt;/p&gt;
&lt;p&gt;Thymeleaf supports 6 kinds of templates which are HTML, XML, Text, JavaScript, CSS and RAW.&lt;/p&gt;
&lt;p&gt;Thus, we have an idea of Thymeleaf. Let&amp;rsquo;s solidify our understanding with a brief definition of process.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;We will prepare a template that extends simple HTML syntax; give Java objects and the template to &lt;strong&gt;template engine.&lt;/strong&gt; Template engine will process these inputs and create an HTML file.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h3 id=&#34;1-dot-2-thymeleaf-standart-dialect&#34;&gt;1.2 Thymeleaf Standart Dialect&lt;/h3&gt;
&lt;p&gt;If you don&amp;rsquo;t want to learn the details you can omit this section but I recommend you to learn terminology of Thymeleaf. This whole section also exists in the documentation but I want to explain them with my own sentences.&lt;/p&gt;
&lt;p&gt;Let&amp;rsquo;s go with the documentation again:&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;An object that applies some logic to a markup artifact is called a processor, and…&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;This sentence seems so simple but let&amp;rsquo;s clarify our understanding by explaining the term &lt;strong&gt;markup&lt;/strong&gt;. Yeah, I know, this is not a mystery for the people who have written at least a few lines with HTML but most of the people don&amp;rsquo;t know what it is. Markups are symbols and texts that we insert to a document to format its content. For instance when you type &lt;code&gt;&amp;lt;h1&amp;gt;Thymeleaf&amp;lt;/h1&amp;gt;&lt;/code&gt; in a HTML document, you define it as the highest level heading. That&amp;rsquo;s why we call it &lt;strong&gt;markup language&lt;/strong&gt;. After this definition, the sentence from the documentation is more clear when you read again: &lt;strong&gt;&amp;ldquo;An object that applies some logic to a markup artifact is called a processor, and…&amp;quot;&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;These processors are combined and called &lt;strong&gt;dialects&lt;/strong&gt;. Thymeleaf provides us Standart Dialect which is mostly enough for basic processing but in case not, you can create your own &lt;strong&gt;processors&lt;/strong&gt; and &lt;strong&gt;dialects&lt;/strong&gt;.&lt;/p&gt;
&lt;h2 id=&#34;2-dot-practical&#34;&gt;2. Practical&lt;/h2&gt;
&lt;p&gt;As I specified at the beginning, this article will be based on Thymeleaf in a Spring Boot app. Therefore, I will explain both Standard Dialect and SpringStandard Dialect. Now, go to &lt;a href=&#34;https://start.spring.io/&#34;&gt;https://start.spring.io/&lt;/a&gt; or use IDE plugins to create the project. Spring Web and Thymeleaf dependencies are enough.&lt;/p&gt;
&lt;h3 id=&#34;2-dot-1-folder-hierarchy&#34;&gt;2.1 Folder Hierarchy&lt;/h3&gt;
&lt;p&gt;When you create a Thymeleaf dependent project with Spring Initalzr, this is what you get by default:&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/thymeleaf-crash-course/project-hierarchy.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Put your static content (e.g. css, js, img) in &lt;code&gt;static&lt;/code&gt; folder and templates in &lt;code&gt;templates&lt;/code&gt; folder. But it&amp;rsquo;s not a must. You can change this default also.&lt;/p&gt;
&lt;p&gt;Best approach is to set &lt;code&gt;spring.resources.static-locations&lt;/code&gt; property in &lt;strong&gt;application.properties&lt;/strong&gt; file. For instance:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;spring.resources.static-locations=file:/awesome/path
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;or&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;spring.resources.static-locations=classpath:/resources/my_static_content
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;You can change templates folder as well.&lt;/p&gt;
&lt;h3 id=&#34;2-dot-2-syntax&#34;&gt;2.2 Syntax&lt;/h3&gt;
&lt;h4 id=&#34;2-dot-2-dot-1-simple-expressions&#34;&gt;2.2.1 Simple Expressions&lt;/h4&gt;
&lt;pre&gt;&lt;code class=&#34;language-nil&#34; data-lang=&#34;nil&#34;&gt;spring.thymeleaf.prefix=classpath:/my_templates/
&lt;/code&gt;&lt;/pre&gt;&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Variable Expressions(&lt;code&gt;${...}&lt;/code&gt;)&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;When you send data in model object with a controller, you can process them with this syntax.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt; Hello &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;span&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${username}&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;span&lt;/span&gt;&amp;gt; &amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;We will cover &lt;code&gt;th:...&lt;/code&gt; attributes later.
Just focus on &lt;code&gt;${...}&lt;/code&gt; part.&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Selection Variable Expressions(&lt;code&gt;*{...}&lt;/code&gt;)&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;This is another expression to process variables and more convenient for some cases. Instead of picking an object from whole model context, you can select from particular selected context. Let&amp;rsquo;s clarify this with an example:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;h3&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${post.title}&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;h3&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${post.excerpt}&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;This is standard variable expression. It&amp;rsquo;s possible to use selection variable expression syntax:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:object&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${post}&amp;#34;&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;h3&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;*{title}&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;h3&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;*{excerpt}&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Message Expressions(&lt;code&gt;#{...}&lt;/code&gt;)&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Best way to extract static texts to achieve i8n is using &lt;code&gt;MessageSource&lt;/code&gt;. You can process these texts with this syntax. For instance if you want to process the text below:&lt;/p&gt;
&lt;pre&gt;&lt;code class=&#34;language-nil&#34; data-lang=&#34;nil&#34;&gt;greeting.title=Message Expressions
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;You can write:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;h1&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;#{greeting.title}&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;h1&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;You can also pass variables to this texts:&lt;/p&gt;
&lt;pre&gt;&lt;code class=&#34;language-nil&#34; data-lang=&#34;nil&#34;&gt;greeting.text=Hello {0}! How are you today?
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;with:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;#{greeting.text(${username})}&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Link URL Expressions(&lt;code&gt;@{...}&lt;/code&gt;)&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;There are some attributes that needs URL as input. Thymeleaf provides a good syntax for URLs.&lt;/p&gt;
&lt;p&gt;You can;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;create &lt;strong&gt;absolute URL&lt;/strong&gt;s:&lt;/li&gt;
&lt;/ul&gt;
 &lt;!--listend--&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;a&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:href&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;@{https://google.com}&amp;#34;&lt;/span&gt;&amp;gt;...&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;a&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;ul&gt;
&lt;li&gt;create &lt;strong&gt;Context-relative URL&lt;/strong&gt;s:&lt;/li&gt;
&lt;/ul&gt;
 &lt;!--listend--&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;a&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:href&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;@{/comments}&amp;#34;&lt;/span&gt;&amp;gt;...&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;a&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Server-relative URL&lt;/strong&gt;s:&lt;/li&gt;
&lt;/ul&gt;
 &lt;!--listend--&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;a&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:href&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;@{~/posts}&amp;#34;&lt;/span&gt;&amp;gt;...&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;a&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Protocol-relative URL&lt;/strong&gt;s:&lt;/li&gt;
&lt;/ul&gt;
 &lt;!--listend--&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;a&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:href&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;@{//google.com}&amp;#34;&lt;/span&gt;&amp;gt;...&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;a&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;ul&gt;
&lt;li&gt;use variables inside URLs with expression preprocessing which  process the expression between &amp;ldquo;__ __&amp;rdquo; :&lt;/li&gt;
&lt;/ul&gt;
 &lt;!--listend--&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;a&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:href&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;@{/users/__${userId}__/posts}&amp;#34;&lt;/span&gt;&amp;gt;...&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;a&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;ul&gt;
&lt;li&gt;define URL parameters:&lt;/li&gt;
&lt;/ul&gt;
 &lt;!--listend--&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;a&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:href&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;@{/posts(page=${pageNumber}, tag=&amp;#39;java&amp;#39;)}&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;a&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Fragment Expressions(&lt;code&gt;~{...}&lt;/code&gt;)&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;I think its much harder than it should be for a crash course.&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 id=&#34;2-dot-2-dot-2-constructing-texts&#34;&gt;2.2.2 Constructing Texts&lt;/h4&gt;
&lt;p&gt;Thymeleaf provides a good syntax to construct texts. First one is &lt;code&gt;+&lt;/code&gt; operator.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;span&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;&amp;#39;Hello&amp;#39; + ${username} + &amp;#39;! How are you today?&amp;#39;&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;span&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;You can do the same with &lt;strong&gt;literal substitutions:&lt;/strong&gt;&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;span&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;|Hello ${username}!How are you today?|&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;span&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Combining literal substitutions with other types is also possible.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;span&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;&amp;#39;Combined: &amp;#39; + |Hello ${username}!How are you today?|&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;span&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h4 id=&#34;2-dot-2-dot-3-arithmetic-operations-comparators-and-equality&#34;&gt;2.2.3 Arithmetic Operations, Comparators and Equality&lt;/h4&gt;
&lt;p&gt;You can use arithmetic operators in Thymeleaf also.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:with&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;totalCost=${perPrice} * ${totalCount}&amp;#34;&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;span&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;|Total Cost: ${totalCost}|&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;span&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:if&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${currentProfile} == &amp;#39;DEV&amp;#39;&amp;#34;&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;span&lt;/span&gt;&amp;gt;Wubba Lubba Dub Dub&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;span&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;You can also try &lt;code&gt;&amp;lt; (&amp;amp;gt;)&lt;/code&gt;, &lt;code&gt;&amp;gt; (&amp;amp;lt;)&lt;/code&gt;, &lt;code&gt;&amp;gt;=&lt;/code&gt;, &lt;code&gt;≤&lt;/code&gt;, &lt;code&gt;!=&lt;/code&gt; or their textual aliases &lt;code&gt;gt&lt;/code&gt;, &lt;code&gt;lt&lt;/code&gt;, &lt;code&gt;ge&lt;/code&gt;, &lt;code&gt;le&lt;/code&gt;, &lt;code&gt;not&lt;/code&gt;, &lt;code&gt;eq&lt;/code&gt;, &lt;code&gt;neq/ne&lt;/code&gt;.&lt;/p&gt;
&lt;h4 id=&#34;2-dot-2-dot-4-th-if-th-unless-th-switch-th-case&#34;&gt;2.2.4 &lt;code&gt;th:if&lt;/code&gt;, &lt;code&gt;th:unless&lt;/code&gt;, &lt;code&gt;th:switch&lt;/code&gt;, &lt;code&gt;th:case&lt;/code&gt;&lt;/h4&gt;
&lt;p&gt;I think there is no need to explain &lt;code&gt;th:if&lt;/code&gt;.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:if&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${username} neq null&amp;#34;&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;span&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;|User exists with name ${username}|&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;span&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;There is also &lt;code&gt;th:unless&lt;/code&gt; which is inverse of &lt;code&gt;th:if&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;&lt;code&gt;th:switch&lt;/code&gt; / &lt;code&gt;th:case&lt;/code&gt; is also the same.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:switch&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${currentProfile}&amp;#34;&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:case&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;&amp;#39;DEV&amp;#39;&amp;#34;&lt;/span&gt;&amp;gt;Dev profile.&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:case&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;&amp;#39;PROD&amp;#39;&amp;#34;&lt;/span&gt;&amp;gt;Prod profile.&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h4 id=&#34;2-dot-2-dot-5-loops-with-th-each&#34;&gt;2.2.5 Loops with &lt;code&gt;th:each&lt;/code&gt;&lt;/h4&gt;
&lt;p&gt;Arrays and any kinds of objects that implement &lt;code&gt;Iterable&lt;/code&gt;, &lt;code&gt;Enumaration&lt;/code&gt;, &lt;code&gt;Iterator&lt;/code&gt;, &lt;code&gt;Map&lt;/code&gt; can be used for iteration.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;ul&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:each&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;post : ${posts}&amp;#34;&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;li&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:object&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${post}&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;|*{title} - *{excerpt}|&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;li&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;ul&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h4 id=&#34;2-dot-2-dot-6-ternary-and-elvis-operator&#34;&gt;2.2.6 Ternary and Elvis Operator&lt;/h4&gt;
&lt;p&gt;Ternary operator is not an unfamiliar term. So there&amp;rsquo;s no need to explain.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${username == null} ? &amp;#39;Anonymous&amp;#39; : ${username}&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Elvis operator is like Ternary operator but it doesn&amp;rsquo;t have &lt;strong&gt;then&lt;/strong&gt; part. Let&amp;rsquo;s write the ternary expression above with the Elvis operator.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${username}?: &amp;#39;Anonymous&amp;#39;&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h4 id=&#34;2-dot-2-dot-7-th-attributes&#34;&gt;2.2.7 th:* Attributes&lt;/h4&gt;
&lt;p&gt;We&amp;rsquo;ve gone through most of the syntax. You can use &lt;code&gt;th:...&lt;/code&gt; syntax for all HTML5 attributes. There are some examples below:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;img&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:src&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;@{/bernard-black.jpg}&amp;#34;&lt;/span&gt;/&amp;gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;form&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:action&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;@{~/users}&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;method&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;post&amp;#34;&lt;/span&gt; /&amp;gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;button&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:value&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;#{save_button}&amp;#34;&lt;/span&gt;&amp;gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;checkbox&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:checked&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${isUserActive}&amp;#34;&lt;/span&gt;&amp;gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:data-index&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${index}&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h4 id=&#34;2-dot-2-dot-8-general-attribute-modification&#34;&gt;2.2.8 General Attribute Modification&lt;/h4&gt;
&lt;p&gt;Standard Dialect has &lt;code&gt;th:attr&lt;/code&gt;, &lt;code&gt;th:attrappend&lt;/code&gt;, &lt;code&gt;th:attrprepend&lt;/code&gt;, &lt;code&gt;th:classappend&lt;/code&gt;, &lt;code&gt;th:styleappend&lt;/code&gt; to modify attributes.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;button&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:attr&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;value=&amp;#39;Click me!&amp;#39;&amp;#34;&lt;/span&gt;/&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;As you see, &lt;code&gt;th:attr&lt;/code&gt; does not offer a new feature. But the others are more useful. I won&amp;rsquo;t use all of them in this article. Here&amp;rsquo;s an example:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:classappend&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${isMessageNew}? &amp;#39;notification&amp;#39;&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${message}&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h4 id=&#34;2-dot-2-dot-9-local-variables&#34;&gt;2.2.9 Local Variables&lt;/h4&gt;
&lt;p&gt;There are two types of local variable definitions in Thymeleaf. First one is &lt;code&gt;th:object&lt;/code&gt;. I have gave an example at &lt;strong&gt;2.2.1.&lt;/strong&gt; But let&amp;rsquo;s remember it again:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:object&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${post}&amp;#34;&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;h3&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;*{title}&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;h3&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;*{excerpt}&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;In this example, fields of &lt;code&gt;${post}&lt;/code&gt; is accessible only within &lt;code&gt;div&lt;/code&gt; tag. That&amp;rsquo;s why we call it local variable.&lt;/p&gt;
&lt;p&gt;Another option is &lt;code&gt;th:with&lt;/code&gt;. This option is more flexible relatively. You can declare a variable in a tag and use it with child tags.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:with&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;featuringPost=${posts[2]}&amp;#34;&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;|Post of the week: ${featuringPost.title}|&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h4 id=&#34;2-dot-2-dot-10-thymeleaf-comment-blocks&#34;&gt;2.2.10 Thymeleaf Comment Blocks&lt;/h4&gt;
&lt;p&gt;As you know we use &lt;code&gt;&amp;lt;!-- --&amp;gt;&lt;/code&gt; syntax to create a comment block in HTML. It&amp;rsquo;s the same with Thymeleaf since Thymeleaf treats them in the same way. But there&amp;rsquo;s another option. You can create parser-level comment blocks that is removed after the template is parsed and won&amp;rsquo;t be visible to end-users.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;&amp;lt;!-- Users can see me! --&amp;gt;&lt;/span&gt;

&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;&amp;lt;!--/* I&amp;#39;m invisible! */--&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;There are also prototype-only comment blocks and they are very useful with th:block. But it&amp;rsquo;s much for a crash course. You can see &lt;a href=&#34;https://www.thymeleaf.org/doc/tutorials/3.0/usingthymeleaf.html#thymeleaf-prototype-only-comment-blocks&#34;&gt;11.3&lt;/a&gt; and &lt;a href=&#34;https://www.thymeleaf.org/doc/tutorials/3.0/usingthymeleaf.html#synthetic-thblock-tag&#34;&gt;11.4&lt;/a&gt;.&lt;/p&gt;
&lt;h4 id=&#34;2-dot-2-dot-11-expression-inlining&#34;&gt;2.2.11 Expression Inlining&lt;/h4&gt;
&lt;p&gt;So far, we have seen only tag attributes but Standard Dialect provides also expression inlining. We&amp;rsquo;ve seen different options:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt; Hello &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;span&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${username}&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;span&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;|Hello ${username}|&amp;#34;&lt;/span&gt;&amp;gt; &amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;&amp;#39;Hello &amp;#39; + ${username}&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;All of them are nice for different cases but you can also use:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;Hello [[${username}]]&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;But personally, I don&amp;rsquo;t find them useful.&lt;/p&gt;
&lt;h3 id=&#34;2-dot-3-expression-objects&#34;&gt;2.3 Expression Objects&lt;/h3&gt;
&lt;p&gt;So far, we have provided some data to Thymeleaf and used them. There are also some objects which are always available. There are many objects and they have more than 100 methods totally and this would make this article really long. So I will show none or one example per object. &lt;strong&gt;2.3.1&lt;/strong&gt; and &lt;strong&gt;2.3.2&lt;/strong&gt; will be mostly a list of objects. You can find more in the documentation. &lt;a href=&#34;https://www.thymeleaf.org/doc/tutorials/3.0/usingthymeleaf.html#appendix-a-expression-basic-objects&#34;&gt;[1]&lt;/a&gt; &lt;a href=&#34;https://www.thymeleaf.org/doc/tutorials/3.0/usingthymeleaf.html#appendix-b-expression-utility-objects&#34;&gt;[2]&lt;/a&gt;&lt;/p&gt;
&lt;h4 id=&#34;2-dot-3-dot-1-expression-basic-objects&#34;&gt;2.3.1 Expression Basic Objects&lt;/h4&gt;
&lt;p&gt;First two objects are base objects and  the others are Web context namespace shortcuts.&lt;/p&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;#ctx&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Context object. There are also two synonyms: &lt;strong&gt;#vars&lt;/strong&gt; and &lt;strong&gt;#root.&lt;/strong&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;#locale&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Gets locale of current request.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${#locale}&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;param&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Gets request parameters.&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;session&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Gets session attributes.&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;application&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Gets application/servlet context attributes.&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h4 id=&#34;2-dot-3-dot-2-expression-utility-objects&#34;&gt;2.3.2 Expression Utility Objects&lt;/h4&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;#execInfo&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;It provides information about processed template.&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;#messages&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Another option for use externalized variables.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${#messages.msg(&amp;#39;ext_msg&amp;#39;)}&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;#uris&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Let&amp;rsquo;s you perform URI/URL operations.&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;#conversions&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Another option for double brackets. You can set target class.&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;#dates&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Methods for &lt;code&gt;java.util.Date&lt;/code&gt; objects.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${#dates.createNow()}&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;#calendars&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;&lt;code&gt;java.util.Calendar&lt;/code&gt; version of &lt;strong&gt;#dates&lt;/strong&gt;.&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;#numbers&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Utilities for number objects.&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;#string&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Utilities for &lt;code&gt;String&lt;/code&gt;.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:if&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${#strings.equals(currentProfile, &amp;#39;DEV&amp;#39;)}&amp;#34;&lt;/span&gt;&amp;gt;Dev Profile&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;#objects&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;#bools&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;#arrays&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;#lists&lt;/strong&gt;&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:if&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${#lists.size(draftPosts) == 0}&amp;#34;&lt;/span&gt;&amp;gt;No drafts.&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;#sets&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;#maps&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;#aggregates&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;!--list-separator--&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;#ids&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;3-dot-a-few-words&#34;&gt;3. A Few Words&lt;/h2&gt;
&lt;p&gt;As the title suggests it&amp;rsquo;s a crash course only. Two documentations which I&amp;rsquo;ve used is much larger. You can go further by checking them. I&amp;rsquo;m thinking of writing a few blog posts about Thymeleaf also. If I do so, I will add their links here.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Github Repo:&lt;/strong&gt; &lt;a href=&#34;https://github.com/kamer/thymeleaf-crash-course&#34;&gt;https://github.com/kamer/thymeleaf-crash-course&lt;/a&gt;&lt;/p&gt;
</description>
        </item>
        
        <item>
            <title>Custom Javax Annotation Error Handling in Spring</title>
            <link>http://kamer.dev/custom-javax-annotation-error-handling/</link>
            <pubDate>Sun, 02 Feb 2020 01:41:00 +0000</pubDate>
            
            <guid>http://kamer.dev/custom-javax-annotation-error-handling/</guid>
            <description>&lt;p&gt;Hello! In this article, I&amp;rsquo;m gonna cover how to override default exception handler method for &lt;code&gt;MethodArgumentNotValidException&lt;/code&gt;  which is thrown when Java Bean Validation Annotations are violated.&lt;/p&gt;
&lt;h2 id=&#34;what-is-java-bean-validation&#34;&gt;What is Java Bean Validation?&lt;/h2&gt;
&lt;p&gt;Java Bean Validation is a specification that is defined in &lt;a href=&#34;https://beanvalidation.org/2.0/&#34;&gt;JSR-380&lt;/a&gt;. It makes possible defining constraints with annotations, write custom constraints, etc. I will use &lt;a href=&#34;http://hibernate.org/validator/&#34;&gt;Hibernate Validator&lt;/a&gt; since it is the only certified implementation of Bean Validation 2.0. It&amp;rsquo;s not a requirement to use with Spring but I&amp;rsquo;m going to implement it with Spring Boot because of its popularity. I will not explain how to use these annotations however you can find it in &lt;a href=&#34;https://kamer.dev/validations-in-spring-boot/&#34;&gt;one of my articles&lt;/a&gt;.&lt;/p&gt;
&lt;h2 id=&#34;create-a-simple-project-and-provide-some-annotations&#34;&gt;Create a Simple Project and Provide Some Annotations&lt;/h2&gt;
&lt;p&gt;Create a project with Spring Initializr and select Web and Lombok dependencies. Because web-starter includes Hibernate Validator. Then create a class named User as below.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Data&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;User&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Length&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;min &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; 2&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; max &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; 30&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; message &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Name must be between 2-30 characters. &amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f&#34;&gt;@Pattern&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;regexp &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;^[a-zA-Z]+(([&amp;#39;,. -][a-zA-Z ])?[a-zA-Z]*)*$&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; message &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Name is invalid.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String name&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Length&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;min &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; 2&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; max &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; 30&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; message &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Surname must be between 2-30 characters.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f&#34;&gt;@Pattern&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;regexp &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;^[a-zA-Z]+(([&amp;#39;,. -][a-zA-Z ])?[a-zA-Z]*)*$&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; message &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Surname is invalid.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String surname&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Email&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;message &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Enter a valid email address.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String email&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;block-tip&#34;&gt;
  &lt;div&gt;&lt;/div&gt;
&lt;p&gt;Using an external message source for error messages is better but I didn&amp;rsquo;t use it because it would make this article longer.&lt;/p&gt;
&lt;/div&gt;
&lt;p&gt;Then create a RestController and accept User as a &lt;code&gt;@Valid&lt;/code&gt; input.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@RestController&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@RequestMapping&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/api/users&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;UserRestController&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@PostMapping&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; ResponseEntity&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;User&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;saveUser&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Valid&lt;/span&gt; &lt;span style=&#34;color:#a2f&#34;&gt;@RequestBody&lt;/span&gt; User user&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; ResponseEntity&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;ok&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;user&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;block-important&#34;&gt;
  &lt;div&gt;&lt;/div&gt;
&lt;p&gt;Do not forget to use &lt;code&gt;@Valid&lt;/code&gt; annotation. Because it makes sure that the annotated parameter is validated.&lt;/p&gt;
&lt;/div&gt;
&lt;p&gt;Run the application and send an example request. (You don&amp;rsquo;t have to use cURL of course. I sent this request with Postman. You can just copy this and import it as a raw text to Postman.)&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-bash&#34; data-lang=&#34;bash&#34;&gt;curl --location --request POST &lt;span style=&#34;color:#b44&#34;&gt;&amp;#39;http://localhost:8080/api/users&amp;#39;&lt;/span&gt; &lt;span style=&#34;color:#b62;font-weight:bold&#34;&gt;\
&lt;/span&gt;&lt;span style=&#34;color:#b62;font-weight:bold&#34;&gt;&lt;/span&gt;--header &lt;span style=&#34;color:#b44&#34;&gt;&amp;#39;Content-Type: application/json&amp;#39;&lt;/span&gt; &lt;span style=&#34;color:#b62;font-weight:bold&#34;&gt;\
&lt;/span&gt;&lt;span style=&#34;color:#b62;font-weight:bold&#34;&gt;&lt;/span&gt;--data-raw &lt;span style=&#34;color:#b44&#34;&gt;&amp;#39;{
&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;      &amp;#34;name&amp;#34;: &amp;#34;Marion&amp;#34;,
&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;      &amp;#34;surname&amp;#34;: &amp;#34;Cotillard&amp;#34;,
&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;      &amp;#34;email&amp;#34;: &amp;#34;marion@cotillard.com&amp;#34;,
&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;      &amp;#34;birthdate&amp;#34;: &amp;#34;1975-09-30&amp;#34;
&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;}&amp;#39;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;This request will return 200 as could be expected. Now let&amp;rsquo;s break some rules:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-bash&#34; data-lang=&#34;bash&#34;&gt;curl --location --request POST &lt;span style=&#34;color:#b44&#34;&gt;&amp;#39;http://localhost:8080/api/users&amp;#39;&lt;/span&gt; &lt;span style=&#34;color:#b62;font-weight:bold&#34;&gt;\
&lt;/span&gt;&lt;span style=&#34;color:#b62;font-weight:bold&#34;&gt;&lt;/span&gt;--header &lt;span style=&#34;color:#b44&#34;&gt;&amp;#39;Content-Type: application/json&amp;#39;&lt;/span&gt; &lt;span style=&#34;color:#b62;font-weight:bold&#34;&gt;\
&lt;/span&gt;&lt;span style=&#34;color:#b62;font-weight:bold&#34;&gt;&lt;/span&gt;--data-raw &lt;span style=&#34;color:#b44&#34;&gt;&amp;#39;{
&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;      &amp;#34;name&amp;#34;: &amp;#34;M&amp;#34;,
&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;      &amp;#34;surname&amp;#34;: &amp;#34;Cotillard&amp;#34;,
&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;      &amp;#34;email&amp;#34;: &amp;#34;marion@cotillard.com&amp;#34;,
&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;      &amp;#34;birthdate&amp;#34;: &amp;#34;1975-09-30&amp;#34;
&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;}&amp;#39;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;I just broke &lt;code&gt;@Length&lt;/code&gt; rule on &lt;code&gt;name&lt;/code&gt; field. This request responded with a long response:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-json&#34; data-lang=&#34;json&#34;&gt;{
  &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;timestamp&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;2020-02-01T21:27:06.935+0000&amp;#34;&lt;/span&gt;,
  &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;status&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#666&#34;&gt;400&lt;/span&gt;,
  &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;error&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Bad Request&amp;#34;&lt;/span&gt;,
  &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;errors&amp;#34;&lt;/span&gt;: [
    {
      &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;codes&amp;#34;&lt;/span&gt;: [
	&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Length.user.name&amp;#34;&lt;/span&gt;,
	&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Length.name&amp;#34;&lt;/span&gt;,
	&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Length.java.lang.String&amp;#34;&lt;/span&gt;,
	&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Length&amp;#34;&lt;/span&gt;
      ],
      &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;arguments&amp;#34;&lt;/span&gt;: [
	{
	  &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;codes&amp;#34;&lt;/span&gt;: [
	    &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;user.name&amp;#34;&lt;/span&gt;,
	    &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;name&amp;#34;&lt;/span&gt;
	  ],
	  &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;arguments&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;null&lt;/span&gt;,
	  &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;defaultMessage&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;name&amp;#34;&lt;/span&gt;,
	  &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;code&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;name&amp;#34;&lt;/span&gt;
	},
	&lt;span style=&#34;color:#666&#34;&gt;30&lt;/span&gt;,
	&lt;span style=&#34;color:#666&#34;&gt;2&lt;/span&gt;
      ],
      &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;defaultMessage&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Name must be between 2-30 characters. &amp;#34;&lt;/span&gt;,
      &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;objectName&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;user&amp;#34;&lt;/span&gt;,
      &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;field&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;name&amp;#34;&lt;/span&gt;,
      &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;rejectedValue&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;M&amp;#34;&lt;/span&gt;,
      &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;bindingFailure&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;false&lt;/span&gt;,
      &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;code&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Length&amp;#34;&lt;/span&gt;
    }
  ],
  &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;message&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Validation failed for object=&amp;#39;user&amp;#39;. Error count: 1&amp;#34;&lt;/span&gt;,
  &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;path&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/api/users&amp;#34;&lt;/span&gt;
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;This can be a confusing response but it&amp;rsquo;s possible to create a custom response.&lt;/p&gt;
&lt;h2 id=&#34;override-exception-handler&#34;&gt;Override Exception Handler&lt;/h2&gt;
&lt;p&gt;Firstly, create a POJO for the custom response.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Getter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Setter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Builder&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@AllArgsConstructor&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;CustomFieldError&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String field&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String message&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;You can add extra fields but this is enough for this article. Then create an exception handler method:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@ExceptionHandler&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;MethodArgumentNotValidException&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;class&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; ResponseEntity&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;Object&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;handleUserMethodFieldErrors&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;MethodArgumentNotValidException ex&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; WebRequest request&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
      &lt;span style=&#34;color:#080;font-style:italic&#34;&gt;// some logic
&lt;/span&gt;&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Javax Annotations throws &lt;code&gt;MethodArgumentNotValidException.class&lt;/code&gt; so, overrode this exception. In the method, extract field errors and create &lt;code&gt;CustomFieldError&lt;/code&gt; objects from them.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; List&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;FieldError&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; fieldErrors &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; ex&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;getBindingResult&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;().&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;getFieldErrors&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;

&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; List&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;CustomFieldError&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; customFieldErrors &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; ArrayList&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&amp;gt;();&lt;/span&gt;

&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;for&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;FieldError fieldError &lt;span style=&#34;color:#666&#34;&gt;:&lt;/span&gt; fieldErrors&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; String field &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; fieldError&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;getField&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;

      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; String message &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; fieldError&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;getDefaultMessage&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;

      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; CustomFieldError customFieldError &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; CustomFieldError&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;builder&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;().&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;field&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;field&lt;span style=&#34;color:#666&#34;&gt;).&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;message&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;message&lt;span style=&#34;color:#666&#34;&gt;).&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;build&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;

      customFieldErrors&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;customFieldError&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;You can also get &lt;code&gt;rejectedValue&lt;/code&gt; and &lt;code&gt;errorCode&lt;/code&gt;. Then create an HTTP response and return.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; ResponseEntity&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;badRequest&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;().&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;body&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;customFieldErrors&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Run the project again and send the same request. This will return 400 response with the body below:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-json&#34; data-lang=&#34;json&#34;&gt;[
      {
	      &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;field&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;name&amp;#34;&lt;/span&gt;,
	      &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;message&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Name must be between 2-30 characters. &amp;#34;&lt;/span&gt;
      }
]
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;You can customise this response or override similar exception handlers with the same approach.&lt;/p&gt;
&lt;p&gt;Github Repo: &lt;a href=&#34;https://github.com/kamer/custom-javax-annotation-error-handling&#34;&gt;https://github.com/kamer/custom-javax-annotation-error-handling&lt;/a&gt;&lt;/p&gt;
</description>
        </item>
        
        <item>
            <title>Kitap İncelemesi: Docker Deep Dive</title>
            <link>http://kamer.dev/kitap-incelemesi-docker-deep-dive/</link>
            <pubDate>Sat, 28 Dec 2019 22:53:19 +0000</pubDate>
            
            <guid>http://kamer.dev/kitap-incelemesi-docker-deep-dive/</guid>
            <description>&lt;p&gt;Bir süredir Docker hakkındaki bilgimi artırmak ve temel bilgilerimi pekiştirmek için bir kitap okumayı düşünüyordum. Birçok kitap arasında hangisini okuyacağıma karar veremediğim için en kısa yol olan akışına bırakmayı tercih etmiştim. Derken Twitter`da &lt;a href=&#34;https://twitter.com/ozgurozturknet&#34;&gt;@ozgurozturknet&lt;/a&gt;&amp;lsquo;in Docker ve Kubernetes için kitap önerdiği &lt;a href=&#34;https://twitter.com/ozgurozturknet/status/1207654445586272257&#34;&gt;twiti&lt;/a&gt; gördüm.&lt;/p&gt;
&lt;p&gt;Ben de daha önceki araştırmalarımda gördüğüm bu kitaba hemen başladım. Genel olarak akıcı ve okuması keyifli bir kitap olduğunu söyleyebilirim. Bu yüzden çok kısa sürede bitti. Bu kısa incelemenin kitabı okumak konusunda kararsız olanlar için faydalı olacağını düşünüyorum.&lt;/p&gt;
&lt;h2 id=&#34;kitabı-nereden-edinebilirim&#34;&gt;Kitabı nereden edinebilirim?&lt;/h2&gt;
&lt;p&gt;Kitabın fiziksel baskısını &lt;a href=&#34;https://www.amazon.com/Docker-Deep-Dive-Nigel-Poulton-ebook/dp/B01LXWQUFF&#34;&gt;Amazon&lt;/a&gt;&amp;lsquo;dan 55 dolara alabilirsiniz. Kurları düşündüğümüzde bu çok mantıklı gelmiyor. Diğer bir seçenek ise &lt;a href=&#34;https://leanpub.com/dockerdeepdive&#34;&gt;Leanpub&lt;/a&gt;&amp;lsquo;dan 10 dolar karşılığında dijital formatlarını satın almak. Yazar kitabı sürekli olarak güncel tutacağına ve herhangi bir formatta kitabı satın alanların güncel halinin dijital kopyalarına erişimi olacağına dair garanti veriyor. Eğer ücretsiz olarak ulaşmak isterseniz de libgen&amp;rsquo;den ulaşabilirsiniz. Fakat bu durumda -en azından şimdilik- kitabın güncel olmayan bir kopyasına ulaşırsınız. (2019 Aralık itibariyle en güncel kopyası 2017 Ekim&amp;rsquo;e ait.)&lt;/p&gt;
&lt;h2 id=&#34;kitap-kime-hitap-ediyor&#34;&gt;Kitap kime hitap ediyor?&lt;/h2&gt;
&lt;p&gt;Daha kitabın en başında yazdığı üzere Docker&amp;rsquo;ın nasıl çalıştığını merak etmiyorsanız bu kitapla vakit kaybetmeyin. Çünkü teorik yönü daha ağır basan bir kitap ve pratik için daha iyi seçenekler bulabilirsiniz. Tabii bu kitap da komutları nasıl kullanmanız gerektiğini anlatıyor, gerçek örnekler veriyor ama odak noktası genel olarak Docker&amp;rsquo;ın iç yapısı. Seviye olarak değerlendirdiğimde ise her seviyeye hitap edeceğini düşünüyorum.
Eğer daha önce birkaç Docker komutu bile yazmadıysanız en azından  bir &lt;em&gt;container&lt;/em&gt; oluşturmanızı tavsiye ederim. Kitabın başlangıcında sizi daha rahat hissettirecektir.&lt;/p&gt;
&lt;h2 id=&#34;kitap-hangi-konuları-içeriyor&#34;&gt;Kitap hangi konuları içeriyor?&lt;/h2&gt;
&lt;p&gt;Docker&amp;rsquo;ın geçmişi, Docker Inc., Docker ve VM farkı, OCI gibi konularla &lt;em&gt;The big picture stuff&lt;/em&gt; kısmını tamamlıyorsunuz. Sonra daha teknik kısımlar olan Docker Engine, Image, Container, Uygulama Dockerize etme, Swarm Modu, Docker Networking, ve Güvenlik konularıyla da kitabı bitiriyorsunuz. Temelde ihtiyaç duyacağınız birçok konu başlığını akıcı bir dille anlatıyor.&lt;/p&gt;
&lt;h2 id=&#34;konuları-nasıl-bir-yöntem-ile-anlatıyor&#34;&gt;Konuları nasıl bir yöntem ile anlatıyor?&lt;/h2&gt;
&lt;p&gt;Her bölüme TLDR kısmı ile başlıyor. Bu kısımda adı üstünde TLDR seviyesinde yüzeysel bir bilgi sunuyor. Genel olarak ne anlatacağını özetliyor diyebilirim. Sonra &lt;em&gt;Deep Dive&lt;/em&gt; bölümü ile konunun asıl kısmını anlatıyor. Bu kısımda genelde o konunun geçmişinden başlayıp gelişimini anlatıyor. Docker&amp;rsquo;ın yapısında alınan bazı kararların sebebini açıklaması benim çok hoşuma gitti. Aynı zamanda bu kısımda kitabı okuyan kişinin pratik yapabileceği basit örnekler de veriyor. &lt;em&gt;Deep Dive&lt;/em&gt; kısmından sonra o bölümde kullanılan komutları açıkladığı &lt;em&gt;commands&lt;/em&gt; kısmı geliyor. Son olarak da &lt;em&gt;summary&lt;/em&gt; kısmında bölümün çok kısa bir özetini yapıp diğer bölüme geçiyor.&lt;/p&gt;
&lt;h2 id=&#34;son-birkaç-cümle&#34;&gt;Son birkaç cümle&lt;/h2&gt;
&lt;p&gt;Genel olarak kitaptan memnun kaldığımı söyleyebilirim. Docker&amp;rsquo;la ilgili olarak sadece kendi dokümanlarını okuduğum için karşılaştırma yapabileceğim bir kitap yok ama Docker&amp;rsquo;a başlangıç yapmak isteyen birine önerebileceğim bir kitap. Eğer maksadınız Docker&amp;rsquo;ı sadece kullanmak ise bu kitapla vakit kaybetmeden direkt dokümandan faydalanın. Çünkü bu kitap size pratikten çok teorik bilgi aktarmak için yazılmış bir kitap. Ama kullandığınız aracın nasıl çalıştığı hakkında bilgi sahibi olmanın önemini göz ardı etmeyin.&lt;/p&gt;
</description>
        </item>
        
        <item>
            <title>Docker ile PostgreSQL Kurulumu</title>
            <link>http://kamer.dev/docker-ile-postgresql-kurulumu/</link>
            <pubDate>Sat, 21 Dec 2019 23:07:12 +0000</pubDate>
            
            <guid>http://kamer.dev/docker-ile-postgresql-kurulumu/</guid>
            <description>&lt;p&gt;Merhaba, bu yazıda Docker ile PostgreSQL &lt;em&gt;container&lt;/em&gt;&amp;lsquo;ı ayağa kaldırmayı ve kullanmayı anlatacağım. Yazı herhangi bir Docker bilgisi gerektirmemektedir. Yalnızca kulak aşinalığı yeterlidir. Komutları tek tek açıklayacağım.&lt;/p&gt;
&lt;p&gt;Bilgisayarınızda Docker&amp;rsquo;ın kurulu olduğunu varsayıyorum. Eğer yüklü değilse &lt;a href=&#34;https://docs.docker.com/v17.12/install/&#34;&gt;bu bağlantı&lt;/a&gt;ya giderek kurulum yapabilirsiniz.&lt;/p&gt;
&lt;h2 id=&#34;1-dot-uygun-bir-image-bulmak&#34;&gt;1. Uygun bir &lt;em&gt;image&lt;/em&gt; bulmak&lt;/h2&gt;
&lt;p&gt;Bu adım zorunlu değildir. Docker&amp;rsquo;ı giriş seviyesinde bilenler için ekstra bir adımdır.&lt;/p&gt;
&lt;p&gt;Kullanmak istediğimiz &lt;em&gt;image&lt;/em&gt;&amp;lsquo;ı Docker Hub&amp;rsquo;dan arayacağız. Bunun için terminalden &lt;code&gt;docker search postgresql&lt;/code&gt; şeklinde bir arama yapabiliriz. Bu arama aşağıdaki çıktıyı verecektir:&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/docker-postgres-kurulum/docker-search.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;En üstte postgres adıyla yayınlanmış official olarak işaretlenmiş bir &lt;em&gt;image&lt;/em&gt; göreceksiniz. Bu bizim işimizi görüyor.&lt;/p&gt;
&lt;p&gt;Arama yapmak için diğer bir seçenek ise Docker Hub&amp;rsquo;dır. Bunun için &lt;a href=&#34;https://hub.docker.com/&#34;&gt;https://hub.docker.com/&lt;/a&gt;  adresine giderek arama yapabilirsiniz.&lt;/p&gt;
&lt;h2 id=&#34;2-dot-image-ı-indirmek-ve-container-oluşturmak&#34;&gt;2. Image&amp;rsquo;ı indirmek ve container oluşturmak&lt;/h2&gt;
&lt;p&gt;Bir önceki adımda kullanacağımız &lt;em&gt;image&lt;/em&gt;&amp;lsquo;ı bulduk. (postgres) Şimdi de &lt;em&gt;image&lt;/em&gt; dosyasını indirip &lt;em&gt;container&lt;/em&gt; oluşturacağız.&lt;/p&gt;
&lt;p&gt;Bunun için &lt;code&gt;docker pull postgres&lt;/code&gt; yazın ve indirmenin bitmesini bekleyin. İndirme bittikten sonra kontrol etmek isterseniz &lt;code&gt;docker images&lt;/code&gt; veya &lt;code&gt;docker image ls&lt;/code&gt; komutlarını kullanabilirsiniz.&lt;/p&gt;
&lt;p&gt;Eğer &lt;em&gt;image&lt;/em&gt; sorunsuz olarak indiyse aşağıdaki komut ile &lt;em&gt;container&lt;/em&gt; oluşturabilirsiniz:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-bash&#34; data-lang=&#34;bash&#34;&gt;docker run --name &amp;lt;CONTAINER_ADI&amp;gt; -e &lt;span style=&#34;color:#b8860b&#34;&gt;POSTGRES_PASSWORD&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&amp;lt;ROOT_PAROLASI&amp;gt; -d -p 5432:5432 -v &amp;lt;HOST&lt;span style=&#34;&#34;&gt;&amp;#39;&lt;/span&gt;TA_HERHANGI_BIR_DIZIN&amp;gt;:/var/lib/postgresql/data  postgres
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Komutu parça parça inceleyelim.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;docker run&lt;/code&gt;: Herhangi bir image ismi verdiğinizde o image&amp;rsquo;ı kullanarak bir container oluşturur ve dilediğiniz komutları çalıştırır.&lt;/li&gt;
&lt;li&gt;&lt;code&gt;--name&lt;/code&gt;: Container adı vermek için kullanılır.&lt;/li&gt;
&lt;li&gt;&lt;code&gt;-e&lt;/code&gt;: Ortam değişkeni(environment variable) tanımlamak için kullanılır. Her image&amp;rsquo;ın kendine ait ortam değişkenleri olur. postgres&amp;rsquo;in diğer değişkenlerini görmek için &lt;a href=&#34;https://github.com/docker-library/docs/tree/master/postgres#environment-variables&#34;&gt;bu bağlantıya&lt;/a&gt; gidebilirsiniz. Bizim kullandığımız &lt;code&gt;POSTGRES_PASSWORD&lt;/code&gt; değişkeni superuser parolasıdır. Eğer &lt;code&gt;POSTGRES_USER&lt;/code&gt; değişkenini kullanmazsanız varsayılan superuser olan &lt;code&gt;postgres&lt;/code&gt;&amp;lsquo;in parolasını belirlemiş olursunuz.&lt;/li&gt;
&lt;li&gt;&lt;code&gt;-d&lt;/code&gt;: &lt;strong&gt;Container&lt;/strong&gt;&amp;lsquo;ı arkaplanda oluşturur ve &lt;em&gt;container&lt;/em&gt; ID&amp;rsquo;sini ekrana yazdırır. (&lt;code&gt;--detach&lt;/code&gt;)&lt;/li&gt;
&lt;li&gt;&lt;code&gt;-p&lt;/code&gt;: &lt;strong&gt;Container&lt;/strong&gt; portlarını açar. Burada postgres&amp;rsquo;in varsayılan portu olan 5432&amp;rsquo;yi 5432 portunda açtık. Böylece host olan sistemden erişebileceğiz.&lt;/li&gt;
&lt;li&gt;&lt;code&gt;-v&lt;/code&gt;: &lt;strong&gt;Container&lt;/strong&gt;&amp;lsquo;lar silindiğinde içindeki veriler de silinir. Volume kullanarak container içindeki bir dizini host olan bilgisayardaki bir dizin ile eşleştiriyoruz. Böylece &lt;em&gt;container&lt;/em&gt; silindiğinde verileri kaybetmiyoruz. İlk kısım host&amp;rsquo;taki dizin, ikincisi ise container içinde eşleştirdiğimiz dizin.&lt;/li&gt;
&lt;li&gt;&lt;code&gt;postgres&lt;/code&gt;: bu da kullanılacak olan image adı.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Yukarıdaki taslağı kullanarak aşağıdaki gibi bir komut çalıştırıyorum:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-bash&#34; data-lang=&#34;bash&#34;&gt;docker run --name docker_postgres -e &lt;span style=&#34;color:#b8860b&#34;&gt;POSTGRES_PASSWORD&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;123456&lt;/span&gt; -d -p 5432:5432 -v &lt;span style=&#34;color:#b8860b&#34;&gt;$HOME&lt;/span&gt;/docker/volumes/postgres:/var/lib/postgresql/data postgres
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Komutu çalıştırdığımda &lt;code&gt;-d&lt;/code&gt; yazdığım için ekrana yalnızca &lt;em&gt;container&lt;/em&gt; id&amp;rsquo;sini yazacak. &lt;strong&gt;Container&lt;/strong&gt;&amp;lsquo;ın çalışıp çalışmadığını görmek için &lt;code&gt;docker container ls&lt;/code&gt; veya &lt;code&gt;docker ps&lt;/code&gt; yazabilirsiniz.&lt;/p&gt;
&lt;h2 id=&#34;3-dot-psql-e-erişmek&#34;&gt;3. psql&amp;rsquo;e Erişmek&lt;/h2&gt;
&lt;p&gt;Çalışan container&amp;rsquo;ın &lt;code&gt;psql&lt;/code&gt; terminaline erişmek için ise aşağıdaki komutu yazıyoruz:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-bash&#34; data-lang=&#34;bash&#34;&gt;docker &lt;span style=&#34;color:#a2f&#34;&gt;exec&lt;/span&gt; -it &amp;lt;CONTAINER_ADI&amp;gt; psql -U &amp;lt;KULLANICI_ADI&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Bu komutu da parçalara bölelim:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;docker exec&lt;/code&gt;: Çalışan bir &lt;em&gt;container&lt;/em&gt; içinde komut çalıştırmak için kullanırız.&lt;/li&gt;
&lt;li&gt;&lt;code&gt;-it&lt;/code&gt;: t ile komut yazabileceğimiz bir terminal istediğimizi (tty),  i ile de bu terminalin interaktif olmasını istediğimizi belirtiyoruz. (interactive)&lt;/li&gt;
&lt;li&gt;&lt;code&gt;psql -U&lt;/code&gt;: Bunun zaten docker ile bir ilgisi yok. Eğer &lt;code&gt;docker run&lt;/code&gt; komutunu çalıştırırken &lt;code&gt;POSTGRES_USER&lt;/code&gt; ortam değişkeniyle bir kullanıcı adı belirlemediyseniz varsayılan kullanıcı olan &lt;code&gt;postgres&lt;/code&gt;&amp;lsquo;i girmeniz gerekiyor.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Bundan sonraki aşamalar Docker&amp;rsquo;dan bağımsız olarak ilerliyor. Psql ile veritabanı oluşturup dilediğiniz client ile bağlanabilirsiniz. Bu yazıyı hazırlarken yalnızca Docker dokümanlarından faydalandım. Komutların referansları aşağıdadır:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://docs.docker.com/engine/reference/commandline/search/&#34;&gt;docker search&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://docs.docker.com/engine/reference/commandline/pull/&#34;&gt;docker pull&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://docs.docker.com/engine/reference/commandline/images/&#34;&gt;docker images&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://docs.docker.com/engine/reference/commandline/image%5Fls/&#34;&gt;docker image ls&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://docs.docker.com/engine/reference/commandline/run/&#34;&gt;docker run&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://docs.docker.com/engine/reference/commandline/container%5Fls/&#34;&gt;docker container ls&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://docs.docker.com/engine/reference/commandline/ps/&#34;&gt;docker ps&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://docs.docker.com/engine/reference/commandline/exec/&#34;&gt;docker exec&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://github.com/docker-library/docs/tree/master/postgres&#34;&gt;docker postgres image dokümanı&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
</description>
        </item>
        
        <item>
            <title>Validations is Spring Boot</title>
            <link>http://kamer.dev/validations-in-spring-boot/</link>
            <pubDate>Mon, 30 Sep 2019 19:27:12 +0000</pubDate>
            
            <guid>http://kamer.dev/validations-in-spring-boot/</guid>
            <description>&lt;p&gt;Hello! In this article, I`m gonna cover validations in a Spring Boot app. The only requirement for you to understand this topic is to be able to create controllers in Spring Boot and of course, be comfortable with Java.&lt;/p&gt;
&lt;p&gt;You can find source code for examples here: &lt;a href=&#34;https://github.com/kamer/validations-in-spring-boot&#34;&gt;https://github.com/kamer/validations-in-spring-boot&lt;/a&gt;&lt;/p&gt;
&lt;div class=&#34;ox-hugo-toc toc&#34;&gt;
&lt;div&gt;&lt;/div&gt;
&lt;div class=&#34;heading&#34;&gt;Table of Contents&lt;/div&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;#why-do-we-need-both-client-side-and-server-side-validation&#34;&gt;Why do we need both client-side and server-side validation?&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#javax-validation-constraints&#34;&gt;Javax Validation Constraints&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#creating-your-own-validation-annotations&#34;&gt;Creating Your Own Validation Annotations&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#combining-multiple-annotations&#34;&gt;Combining Multiple Annotations&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;#creating-custom-validator-class&#34;&gt;Creating Custom Validator Class&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;
&lt;!--endtoc--&gt;
&lt;h2 id=&#34;why-do-we-need-both-client-side-and-server-side-validation&#34;&gt;Why do we need both client-side and server-side validation?&lt;/h2&gt;
&lt;p&gt;In web applications, we generally use both client-side and server-side validations for form data or any other data that goes to server-side.
Why do we bother with both of them?&lt;/p&gt;
&lt;p&gt;Because we use client-side validation to validate and respond quickly. For instance, we have a field that accepts phone number. So, first of all, we should prevent user to type any character other than numbers. Also, we have a pattern that validates phone number. If we control and reject any incorrect input value on the client-side we eliminate the time for this request to go server-side and get rejected. So we can say that client-side validations are mostly used to give user fast feedback and validate syntactical things. (e.g. pattern, length, characters)&lt;/p&gt;
&lt;p&gt;But client-side validations can be considered useless since they can be easily manipulated or disabled. Here&amp;rsquo;s a great representation what it is like to trust any kind of client-side validation.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/validations-spring-boot/client-side-validation.jpg&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;If we go on with the above image, we should create a validation mechanism that rejects any other number than 911 as input. Here&amp;rsquo;s where server-side validation comes into play. Briefly, server-side validation is our last chance to reject incorrect inputs properly. Also, we validate constraints that need more logical operations on server-side. For instance, rejecting creation of an employee if the manager of the department is not assigned yet. Enough for introduction, let&amp;rsquo;s get our hands dirty.&lt;/p&gt;
&lt;h2 id=&#34;javax-validation-constraints&#34;&gt;Javax Validation Constraints&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;javax.validation&lt;/strong&gt; is the top-level package for Bean Validation API and it has some predefined annotation-based constraints in &lt;strong&gt;constraints&lt;/strong&gt; package for us to use. Here are some examples.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;If we want to check a field if it&amp;rsquo;s null, we use &lt;code&gt;@NotNull&lt;/code&gt; annotation.&lt;/li&gt;
&lt;/ul&gt;
&lt;!--listend--&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@NotNull&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;message &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Name cannot be null.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String name&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;In the above example &lt;strong&gt;name&lt;/strong&gt; field cannot be null. But it can be empty. If we use &lt;code&gt;@NotBlank&lt;/code&gt; &lt;strong&gt;name&lt;/strong&gt; cannot be null and must contain at least non-whitespace one character or if we use &lt;code&gt;@NotEmpty&lt;/code&gt; annotation &lt;strong&gt;name&lt;/strong&gt; cannot be null and &lt;code&gt;name.length() &amp;gt; 0&lt;/code&gt;. So it can accept a String that has whitespace character.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;If we limit any number input we use &lt;code&gt;@Max&lt;/code&gt; and &lt;code&gt;@Min&lt;/code&gt; annotations.&lt;/li&gt;
&lt;/ul&gt;
&lt;!--listend--&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Min&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;value &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; 3&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; message &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Experience must be at least 3 years.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Integer experienceInYears&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;ul&gt;
&lt;li&gt;&lt;code&gt;@Positive&lt;/code&gt;, &lt;code&gt;@Negative&lt;/code&gt;, &lt;code&gt;@PositiveOrZero&lt;/code&gt; and &lt;code&gt;@NegativeOrZero&lt;/code&gt; annotations do what their name suggests.&lt;/li&gt;
&lt;/ul&gt;
&lt;!--listend--&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@PositiveOrZero&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;message &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;You cannot have negative numbers of children.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Integer numberOfChildren&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;ul&gt;
&lt;li&gt;&lt;code&gt;@Size&lt;/code&gt; annotation gives minimum and maximum values for size of anything. (&lt;strong&gt;CharSequence&lt;/strong&gt;, &lt;strong&gt;Collection&lt;/strong&gt;, &lt;strong&gt;Map&lt;/strong&gt;, &lt;strong&gt;Array&lt;/strong&gt;)&lt;/li&gt;
&lt;/ul&gt;
&lt;!--listend--&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Size&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;min &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; 2&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; max &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; 35&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; message &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Surname must be 2-35 characters long.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String surname&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;ul&gt;
&lt;li&gt;&lt;code&gt;@Past&lt;/code&gt;, &lt;code&gt;@Future&lt;/code&gt;, &lt;code&gt;@PastOrPresent&lt;/code&gt;, &lt;code&gt;@FutureOrPresent&lt;/code&gt; annotations validate date types according to their name.&lt;/li&gt;
&lt;/ul&gt;
&lt;!--listend--&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Past&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;message &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Date input is invalid for a birth date.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; LocalDate dateOfBirth&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;ul&gt;
&lt;li&gt;You can validate any regex pattern with &lt;code&gt;@Pattern&lt;/code&gt; annotation.&lt;/li&gt;
&lt;/ul&gt;
&lt;!--listend--&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Pattern&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;regexp &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;^4[0-9]{12}(?:[0-9]{3})?$&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; message &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Only Visa cards are accepted.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String cardNumber&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;ul&gt;
&lt;li&gt;No need to explain &lt;code&gt;@Mail&lt;/code&gt; annotation.&lt;/li&gt;
&lt;/ul&gt;
&lt;!--listend--&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Email&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;message &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Enter a valid email address.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String email&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;I explained the most important ones above. If you want to see the others you can find them &lt;a href=&#34;https://docs.oracle.com/javaee/7/api/javax/validation/package-summary.html&#34;&gt;here&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;I created a dummy example to try these constraints and show validation messages on form inputs with Thymeleaf. We should annotate controller input with &lt;code&gt;@Valid&lt;/code&gt; to activate these constraints.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@PostMapping&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/javax-constraints&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
String &lt;span style=&#34;color:#00a000&#34;&gt;postJavaxConstraints&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Valid&lt;/span&gt; JavaxValidationConstraints javaxValidationConstraints&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; BindingResult bindingResult&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
   &lt;span style=&#34;color:#666&#34;&gt;...&lt;/span&gt;
   &lt;span style=&#34;color:#666&#34;&gt;...&lt;/span&gt;
   &lt;span style=&#34;color:#666&#34;&gt;...&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Then show error messages on Thymeleaf.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/validations-spring-boot/javax-validation-messages.png&#34;/&gt;
&lt;/figure&gt;

&lt;h2 id=&#34;creating-your-own-validation-annotations&#34;&gt;Creating Your Own Validation Annotations&lt;/h2&gt;
&lt;p&gt;If you have followed previous chapter well you should&amp;rsquo;ve seen that you achieve almost anything with Javax Validation Constraints. But sometimes defining your own annotations can seem a much better option though.&lt;/p&gt;
&lt;p&gt;Here&amp;rsquo;s one example. We want to validate &lt;strong&gt;creditCard&lt;/strong&gt; field with &lt;code&gt;@Pattern&lt;/code&gt;.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@NotEmpty&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;message &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;You must enter a credit card number.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Pattern&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;regexp &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;^(?:4[0-9]{12}(?:[0-9]{3})?|[25][1-7]&amp;#34;&lt;/span&gt;
		&lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;[0-9]{14}|6(?:011|5[0-9][0-9])[0-9]{12}&amp;#34;&lt;/span&gt;
		&lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;|3[47][0-9]{13}|3(?:0[0-5]|[68][0-9])&amp;#34;&lt;/span&gt;
		&lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;[0-9]{11}|(?:2131|1800|35\\d{3})\\d{11})$&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt;
	    message &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Invalid card number.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String creditCard&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Do you see any problem here? It seems too ugly considering we will have at least 5 more fields with at least 2 validation annotations and so on.
In this type of situation we can choose defining our own annotation.&lt;/p&gt;
&lt;p&gt;First of all create an annotation as below.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Documented&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Constraint&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;validatedBy &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; CreditCardValidator&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;class&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Target&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;({&lt;/span&gt; ElementType&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;FIELD&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;})&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Retention&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;RetentionPolicy&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;RUNTIME&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f&#34;&gt;@interface&lt;/span&gt; CreditCard &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    String &lt;span style=&#34;color:#00a000&#34;&gt;message&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;default&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Invalid card number&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    Class&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;?&amp;gt;[]&lt;/span&gt; groups&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;default&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{};&lt;/span&gt;
    Class&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;?&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;extends&lt;/span&gt; Payload&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;[]&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;payload&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;default&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{};&lt;/span&gt;
 &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;We want our annotation to serve at runtime, to be used with field types and to be validated by CreditCardValidator class.&lt;/p&gt;
&lt;p&gt;So here&amp;rsquo;s our validator class.&lt;/p&gt;
&lt;p&gt;We implement ConstraintValidator&amp;lt;[AnnotationsName], [TargetType]&amp;gt; and enforcedly override &lt;code&gt;initialize()&lt;/code&gt; and &lt;code&gt;isValid()&lt;/code&gt; methods.
&lt;strong&gt;initialize&lt;/strong&gt; method is guaranteed to be run before any use of this validation and &lt;strong&gt;isValid&lt;/strong&gt; method is where we reject or accept any value.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;CreditCardValidator&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;implements&lt;/span&gt; ConstraintValidator&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;CreditCard&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;static&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; String CREDIT_CARD_REGEX &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;^(?:4[0-9]{12}(?:[0-9]{3})?|[25][1-7][0-9]{14}|6(?:011|5[0-9][0-9])[0-9]{12}|3[47][0-9]{13}|3(?:0[0-5]|[68][0-9])[0-9]{11}|(?:2131|1800|35\\d{3})\\d{11})$&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;static&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; Pattern CREDIT_CARD_PATTERN &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; Pattern&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;compile&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;CREDIT_CARD_REGEX&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

      &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;initialize&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;CreditCard constraintAnnotation&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

      &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

      &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;boolean&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;isValid&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;String creditCardNumber&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; ConstraintValidatorContext context&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	      Matcher matcher &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; CREDIT_CARD_PATTERN&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;matcher&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;creditCardNumber&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; matcher&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;matches&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;

      &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Our annotation is ready. Let&amp;rsquo;s use them like the ones above.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@PostMapping&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/custom-constraint-annotation&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
      String &lt;span style=&#34;color:#00a000&#34;&gt;postCustomConstraint&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Valid&lt;/span&gt; CustomConstraintAnnotation customConstraintAnnotation&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; BindingResult bindingResult&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;if&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;bindingResult&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;hasErrors&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()){&lt;/span&gt;

		      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;custom-constraint-annotation&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
	      &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
	&lt;span style=&#34;color:#666&#34;&gt;...&lt;/span&gt;
	&lt;span style=&#34;color:#666&#34;&gt;...&lt;/span&gt;
	&lt;span style=&#34;color:#666&#34;&gt;...&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;All validation errors are saved in BindingResult object and we can show error messages with Thymeleaf.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;form&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;role&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;form&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:object&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${customConstraintAnnotation}&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:action&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;@{/custom-constraint-annotation}&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:method&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;post&amp;#34;&lt;/span&gt;&amp;gt;

    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;style&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;color: red;&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:if&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${#fields.hasErrors(&amp;#39;*&amp;#39;)}&amp;#34;&lt;/span&gt;&amp;gt;
	&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;strong&lt;/span&gt;&amp;gt;Errors&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;strong&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;p&lt;/span&gt;&amp;gt;
	&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;ul&lt;/span&gt;&amp;gt;
	    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;li&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:each&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;err : ${#fields.errors(&amp;#39;*&amp;#39;)}&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${err}&amp;#34;&lt;/span&gt;&amp;gt;&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;li&lt;/span&gt;&amp;gt;
	&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;ul&lt;/span&gt;&amp;gt;
    &amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;div&lt;/span&gt;&amp;gt;

    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;label&lt;/span&gt;&amp;gt;Credit Card Number&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;label&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;br&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;text&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;id&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;creditCard&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;name&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;creditCard&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:field&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;*{creditCard}&amp;#34;&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;br&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;submit&amp;#34;&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;form&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/validations-spring-boot/custom-annotation.png&#34;/&gt;
&lt;/figure&gt;

&lt;h2 id=&#34;combining-multiple-annotations&#34;&gt;Combining Multiple Annotations&lt;/h2&gt;
&lt;p&gt;Another way of implementing good validations is combining multiple validation annotations. Hibernate documentation calls it &lt;a href=&#34;https://docs.jboss.org/hibernate/stable/validator/reference/en-US/html%5Fsingle/?v=5.4#section-constraint-composition&#34;&gt;Constraint composition&lt;/a&gt;. It&amp;rsquo;s quite simple. First of all create an annotation type and fill as below.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@NotEmpty&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Size&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;min &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; 8&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Pattern&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;regexp &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;\&amp;#34;^(?=.*[a-z])(?=.*[A-Z])(?=.*\\d)[a-zA-Z\\d]$\&amp;#34;&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Target&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;({&lt;/span&gt; METHOD&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; FIELD&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; ANNOTATION_TYPE &lt;span style=&#34;color:#666&#34;&gt;})&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Retention&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;RUNTIME&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Constraint&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;validatedBy &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{})&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Documented&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f&#34;&gt;@interface&lt;/span&gt; CombinedPasswordConstraint &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

      String &lt;span style=&#34;color:#00a000&#34;&gt;message&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;default&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Invalid password.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

      Class&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;?&amp;gt;[]&lt;/span&gt; groups&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;default&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{};&lt;/span&gt;

      Class&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;?&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;extends&lt;/span&gt; Payload&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;[]&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;payload&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;default&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{};&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;You can add different messages for each annotation. Then use it like the other constraints.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/validations-spring-boot/constraint-composition.png&#34;/&gt;
&lt;/figure&gt;

&lt;h2 id=&#34;creating-custom-validator-class&#34;&gt;Creating Custom Validator Class&lt;/h2&gt;
&lt;p&gt;We&amp;rsquo;ve been through constraints so far. It&amp;rsquo;s time to create a more complicated validation with a custom validator class. In previous examples we&amp;rsquo;ve validated syntactical things. But generally we need more complicated things that possibly need a database query.&lt;/p&gt;
&lt;p&gt;I&amp;rsquo;m repeating prior example. You have created a department in your imaginary app. Then you try to add a new employee to this department. But you want to add a constraint that requires assigning a manager before assigning an employee. So you should add a validator that checks either this department has a manager or not. This is possible with custom validator. But you can also validate simple things like regex patterns.&lt;/p&gt;
&lt;p&gt;Let&amp;rsquo;s create one.&lt;/p&gt;
&lt;p&gt;I&amp;rsquo;m gonna show you a simplified example. First of all, create a dummy class and fill it as below.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;CustomValidationEntity&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String email&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Long departmentId&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; Boolean &lt;span style=&#34;color:#00a000&#34;&gt;existManagerByDepartmentId&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;Long departmentId&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;false&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
      &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; Boolean &lt;span style=&#34;color:#00a000&#34;&gt;existEmployeeWithMail&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;String email&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;true&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
      &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;It will always say &amp;lsquo;department has no manager&amp;rsquo; and &amp;lsquo;this email already exist&amp;rsquo; whatever we enter.&lt;/p&gt;
&lt;p&gt;Then create validator class as below. I&amp;rsquo;m gonna explain details.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Component&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;CustomValidator&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;implements&lt;/span&gt; Validator &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

      &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;boolean&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;supports&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;Class&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;?&amp;gt;&lt;/span&gt; clazz&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; CustomValidationEntity&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;class&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;isAssignableFrom&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;clazz&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
      &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

      &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;validate&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;Object target&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; Errors errors&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	      CustomValidationEntity customValidationEntity &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;CustomValidationEntity&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; target&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

	      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;if&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;customValidationEntity&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;existEmployeeWithMail&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;customValidationEntity&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;getEmail&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()))&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

		      errors&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;rejectValue&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;email&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;null&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Employee with this email is already exists.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	      &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

	      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;if&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;(!&lt;/span&gt;customValidationEntity&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;existManagerByDepartmentId&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;customValidationEntity&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;getDepartmentId&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()))&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

		      errors&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;reject&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;null&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Department does not have a manager.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	      &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

      &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;This Validator interface that we extend is &lt;code&gt;org.springframework.validation.Validator;&lt;/code&gt;. Not javax&amp;hellip; one. This interface gives us two methods.
&lt;code&gt;supports()&lt;/code&gt; method controls if the target object is what we intended to validate and &lt;code&gt;validate()&lt;/code&gt; method is where we control and reject things.
You can reject the whole object and add a global error message with &lt;code&gt;reject()&lt;/code&gt; or reject a single value and add an error message for this value with &lt;code&gt;rejectValue()&lt;/code&gt;. Then you should annotate this class with &lt;code&gt;@Component&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;Let&amp;rsquo;s use our validator. But we will do something different than using constraints. After annotating object parameter in the controller with &lt;code&gt;@Valid&lt;/code&gt;, we will add an InitBinder method in that controller.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@InitBinder&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;bindValidator&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;WebDataBinder webDataBinder&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
    webDataBinder&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;addValidators&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;customValidator&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;This &lt;code&gt;@InitBinder&lt;/code&gt; annotated method will initialize &lt;strong&gt;WebDataBinder&lt;/strong&gt;. Since &lt;strong&gt;WebDataBinder&lt;/strong&gt; prepares objects that come from requests for controllers, it can validate before the request reaches controller. That&amp;rsquo;s it. Let&amp;rsquo;s try our example.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/validations-spring-boot/custom-validator-error.png&#34;/&gt;
&lt;/figure&gt;

</description>
        </item>
        
        <item>
            <title>Spring Boot Uygulamasında Üye Kaydı ve Girişi</title>
            <link>http://kamer.dev/spring-boot-uygulamasinda-uye-kaydi-ve-girisi/</link>
            <pubDate>Fri, 27 Sep 2019 19:27:12 +0000</pubDate>
            
            <guid>http://kamer.dev/spring-boot-uygulamasinda-uye-kaydi-ve-girisi/</guid>
            <description>&lt;div class=&#34;block-plain&#34;&gt;
  &lt;div&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;Güncelleme 02.05.2020:&lt;/strong&gt; &lt;code&gt;csrf().disabled()&lt;/code&gt; konfigürasyonu ve CustomAuthenticationProvider sınıfı kaldırıldı. Ayrıca Optional kullanımını değiştirdim ve &lt;code&gt;orElseThrow()&lt;/code&gt; metodunu kullandım. Değerli yorumları için &lt;a href=&#34;https://twitter.com/gokcensedat&#34;&gt;@gokcensedat&lt;/a&gt; ve &lt;a href=&#34;https://twitter.com/utkuozdemir&#34;&gt;@utkuozdemir&lt;/a&gt;&amp;lsquo;e teşekkür ederim.&lt;/p&gt;
&lt;/div&gt;
&lt;p&gt;Merhaba, bu yazımda Spring Boot uygulamasında kullanıcı kaydı, onay maili gönderme ve kullanıcı girişi işlemlerinin nasıl yapılacağını anlatacağım. Ana konudan sapmamak için &lt;strong&gt;exception handling&lt;/strong&gt; kısımlarından bahsetmeyeceğim. Spring Boot hakkında bilgi sahibi olmanız, tercihen bir IDE kullanmanız gerekmektedir.&lt;/p&gt;
&lt;p&gt;Doğrudan kaynak kodları incelemek için: &lt;a href=&#34;https://github.com/kamer/spring-boot-user-registration&#34;&gt;https://github.com/kamer/spring-boot-user-registration&lt;/a&gt;&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;└── main
    ├── java
    │   └── com
    │       └── kamer
    │           └── springbootuserregistration
    │               ├── config
    │               │   ├── CustomAuthenticationProvider.java
    │               │   ├── WebConfig.java
    │               │   └── WebSecurityConfig.java
    │               ├── entity
    │               │   ├── User.java
    │               │   └── UserRole.java
    │               ├── SpringBootUserRegistrationApplication.java
    │               └── user
    │                   ├── ConfirmationToken.java
    │                   ├── ConfirmationTokenRepository.java
    │                   ├── ConfirmationTokenService.java
    │                   ├── EmailSenderService.java
    │                   ├── UserController.java
    │                   ├── UserRepository.java
    │                   └── UserService.java
    └── resources
	├── application.yml
	├── static
	└── templates
	    ├── sign-in.html
	    └── sign-up.html
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;spring-initialzr-ile-projenin-oluşturulması&#34;&gt;Spring Initialzr ile Projenin Oluşturulması&lt;/h2&gt;
&lt;p&gt;&lt;a href=&#34;https://start.spring.io/&#34;&gt;https://start.spring.io/&lt;/a&gt; adresine giderek veya kullandığınız IDE’nin ilgili &lt;strong&gt;plugin&lt;/strong&gt;’lerini kullanarak bir proje oluşturun.
Projede Spring Web, Lombok, Thymeleaf, Spring Security, Java Mail Sender, H2 ve Spring Data JPA &lt;strong&gt;dependency&lt;/strong&gt;’lerini seçin.
Tercihen farklı bir veritabanı da kullanabilirsiniz.&lt;/p&gt;
&lt;h2 id=&#34;user-entity-sinin-oluşturulması&#34;&gt;User Entity’sinin Oluşturulması&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;entity&lt;/strong&gt; adında bir &lt;strong&gt;package&lt;/strong&gt; oluşturun ve içinde UserRole adında bir &lt;strong&gt;enum&lt;/strong&gt; yaratın. Kullanıcı rollerini tutacağımız bu &lt;strong&gt;enum&lt;/strong&gt;da ADMIN ve USER adında iki değer olacak.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;enum&lt;/span&gt; UserRole &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    ADMIN&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; USER
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Sonra &lt;strong&gt;User&lt;/strong&gt; adında bir &lt;strong&gt;class&lt;/strong&gt; yaratın. Bu class &lt;strong&gt;UserDetails interface&lt;/strong&gt;’ini implement etmeli. UserDetails &lt;strong&gt;interface&lt;/strong&gt;’i temel kullanıcı bilgilerinin metotlarını barındıran bir interface. Örnek bir kullanımını görmek için &lt;strong&gt;org.springframework.security.core.userdetails.User&lt;/strong&gt; sınıfına bakabilirsiniz. Hatta doğrudan bu sınıfı &lt;strong&gt;extend&lt;/strong&gt; edip eklemek istediğiniz değişkenleri ekleyebilirsiniz. Ben &lt;strong&gt;extend&lt;/strong&gt; etmeden sıfırdan bir &lt;strong&gt;class&lt;/strong&gt; oluşturacağım. Birkaç değişken oluşturup &lt;strong&gt;UserDetails&lt;/strong&gt;’dan gelen metotların &lt;strong&gt;body&lt;/strong&gt;lerini dolduracağız.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Setter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Builder&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@EqualsAndHashCode&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@NoArgsConstructor&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@AllArgsConstructor&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Entity&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;name &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Users&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;User&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;implements&lt;/span&gt; UserDetails &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Id&lt;/span&gt;
    &lt;span style=&#34;color:#a2f&#34;&gt;@GeneratedValue&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;strategy &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; GenerationType&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;IDENTITY&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Long id&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String name&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String surname&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String email&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String password&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Builder.Default&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; UserRole userRole &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; UserRole&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;USER&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Builder.Default&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Boolean locked &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;false&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Builder.Default&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Boolean enabled &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;false&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; Collection&lt;span style=&#34;color:#666&#34;&gt;&amp;amp;&lt;/span&gt;lt&lt;span style=&#34;color:#666&#34;&gt;;?&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;extends&lt;/span&gt; GrantedAuthority&lt;span style=&#34;color:#666&#34;&gt;&amp;amp;&lt;/span&gt;gt&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt; getAuthorities&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; SimpleGrantedAuthority simpleGrantedAuthority &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; SimpleGrantedAuthority&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;userRole&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;name&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;());&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; Collections&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;singletonList&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;simpleGrantedAuthority&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; String &lt;span style=&#34;color:#00a000&#34;&gt;getPassword&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; password&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; String &lt;span style=&#34;color:#00a000&#34;&gt;getUsername&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; email&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;boolean&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;isAccountNonExpired&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;true&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;boolean&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;isAccountNonLocked&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;!&lt;/span&gt;locked&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;boolean&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;isCredentialsNonExpired&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;true&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;boolean&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;isEnabled&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; enabled&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;&lt;strong&gt;expired&lt;/strong&gt; değişkenini kullanmayacağım için &lt;strong&gt;isAccountNonExpired&lt;/strong&gt; ve &lt;strong&gt;isCredentialsNonExpired&lt;/strong&gt; metotlarından true döndürdüm. Username yerine email kullanacağım için de &lt;strong&gt;getUsername&lt;/strong&gt; metodundan email döndürdüm. Diğerlerini metot isimlerinden çıkarabilirsiniz.&lt;/p&gt;
&lt;h2 id=&#34;userservice-in-oluşturulması&#34;&gt;UserService’in Oluşturulması&lt;/h2&gt;
&lt;p&gt;Kullanıcı kaydı işlemlerini yapacağımız UserService &lt;strong&gt;class&lt;/strong&gt;ı için user adında bir &lt;strong&gt;package&lt;/strong&gt; oluşturacağız. Bu &lt;strong&gt;class&lt;/strong&gt; da UserDetailsService &lt;strong&gt;interface&lt;/strong&gt;ini implement edecek. Bu &lt;strong&gt;interface&lt;/strong&gt;ten loadByUsername adında bir metot alacağız. email kullanacağımız için bu sınıf da adı &lt;strong&gt;loadByUsername&lt;/strong&gt; olsa da mail parametresi alıp ona göre kullanıcı döndürecek.&lt;/p&gt;
&lt;p&gt;Tabii veritabanından kullanıcı çekmek için önce repository’e ihtiyacımız var. Hemen aynı sınıf içinde UserRepository &lt;strong&gt;interface&lt;/strong&gt;i oluşturuyoruz ve içinde &lt;strong&gt;findByEmail&lt;/strong&gt; metot imzasını oluşturuyoruz.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;interface&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;UserRepository&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;extends&lt;/span&gt; CrudRepository&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;User&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; Long&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    Optional&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;User&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;findByEmail&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;String email&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Şimdi UserService’e geri dönüp &lt;strong&gt;loadByUsername&lt;/strong&gt; metodunun içini doldurabiliriz.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; UserDetails &lt;span style=&#34;color:#00a000&#34;&gt;loadUserByUsername&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;String email&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;throws&lt;/span&gt; UsernameNotFoundException &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; Optional&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;User&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; optionalUser &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; userRepository&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;findByEmail&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;email&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;if&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;optionalUser&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;isPresent&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;())&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; optionalUser&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;get&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;else&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;throw&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; UsernameNotFoundException&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;MessageFormat&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;format&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;User with email {0} cannot be found.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; email&lt;span style=&#34;color:#666&#34;&gt;));&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;confirmationtoken-classının-oluşturulması&#34;&gt;ConfirmationToken Classının Oluşturulması&lt;/h2&gt;
&lt;p&gt;Her kullanıcı kaydolduğunda bir token oluşturacağız ve göndereceğimiz mailde bu token ile eşsiz bir link oluşturacağız. user &lt;strong&gt;package&lt;/strong&gt;ı içinde ConfirmationToken adında bir class yaratıyoruz ve aşağıdaki şekilde dolduruyoruz.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Entity&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Getter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@Setter&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@AllArgsConstructor&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@NoArgsConstructor&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;ConfirmationToken&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Id&lt;/span&gt;
    &lt;span style=&#34;color:#a2f&#34;&gt;@GeneratedValue&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;strategy &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; GenerationType&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;IDENTITY&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Long id&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String confirmationToken&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; LocalDate createdDate&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@OneToOne&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;targetEntity &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; User&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;class&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; fetch &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; FetchType&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;EAGER&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f&#34;&gt;@JoinColumn&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;nullable &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;false&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; name &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;user_id&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; User user&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    ConfirmationToken&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;User user&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;this&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;user&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; user&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;this&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;createdDate&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; LocalDate&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;now&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;this&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;confirmationToken&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; UUID&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;randomUUID&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;().&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;toString&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Her kullanıcıya bir &lt;strong&gt;token&lt;/strong&gt; vereceğimiz için OneToOne ilişki kuruyoruz ve &lt;strong&gt;token&lt;/strong&gt;ların bir geçerlilik süresi olacağı için createdDate değişkeni tutuyoruz.&lt;/p&gt;
&lt;h2 id=&#34;örnek-kullanıcı-kaydı-senaryosuna-göre-metotların-yazılması&#34;&gt;Örnek Kullanıcı Kaydı Senaryosuna Göre Metotların Yazılması&lt;/h2&gt;
&lt;p&gt;Servisleri ve tüm metotları en baştan yazmak yerine aşama aşama gitmeyi daha doğru buluyorum. Böylece gerçek bir geliştirme akışına daha yakın bir yazı olacak.&lt;/p&gt;
&lt;p&gt;Kullanıcı kaydında önce kullanıcı bilgilerini alacağız. Sonra &lt;strong&gt;BCryptPasswordEncoder&lt;/strong&gt; ile parolayı encode edeceğiz ve kullanıcıyı &lt;strong&gt;enabled=false(default)&lt;/strong&gt; olacak şekilde kaydedeceğiz. Sonra bir ConfirmationToken oluşuturup bu &lt;strong&gt;token&lt;/strong&gt;’ı kullanıcı ile ilişkilendireceğiz.
&lt;strong&gt;Token&lt;/strong&gt; ile eşsiz bir link oluşturup kullanıcıya mail yoluyla göndereceğiz. Kullanıcı bu linke tıkladığında ise ilgili kullanıcının enabled alanı &lt;strong&gt;true&lt;/strong&gt; olacak ve &lt;strong&gt;token&lt;/strong&gt; silinecek.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;signUpUser&lt;/strong&gt; metodunu oluşturmadan önce ConfirmationTokenRepository ve ConfirmationTokenService oluşturup yeni token kaydetmek için bir metot oluşturacağız.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Repository&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;interface&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;ConfirmationTokenRepository&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;extends&lt;/span&gt; CrudRepository&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;ConfirmationToken&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; Long&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Service&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@AllArgsConstructor&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;ConfirmationTokenService&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; ConfirmationTokenRepository confirmationTokenRepository&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;saveConfirmationToken&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;ConfirmationToken confirmationToken&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	confirmationTokenRepository&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;save&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;confirmationToken&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Şimdi &lt;strong&gt;UserService&lt;/strong&gt;e gidip &lt;strong&gt;signUpUser&lt;/strong&gt; metodunu yazalım.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;signUpUser&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;User user&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; String encryptedPassword &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; bCryptPasswordEncoder&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;encode&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;user&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;getPassword&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;());&lt;/span&gt;

    user&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;setPassword&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;encryptedPassword&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; User createdUser &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; userRepository&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;save&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;user&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; ConfirmationToken confirmationToken &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; ConfirmationToken&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;user&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

    confirmationTokenService&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;saveConfirmationToken&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;confirmationToken&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;mail-confirmation-metotlarının-yazılması&#34;&gt;Mail Confirmation Metotlarının Yazılması&lt;/h2&gt;
&lt;p&gt;Senaryoda kullanıcı, kendisine gelen maile tıkladığında çalışacak olan metodu yazalım. Önce link ile maili onayladıktan sonra &lt;strong&gt;token&lt;/strong&gt;&amp;lsquo;ı silecek olan metodu yazalım.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;deleteConfirmationToken&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;Long id&lt;span style=&#34;color:#666&#34;&gt;){&lt;/span&gt;

    confirmationTokenRepository&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;deleteById&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;id&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Şimdi de maili &lt;strong&gt;confirm&lt;/strong&gt; edecek olan metodu yazalım.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;confirmUser&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;ConfirmationToken confirmationToken&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

  &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; User user &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; confirmationToken&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;getUser&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;

  user&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;setEnabled&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;true&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

  userRepository&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;save&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;user&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

  confirmationTokenService&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;deleteConfirmationToken&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;confirmationToken&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;getId&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;());&lt;/span&gt;

&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;spring-mail-ayarları&#34;&gt;Spring Mail Ayarları&lt;/h2&gt;
&lt;p&gt;Ben Gmail için örnek bir yml dosyasını aşağıda paylaşıyorum. Eğer 2-factor kullanıyorsanız uygulama için özel bir parola oluşturmanız gerekiyor.
(&lt;a href=&#34;https://support.google.com/mail/answer/185833?hl=en&#34;&gt;https://support.google.com/mail/answer/185833?hl=en&lt;/a&gt;) yml yerine &lt;strong&gt;application.properties&lt;/strong&gt; de kullanabilirsiniz.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;spring:
  mail:
    host: smtp.gmail.com
    port: 587
    username: &amp;lt;MAIL ADRESI&amp;gt;
    password: &amp;lt;PAROLA&amp;gt;
    properties:
      mail:
	smtp:
	  auth: true
	  starttls:
	    enable: true
	  connectiontimeout: 5000
	  timeout: 3000
	  writetimeout: 5000
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;emailservice-in-ve-mail-gönderen-metodun-yazılması&#34;&gt;EmailService’in ve Mail Gönderen Metodun Yazılması&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;user package&lt;/strong&gt;&amp;lsquo;ı içinde &lt;strong&gt;EmailSenderService&lt;/strong&gt; adında bir &lt;strong&gt;class&lt;/strong&gt; oluşturun ve aşağıdaki şekilde doldurun.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Service&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@AllArgsConstructor&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;EmailSenderService&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; JavaMailSender javaMailSender&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Async&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;sendEmail&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;SimpleMailMessage email&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	javaMailSender&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;send&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;email&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Şimdi de &lt;strong&gt;UserService&lt;/strong&gt; içinde mail gönderen metodu yazalım.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;sendConfirmationMail&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;String userMail&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; String token&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; SimpleMailMessage mailMessage &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; SimpleMailMessage&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
    mailMessage&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;setTo&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;userMail&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    mailMessage&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;setSubject&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Mail Confirmation Link!&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    mailMessage&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;setFrom&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;&amp;lt;MAIL&amp;gt;&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    mailMessage&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;setText&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;
	    &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Thank you for registering. Please click on the below link to activate your account.&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;http://localhost:8080/sign-up/confirm?token=&amp;#34;&lt;/span&gt;
		    &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; token&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

    emailSenderService&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;sendEmail&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;mailMessage&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;websecurityconfig-ve-webconfig-class-ı-ile-security-konfigürasyonunun-yapılması&#34;&gt;WebSecurityConfig ve WebConfig Class’ı ile Security Konfigürasyonunun Yapılması&lt;/h2&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Configuration&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@AllArgsConstructor&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;WebSecurityConfig&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;extends&lt;/span&gt; WebSecurityConfigurerAdapter &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; UserService userService&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; BCryptPasswordEncoder bCryptPasswordEncoder&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

      &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;protected&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;configure&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;HttpSecurity http&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;throws&lt;/span&gt; Exception &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	      http
			      &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;authorizeRequests&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt;
			      &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;antMatchers&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/sign-up/**&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/sign-in/**&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
			      &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;permitAll&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt;
			      &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;anyRequest&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt;
			      &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;authenticated&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt;
			      &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;and&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt;
			      &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;formLogin&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt;
			      &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;loginPage&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/sign-in&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
			      &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;permitAll&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
      &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

      &lt;span style=&#34;color:#a2f&#34;&gt;@Autowired&lt;/span&gt;
      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;configureGlobal&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;AuthenticationManagerBuilder auth&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;throws&lt;/span&gt; Exception &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	      auth&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;userDetailsService&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;userService&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
			      &lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;passwordEncoder&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;bCryptPasswordEncoder&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
      &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Configuration&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;WebConfig&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

      &lt;span style=&#34;color:#a2f&#34;&gt;@Bean&lt;/span&gt;
      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; BCryptPasswordEncoder &lt;span style=&#34;color:#00a000&#34;&gt;bCryptPasswordEncoder&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; BCryptPasswordEncoder&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
      &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Burada hangi sayfaların &lt;strong&gt;authentication&lt;/strong&gt; olmadan kullanılabileceğini, giriş işlemini hangi &lt;strong&gt;path&lt;/strong&gt;&amp;lsquo;in &lt;strong&gt;handle&lt;/strong&gt; edeceğini seçiyoruz.&lt;/p&gt;
&lt;h2 id=&#34;controller-ların-yazılması-ve-sayfaların-oluşturulması&#34;&gt;Controller’ların Yazılması ve Sayfaların Oluşturulması&lt;/h2&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@Controller&lt;/span&gt;
&lt;span style=&#34;color:#a2f&#34;&gt;@AllArgsConstructor&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;UserController&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; UserService userService&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;final&lt;/span&gt; ConfirmationTokenService confirmationTokenService&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@GetMapping&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/sign-in&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    String &lt;span style=&#34;color:#00a000&#34;&gt;signIn&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;sign-in&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@GetMapping&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/sign-up&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    String &lt;span style=&#34;color:#00a000&#34;&gt;signUp&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;sign-up&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@PostMapping&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/sign-up&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    String &lt;span style=&#34;color:#00a000&#34;&gt;signUp&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;User user&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	userService&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;signUpUser&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;user&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;redirect:/sign-in&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@GetMapping&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/confirm&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt;
    String &lt;span style=&#34;color:#00a000&#34;&gt;confirmMail&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#a2f&#34;&gt;@RequestParam&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;token&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; String token&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	Optional&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;ConfirmationToken&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; optionalConfirmationToken &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; confirmationTokenService&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;findConfirmationTokenByToken&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;token&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	optionalConfirmationToken&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;ifPresent&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;userService&lt;span style=&#34;color:#666&#34;&gt;::&lt;/span&gt;confirmUser&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;/sign-in&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Şimdi de &lt;strong&gt;controller&lt;/strong&gt;&amp;lsquo;da yönlendirdiğimiz sayfaları hazırlayalım.&lt;/p&gt;
&lt;h2 id=&#34;thymeleaf-ile-sayfaların-oluşturulması&#34;&gt;Thymeleaf ile Sayfaların Oluşturulması&lt;/h2&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&lt;span style=&#34;color:#080&#34;&gt;&amp;lt;!DOCTYPE html&amp;gt;&lt;/span&gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;html&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;xmlns:th&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;http://www.thymeleaf.org&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;lang&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;en&amp;#34;&lt;/span&gt;&amp;gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;head&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;title&lt;/span&gt;&amp;gt;Spring Boot User Authentication&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;title&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;head&lt;/span&gt;&amp;gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;body&lt;/span&gt;&amp;gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;form&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;role&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;form&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:action&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;@{/sign-in}&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:method&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;post&amp;#34;&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;lable&lt;/span&gt;&amp;gt;Username&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;lable&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;text&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;id&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;username&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;name&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;username&amp;#34;&lt;/span&gt;&amp;gt;

    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;lable&lt;/span&gt;&amp;gt;Password&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;lable&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;password&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;id&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;password&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;name&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;password&amp;#34;&lt;/span&gt;&amp;gt;

    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;submit&amp;#34;&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;form&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;body&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;html&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&lt;span style=&#34;color:#080&#34;&gt;&amp;lt;!DOCTYPE html&amp;gt;&lt;/span&gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;html&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;xmlns:th&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;http://www.thymeleaf.org&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;lang&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;en&amp;#34;&lt;/span&gt;&amp;gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;head&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;title&lt;/span&gt;&amp;gt;Spring Boot User Authentication&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;title&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;head&lt;/span&gt;&amp;gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;body&lt;/span&gt;&amp;gt;
&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;form&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;role&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;form&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:action&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;@{/sign-up}&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:method&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;post&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:object&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;${user}&amp;#34;&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;lable&lt;/span&gt;&amp;gt;Name&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;lable&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;text&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;id&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;name&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;name&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;name&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:field&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;*{name}&amp;#34;&lt;/span&gt;&amp;gt;

    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;lable&lt;/span&gt;&amp;gt;Surname&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;lable&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;text&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;id&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;surname&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;name&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;surname&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:field&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;*{surname}&amp;#34;&lt;/span&gt;&amp;gt;

    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;lable&lt;/span&gt;&amp;gt;Email&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;lable&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;text&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;id&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;email&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;name&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;email&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:field&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;*{email}&amp;#34;&lt;/span&gt;&amp;gt;

    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;lable&lt;/span&gt;&amp;gt;Password&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;lable&lt;/span&gt;&amp;gt;
    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;password&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;id&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;password&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;name&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;password&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;th:field&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;*{password}&amp;#34;&lt;/span&gt;&amp;gt;

    &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;input&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;type&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;submit&amp;#34;&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;form&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;body&lt;/span&gt;&amp;gt;
&amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;html&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Buraya kadar eksiksiz takip ettiyseniz &lt;a href=&#34;http://localhost:8080/sign-up&#34;&gt;http://localhost:8080/sign-up&lt;/a&gt; adresinden kullanıcı kaydı yapabilirsiniz. Tabii ki bu haliyle yetersiz bir proje. Çünkü &lt;strong&gt;exception handling&lt;/strong&gt; kısımlarını eklemedim. Aynı zamanda &lt;strong&gt;token&lt;/strong&gt;&amp;lsquo;ların geçerliliğini kontrol etme gibi şeyleri de kontrol etmedim. Bunlar basit işlemler olduğu için yalnızca üye kaydı ve girişi yapacağınız kısımdan bahsettim.&lt;/p&gt;
</description>
        </item>
        
        <item>
            <title>CAP Teorisi ve Blokzincir</title>
            <link>http://kamer.dev/cap-teorisi-ve-blokzincir/</link>
            <pubDate>Sat, 06 Jul 2019 19:27:12 +0000</pubDate>
            
            <guid>http://kamer.dev/cap-teorisi-ve-blokzincir/</guid>
            <description>&lt;p&gt;Dağıtık sistemler hakkında bazı tezler öne süren CAP teorisi, 2000 yılında Eric Brewer tarafından ortaya atılmış ve 2002 yılında Seth Gilbert ve Nancy Lynch tarafından ispatı yayınlanmıştır. O zamandan bu yana da birçok dağıtık sistemin tasarımını etkilemiştir. Peki CAP teorisi blockzincir teknolojisine dair düşüncelerimizi ne yönde etkileyebilir? Bu sorunun cevabını verebilmek için öncelikle CAP teorisini inceleyelim.&lt;/p&gt;
&lt;h2 id=&#34;cap-teorisi&#34;&gt;CAP Teorisi&lt;/h2&gt;
&lt;p&gt;Teori, veri paylaşımının yapıldığı dağıtık sistemlerin tasarımında bazı “trade-off”lara dikkat çeker. Bu sistemlerde aşağıda bahsedeceğim üç özellikten en fazla iki tanesinin garanti edilebileceğini öne sürer. Baş harfleriyle teoriye adını veren özellikler şunlardır:&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;C&lt;/strong&gt;onsistency(Tutarlılık): Ağda bulunan her düğümün(node) verilerin en güncel halini barındırmasıdır. Yani her düğümün aynı veriye sahip olmasıdır. Gilbert ve Lynch’in consistency yerine “atomic” kelimesini kullandıkları bu özellik hakkında belirlediği önemli bir ayrıntıyı gözden kaçırmamak lazım. Bir sistem ya “consistent”tır, ya da değildir. Yani yarım tutarlı ve büyük oranda tutarlı gibi ifadeler bu tanımın kapsamına girmez.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;A&lt;/strong&gt;vailability(Ulaşılabilirlik): Tüm aktif düğümler kendilerine gelen bütün isteklere belli bir zaman içinde cevap vermek zorundadır.
Burada tek gereklilik bütün isteklere cevap verilmesi. Verinin tutarlı olup olmaması bu özelliğin dışındadır. Diğer yandan ulaşılabilir bir sistemde mevcut düğüm cevap veremiyorsa da ağdaki işlemler devam eder.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;P&lt;/strong&gt;artition tolerance(Bölünme toleransı): Ağ problemlerinde sistemin devamlılığını sürdürmesidir. Ağ hatalarından dolayı sistemdeki düğümler bölünebilir. Bu gibi bölünmelerde A’nın veya C’nin sürdürülmesidir. Yani sistemin hata toleransı sağlamasıdır.&lt;/p&gt;
&lt;p&gt;Yukarıdaki üç kavramın üçü de aynı anda sağlanamayacağından teori üç alt kategoriye ayrılıyor. Yani ikişer olarak bu kavramların başarıldığı kombinasyonlara.&lt;/p&gt;
&lt;h3 id=&#34;1-dot-ca&#34;&gt;1. CA&lt;/h3&gt;
&lt;p&gt;Teoriyi blokzincir ışığında değerlendirdiğimiz için bu ihtimal üzerine kafa yormaya gerek yok. Partition tolerance zaten blokzincirlerin karakteristik bir özelliği. Tek bir düğümü olan merkezi veritabanları bu kategoriye girer.&lt;/p&gt;
&lt;h3 id=&#34;2-dot-cp&#34;&gt;2. CP&lt;/h3&gt;
&lt;p&gt;Bu tip bir ağda partition durumunda tolerans sağlanır fakat verilerin tüm düğümler arasında güncel olup olmadığı sorusu bir zafiyete sebep olur. Çünkü bölünen düğümlerle iletişim kuramayız. Bu durumunda bir trade-off yapmamız gerekiyor. C’yi seçtiğimizde,verilerin güncel olmaması ihtimalinden dolayı hata mesajı göndererek cevap veririz.&lt;/p&gt;
&lt;h3 id=&#34;3-dot-ap&#34;&gt;3. AP&lt;/h3&gt;
&lt;p&gt;CP sistemlerdeki P için bir değişme yoktur. Fakat C ve A arasındaki seçimimizde tercih hakkımızı A’dan yana kullanırsak AP sisteme sahip oluruz. AP sistemde istemcilerden gelen tüm isteklere cevap verilir. Fakat partition durumunda bu verilerin en güncel olup olmadığı doğrulanmaz.&lt;/p&gt;
&lt;h2 id=&#34;blokzincir-ağları-hangi-özellikten-feragat-ediyor-olabilir&#34;&gt;Blokzincir Ağları Hangi Özellikten Feragat Ediyor Olabilir?&lt;/h2&gt;
&lt;p&gt;Bu konuyu düşünürken hepimizin aşina olduğu Bitcoin örneği üzerinden ilerleyeceğim. Teoriye göre dağıtık bir sistemde bir özellikten feragat etmek zorundayız. Peki bitcoin hangisinden feragat ediyor? İhtimallerle beraber değerlendirelim.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Partition Tolerance:&lt;/strong&gt; Önce bunu aradan çıkaralım. Herhangi bir blokzincirde partition tolerance’tan feragat edemeyiz. Zaten blokzincir teknolojisinin sağladığı en önemli şeylerden biri bu toleranstır.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Availability:&lt;/strong&gt; Eğer bitcoinde availability’den feragat edilirse bir düğümde bağlantı problemi yaşandığında bitcoin transferleri duracaktır. Çünkü ulaşılabilir bir ağda mevcut düğümde problem yaşandığında da ağ işlevine devam eder.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Consistency:&lt;/strong&gt; Tutarlılıktan feragat edersek de yine ciddi bir zafiyetimiz olur. Tutarlı olmayan hayali bir bitcoin ağında işlemlerin gerçekleştiği garanti edilemez. İşlemi başlatabiliriz fakat bu işlemin, yeterli sayıda düğüme ulaşmadığı için, gerçekleşmeme şansı olur.&lt;/p&gt;
&lt;p&gt;Birer birer incelediğimizde üç özelliğin de eksikliği ciddi zafiyetler yaratacak gibi duruyor. Öyleyse Bitcoin, CAP teorisini çürütüyor mu?&lt;/p&gt;
&lt;p&gt;Kısa cevap, hayır çürütmüyor. Uzun cevap için konudan sapmadan CAP teorisini biraz daha irdelememiz gerekiyor. Öncelikle şunu düşünelim, bir sistemin tutarlı olması için ne gerekir? Daha önce de bahsettiğimiz gibi tüm düğümler verilerin en güncel halini barındırmalı. Bunu sağlamak için de bölünme durumunda ağ bunu tespit edebilmeli. Her dağıtık sistem bunu sağlamak için farklı stratejiler kullanır. Bu stratejilerden biri de consensus(fikir birliği) algoritmalarıdır. Yani çoğunluğun fikir birliğine varması. Bitcoinde bölünme tespiti ve tutarlılık için fikir birliği algoritmaları ne kadar uygulanabilir? Daha açık bir ifadeyle şu an, şu saniye bitcoinde fikir birliğine varılması için kaç düğümün aynı fikirde olması gerekiyor? Bu sorunun cevabı çok değişken. Çünkü public bir ağ ve ağa katılmak, ağdan ayrılmak gibi işlemler çok kolay. Yani çoğunluk hesaplamak çok zor bir işlem. Hadi bunu örneklendirelim. Bir felaket sonucu Amerika kıtası ve dünyanın geri kalanı arasında internet erişiminin koptuğunu düşünün. Bu durumda bitcoin, tutarlılığını nasıl sağlayacak? Bitcoinin çalışma prensibini düşündüğümüzde böyle bir durumda iki zincir olacağını ve bitcoinin eskisi gibi çalışmaya devam edeceğini tahmin edebiliriz. Çünkü bölünme toleransı sayesinde sistem işlevselliğini devam ettiriyor. Ama tutarsız olarak. Çünkü iki farklı zincirde gerekli işlem gücü sağlandığında farklı işlemler devam edecek.&lt;/p&gt;
&lt;p&gt;Bu durumda bitcoinin consistency’den, yani tutarlılıktan feragat ettiğini söyleyebiliriz. Yazının başından bu yana tutarlılık hakkında söylediklerim bitcoin için de geçerlidir. Bitcoinde bir işlem başlattığımızda bunun gerçekleşmeme olasılığı mevcuttur. Fakat elbette bu olasılık yukarıda bahsettiğim gibi ihtimali düşük senaryolar dahilinde gerçekleşir. Bitcoin tarihindeki forklara bakarsanız consistency problemlerinin zaman zaman yaşandığını ama yaşanan geçici problemlerin düzeltildiğini görebilirsiniz.&lt;/p&gt;
&lt;h2 id=&#34;yararlandığım-kaynaklar&#34;&gt;Yararlandığım Kaynaklar&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://dzone.com/articles/understanding-the-cap-theorem&#34;&gt;https://dzone.com/articles/understanding-the-cap-theorem&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://howtodoinjava.com/hadoop/brewers-cap-theorem-in-simple-words/&#34;&gt;https://howtodoinjava.com/hadoop/brewers-cap-theorem-in-simple-words/&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://cryptographics.info/cryptographics/blockchain/cap-theorem/&#34;&gt;https://cryptographics.info/cryptographics/blockchain/cap-theorem/&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://paulkernfeld.com/2016/01/15/bitcoin-cap-theorem.html&#34;&gt;https://paulkernfeld.com/2016/01/15/bitcoin-cap-theorem.html&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
</description>
        </item>
        
        <item>
            <title>NativeScript-Vue ile Mobil Uygulama Geliştirme</title>
            <link>http://kamer.dev/nativescript-vue-ile-mobil-uygulama-gelistirme/</link>
            <pubDate>Sun, 02 Jun 2019 14:27:02 +0000</pubDate>
            
            <guid>http://kamer.dev/nativescript-vue-ile-mobil-uygulama-gelistirme/</guid>
            <description>&lt;div class=&#34;block-plain&#34;&gt;
  &lt;div&gt;&lt;/div&gt;
&lt;p&gt;Bu yazı 2 Haziran 2019 tarihinde yazılmıştır. Geçen sürede birçok şey değişmiş olabilir. Yazıya başlamadan önce bu durumu göz önünde bulundurmanızı tavsiye ederim.&lt;/p&gt;
&lt;/div&gt;
&lt;p&gt;Bir süredir VueJS kullanarak mobil uygulama geliştirme konusunda bir araştırma yapmayı düşünüyordum. Araştırmalarım sonucu zaten çok fazla seçeneğim olmadığını farkettim ve NativeScript’i denemeye karar verdim. Henüz React Native ile karşılaştırılabilecek seviyede değil. Fakat aktif bir topluluğa sahip ve bu yüzden ileride adını daha çok duyacağımızı düşünüyorum. Öncelikle kısaca nativescript’in ne olduğundan bahsedeyim.&lt;/p&gt;
&lt;p&gt;Nativescript, Angular, VueJS, TypeScript, or JavaScript kullanarak IOS ve Android uygulama geliştirme imkanı sunan açık kaynak kodlu bir framework. Eğer VueJS ile kod yazmayı seviyorsanız NativeScript-vue ile uygulama geliştirmek sizin için keyifli bir deneyim olabilir. Eğer çok profesyonel bir uygulamaya ihtiyacınız yoksa ve yeni bir dil/framework öğrenmenize engel bir şeyler varsa NativeScript-Vue işinizi görecektir. İncelediğim kadarıyla güzel bir dokümanları var ve Slack üzerinde faaliyet gösteren aktif bir toplulukları var.&lt;/p&gt;
&lt;p&gt;Bu yazıda basit bir uygulama geliştirerek NativeScript’in nasıl çalıştığını göreceğiz. Pratik olması açısından &lt;strong&gt;NativeScript Playground&lt;/strong&gt; ortamını kullanacağız. Bu ortam, doğrudan tarayıcı üzerinde NativeScript uygulamaları geliştirmenize imkan tanıdığı için SDK kurmak gibi şeyler ile uğraşmanıza gerek yok.&lt;/p&gt;
&lt;h2 id=&#34;1-dot-çalışma-ortamımızı-hazırlıyoruz&#34;&gt;1. Çalışma Ortamımızı Hazırlıyoruz&lt;/h2&gt;
&lt;p&gt;Öncelikle &lt;a href=&#34;https://play.nativescript.org&#34;&gt;https://play.nativescript.org&lt;/a&gt; linkine gidin ve üye olun. Bu zorunlu değil fakat projelerinizin bulut üzerinde bulunmasına imkan tanıdığı için tavsiye ederim. İkinci olarak IOS veya Android cihazınıza NativeScript Playground ve NativeScript Preview uygulamalarını yükleyin. Bunlar da kodunuzun canlı önizlemesini görmeniz için gerekiyor. Linkleri aşağıda bulabilirsiniz.&lt;/p&gt;
&lt;h2 id=&#34;2-dot-nativescript-playground-ı-tanıyalım&#34;&gt;2. NativeScript Playground’ı Tanıyalım&lt;/h2&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/nativescript-vue/nativescript-playground.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Playground’ı ilk açtığınızda sizi bu ekran karşılayacak. Gördüğünüz gibi sol üstte Project Explorer var. Yanındaki +’ya tıklayarak npm paketleri, klasörler, dosyalar ekleyebilirsiniz. Sol altta Components sekmesi altında NativeScript bileşenleri bulunmakta. Doğrudan kod yazarak geliştirme yapabileceğiniz gibi buradan çek-bırak ile de çalışabilirsiniz. Editörün masaüstü kod editörlerinde olduğu gibi kod tamamlama gibi özellikleri var. Sağ üstte preview butonuyla da uygulamanızı telefonunuz üzerinden test edebilirsiniz.&lt;/p&gt;
&lt;h2 id=&#34;3-dot-projemizin-template-ini-hazırlayalım&#34;&gt;3. Projemizin Template’ini Hazırlayalım&lt;/h2&gt;
&lt;p&gt;Projemiz deneysel bir şey olacağı için fazla ayrıntıya girmeyeceğim. Breaking Bad dizisine ait repliklerin rastgele verildiği bir Rest Api’yi kullanacağımız bir proje olacak. Öncelikle taslak olarak verilen kodda Page etiketi arasındaki kodları silelim. Sonra Page etiketine ActionBar istemediğimize dair bir attribute ekleyelim.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;Page&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;class&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;page&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;actionBarHidden&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;true&amp;#34;&lt;/span&gt;&amp;gt; &amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;Page&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Sonra sol altta componentlerin olduğu kısımdan çek-bırak yaparak veya doğrudan kod ile StackLayout ekliyoruz. Layout’a attribute olarak ise dikey hizalama yapmak için orientetion attribute’u ekliyoruz.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;StackLayout&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;orientation&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;vertical&amp;#34;&lt;/span&gt; &amp;gt; &amp;lt;/&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;StackLayout&lt;/span&gt;&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;İçine ise iki tane label ekleyelim. Biri repliğin bulunucağı, diğeri ise repliği söyleyen kişinin adının bulunacağı bileşen. Taşma durumunda yazının bir satır aşağı kayabilmesi için textWrap atttibute’unu true yapalım ve label içeriklerini VueJS ile bind edelim.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-html&#34; data-lang=&#34;html&#34;&gt;&amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;Label&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;id&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;quote&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;textWrap&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;true&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;quote&amp;#34;&lt;/span&gt; /&amp;gt; &amp;lt;&lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;Label&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;id&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;author&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;textWrap&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;true&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;:text&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;author&amp;#34;&lt;/span&gt; /&amp;gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;4-dot-api-i̇şlemleri&#34;&gt;4. API İşlemleri&lt;/h2&gt;
&lt;p&gt;Şimdi Script’e gelip data içinde &lt;code&gt;quote&lt;/code&gt; ve &lt;code&gt;author&lt;/code&gt; değişkenlerini tanımlayalım. İlk değerleri boş olsun. Sonra methods kısmında fetchQuote adında bir metot tanımlayalım. Bu metot içinde API&amp;rsquo;ye bağlanıp sözü çekeceğiz. Bunun için Script içinde bir import satırı ekleyeceğiz.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-js&#34; data-lang=&#34;js&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;import&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;*&lt;/span&gt; as http from &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;http&amp;#34;&lt;/span&gt;;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Bunu ekledikten sonra metot içine gelip aşağıdaki kodu ekleyin.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-js&#34; data-lang=&#34;js&#34;&gt;http.getJSON(&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;https://breaking-bad-quotes.herokuapp.com/v1/quotes&amp;#34;&lt;/span&gt;)
.then( res =&amp;gt; {
  &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;this&lt;/span&gt;.quote &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; res[&lt;span style=&#34;color:#666&#34;&gt;0&lt;/span&gt;].quote
  &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;this&lt;/span&gt;.author &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; res[&lt;span style=&#34;color:#666&#34;&gt;0&lt;/span&gt;].author;
},
error( error =&amp;gt; {
  console.log(error);
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Burada API’den istek atıp gelen JSON cevabı değişkenlerimize veriyoruz. Bir hata olması durumunda ise konsola yazdırmasını istedik. Gerçek bir uygulama için yeterli bir exception handling yöntemi değil elbette fakat şimdilik bu yeterli.&lt;/p&gt;
&lt;p&gt;Şimdi de uygulamayı her açtığımızda otomatik olarak bir replik çekmesi için Script kısmında created() açıyoruz ve içine &lt;code&gt;this.fetchQuote();&lt;/code&gt; yazıyoruz. Şimdiye kadar geldiğimiz aşamayı görmek için sağ üstte Preview butonuna basın ve çıkan QR kodunu Playground uygulamasına okutun.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/nativescript-vue/native-script-demo1.jpeg&#34;/&gt;
&lt;/figure&gt;

&lt;h2 id=&#34;5-dot-görsellik-ve-event-ekleyelim&#34;&gt;5. Görsellik ve Event Ekleyelim&lt;/h2&gt;
&lt;p&gt;Eğer şimdiye kadar doğru takip ettiyseniz yukarıdaki gibi bir sonuç elde edeceksiniz. Bundan sonra her Ctrl+S yaptığınızda bu uygulama güncellenecek.&lt;/p&gt;
&lt;p&gt;Temel fonksiyonumuzu yerine getirdiğimize göre şimdi de biraz görsellik katalım. İlk olarak sol üstte Project explorer’ın olduğu kısımda +’ya basıp assets adında bir klasör ekleyelim ve içine &lt;a href=&#34;./static/images/nativescript-vue/breaking-bad-wallpaper.jpg&#34;&gt;şu linkteki&lt;/a&gt; resmi yükleyin. Sonra Style kısmına aşağıdaki kodu ekleyin.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-css&#34; data-lang=&#34;css&#34;&gt;#&lt;span style=&#34;color:#00f;font-weight:bold&#34;&gt;quote&lt;/span&gt; {
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;font-size&lt;/span&gt;: &lt;span style=&#34;color:#666&#34;&gt;40&lt;/span&gt;&lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;px&lt;/span&gt;;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;text-align&lt;/span&gt;: &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;right&lt;/span&gt;;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;margin-top&lt;/span&gt;: &lt;span style=&#34;color:#666&#34;&gt;30&lt;/span&gt;&lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;%&lt;/span&gt;;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;font-weight&lt;/span&gt;: &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;bold&lt;/span&gt;;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;margin-right&lt;/span&gt;: &lt;span style=&#34;color:#666&#34;&gt;10&lt;/span&gt;&lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;px&lt;/span&gt;;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;color&lt;/span&gt;: &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;white&lt;/span&gt;;
}

#&lt;span style=&#34;color:#00f;font-weight:bold&#34;&gt;author&lt;/span&gt; {
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;text-align&lt;/span&gt;: &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;right&lt;/span&gt;;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;font-size&lt;/span&gt;: &lt;span style=&#34;color:#666&#34;&gt;25&lt;/span&gt;&lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;px&lt;/span&gt;;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;margin-top&lt;/span&gt;: &lt;span style=&#34;color:#666&#34;&gt;10&lt;/span&gt;&lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;%&lt;/span&gt;;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;margin-right&lt;/span&gt;: &lt;span style=&#34;color:#666&#34;&gt;3&lt;/span&gt;&lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;px&lt;/span&gt;;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;color&lt;/span&gt;: &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;white&lt;/span&gt;;
}

.&lt;span style=&#34;color:#00f&#34;&gt;page&lt;/span&gt; {
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;background-image&lt;/span&gt;: &lt;span style=&#34;color:#a2f&#34;&gt;url&lt;/span&gt;(&lt;span style=&#34;color:#b44&#34;&gt;&amp;#39;~/assets/breaking-bad1.jpg&amp;#39;&lt;/span&gt;);
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;background-position&lt;/span&gt;: &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;center&lt;/span&gt;;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;background-size&lt;/span&gt;: &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;cover&lt;/span&gt;;
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Kaydettiğinizde aşağıdaki gibi bir şey çıkması lazım.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/nativescript-vue/native-script-demo2.jpeg&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Uygulamamıza son bir özellik daha ekleyelim. Ekrana her tıkladığımızda yeni replik getirsin. Bunun için event’leri kullanacağız.&lt;/p&gt;
&lt;p&gt;Page elementine gelin ve &lt;code&gt;@tap=&amp;quot;fetchQuote&amp;quot;&lt;/code&gt; yazın. Ekrana dokunduğunuzda o metotu çağıracaktır.&lt;/p&gt;
&lt;p&gt;Eğer şimdiye kadar yazıyı doğru takip ettiyseniz aşağıdaki gibi bir sonuç elde etmeniz gerekiyor.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/nativescript-vue/native-script-demo3.gif&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Yapacaklarımız bu kadar. Umarım NativeScript-Vue’yu sevmişsinizdir. Daha fazlasını öğrenmek için ilk tavsiyem NativeScript Playground’da sağ tarafta bulunan iki dersi takip etmeniz. İki örnek ders var. Sonra gayet güzel bir örnek olan &lt;a href=&#34;https://github.com/tralves/groceries-ns-vue&#34;&gt;market listesi uygulaması&lt;/a&gt;nı inceleyin. En iyi kaynak ise bence &lt;a href=&#34;https://nativescript-vue.org/en/docs/introduction/&#34;&gt;kendi dokümanları&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Projeye ait kodlar için:&lt;/strong&gt; &lt;a href=&#34;https://github.com/kamer/nativescipt-vue-breakingbad-replikleri&#34;&gt;https://github.com/kamer/nativescipt-vue-breakingbad-replikleri&lt;/a&gt;&lt;/p&gt;
</description>
        </item>
        
        <item>
            <title>Arch Linux’da Wi-fi’ye Nasıl Bağlanılır?</title>
            <link>http://kamer.dev/arch-linuxta-wi-fiye-nasil-baglanilir/</link>
            <pubDate>Sun, 02 Jun 2019 14:19:51 +0000</pubDate>
            
            <guid>http://kamer.dev/arch-linuxta-wi-fiye-nasil-baglanilir/</guid>
            <description>&lt;p&gt;Merhabalar. Dün uzun zamandır yüklemeyi düşündüğüm Arch Linux’a geçtim. Her ne kadar rolling-release bir dağıtım olduğu için zaman zaman stabiliteden ödün verdiğine dair eleştirilerin hedefi olsa da okuduğum kadarıyla sevdiğim ve merak ettiğim bir dağıtımdı. Şu anki kısa deneyimimde de ilk izlenimim olumlu yönde.&lt;/p&gt;
&lt;p&gt;Arch Linux’la alakalı en çok duyduğum iki şey çok iyi bir topluluğunun olduğu ve wiki/forum sayfalarının birçok konuda yeterli olduğuydu. ISO imajını indirme aşamasından itibaren sadece forum ve wiki sayfalarına bakıp Google araması yapmadığımı düşündüğümde duyduklarımın doğru olduğunu söyleyebilirim. Zaten çok sık güncelleme alan bir dağıtım olduğu için Wiki sayfası dışında arama yapmak da pek önerilmiyor. Yani Arch Linux’un tavsiyesine uyduğunuz takdirde bu yazıyı okumamanız gerekiyor fakat bu yazıda anlatacaklarım ve Arch Linux hakkında ileride yazacağım yazılar Wiki sayfasında Türkçesi olmayan konular. İngilizce bilmeyen kişilerin faydalanması için yazıyorum.&lt;/p&gt;
&lt;h2 id=&#34;netctl&#34;&gt;netctl&lt;/h2&gt;
&lt;p&gt;netctl, terminal’den çalışan, profil temelli bir ağ yöneticisidir. Profil kelimesini özellikle yazdım, çünkü yapacağımız işlemlerde bu bilgi aklınızda bulunmalı. netctl bir Arch projesidir ve base package’da olduğu için muhtemelen sisteminizde yüklüdür fakat biz yine de işimizi garantiye almak adına netctl ve Wifi’ya bağlanmak için gerekli olan paketleri indirelim. Bunun için elbette pacman kullanacağız. Terminali açın ve aşağıdaki komutu yazın.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-bash&#34; data-lang=&#34;bash&#34;&gt;sudo pacman -S netctl wpa_supplicant dhcpcd dialog
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Eğer bu paketlerin bilgisayarınızda olup olmadığını öğrenmek isterseniz aşağıdaki komutu yazın.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-bash&#34; data-lang=&#34;bash&#34;&gt;sudo pacman -Qi paketAdi
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Bu komutta -Q query anlamına gelen sorgu işlemini yapar, -i ise information’dır ve o paket hakkında bilgi verir.
Bu paketleri yükledikten sonra iki farklı şekilde Wifi’a bağlanmayı bağlanmayı anlatacağım.&lt;/p&gt;
&lt;h3 id=&#34;netctl-örnek-profil-dosyasını-kullanarak&#34;&gt;netctl Örnek Profil Dosyasını Kullanarak&lt;/h3&gt;
&lt;p&gt;Önce netctl örnek profil dosyasını kullanmak için aşağıdaki komutu yazacağız:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-bash&#34; data-lang=&#34;bash&#34;&gt;sudo cp /etc/netctl/examples/wireless-wpa /etc/netctl/ornekProfilAdi
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Yukarıdaki kod parçası ilk dizinde bulunan wireless-wpa dosyasını ikinci dizine kopyalar. Yukarıdaki dizin dışında bir yere kopyalamak da mümkündür fakat profil dosyaları  &lt;code&gt;/etc/netctl&lt;/code&gt;  dizininde tutulur. Kopyalama işleminden sonra  &lt;code&gt;sudo nano /etc/netctl/ornekProfilAdi&lt;/code&gt;  komutu ile profil dosyasını düzenleyeceğiz. Karşınıza aşağıdaki gibi bir dosya açılmış olması lazım.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-bash&#34; data-lang=&#34;bash&#34;&gt;&lt;span style=&#34;color:#b8860b&#34;&gt;Description&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#39;A simple WPA encrypted wireless connection&amp;#39;&lt;/span&gt;
&lt;span style=&#34;color:#b8860b&#34;&gt;Interface&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;wlan0
&lt;span style=&#34;color:#b8860b&#34;&gt;Connection&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;wireless

&lt;span style=&#34;color:#b8860b&#34;&gt;Security&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;wpa
&lt;span style=&#34;color:#b8860b&#34;&gt;IP&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;dhcp

&lt;span style=&#34;color:#b8860b&#34;&gt;ESSID&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#39;MyNetwork&amp;#39;&lt;/span&gt;
&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;# Prepend hexadecimal keys with \&amp;#34;&lt;/span&gt;
&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;# If your key starts with &amp;#34;, write it as &amp;#39;&amp;#34;&amp;#34;&amp;lt;key&amp;gt;&amp;#34;&amp;#39;&lt;/span&gt;
&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;# See also: the section on special quoting rules in netctl.profile(5)&lt;/span&gt;
&lt;span style=&#34;color:#b8860b&#34;&gt;Key&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#39;WirelessKey&amp;#39;&lt;/span&gt;
&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;# Uncomment this if your ssid is hidden&lt;/span&gt;
&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;#Hidden=yes&lt;/span&gt;
&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;# Set a priority for automatic profile selection&lt;/span&gt;
&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;#Priority=10&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Burada değiştirmeniz gerekenleri sırasıyla yazıyorum:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Interface adınızı öğrenmek için  &lt;code&gt;ip link list&lt;/code&gt;  komutunu kullanın. Output’ta listelenen isimler arasında w ile başlayan bir isim olacak.  &lt;em&gt;(wlp2s0 gibi)&lt;/em&gt; Bu isim sizin interface parametreniz olacak.&lt;/li&gt;
&lt;li&gt;ESSID ise wifi adınız.&lt;/li&gt;
&lt;li&gt;Son olarak key kısmına şifrenizi yazdıktan sonra Ctrl-O yapıp enter’a basıp kaydedin. Sonra ctrl+x’e basıp nano’dan çıkın.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Artık profilimiz tamam. Profili çalıştırmak için  &lt;code&gt;netctl start ornekProfilAdi&lt;/code&gt;  komutunu çalıştırın ve  &lt;code&gt;ping -c 5 8.8.8.8&lt;/code&gt;  komutu ile bağlantınızı test edin. Eğer tüm adımları doğru takip ettiyseniz internete bağlanmış olmanız lazım. Fakat start komutu yalnızca bilgisayarınızı kapatana kadar geçerlidir. Bu komutu her bilgisayarınızı açtığınızda çalıştırmak isterseniz  ~sudo netctl enable ornekProfilAdi~komutunu çalıştırın. İşlem bu kadar.&lt;/p&gt;
&lt;h3 id=&#34;wifi-menu-kullanarak&#34;&gt;wifi-menu Kullanarak&lt;/h3&gt;
&lt;p&gt;Profil oluşturmak için basit bir araç olan  &lt;em&gt;wifi-menu&lt;/em&gt;’yu kullanmak için komut satırına &lt;code&gt;sudo wifi-menu&lt;/code&gt; yazın. Bu komut çevrenizdeki wifi noktalarını arayıp listeleyecek.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/arch-linux-wifi/wifi-menu.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Bu liseten bağlanmak istediğiniz Wifi erişim noktasını seçin. Sonra size bir profil adı soracak. İstediğiniz bir adı girin. Daha sonra parolayı da girdiğinizde profil oluşturulacak ve bağlanacak. Eğer tüm adımları doğru takip ettiyseniz internete bağlanmış olmanız lazım. Fakat start komutu yalnızca bilgisayarınızı kapatana kadar geçerlidir. Bu komutu her bilgisayarınızı açtığınızda çalıştırmak isterseniz  &lt;code&gt;sudo netctl enable ornekProfilAdi&lt;/code&gt; komutunu çalıştırın.&lt;/p&gt;
&lt;p&gt;Arch Linux’da Wifi’ya bağlanma işlemi bu kadar. Her ne kadar zor gibi gözükse de neyi neden yaptığımızı öğrendikten sonra zor sayılmaz.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Kaynak:&lt;/strong&gt; &lt;a href=&#34;https://wiki.archlinux.org/index.php/netctl&#34;&gt;https://wiki.archlinux.org/index.php/netctl&lt;/a&gt;&lt;/p&gt;
</description>
        </item>
        
        <item>
            <title>Merkeziyetsizlik Kavramından Ne Anlamalıyız?</title>
            <link>http://kamer.dev/merkeziyetsizlik-kavramindan-ne-anlamaliyiz/</link>
            <pubDate>Sun, 26 May 2019 13:58:50 +0000</pubDate>
            
            <guid>http://kamer.dev/merkeziyetsizlik-kavramindan-ne-anlamaliyiz/</guid>
            <description>&lt;p&gt;Kripto paraların hayatımıza girmesiyle beraber merkeziyetsizlik kavramı da sıklıkla duyduğumuz kelimelerden biri oldu. Blockzincir teknolojisinden ve kripto paralardan bahsederken bu teknolojilerin merkeziyetsiz olmasını övüyoruz. Blokzincir dünyasında gün aşırı merkeziyetsiz bir uygulamanın çıktığını duyuyor ve çoğunlukla bundan mutluluk duyuyoruz. Bir çoğumuzun merkeziyetsiz internete dönüş gibi büyük hayalleri var. Peki ya bu kavramın üzerine yeterince düşündük mü? Merkeziyetsizliğe gerçekten ihtiyacımız var mı? Merkeziyetsizliği başarabildik mi? Bunu başarmak gerçekten mümkün mü?&lt;/p&gt;
&lt;p&gt;Dünyayı şekillendireceğini düşündüğümüz bu teknolojinin vaadettiği yenilikleri iyice ölçüp tartmamız gerektiğini düşünüyorum. En azından bu yeniliklere gerçekten ihtiyacımız olup olmadığını bilirsek projelerin etiketlerinden çok hayatımıza getireceği faydaya göre değerlendirebiliriz. Yoksa adının başında &lt;strong&gt;decentralized&lt;/strong&gt; yazan veya etiketinde &lt;strong&gt;dApp&lt;/strong&gt; olan her proje bize güzel görünür.&lt;/p&gt;
&lt;h2 id=&#34;merkeziyetsizlik-nedir&#34;&gt;Merkeziyetsizlik nedir?&lt;/h2&gt;
&lt;p&gt;Öncelikle merkeziyetsizliği anlayalım. Bu kavram Türkçede de İngilizcede de merkezin olmayışıyla kendine bir tanım bulduğu için önce merkezi olmayı tanımlayıp ondan sonra merkeziyetsizliği anlamaya çalışmak daha doğru. Bir örnekle başlayacağım. Örneğin markete gittiniz ve kasada kredi kartınızı uzattınız. Kasiyer bakiyenizin yetersiz olduğunu söyleyerek sizden başka bir kart vermenizi veya nakit ödeme yapmanızı rica etti. Fakat hesabınızda yeterli para olduğuna kesin eminsiniz. Böyle bir olayın gerçekleşme olasılığı çok düşük fakat kartı ATM’ye taktığınızda da 0 TL bakiye gördünüz. Bu durumda ne yapmanız gerekiyor? Paranızın var olduğuna emin olmanız yeterli değil, kasiyeri ikna etmeniz de anlamsız. Paranızın gerçekten var olabilmesi için bankanın ikna olması gerekiyor. Çünkü banka sistemi merkezi bir sistemdir. Yani tepedeki bir sistemin kendi altında bulunan sistemleri yönettiği, bir bilginin geçerli olmasının tek koşulunun hiyerarşinin tepesindeki aktörün bu bilgiyi doğrulaması olduğu bir sistem. Daha sıra dışı bir örnek vereyim. Bir gün yolda giderken GBT sorgusuna takıldınız ve sorguyu yapan polis memuru, sistemde TC kimlik numaranızın bulunmadığını söyledi. Yıllardır taşıdığınız bir kimlik, siz kendinizden eminsiniz fakat bu durumda sizin emin olmanız bir şey ifade etmez. Sizin, ailenizin, arkadaşlarınızın veya sizi tanıyan herkesin bu bilgiyi doğrulaması da bu bilgiyi geçerli yapmaz. Devletin, yani merkezi olan bu sistemin doğrulamadığı tüm bilgiler geçersizdir.&lt;/p&gt;
&lt;p&gt;Merkeziyetsiz bir sistemden bahsettiğimiz andan itibaren merkezi sistemde uygulanan yukarıdan-aşağıya(top-down) doğrulama hiyerarşisi yerine yatay bir karar verme mekanizması devreye girer. Yani paranızın olduğunu ispat etmeniz gereken merkez ortadan kalkar, bunun yerine yeterli sayıda insanın sizin paranız olduğuna ikna olması gerekir. Aynı şekilde kimliğinizi doğrulamak için arkadaşlarınızın, ailenizin, sizi tanıyan kişilerin kefil olması yeterli olabilir.&lt;/p&gt;
&lt;p&gt;Merkeziyetsizlikle karıştırılan bir kavram var, dağıtıklık. (distribution) Dağıtık bir sistemde, bilgi veya sistemin hesaplama gücü, sistemdeki düğümler arasında paylaştırılır. Buna örnek olarak DNA analizinin gerektirdiği yüksek işlem gücünün bir ağdaki bilgisayarlar arasında paylaştırılmasını verebiliz. Dolayısıyla bir sistem hem merkezi hem de dağıtık olabilir. Aynı şekilde bir sistem hem merkeziyetsiz hem de dağıtık olabilir.&lt;/p&gt;
&lt;p&gt;Merkeziyetsizlik tanımını bitirmeden değinmek istediğim bir konu var. Ethereum’un kurucusu olan Vitalik Buterin, “The Meaning of Decentralization” adıyla yayınladığı bir yazısında üç tip merkeziyetsizlikten bahsediyor.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Mimari Merkeziyetsizlik (Architectural decentralization):&lt;/strong&gt; Sistemdeki bilgisayar sayısıyla ve sistemin devre dışı kalan düğümlerden kaçını tolere edebileceğiyle ilgilidir.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Yönetimsel Merkeziyetsizlik (Political decentralization):&lt;/strong&gt; Sistemdeki bilgisayarları yöneten kişi ve kurum sayısını belirtir.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Mantıksal Merkeziyetsizlik:&lt;/strong&gt; Sistemi iki veya daha fazla parçaya böldüğümüzde sistemin buna vereceği tepkiyi ve sistemin tek bir büyük bilgisayar gibi davranıp davranmadığını kapsar.&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Public blokzincirler yönetimsel merkeziyetsizdir. Çünkü herhangi kişi ve kurumun sistemi yönetme yetkisi yoktur. Aynı zamanda mimari merkeziyetsizdir çünkü mimari olarak tek hata noktası (single point of failure) yoktur. Sisteme bağlı birden fazla cihaz olduğu için her düğüm kayıt defterinin bir kopyasını tutar. Ancak tek bir bilgisayar gibi davrandığı için mantıksal merkeziyetsiz değildir.&lt;/p&gt;
&lt;h2 id=&#34;merkeziyetsizlik-bize-ne-vadediyor&#34;&gt;Merkeziyetsizlik bize ne vadediyor?&lt;/h2&gt;
&lt;p&gt;Blokzincirle beraber hayatımıza daha çok giren merkeziyetsizlik kavramının dünyanın büyük çoğunluğunu heyecanlandırdığını kabul etmek lazım. Bence bunda iki büyük etken var. Birincisi merkeziyetsizliğin bize vadettikleri. Zira vadettiği şeyler birçok soruna çözüm buluyor. Diğeri ise şu, yakın zamanda Deniz Özgür’ün de ifade ettiği gibi &lt;a href=&#34;https://koinbulteni.com/deniz-ozgur-merkeziyetsizlik-kavraminin-ici-bosaltiliyor-43426.html&#34;&gt;merkeziyetsizlik kavramının içi boşaltılıyor&lt;/a&gt;. Çünkü birçok kişi merkeziyetsizliği sindirmeden süslü cümlelerle merkeziyetsizliği övüyor. Amaç, merkeziyetsizliğin bize vadettikleri olması gerekirken merkeziyetsizliğin kendisi bir amaç haline dönüşüyor ve ürünün sunduklarından çok tam olarak uygulanıp uygulanmadığından emin olmadığımız bir teknoloji bizi tatmin ediyor. Bu yazıda anlatmaya çabaladığım şey de bu aslında. Merkeziyetsizliğin bir araç olduğunun bilincine varmak ve bu aracın hangi sorunları çözebileceği üzerine düşünebilecek altyapıyı hazırlamak. Peki merkeziyetsizlik bize ne vadediyor?&lt;/p&gt;
&lt;h3 id=&#34;hata-toleransı&#34;&gt;Hata Toleransı&lt;/h3&gt;
&lt;p&gt;Karşımıza en çok çıkan argüman muhtemelen bu. Mantığı da gayet basit ve sistemin dağıtık olmasının sağladığı bir avantaj. Teknik alana çok fazla girmeden bir örnekle açıklayacağım. İnternette bir dosyayı indirmek istediğinizde sunucuda bir noktaya HTTP isteği gönderirsiniz. İletişime geçtiğiniz tek bir nokta vardır. Eğer o an o sunucu size cevap veremezse hata alırsınız. Bu hatayı telafi etmenin bir yolu yoktur. Ama merkeziyetsizliğin örneklerinden biri olan ve 2004 yılında kurulmuş olan BitTorrent, dosya paylaşımı için daha farklı bir yaklaşım kullanır.
Ağdaki her cihaz aynı zamanda birer sunucudur. Dolayısıyla bir dosya indirmek için birden fazla sunucuya istek gönderirsiniz ve dosyayı bu sunuculardan parçalar halinde indirirsiniz. Eğer ağda herhangi bir sunucu dosya aktarımı sırasında ağdan düşerse başka bir sunucuya istek gönderilir. Sistemde o dosyayı barındıran hiçbir sunucu kalmayıncaya kadar indirme işlemi devam eder. Böylece yüksek oranda hata toleransı sağlar.&lt;/p&gt;
&lt;p&gt;Buraya kadar hiçbir sorun yok. Ama hata toleransını sağlamak elbette bu kadar kolay değil. Örneğin sadece Türkiye’de kullanılan ve ülke vatandaşlarına yönelik merkeziyetsiz bir uygulama düşünün. Ülke çapında oluşabilecek bir internet kesintisinde sistem devre dışı kalacaktır. Böyle bir kesinti daha önce oldu. Dolayısıyla 82 milyon düğümlük dağıtık bir sistem dahi olsa hata toleransını başaramama ihtimali mevcut. Bu sadece ihtimallerden biri. Kısa bir beyin fırtınası ile birçok senaryo çıkarılabilir.&lt;/p&gt;
&lt;h3 id=&#34;saldırı-dayanıklılığı&#34;&gt;Saldırı Dayanıklılığı&lt;/h3&gt;
&lt;p&gt;Merkezi bir sistemde genellikle saldırı yapacağınız hedef bellidir. Bir veya birkaç sunucuya saldırı yapacaksınızdır. Dolayısıyla elinizdeki kaynakları ona uygun olarak düzenleyebilirsiniz. Örneğin herhangi bir sisteme saldırmaya yetecek kaynağınız yoksa zaafiyetlerini ararsınız ve minimum maliyetle maksimum zafiyeti yaratacağınız bir nokta ararsınız. Bu, hassas bilgilerin tutulduğu bir yer olabilir, kritik işlemlerin yapıldığı bir yer olabilir, hayal gücünüze kalmış. Fakat merkeziyetsiz bir sistemde böyle bir nokta yoktur. Eğer saldırmanız gereken bir hedef varsa bu hedef, ağın tamamı olur. Dolayısıyla saldırı dayanaklılığı büyük ölçüde artar.&lt;/p&gt;
&lt;h3 id=&#34;hileli-i̇ş-birliği-direnci--collusion-resistance&#34;&gt;Hileli İş Birliği Direnci (Collusion Resistance)&lt;/h3&gt;
&lt;p&gt;Bu başlığın Türkçe karşılığını bulmak zor olduğundan İngilizce’sini de ekledim. Hileli işbirliğinden kasıt ise şu, bir topluluğun içinde bu topluluğun çıkarlarına uygun hareket etmeyen kötü niyetli bazı gruplar olabilir. Bu oluşuma &lt;strong&gt;collusion&lt;/strong&gt; diyoruz. Örnek vermek gerekirse 4054 Sayılı Rekabetin Korunması Hakkında Kanunun amaçlarından biri piyasada oluşabilecek hileli iş birliklerini(collusion) önlemektir.
Buna yönelik olarak ülke sınırları içinde faaliyet gösteren ve piyasaları olumsuz etkileyecek nitelikte her türlü teşebbüsü engelleyici düzenlemeler yapar. Hileli iş birliği kelimesinin neyi kastettiğini açıklığa kavuşturduktan sonra bunu bir de merkeziyetsiz sistemler bağlamında inceleyelim.&lt;/p&gt;
&lt;p&gt;Fikir birliği (consensus) algoritmalarında genellikle yapılan işlemin geçerli sayılabilmesi için gereken bir çoğunluk olur. 51 saldırıları da adını buradan alır. Yani ağdaki bilgisayar gücünün yüzde 50&amp;rsquo;sinden fazlasına sahip olduğunuzda sistemde double-spending yapabilirsiniz. Hatta 21 Nisan 2019&amp;rsquo;da yayınlanan bir makaleye göre Ethereum ağında 25%’lik bir işlem gücüne sahip olmanız durumunda sistemde selfish-mining zafiyetini kullanabiliyorsunuz. Yani Ethereum ağında kötü maksatlar ile bir araya gelen yüzde 25&amp;rsquo;lik bir çoğunluk ağı zafiyete uğratabiliyor. Yani merkeziyetsiz sistemlerin bu konuda tam bir dirence sahip olduğunu söyleyemeyiz. Ama bu direnç merkezi sistemlere göre daha iyi durumdadır.
Dağıtıklık ne ölçüde artarsa bu iş birliğine karşı direnç o ölçüde artar. Merkezi sistemlerde ise zaten sistemde söz hakkı olan aktörlerin sayısı az veya tek olduğundan bu iş birliğine karşı direnç yok denecek kadar azdır.&lt;/p&gt;
&lt;h2 id=&#34;merkeziyetsizliği-başarabildik-mi&#34;&gt;Merkeziyetsizliği başarabildik mi?&lt;/h2&gt;
&lt;p&gt;Merkeziyetsizliğin bize vadettiği şeylerin bir kısmını olası eksik yönleriyle beraber inceledik. Peki şu anda merkeziyetsizliği başardık mı? Biraz da bunun üzerine kafa yoralım.&lt;/p&gt;
&lt;p&gt;Öncelikle şunu belirtmekte fayda görüyorum. Merkezi veya merkeziyetsiz olmak siyah-beyaz gibi net bir ayrıma sahip değil. Değerlendirme yaparken “ne kadar merkezi?” veya “ne kadar merkeziyetsiz?” gibi soruları sormak daha doğru olacaktır. Bitcoin’i ele alalım. Zira merkeziyetsizlik deyince aklımıza ilk gelen örnek genelde Bitcoin oluyor. 2014 Mayıs ayında, yani bundan tam 5 sene önceki hashrate dağılımına baktığımızda GHash %32 ile başı çekiyor. Arkasından F2Pool 13%, BTC Guild 12% ile takip ediyor. Yani üç büyük aktör toplamda 57%’lik bir hashrate’e sahip. Elimizdeki en güncel veri olan 2019 Nisan verilerine baktığımızda ise 16% ile &lt;a href=&#34;http://btc.com&#34;&gt;BTC.com&lt;/a&gt; ilk sırada. Arkasından AntPool 12%, F2Pool 11% ile takip ediyor. Yani ağdaki üç büyük aktörü topladığımızda hashrate’in yüzde 39&amp;rsquo;unu teşkil ediyor. Bu açıdan baktğımızda hashrate’in dağıtık olması açısından olumlu bir ilerleme var. Ama hayal ettiğimiz türden bir merkeziyetsizlik değil. Peki bitcoin’e ulaşma araçlarımız? Üçüncü parti bir aracıya, merkezi bir sisteme başvurmadan Bitcoin alan/alabilen kaç kişiyiz? Bu soruların cevapları aslında tam merkeziyetsizlikten henüz uzak olduğumuzu gösteriyor.
Paramızı merkezi bir banka yerine merkezi bir borsada tutmamız gerçekten mantıklı mı? Kaçımız kripto varlıklarını merkezi olmayan bir yerde tutuyor? Bu sayı gün geçtikçe kesinlikle artıyor ama tatmin edici bir sayıya ulaşana kadar tam merkeziyetsiz bir sisteme sahip olduğumuzu söylemek güç. Teoride merkeziyetsiz olabilir ama pratikte merkezi sistemlere ihtiyacımızı azaltamıyorsak merkeziyetsizliğin vadettiği yeniliklerden uzağız demektir.&lt;/p&gt;
&lt;p&gt;Kısaca toparlamak gerekirse merkeziyetsizliği başarmış sistemler var. Fakat tam anlamıyla hayal ettiğimiz seviyede değiller. Bu ivmeyle yükselen bir teknolojinin hayal ettiğimiz günlere gelmesi işten bile değil. Sadece merkeziyetsizlik fikrinin arkasında yatan sebepleri iyice sindirmemiz lazım. Bu da ancak üzerine kafa yorarak olur. Bir teknolojinin felsefi temellerinden bağımsız olarak yayılması beklenemez.&lt;/p&gt;
&lt;h2 id=&#34;madem-merkeziyetsizlik-yenilikler-sunuyor-kurumlar-neden-merkeziyetsiz-sistemlere-geçiş-yapmadı&#34;&gt;Madem merkeziyetsizlik yenilikler sunuyor, kurumlar neden merkeziyetsiz sistemlere geçiş yapmadı?&lt;/h2&gt;
&lt;p&gt;Merkeziyetsizliğin bize sunduğu yenilikleri düşündüğümüzde bu yaklaşımın hayatımızın daha çok içinde olmasını bekleriz. Fakat pratikte çok da fazla değişikliğin olduğu söylenemez. Bu da doğal olarak bir soruyu getiriyor, kurumlar neden merkeziyetsiz sistemlere geçiş yapmadı?&lt;/p&gt;
&lt;p&gt;Merkeziyetsizlik ve blokzincir üzerine konuşulanları gözlemlediğimizde insanların sık sık yanılgıya düştüğü bir konuyla karşılaşıyoruz. Birçok kişi sırf merkeziyetsizlik fikrini benimsediği için her sektöre ve ihtiyaca uygulanabileceğini düşünüyor. Ancak durum öyle değil. Bu fikir bizi yazının başlarında bahsettiğim &lt;strong&gt;teknolojiyi araç yerine amaç olarak kullanma&lt;/strong&gt; sorununa getiriyor. Eğer sistem içinde aktörlerin birbirine karşı veya aktörlerin sistem dışındaki aktörlere karşı şeffaflık ihtiyacı yoksa, gizlilik ihtiyacı yoksa, bilginin tüm aktörler arasında güncel ve doğru olması önemli değilse, bilgiyi oluşturma ve yazma yetkisi yalnızca bir merkezdeyse, aktörler arasında karşılıklı bir güven ilişkisine ihtiyaç yoksa blokzincir kullanarak merkeziyetsizlik uygulamanıza gerek yok. Biraz da blokzinciri hayatımızda neden daha fazla görmediğimize bakalım.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Bir kurumun blokzincir kullanmasının genelde üç temel sebebi olur. Hız, düşük maliyet ve merkeziyetsizlik. Fakat bu teknolojinin nispeten yeni bir teknoloji olmasından dolayı bu üç isteği de karşılamak kolay değil.&lt;/li&gt;
&lt;li&gt;Büyük kurumlar genellikle saniyede yüzlerce işlem kapasitesine ihtiyaç duyarlar. Bunun için ölçeklenebilirliği yüksek bir zincire ihtiyaç var. Bu da blokzincirin en büyük sorunlarından biri.&lt;/li&gt;
&lt;li&gt;Binlerce, milyonlarca lira yatırımları bir sisteme yatıracak yöneticiler bu teknolojiye tamamen güvenebilmeli. Kendini tamamen ispat edecek seviyeye gelmesine zaman olan ve yeterince olgunlaşmayan bir teknolojiye yatırım yapacak cesarete sahip olmak için bu fikri sindirebilmek lazım.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;sonuç&#34;&gt;Sonuç&lt;/h2&gt;
&lt;p&gt;Bu yazıda merkeziyetsizlik ve biraz da blokzincir üzerine düşüncelerimi aktarmaya çalıştım. Bu iki kavram beni de heyacanlandırıyor fakat eleştirmeden ve eksik yanlarını aramadan bu teknolojiyi daha iyi bir seviyeye getiremeyiz. Bu sebeple biraz eleştirel yaklaşmaya çalıştım. Bir cümle ile yazdıklarımı özetlemek gerekirse, merkeziyetsizlik fikri günümüzde birçok sorunun çözümüne götürüyor bizi. Bu, bizi sorunlara tozpembe bakmaya götürmemeli. Ancak doğru değerlendirmeler yaparak bu aracı bizi doğru amaçlara götürmesi için kullanabiliriz.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Yararlandığım Kaynaklar:&lt;/strong&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://koinbulteni.com/deniz-ozgur-merkeziyetsizlik-kavraminin-ici-bosaltiliyor-43426.html&#34;&gt;https://koinbulteni.com/deniz-ozgur-merkeziyetsizlik-kavraminin-ici-bosaltiliyor-43426.html&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.buybitcoinworldwide.com/ethereum/mining-pools/&#34;&gt;https://www.buybitcoinworldwide.com/ethereum/mining-pools/&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.rekabet.gov.tr/tr/Sayfa/Mevzuat/4054-sayili-kanunAspxAutoDetectCookieSupport=1&#34;&gt;https://www.rekabet.gov.tr/tr/Sayfa/Mevzuat/4054-sayili-kanunAspxAutoDetectCookieSupport=1&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://medium.com/@VitalikButerinthe-meaning-of-decentralization-a0c92b76a274&#34;&gt;https://medium.com/@VitalikButerinthe-meaning-of-decentralization-a0c92b76a274&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://arxiv.org/pdf/1901.04620.pdf&#34;&gt;https://arxiv.org/pdf/1901.04620.pdf&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://cippic.ca/sites/default/files/CDM%20submission%20CAIPv.Bell%20-%20Appendix1.pdf&#34;&gt;https://cippic.ca/sites/default/files/CDM%20submission%20CAIPv.Bell%20-%20Appendix1.pdf&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://eprint.iacr.org/2017/375.pdf&#34;&gt;https://eprint.iacr.org/2017/375.pdf&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://due.com/blog/why-arent-more-companies-using-the-blockchain/&#34;&gt;https://due.com/blog/why-arent-more-companies-using-the-blockchain/&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
</description>
        </item>
        
        <item>
            <title>Hyperledger Ekosistemindeki 13 Proje</title>
            <link>http://kamer.dev/hyperledger-ekosistemindeki-13-proje/</link>
            <pubDate>Sat, 25 May 2019 14:06:02 +0000</pubDate>
            
            <guid>http://kamer.dev/hyperledger-ekosistemindeki-13-proje/</guid>
            <description>&lt;p&gt;Hyperledger platformunun teknoloji dünyasına girmesinin üzerinden 4 yıldan daha az bir zaman oldu. Bu süre içinde 19 Mayıs 2019 itibariyle 13 tane proje duyuruldu. Eğer merakınız varsa veya hızla gelişen bu platforma çok geç kalmadan dahil olmak isterseniz ayrıntılarıyla olmasa da yüzeysel olarak bu 13 projenin ne işe yaradığını bilmenizi tavsiye ederim.&lt;/p&gt;
&lt;p&gt;Hyperledger’ın kendi sitesine girdiğimizde bizi “Hyperledger Serası&amp;quot;nı temsil eden aşağıdaki görsel karşılıyor.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/hyperledger-ecosystem/hyperledger-greenhouse.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Projelerin kendi sayfalarına girdiğimizde de -bence- yeni başlayan meraklı zihinlere pek de hitap etmeyen teknik açıklamalar buluyoruz. Bu yazıyı yazma amacım teknik ayrıntılardan olabildiğince arındırarak Hyperledger projelerini anlatmak. Projeleri kronolojik sıraya göre anlatacağım. Anlatacağım 13 projeden yalnızca 3 tanesi -Fabric, Sawtooth, Iroha- bir blokzincir. Diğerleri ise özelleşmiş bazı alanlarda bize kolaylık sağlayan araçlar barındırıyor. Temel kaynağım projelerin Github sayfaları ve resmi dokümanları. Bunların dışında yararlandığım kaynaklar ise sayfanın sonunda yer alıyor.&lt;/p&gt;
&lt;h2 id=&#34;hyperledger-fabric&#34;&gt;Hyperledger Fabric&lt;/h2&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/hyperledger-ecosystem/fabric-logo.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Bu ekosistemin ilk projesi olan Fabric, aynı zamanda en çok bilinen proje. Hatta Hyperledger’ın Hyperledger Fabric olduğuna dair yaygın bir yanlış da var. Fabric, kurumlar için tasarlanmış kapalı blokzincir uygulamaları geliştirmeye yarayan, modüler yapıda bir framework’tür. Genel amaçlı yazılım dilleri ile geliştirme yapmaya izin veren ilk blokzincirdir. İngilizce’de &lt;strong&gt;plug and play&lt;/strong&gt; adı verilen bir yapıdadır. Yani modülerdir ve uygulamanın içine amacınıza yönelik olarak hazırlanmış bileşenleri &lt;strong&gt;tak-çalıştır&lt;/strong&gt; yöntemi ile ekleyebilirsiniz.&lt;/p&gt;
&lt;p&gt;Kurumsal blokzincir gerekliliklerinde genellikle gizlilik ve kimlik doğrulaması ön plandadır. Fabric her ikisini de sağlar. Üyelik Servis Sağlayıcı(Membership Service Provider-MSP) sayesinde ağa yalnızca kimlik doğrulaması yapmış kişiler bağlanabilir. Kanallar sayesinde de kullanıcı grupları oluşturulup her gruba farklı yetki tanımları verilebilir. Böylece her veri ağdaki her katılımcının okuması/oluşturması/güncellemesi/silmesi için açık değildir.&lt;/p&gt;
&lt;p&gt;Hyperledger bir kriptopara projesi değildir. Dolayısıyla Fabric ağı kriptopara transferi için değildir. Ağda varlıklar(asset) vardır. Bu varlıkların maddi değeri olabilir. Yalnızca veri barındıran varlıklar da olabilir.&lt;/p&gt;
&lt;p&gt;Fabric’in çalışma prensiplerini aşağıdaki maddeler ile açıklayabiliriz:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;İşlemler, chaincode’lar(smart contract) ile güvence altına alınır ve tüm katılımcılar Docker konteynırları çalıştırarak ağa bağlanır.&lt;/li&gt;
&lt;li&gt;İşlemler kriptopara olmadan gerçekleştirilir.&lt;/li&gt;
&lt;li&gt;Tüm işlemler gizli ve güvenlidir. Bilgiler, yalnızca ağdaki katılımcıların fikir birliği(consensus) ile güncellenir.&lt;/li&gt;
&lt;li&gt;Tüm işlemlerin içeriği kriptoludur. Böylece içerik tüm kullanıcılar tarafından görüntülenemez.&lt;/li&gt;
&lt;li&gt;Katılımcılar ağa erişim sağlamak için üyelik servislerine kimlik kanıtı yapmak zorundadır.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;hyperledger-sawtooth&#34;&gt;Hyperledger Sawtooth&lt;/h2&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/hyperledger-ecosystem/sawtooth-logo.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Sawtooth, dağıtık kayıt defterleri oluşturmak, ayağa kaldırmak ve çalıştırmak için kullanılan modüler bir kurumsal blokzincir platformudur. Dikkat ettiyseniz gizlilik, kapalılık gibi bir terim kullanmadım. Sawtooth’un odak noktası kayıt defterlerini dağıtık yapmak ve akıllı kontratlar ile sistemi güvenli kılmaktır. Geçen zamanın kanıtı(proof of elapsed time-PoET) adı verilen bir consensus algoritması kullanır. Bu algoritma ile kaynak tüketimi minimize edilir.&lt;/p&gt;
&lt;p&gt;Sawtooth ile Fabric arasındaki temel iki fark ise aşağıdaki gibidir:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Ağ tipi:&lt;/strong&gt; Fabric’te ağa katılmak için MSP’ye kaydolup kimlik kanıtı yapmak zorunda olduğumuzdan bahsetmiştim. Sawtooth ile hem izinli hem de izinsiz blokzincirler geliştirebilirsiniz.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Gizlilik:&lt;/strong&gt; Sawtooth’ta tüm katılımcıların ağdaki işlemleri görme yetkisi vardır. Fabric’te ise farklı yetki tanımları ile verilerin gizliliğini sağlamak mümkün.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Sawtooth’un günlük hayattaki bir uygulamasını görmek isterseniz Necati Öztaş ve Zahid Dişçi’nin çevirisini yaptığı &lt;a href=&#34;https://medium.com/hyperledger-t%C3%BCrkiye-platformu/scantrust-ile-kahve-%C3%A7ekirde%C4%9Finin-yolculu%C4%9Fu-hyperledger-sawtooth-46313979cc8e&#34;&gt;ScanTrust projesini&lt;/a&gt; inceleyebilirsiniz.&lt;/p&gt;
&lt;h2 id=&#34;hyperledger-iroha&#34;&gt;Hyperledger Iroha&lt;/h2&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/hyperledger-ecosystem/iroha-logo.jpeg&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Iroha projesi, Japon Kaizen felsefesinden esinlenerek geliştirilmiş, adını Japonca bir şiirden almış bir dağıtık kayıt defteri teknolojisidir. Bir grup Japon yazılımcının mobil cihazlara yönelik olarak C++ dilinde geliştirdiği bir frameworktür. C++ ile yazılmış olması performans yönünden Iroha’yı ön plana çıkarıyor. Iroha deyince aklımızda gelmesi gereken iki anahtar kelime performans ve yalınlık.&lt;/p&gt;
&lt;p&gt;Iroha kaynak, bilgi ve dijital kimlik yönetimi konusunda başarılı bir framework. Aynı zamanda bizans hata toleransını sağlayan kendi consensus algoritması var. (Yet Another Consensus-YAC)&lt;/p&gt;
&lt;h2 id=&#34;hyperledger-burrow&#34;&gt;Hyperledger Burrow&lt;/h2&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/hyperledger-ecosystem/burrow-logo.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Burrow, en az Hyperledger kadar geçmişi olan bir proje. ErisDB adıyla Monax tarafından geliştirilmeye başlanmış, daha sonra da Hyperledger çatısı altına Burrow ismiyle girmiştir. Monax’ın CTO’su Casey Kuhlman, Burrow’u diğer projelerden ayıran özelliği tek bir cümle ile açıklıyor: “Burrow, Hyperledger ekosistemi içinde yalnızca bir şeyi iyi yapmak için tasarlandı: EVM (Ethereum Sanal Makinesi) akıllı kontratlarını izinli bir blokzincir ağında çalıştırmak.” Burrow üç ana bileşenden oluşuyor.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Consensus Engine: Ağdaki işlemler Bizans hata toleransına sahip Tendermint protokolü ile yapılıyor. Bu protokol ağın çatallanmasının önüne geçiyor.&lt;/li&gt;
&lt;li&gt;İzinli EVM: Ethereum’un izinli bir ağa çevrildiğini düşünün. Aynı şekilde Solidity dili kullanılarak sağlanmış turing-complete bir sistem var.&lt;/li&gt;
&lt;li&gt;RPC Gateway: İsminin çok teknik duruyor olması gözünüzü korkutmasın. Remote procedure call, istemcilerin(client) sunuclarla(server) haberleşmesini sağlayan bir yapı sunar. Yani kullanıcılar olarak bu gateway’i kullanarak ağ ile konuşabiliriz.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Kuhlman’ın Burrow’u anlatırken en çok üzerinde durduğu iki anahtar kelime hız ve kolaylık. Projeyi geliştirirken vadettikleri işlevselliği sunmanın yanında yazılımcılara hızlıca yaratabilecekleri bir ortamı sağlamaya çalışıyorlar.&lt;/p&gt;
&lt;h2 id=&#34;hyperledger-indy&#34;&gt;Hyperledger Indy&lt;/h2&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/hyperledger-ecosystem/indy-logo.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Indy de Hyperledger ekosisteminde adını en çok duyduğumuz projelerden biri. Indy deyince aklımıza ilk gelmesi gereken anahtar kelime dijital kimlik. Indy, kısaca blokzincir ağı üzerinde depolanan dijital kimlikler oluşturmamızı ve doğrulamamızı sağlayan kayıt defteridir. Bu projede blokzincirlerin dağıtık yapısı ön plana çıkıyor. Bunu bir örnekle açıklayalım. Günümüzde kimlik verilerine olan bakışımız merkezi bir bakış açısı. Verilerimiz kurumlar tarafından depolanıyor ve istedikleri gibi kullanıyorlar. GDPR gibi düzenlemelerin adı geçse de buna birçoğumuz güvenmiyoruz. Bunun yanı sıra verilerimizin nasıl depolandığını da bilmiyoruz. Neredeyse hiçbir kurum verilerimizi yüksek güvenlikli bir sistemde saklayacağını taahhüt etmiyor. Örneğin Nisan 2018&amp;rsquo;de çıkan bir habere göre Facebook, milyonlarca Instagram hesabına ait parolayı düz metin olarak tutuyormuş ve bu parolalara 20000&amp;rsquo;den fazla çalışanın erişimi bulunuyormuş. Bu örnek, dijital kimliklerden bağımsız olarak verilerimizi saklayan şirketlerin ne kadar umursamaz olabileceğini hayal etmeniz içindi. Bir örnek de Türkiye’den verelim. 2016 yılında 46 milyon Türkiye Cumhuriyeti vatandaşının kimlik bilgileri internete sızdı. Şu anda da rahatlıkla ulaşılabilen bu veritabanında TC Kimlik No, ad, soyad, anne adı, baba adı, yaş, doğum yeri, doğum tarihi, nüfusa kayıt olunan il ve açık adres bulunuyor.&lt;/p&gt;
&lt;p&gt;Indy, bu gibi sorunları tamamen çözdüğünü iddia etmiyor. Fakat ayakları yere basan bir vaat olarak dijital kimliklerde alışık olduğumuz denklemi değiştirip kimliklerimizi daha güvenli yapmayı hedefliyor. Bu yeni denklemde herkes kendi kimliğini kendisi yönetiyor. Böylece bir zafiyet milyonlarca kimliği değil bir kimliği hedef alıyor.&lt;/p&gt;
&lt;h2 id=&#34;hyperledger-cello&#34;&gt;Hyperledger Cello&lt;/h2&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/hyperledger-ecosystem/cello-logo.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Cello, Hyperledger ekosisteminin orkestra şefi. Bundan önce bahsettiğim projelerden farklı olarak Cello, ekosistem içinde zincirleri yönetmeyi üstlenmiş bir proje. Daha teknik bir terimle ifade etmek gerekirse Cello, BaaS(blockchain as a service) aracıdır.&lt;/p&gt;
&lt;p&gt;Şimdi yönetmek kavramını biraz daha açalım. Hyperledger’ın kurumsal bir çözüm olarak görüldüğü bir senaryoda tek bir blokzincir ağı yeterli olmayabilir. Bu durumda bu ağları yönetmek ve sürdürmek zor olacaktır. Cello ise bu zorluğu bizim için hafifletmeye çalışıyor. Cello’yu kullanarak;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Bu zincirleri farklı tipte cloud servislerinde ve container cluster’larda ayağa kaldırabilirsiniz.&lt;/li&gt;
&lt;li&gt;Çalışan ağların yaşam döngülerine dair her işlemi yönetebilirsiniz.&lt;/li&gt;
&lt;li&gt;Ağların loglarını, analizlerini takip edebilirsiniz.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Aynı zamanda bu işlemlerin hepsini size sunulan bir dashboard ile yapabilirsiniz.&lt;/p&gt;
&lt;h2 id=&#34;hyperledger-composer&#34;&gt;Hyperledger Composer&lt;/h2&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/hyperledger-ecosystem/composer-logo.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Hyperledger Composer, hızlı ve kolay bir şekilde kurumsal ağlar oluşturmamızı sağlayan bir proje. Bünyesinde barındırdığı araçlarla akıllı kontratlar ve kurumsal ağ tanımı dosyaları oluşturabiliriz. Temel amacı geliştirme süreçlerini hızlandırmak olan Composer projesinin dokümanlarında aylar sürecek bir projeyi haftalar içinde bitirmenizi sağlayacağı vaadi var. Fabric ağını desteklediği için Composer arayüzü üzerinde hazırladığınız bir projeyi doğrudan Fabric ağına import edip kullanabilirsiniz.&lt;/p&gt;
&lt;p&gt;Her ne kadar Hyperledger ekosistemi içinde bulunsa da, proje, Ağustos 2018 yılında durduruldu. Simon Stone, yaptığı yazılı bilgilendirmede projenin mimarisi genişledikçe sürdürmenin zorlaştığı gerekçesiyle projeyi durdurduklarını söyledi. Dolayısıyla production seviyesinde kullanmak doğru olmasa da bile Hyperledger Fabric ile geliştirme yapmaya başlamayı düşünen biri için iyi bir ısınma olabilir.&lt;/p&gt;
&lt;h2 id=&#34;hyperledger-explorer&#34;&gt;Hyperledger Explorer&lt;/h2&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/hyperledger-ecosystem/explorer-logo.jpg&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Daha önce herhangi bir blokzincir ağının block explorer sayfasını açtıysanız bu proje size yabancı gelmeyecek. Hyperledger Explorer ile ağınıza ait birçok bilgiyi sade bir arayüz ile görebilirsiniz. Bu bilgiler arasında katılımcı sayısı, blok sayısı, işlem sayısı, chaincode sayısı, blok ayrıntıları, işlemlere ait detaylar ve grafikler var ve tüm bu bilgiler için API desteği de sağlanıyor. Backend’de NodeJS, frontend’de React, veritabanı olarak da PostgreSQL kullanılıyor.&lt;/p&gt;
&lt;h2 id=&#34;hyperledger-quilt&#34;&gt;Hyperledger Quilt&lt;/h2&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/hyperledger-ecosystem/quilt-logo.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Hyperledger Quilt projesi Interledger protokolünün ekosistemdeki uygulaması. Dolayısıyla öncelikle Interledger’ı anlamak gerekiyor. ILP olarak da bilinen bu protokol, kayıt defterleri arasında para transferi yapmayı sağlıyor. Adından daha anlaşılabileceği gibi ILP bir kayıt defteri değil.
Yalnızca bu kayıt defterlerinin güvenli bir şekilde mesajlaşıp para transferi yapmasını sağlayan protokol. Hyperledger da Quilt projesi ile ekosistem içinde ILP’yi uyguluyor.&lt;/p&gt;
&lt;h2 id=&#34;hyperledger-caliper&#34;&gt;Hyperledger Caliper&lt;/h2&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/hyperledger-ecosystem/caliper-logo.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Bu proje hakkında anlatacak çok fazla bir şey yok. Aslında araç başlığı altında bulunan Aries, Cello, Composer, Explorer, Ursa, Quilt projeleri de tek bir amaca yönelik olarak yapılmış olduğundan ayrıntılı açıklayacak çok da bir şey yok. Caliper aracı Hyperledger ekosistemi içinde performans ölçümü yapan araç. An itibariyle(25 Mayıs 2019) Fabric, Sawtooth, Iroha, Burrow ve Composer projelerini destekliyor. Performans ölçümü için kullandığı belli başlı metrikler var. Bunlar başarı oranı, işlem ve okuma hacmi, işlem ve okuma gecikmesi, kaynak tüketimi.&lt;/p&gt;
&lt;h2 id=&#34;hyperledger-ursa&#34;&gt;Hyperledger Ursa&lt;/h2&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/hyperledger-ecosystem/ursa-logo.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Ursa, topluluktaki geliştiricilerin kriptografik fonksiyonları topladığı bir proje. Blokzincir deyince aklımıza ilk gelen kelimelerden biri olan güvenlik ve kriptografi. Dolayısıyla bu proje de platform içinde önemli bir görevi yerine getiriyor. İki alt kütüphaneden oluşuyor, libursa ve libzmix. Libursa kütüphanesi dijital imzalar, anahtar değişimi, kripto gibi işlemleri yerine getirirken libzmix sıfır bilgi ispatı gibi daha karmaşık işlemleri yapıyor. Projede kriptogafi dünyasında best practice olarak kabul edilen yöntem kullanılarak yeni implementasyonlar yazmak yerine libsodium, openssl ve libsecp256k1 kütüphaneleri kullanılıyor.&lt;/p&gt;
&lt;h2 id=&#34;hyperledger-grid&#34;&gt;Hyperledger Grid&lt;/h2&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/hyperledger-ecosystem/grid-logo.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Kurumsal blokzincir çözümlerinde belki de en çok duyduğumuz çözümler tedarik zincirleri hakkında. Grid de bu talebi karşılamak üzere geliştirilmiş bir proje. Özel olarak bir sektöre yöneldiği için Hyperledger platformunda bir ilk olma özelliğini taşıyor. Grid yalnızca bir framework, bir blokzincir değil. Sawtooth blokzincirini kullanıyor ve temel amacı tedarik zinciri uygulamalarını hızlandırmak ve kolaylaştırmak.&lt;/p&gt;
&lt;h2 id=&#34;hyperledger-aries&#34;&gt;Hyperledger Aries&lt;/h2&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/hyperledger-ecosystem/aries-logo.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Bu proje, bazı özellikleriyle Indy ve Quilt’e benziyor fakat kapsam ve proje tanımı bakımından daha geniş bir amaç hedefliyor. Aries’in amacı blokzincir temelli dijital kimlik verilerini saklamak ve paylaşmak. Kimlik verilerini sakladığı için Indy’e benzese de bu verilerin değişimini Indy dışındaki zincirlerle de yapmayı hedefliyor. Cüzdanlar arası iletişim ve güvenli iletişim barındırdığı için de Quilt’e benziyor fakat Aries ILP protokolünü kullanmıyor ve dijital kimliklere odaklanıyor.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Yararlandığım Kaynaklar&lt;/strong&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://www.edureka.co/blog/hyperledger-fabric/&#34;&gt;https://www.edureka.co/blog/hyperledger-fabric/&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://nxtgen.com/what-is-hyper-ledger&#34;&gt;https://nxtgen.com/what-is-hyper-ledger&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://jaxenter.com/hyperledger-burrow-interview-kuhlman-148519.html&#34;&gt;https://jaxenter.com/hyperledger-burrow-interview-kuhlman-148519.html&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://jaxenter.com/hyperledger-indy-interview-hardman-148796.html&#34;&gt;https://jaxenter.com/hyperledger-indy-interview-hardman-148796.html&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.blockchaindailynews.com/Hyperledger-Says-Hello-to-Cello%5Fa24978.html&#34;&gt;https://www.blockchaindailynews.com/Hyperledger-Says-Hello-to-Cello%5Fa24978.html&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://lists.hyperledger.org/g/composer/message/125&#34;&gt;https://lists.hyperledger.org/g/composer/message/125&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
</description>
        </item>
        
        <item>
            <title>Java Collection Framework (Türkçe)</title>
            <link>http://kamer.dev/java-collection-framework-turkce/</link>
            <pubDate>Sun, 19 May 2019 13:56:31 +0000</pubDate>
            
            <guid>http://kamer.dev/java-collection-framework-turkce/</guid>
            <description>&lt;p&gt;Merhabalar. Bu yazımda Java Collection Framework’ten bahsedeceğim. Öncelikle Oracle’ın sitesinden &lt;a href=&#34;https://docs.oracle.com/javase/8/docs/api/?java/util/Collections.html&#34;&gt;Java 8 Dokümanları&lt;/a&gt;nı inceleyelim.&lt;/p&gt;
&lt;p&gt;java.util paketinde yer alan collection framework’ün hiyerarşik yapısını incelediğimizde en üstte karşımıza &lt;strong&gt;Iterable&lt;T&gt;&lt;/strong&gt; interface’i çıkar. Bu interface’in özelliği kendisini implement eden objeyi for each döngüsünde kullanılabilir hale getirmektir. Dolayısıyla collection framework’te bulunan tüm class’ların içinde for each ile gezebileceğimiz çıkarımını yapabiliriz.&lt;/p&gt;
&lt;p&gt;Iterable&lt;T&gt; interface’inin altında karşımıza &lt;strong&gt;Collection&lt;E&gt;&lt;/strong&gt; interface’i çıkar. Collection, element adı verilen objelerin gruplarını temsil eder. Bazı collection’lar sıralı olur, bazıları sırasız; bazılarında tüm elementler eşsiz olur, bazılarında ise böyle bir zorunluluk yoktur. Bunları ihtiyaçlarımıza göre kullanırız.&lt;/p&gt;
&lt;p&gt;Collection&lt;E&gt; interface’inin altında ise 3 farklı interface vardır. &lt;strong&gt;Set&lt;E&gt;&lt;/strong&gt;, &lt;strong&gt;List&lt;E&gt;&lt;/strong&gt; ve &lt;strong&gt;Queue&lt;E&gt;&lt;/strong&gt;. Bu üç interface collection karakteristik özelliklerinin belirlendiği interface’lerdir.&lt;/p&gt;
&lt;h2 id=&#34;1-dot-set-e&#34;&gt;1. Set&lt;E&gt;&lt;/h2&gt;
&lt;p&gt;Set’in karakteristik özelliği aynı elemandan birden fazla olmasına izin vermemesi ve birden fazla null eleman kabul etmemesidir. Yani e1 ve e2 elementleri için e1.equals(e2) ise bu iki eleman aynı Set içinde barınamaz. Şimdi Set&lt;E&gt; interface’inden türetilen diğer collection framework üyelerine bakalım.&lt;/p&gt;
&lt;h3 id=&#34;hashset-e&#34;&gt;HashSet&lt;E&gt;&lt;/h3&gt;
&lt;p&gt;HashSet&lt;E&gt;’te veriler hashleme yöntemi ile tutulur. Verilerin sırasının korunacağını garanti etmez. Yani önce e1, sonra e2 elementini kaydedip e2, e1 sırasında çekebilirsiniz. Aynı zamanda HashSet&lt;E&gt; non-synchronized olduğu için birden fazla thread aynı anda bir HashSet’e erişip değiştirmeye çalışırsa problem yaşamamak için manuel bir çözüm olarak synchronized erişim sağlamalıyız.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;HashSet&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; meyveler &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; HashSet&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;();&lt;/span&gt;
	meyveler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Elma&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	meyveler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Armut&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	meyveler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Muz&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	meyveler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Çilek&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;// Aynı elementten bir tane daha eklemeye çalışıyoruz.
&lt;/span&gt;&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;&lt;/span&gt;	meyveler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Armut&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;// İki tane null eklemeye çalışıyoruz.
&lt;/span&gt;&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;&lt;/span&gt;	meyveler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;null&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	meyveler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;null&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;print&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;HashSet -&amp;gt; &amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	meyveler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;forEach&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;meyve &lt;span style=&#34;color:#666&#34;&gt;-&amp;gt;&lt;/span&gt; System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;print&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;meyve &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34; &amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Bu kodun çıktısı bende aşağıdaki gibi oldu. Sıralama sizde daha farklı olabilir. Çünkü bildiğiniz üzere HashSet’lerde çıktı rastgele sırayla verilir.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;HashSet -&amp;gt; null Armut Muz Çilek Elma
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;linkedhashset-e&#34;&gt;LinkedHashSet&lt;E&gt;&lt;/h3&gt;
&lt;p&gt;HashSet’ten tek farkı, eklenen elementlerin ekleme sırasına göre tutulmasıdır. (Insertion order) Tekrarlı element eklendiğinde ilk eklenen element bundan etkilenmez.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;LinkedHashSet&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; gunler &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; LinkedHashSet&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;();&lt;/span&gt;
	gunler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Pazartesi&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	gunler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Salı&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	gunler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Çarşamba&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	gunler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Perşembe&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	gunler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Cuma&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	gunler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Cumartesi&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	gunler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Pazar&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;// Aynı elementten tekrar kaydediyoruz.
&lt;/span&gt;&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;&lt;/span&gt;	&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;// Tekrarlı element sıralamayı değiştirmeyecek.
&lt;/span&gt;&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;&lt;/span&gt;	gunler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Pazartesi&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;print&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;LinkedHashSet -&amp;gt; &amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	gunler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;forEach&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;gun &lt;span style=&#34;color:#666&#34;&gt;-&amp;gt;&lt;/span&gt; System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;print&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;gun &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34; &amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Bu kodun çıktısı aşağıdaki gibidir:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;LinkedHashSet -&amp;gt; Pazartesi Salı Çarşamba Perşembe Cuma Cumartesi Pazar
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;treeset-e&#34;&gt;TreeSet&lt;E&gt;&lt;/h3&gt;
&lt;p&gt;TreeSet’lerde elementler artan sıralamayla, yani ascending order ile tutulur. null element kabul etmez. Eklenmeye çalışılırsa NullPointerException hatası verir.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;TreeSet&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;Integer&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; sayilar &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; TreeSet&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;Integer&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;();&lt;/span&gt;
	sayilar&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;4&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	sayilar&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;7&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	sayilar&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;2&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	sayilar&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;9&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;// Tekrarlı element ekliyoruz.
&lt;/span&gt;&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;&lt;/span&gt;	&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;// Kaydetmeyecek.
&lt;/span&gt;&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;&lt;/span&gt;	sayilar&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;7&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	sayilar&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;forEach&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;sayi &lt;span style=&#34;color:#666&#34;&gt;-&amp;gt;&lt;/span&gt; System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;print&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;sayi &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34; &amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Bu kodun çıktısı aşağıdaki gibi olacaktı:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;TreeSet -&amp;gt; 2 4 7 9
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id=&#34;2-dot-list-e&#34;&gt;2. List&lt;E&gt;&lt;/h2&gt;
&lt;p&gt;List’in karakteristik özellikleri tekrarlı elementlere izin vermesi, elementleri ekleme sırasına göre tutması ve istediğimiz index’e element eklememize izin vermesidir.&lt;/p&gt;
&lt;h3 id=&#34;arraylist-e&#34;&gt;ArrayList&lt;E&gt;&lt;/h3&gt;
&lt;p&gt;Collection framework’de en çok kullanılan class’tır. List özelliklerini barındırır.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;ArrayList&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; sehirler &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; ArrayList&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;();&lt;/span&gt;
	sehirler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Ankara&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	sehirler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Amasya&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	sehirler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Sivas&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	sehirler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;İzmir&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	sehirler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Eskişehir&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;// Tekrarlı element ekliyoruz.
&lt;/span&gt;&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;&lt;/span&gt;	sehirler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Amasya&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;// İstediğimiz index&amp;#39;e eleman ekliyoruz.
&lt;/span&gt;&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;&lt;/span&gt;	sehirler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;3&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Isparta&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;print&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;ArrayList -&amp;gt; &amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	sehirler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;forEach&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;sehir &lt;span style=&#34;color:#666&#34;&gt;-&amp;gt;&lt;/span&gt; System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;print&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;sehir &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34; &amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Kodun çıktısı aşağıdaki gibidir:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;ArrayList -&amp;gt; Ankara Amasya Sivas Isparta İzmir Eskişehir Amasya
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;linkedlist-e&#34;&gt;LinkedList&lt;E&gt;&lt;/h3&gt;
&lt;p&gt;Sonuçları bakımından ArrayList ile aynıdır. Fakat aralarında bazı farklar mevcuttur. Arama işlemlerinde LinkedList O(n) iken ArrayList’te O(1)’dir. Silme işlemlerinde ise ArrayList O(n) iken LinkedList O(1)’dir. Ekleme işlemleri de aynı sonuçları verir. Dolayısıyla eğer ekleme ve silme işlemleri sık yapılacaksa LinkedList kullanmak daha avantajlıdır. Arama işlemleri sık yapılacak ise de ArrayList daha avantajlıdır.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;LinkedList&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; filmler &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; LinkedList&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;();&lt;/span&gt;
	filmler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Person of Interest&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	filmler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Black Books&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	filmler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Seinfeld&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	filmler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Fargo&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;// İstediğimiz index&amp;#39;e eleman ekliyoruz.
&lt;/span&gt;&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;&lt;/span&gt;	filmler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;add&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;4&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Akasya Durağı&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;print&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;LinkedList -&amp;gt; &amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	filmler&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;forEach&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;film &lt;span style=&#34;color:#666&#34;&gt;-&amp;gt;&lt;/span&gt; System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;print&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;film &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34; &amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Kodun çıktısı aşağıdaki gibidir:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;LinkedList -&amp;gt; Person of Interest Black Books Seinfeld Fargo Akasya Durağı
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;vector-e&#34;&gt;Vector&lt;E&gt;&lt;/h3&gt;
&lt;p&gt;Vector, nadiren kullanılan bir classtır. Şimdiye kadar hiç kullanıldığını görmedim. Sychronized bir collection’dır ve varsayılan kapasitesi 10’dur. 11. element eklenirken kapasitesini 20 yapar. 21. elementi eklerken 40 yapar. Varsayılan kapasite ve artış değerlerini kullanıcı belirleyebilir.&lt;/p&gt;
&lt;h2 id=&#34;3-dot-queue-e&#34;&gt;3. Queue&lt;E&gt;&lt;/h2&gt;
&lt;p&gt;Queue interface’i FIFO (first in first out) prensibini uygular. Yani sıraya ilk giren kişi ilk çıkar. Günlük hayattaki market sırası gibidir.
Bu da çok kullanılmadığı için örnek vermiyorum.&lt;/p&gt;
&lt;h2 id=&#34;4-dot-map-k-v&#34;&gt;4. Map&amp;lt;K,V&amp;gt;&lt;/h2&gt;
&lt;p&gt;Map interface’i collection sınıfına dahil değildir fakat benzer amaçlar taşıdığı aynı başlık altında öğretilir. Map’ler eşleme tablolarıdır. Bir Map’te tekrarlı key olamaz. Tüm value’lar bir key ile eşlenir ve bu key ile çağrılır.&lt;/p&gt;
&lt;h3 id=&#34;hashmap-k-v&#34;&gt;HashMap&amp;lt;K, V&amp;gt;&lt;/h3&gt;
&lt;p&gt;HashMap’ler sıralamayı garanti etmez. null key ve null value kabul eder.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;HashMap&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; sozluk &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; HashMap&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;();&lt;/span&gt;
    sozluk&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;put&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;pencil&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;kalem&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    sozluk&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;put&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;computer&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;bilgisayar&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    sozluk&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;put&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;bottle&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;şişe&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    sozluk&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;put&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;shoe&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;ayakkabı&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

    sozluk&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;forEach&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;((&lt;/span&gt;kelimeEN&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; kelimeTR&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;-&amp;gt;&lt;/span&gt; System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;print&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;kelimeEN &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;-&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt;kelimeTR &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34; | &amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Bu kodun çıktısı aşağıdaki gibidir:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;HashMap -&amp;gt; computer-bilgisayar | bottle-şişe | pencil-kalem | shoe-ayakkabı |
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;treemap-k-v&#34;&gt;TreeMap&amp;lt;K, V&amp;gt;&lt;/h3&gt;
&lt;p&gt;HashMap’lerden farkı, elementleri artan sıralama (ascending) ile tutmasıdır.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;
TreeMap&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;Integer&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; alisverisListesi &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; TreeMap&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&amp;gt;();&lt;/span&gt;
	alisverisListesi&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;put&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;3&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Süt&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	alisverisListesi&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;put&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;4&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Yumurta&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	alisverisListesi&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;put&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;2&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Un&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	alisverisListesi&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;put&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;1&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Kakao&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;print&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;TreeMap -&amp;gt; &amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	alisverisListesi&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;forEach&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;((&lt;/span&gt;siraNu&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; urun&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;-&amp;gt;&lt;/span&gt; System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;print&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;siraNu &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;.&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; urun &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34; | &amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Bu kodun çıktısı aşağıdaki gibidir:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;TreeMap -&amp;gt; 1.Kakao | 2.Un | 3.Süt | 4.Yumurta |
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;hashtable-k-v&#34;&gt;HashTable&amp;lt;K, V&amp;gt;&lt;/h3&gt;
&lt;p&gt;HashMap ile benzerdir fakat aralarında bazı farklar mevcuttur. HashTable sychronized’tır, dolayısıyla performansı düşüktür. HashMap null değer alırken HashTable almaz.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;Hashtable&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&lt;/span&gt;Integer&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; String&lt;span style=&#34;color:#666&#34;&gt;&amp;gt;&lt;/span&gt; menu &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; Hashtable&lt;span style=&#34;color:#666&#34;&gt;&amp;lt;&amp;gt;();&lt;/span&gt;
	menu&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;put&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;1&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Mercimek Çorbası&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	menu&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;put&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;2&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Alinazik&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	menu&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;put&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;3&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Pilav&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	menu&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;put&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;4&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Kola&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;print&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;HashTable -&amp;gt; &amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	menu&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;forEach&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;((&lt;/span&gt;sira&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; yemek&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;-&amp;gt;&lt;/span&gt; System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;print&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;sira &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;.&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; yemek &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34; | &amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Kodun çıktısı aşağıdaki gibidir:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;HashTable -&amp;gt; 1.Mercimek Çorbası | 2.Alinazik | 3.Pilav | 4.Kola |
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;&lt;strong&gt;Kodlara ait Github linki:&lt;/strong&gt; &lt;a href=&#34;https://github.com/kamer/Java-Collection-Framework&#34;&gt;https://github.com/kamer/Java-Collection-Framework&lt;/a&gt;&lt;/p&gt;
</description>
        </item>
        
        <item>
            <title>Visual Studio Code Kısayolları ve İpuçları</title>
            <link>http://kamer.dev/visual-studio-code-kisayollari-ve-ipuclari/</link>
            <pubDate>Tue, 07 May 2019 13:33:20 +0000</pubDate>
            
            <guid>http://kamer.dev/visual-studio-code-kisayollari-ve-ipuclari/</guid>
            <description>&lt;div class=&#34;block-plain&#34;&gt;
  &lt;div&gt;&lt;/div&gt;
&lt;p&gt;Bu yazı 7 Mayıs 2019 tarihinde yazılmıştır. Geçen sürede birçok şey değişmiş olabilir. Okumaya başlamadan önce bu durumu göz önünde bulundurmanızı tavsiye ederim.&lt;/p&gt;
&lt;/div&gt;
&lt;p&gt;VSCode, Sublime Text, Atom, Brackets gibi editörlerin kod yazarken işlerimizi kolaylaştırdığına şüphe yok. Fakat bu araçları daha etkin kullandığınızda verimliliğinizi daha üst noktalara taşıyabilirsiniz. Bu yazımda Visual Studio Code’da çalışmanızı yaparken bu deneyiminizi daha keyifli hale getirecek bazı kısayollar ve ipuçlarından bahsedeceğim.&lt;/p&gt;
&lt;h2 id=&#34;kısayollar&#34;&gt;Kısayollar&lt;/h2&gt;
&lt;h3 id=&#34;1-dot-command-palette&#34;&gt;1. Command Palette&lt;/h3&gt;
&lt;p&gt;Visual Studio Code’daki tüm komutların bulunduğu pencere. Böylelikle kısayolları bilmeseniz bile her işinizi halledebilirsiniz. Bu yüzden tüm kısayolların adını İngilizce yazdım. Ctrl + Shift + P kısayolu ile kullanabilirsiniz.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/vscode-tips/command-palette.gif&#34;/&gt;
&lt;/figure&gt;

&lt;h3 id=&#34;2-dot-format-document&#34;&gt;2. Format Document&lt;/h3&gt;
&lt;p&gt;Ctrl + Shift + I kısayolu ile kullanabileceğiniz bu özellik kodunuzun girintilerini düzenleyerek estetik açıdan güzel görünmesini sağlıyor.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/vscode-tips/format-document.gif&#34;/&gt;
&lt;/figure&gt;

&lt;h3 id=&#34;3-dot-quick-open&#34;&gt;3. Quick Open&lt;/h3&gt;
&lt;p&gt;Proje dosyalarınız arttıkça dosyalar arasında geçiş yapmak eziyet olabiliyor. Bu özellik sayesinde farenize dokunmadan dosyalar arasında geçiş yapabilirsiniz. Tek yapmanız gereken Ctrl + P yapıp dosya adını yazmak.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/vscode-tips/quick-open.gif&#34;/&gt;
&lt;/figure&gt;

&lt;h3 id=&#34;4-dot-zen-mode&#34;&gt;4. Zen Mode&lt;/h3&gt;
&lt;p&gt;Yalnızca editörünüzün göründüğü, dikkat çekici diğer ögelerin ekranda gösterilmediği mod. Ctrl+K yapıp sonra Z’ye basmanız gerekiyor. Esc ile de eski haline dönüyor.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/vscode-tips/zen-mode.png&#34;/&gt;
&lt;/figure&gt;

&lt;h3 id=&#34;5-dot-multi-cursor-selection&#34;&gt;5. Multi-cursor Selection&lt;/h3&gt;
&lt;p&gt;Benim en sevdiğim özelliklerden biri. Aynı anda birden fazla satırı düzenlemenizi sağlıyor. Ctrl+Shift’e basılı tutup yukarı/aşağı yön tuşlarını kullanarak yapabilirsiniz.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/vscode-tips/multi-cursor.gif&#34;/&gt;
&lt;/figure&gt;

&lt;h3 id=&#34;6-dot-column--box--selection&#34;&gt;6. Column (box) selection&lt;/h3&gt;
&lt;p&gt;Bu da multi-cursor selection’a benzer bir özellik. Kolon seçimi olarak söylenebilir. Normalde yalnızca satır seçerken bu özellik sayesinde sütunları da seçebiliyoruz. Bunun içinde Alt+Shift’e basılı tutup seçim işlemini yapmanız gerekiyor.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/vscode-tips/column-selection.gif&#34;/&gt;
&lt;/figure&gt;

&lt;h3 id=&#34;7-dot-move-line-up-and-down&#34;&gt;7. Move line up and down&lt;/h3&gt;
&lt;p&gt;Herhangi bir satırı veya seçimi mouse kullanmadan kod içinde hareket ettirmenizi sağlayan kısayol. Yalnızca bir yer seçin ve Alt’a basılı tutup yukarı/aşağı yön tuşlarını kullanın.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/vscode-tips/move-line.gif&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Anlatacağım kısayollar bu kadar. Tabii ki çok daha fazla kısayol var ve hepsini anlatmam mümkün değil. En çok kullandığım ve sevdiklerim bunlardı. Tüm bu bilgileri Visual Studio Code’un kendi sitesinden aldım. Daha fazlası için VSCode’un &lt;a href=&#34;https://code.visualstudio.com/shortcuts/keyboard-shortcuts-windows.pdf&#34;&gt;shortcuts cheatsheet&lt;/a&gt;’ini öneririm.&lt;/p&gt;
&lt;h2 id=&#34;i̇puçları&#34;&gt;İpuçları&lt;/h2&gt;
&lt;h3 id=&#34;snippet-oluşturma&#34;&gt;Snippet Oluşturma&lt;/h3&gt;
&lt;p&gt;VSCode’un kendi bünyesinde epey snippet var fakat bu hiçbir yazılımcı için yeterli değildir. Eğer tekrar tekrar yazdığınız kod parçaları varsa snippet oluşturmanızı tavsiye ederim. Bunun için öncelikle Ctrl+Shift+P yapın ve Configure User Snippets’e basın. Karşınıza çıkan listeden New Global Snippets File’ı seçin. Karşınıza dosya yöneticisi çıkacak. Herhangi bir isim verin ve kaydedin. Eğer her şeyi doğru yaptıysanız karşınıza aşağıdaki gibi bir ekran gelecek.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/vscode-tips/new-snippet.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Zaten eğer dikkat ettiyseniz nasıl snippet oluşturacağınızı anlatmışlar ve örnek bir taslak koymuşlar. Doğrudan o taslağı kopyalayın süslü parantezlerin içine yapıştırın. &lt;strong&gt;Print to console&lt;/strong&gt; yazan kısım snippetinizin adı. Scope değişkeninde hangi tip dosyalarda çalışmasını istediğinizi seçiyorsunuz. Prefix değişkeninde, snippetinizin size editör tarafından önerilmesi için yazmanız gereken string’i belirliyorsunuz. Mesela örnek üzerinden konuşmak gerekirse &lt;strong&gt;log&lt;/strong&gt; yazdığınızda ilgili snippeti önerecek size. Body kısmı snippetinizin içeriği. Bu içerikte $1 $2 $3… şeklinde yazdığınız kısım olası değişken isimlerinin bulunacağı kısım. Yani snippet oluşturulduktan sonra Tab tuşu ile gezeceğiniz noktalar. $0 ise snippeti kullandıktan sonra cursor’ün geleceği nihai nokta. Description değişkeninde ise snippetiniz için bir tanım ekleyebiliyorsunuz. Ben for döngüsü için bir örnek yapıyorum:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-json&#34; data-lang=&#34;json&#34;&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;For loop&amp;#34;&lt;/span&gt;&lt;span style=&#34;&#34;&gt;:&lt;/span&gt; {
  &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;scope&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;javascript&amp;#34;&lt;/span&gt;,
  &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;prefix&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;forl&amp;#34;&lt;/span&gt;,
  &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;body&amp;#34;&lt;/span&gt;: [
  &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;for(var i = 0; i &amp;amp;lt; $1; i++) { $0 }&amp;#34;&lt;/span&gt;,
  ],
  &lt;span style=&#34;color:#008000;font-weight:bold&#34;&gt;&amp;#34;description&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Creates a for loop.&amp;#34;&lt;/span&gt;
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Bunu yazıp kaydettikten sonra snippetiniz hazır.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/vscode-tips/snippet.gif&#34;/&gt;
&lt;/figure&gt;

&lt;h3 id=&#34;emmet-eklentisi&#34;&gt;Emmet Eklentisi&lt;/h3&gt;
&lt;p&gt;Bu eklenti VSCode’un içinde yüklü olarak gelen bir eklenti. İçinde bulunan hazır snippetleri sayesinde birçok işinizi hızlıca halledebilirsiniz. Aslında bu yeni bir yazı yazacak kadar büyük bir konu fakat ben iki örnek verip sizi gerekli linke yönlendireceğim.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/vscode-tips/emmet.gif&#34;/&gt;
&lt;/figure&gt;

</description>
        </item>
        
        <item>
            <title>Hyperledger Composer ile Uygulama Geliştirme — 3. Erişim Kontrol Dosyası (.acl)</title>
            <link>http://kamer.dev/hyperledger-composer-ile-uygulama-gelistirme-3-erisim-kontrol-dosyasi-acl/</link>
            <pubDate>Sat, 04 May 2019 13:21:35 +0000</pubDate>
            
            <guid>http://kamer.dev/hyperledger-composer-ile-uygulama-gelistirme-3-erisim-kontrol-dosyasi-acl/</guid>
            <description>&lt;h2 id=&#34;gereklilikler&#34;&gt;Gereklilikler&lt;/h2&gt;
&lt;p&gt;Serinin önceki yazılarını okuduysanız ekstra bir gerekliliğe ihtiyaç yoktur. Elimden geldiğince yeni başlayan insanlara hitap edecek şekilde açıklamaya çalışıyorum.&lt;/p&gt;
&lt;h2 id=&#34;1-dot-giriş&#34;&gt;1. Giriş&lt;/h2&gt;
&lt;p&gt;Merhaba. Model dosyasını oluşturmayı ve modelleme dilini öğrendikten sonra sırada erişim kontrol dosyası (access control file, .acl) var. Öncelikli bu dosyaya neden ihtiyaç duyduğumuzu açıklamakta fayda var. Bunun için blokzinciri temellerine dönüp izinli ve izinsiz blokzincirlerin farkını anlamamız lazım. Deniz Özgür’ün Türkçeye kazandırıp &lt;a href=&#34;https://medium.com/hyperledger-t%C3%BCrkiye-platformu/hyperledgera-giri%C5%9F-f5eddb5e31e0&#34;&gt;Hyperledger’a Giriş&lt;/a&gt; adıyla yayınladığı resmi dokümanda bu farka dair şu kelimeler geçiyor:&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;Çoğu kripto para birimi, herkesin katılabileceği ve kullanmak için tam haklara sahip olduğu izinsiz blok zinciri kullanır. Örneğin herkes Bitcoin veya Ether’ı satın alabilir, çünkü bunlar açık, izinsiz teknolojilerdir.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;!--quoteend--&gt;
&lt;blockquote&gt;
&lt;p&gt;Öte yandan, işletmeler izinli blok zincirler kullanma eğilimindedir. Bu, bir kişinin blok zincirinde belirli eylemleri gerçekleştirmek için belirli gereksinimleri yerine getirmesi gerektiği anlamına gelir. Bazı izin verilen blok zincirleri, önceden kimliklerini belirtmiş ve onaylatmış kişilere bile erişimi kısıtlayabilirler. Diğerleri herkesin katılmasına izin verir, ancak yalnızca güvenilir kimliklerin blok zincirindeki işlemleri doğrulamasına izin verirler.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;Yukarıdaki tanımlar ışığında erişim kontrol dosyası gerekliliğini daha rahat açıklayabiliriz. Örneğin, bir tedarik zincirini Hyperledger ile tasarladığınızı düşünün. Bu zincir üzerinde isteyen herkesin işlem yapabiliyor olması saçma olurdu değil mi? Hatta birçok senaryoda bu zincirin herkes tarafından görülmesi de yanlış bir kullanım şekli olabilir. Dolayısıyla belirli bir kullanıcıya veya kullanıcı grubuna tanımlanmış özel yetkiler olmalı. Erişim kontrol dosyası bize bu yeteneği kazandıran dosyadır. Kendine ait anlaşılması basit bir söz dizimi(syntax) vardır. Yine yazımın giriş kısmını sağlam temellere oturtmak için resmi dokümandaki tanımı irdelemek istiyorum. Resmi dokümanda ACL hakkında aşağıdaki cümle yer alıyor.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;By defining ACL rules you can determine which users/roles are permitted to create, read, update or delete elements in a business network’s domain model.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;by defining ACL rules:&lt;/strong&gt; .acl dosyasını oluştururken yaptığımız şey bir takım kurallar oluşturmaktır.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;which users/roles are permitted to create, read, update, or delete elements:&lt;/strong&gt; Buradaki ifade gayet açık ve net. ACL kurallarının içeriği, kullanıcıların ve kullanıcıların ait olduğu rollerin yapabilecekleri CRUD işlemlerinin(oluşturma, okuma, güncelleme ve silme) kapsamını belirleyecek şekilde olmalı.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;in a business network’s domain model:&lt;/strong&gt; Bir önceki yazıyı okuduysanız bu ifade sizin için yabancı bir şey değil. Composer modelleme dili kullanarak oluşturduğumuz modele domain model demiştik. Yani ağ üzerinde tüm kaynakların tanımlandığı model. Oluşturduğumuz kurallar da bu kaynaklar üzerinde olacaktır elbette.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Bu dosya projenin kök dizininde &lt;code&gt;permissions.acl&lt;/code&gt; adıyla bulunur. Eğer bu dosyayı oluşturmazsanız tüm yetkiler serbest olur.&lt;/p&gt;
&lt;h2 id=&#34;2-dot-sistem-erişim-kuralları-belirlemek&#34;&gt;2. Sistem Erişim Kuralları Belirlemek&lt;/h2&gt;
&lt;p&gt;Daha önce bahsettiğim üzere sistem varlıkları &lt;code&gt;org.hyperledger.composer.system.cto&lt;/code&gt; adresinde bulunuyor. Sistem Erişim Kurallarına örnek olarak ağ erişimini verebiliriz. &lt;code&gt;system.cto&lt;/code&gt; dosyasında aşağıdaki satırlar mevcut:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;asset Network identified by networkId {
  o String networkId
  o String runtimeVersion
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Ağ kuralı belirlemek için ise aşağıdaki satırları yazıyoruz.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;rule AgErisimYetkisi {
  description: &amp;#34;Yöneticiler ağ komutlarına erişebilir.&amp;#34;
  participant: &amp;#34;org.hyperledgertr.proje.Yonetici&amp;#34;
  operation: ALL
  resource: &amp;#34;org.hyperledger.composer.system.Network&amp;#34;
  action: ALLOW
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Yukarıdaki kural üzerinden söz dizimini inceleyelim. İlk satırda kuralımızın adını giriyoruz. Description kısmında kuralın açıklamasını giriyoruz. Participant kısmında kuralı uyguladığımız katılımcı ya da katılımcı grubunu seçiyoruz. Operation’da hangi işlemleri uygulayabileceğini seçiyoruz.
Resource, participant kısmında seçtiğimiz katılımcının/katılımcı grubunun erişebileceği/erişemeyeceği kaynakları belirttiğimiz kısım. Action’da ise kuralın türünü seçiyoruz. Burada ALLOW diyerek izin vermişiz. DENY seçeneği ile bu erişimi engelleyebilirdik. Eğer ağdaki tüm kaynaklara erişim vermek istersek de &lt;code&gt;org.hyperledger.composer.system.*&lt;/code&gt; yazabiliriz. Sisteme ait diğer yetkilere ulaşmak için &lt;a href=&#34;https://github.com/hyperledger/composer/blob/60261521cea0e714cc713967dee1aadd7a557dfe/packages/composer-common/lib/system/org.hyperledger.composer.system.cto&#34;&gt;system.cto dosyasına&lt;/a&gt; veya resmi dokümandaki &lt;a href=&#34;https://hyperledger.github.io/composer/v0.19/systemns/01%5Fsummary&#34;&gt;tabloya&lt;/a&gt; bakabilirsiniz.&lt;/p&gt;
&lt;h2 id=&#34;3-dot-koşullu-erişim-kuralları&#34;&gt;3. Koşullu Erişim Kuralları&lt;/h2&gt;
&lt;p&gt;Yukarıda sistem erişim kuralları tanımlarken dokümanda &lt;strong&gt;“simple ACL rule”&lt;/strong&gt; olarak geçen basit bir kural tanımlaması yaptık. Diğer bir yöntem ise bu kuralı bazı koşullara dayandırmak. Henüz kendim kullanmadığım için doğrudan dokümanda yer alan örneği paylaşıyorum.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;rule SampleConditionalRule {
  description: &amp;#34;Description of the ACL rule&amp;#34;
  participant(m): &amp;#34;org.example.SampleParticipant&amp;#34;
  operation: ALL
  resource(v): &amp;#34;org.example.SampleAsset&amp;#34;
  condition: (v.owner.getIdentifier() == m.getIdentifier())
  action: ALLOW
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Gördüğünüz üzere bu kuralda katılımcı için m, kaynak için ise v değişkeni seçilmiş ve condition kısmında boolean tipinde değer döndüren birJavaScript koşulu yazılmış. Bu kurala göre SampleAsset adındaki varlıklara yalnızca sahiplerinin erişim yetkisi bulunmakta.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;rule SampleConditionalRuleWithTransaction {
  description: &amp;#34;Description of the ACL rule&amp;#34;
  participant(m): &amp;#34;org.example.SampleParticipant&amp;#34;
  operation: READ, CREATE, UPDATE
  resource(v): &amp;#34;org.example.SampleAsset&amp;#34;
  transaction(tx): &amp;#34;org.example.SampleTransaction&amp;#34;
  condition: (v.owner.getIdentifier() == m.getIdentifier())
  action: ALLOW
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Bu da resource, participant ve transaction içeren örnek bir kural.&lt;/p&gt;
&lt;h2 id=&#34;4-dot-kural-alanlarının-ayrıntılı-açıklaması&#34;&gt;4. Kural Alanlarının Ayrıntılı Açıklaması&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;Operation:&lt;/strong&gt; Kuralın geçerli olduğu eylemi belirtir. 5 değer alabilir. CREATE, READ, UPDATE, DELETE, ALL. Birden dazla eylem varsa aralarında virgül kullanarak belirtilir.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Participant:&lt;/strong&gt; İşlemi gerçekleştirecek olan kişi veya kurumu belirtir.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Transaction:&lt;/strong&gt; Katılımcının belirtilen kural dahilinde gerçekleştirebileceği işlemi ifade eder.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Condition:&lt;/strong&gt; Boolean değer döndüren bir JavaScript ifadesi alan condition alanı, kuralları şarta bağlamak için kullanılır.
JavaScript’te &lt;code&gt;if(...)&lt;/code&gt; içine yazılabilecek her şeyi değer olarak alabilir.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Action:&lt;/strong&gt; İki değer alabilir, ALLOW ve DENY. Kural, bu alana bağlı olarak kapsamını daraltır.&lt;/p&gt;
&lt;p&gt;Giriş seviyesinde, Hyperledger Composer.acl dosyasına dair söyleyebileceklerim bundan ibaret. Bu konuyu daha iyi anlamak için örnek .acl dosyalarına göz atmak faydalı olabilir.&lt;/p&gt;
&lt;hr/&gt;
&lt;p&gt;&lt;strong&gt;Kaynak:&lt;/strong&gt; Hyperledger Composer Resmi Dokümanı&lt;/p&gt;
</description>
        </item>
        
        <item>
            <title>Hyperledger Composer ile Uygulama Geliştirme — 2. Composer Modelleme Dili (.cto Dosyası)</title>
            <link>http://kamer.dev/hyperledger-composer-ile-uygulama-gelistirme-2-composer-modelleme-dili/</link>
            <pubDate>Tue, 23 Apr 2019 13:16:28 +0000</pubDate>
            
            <guid>http://kamer.dev/hyperledger-composer-ile-uygulama-gelistirme-2-composer-modelleme-dili/</guid>
            <description>&lt;p&gt;Merhaba. Bir önceki &lt;a href=&#34;http://kamer.dev/hyperledger-composer-ile-uygulama-gelistirme-1-temel-kavramlar&#34;&gt;yazımda&lt;/a&gt;  uygulamadaki olası aktörlerden ve bunları nasıl tanımlayacağımızdan, Kurumsal Ağ Tanımından(Business Network Definition) ve Kurumsal Ağ Tanımının bileşenlerinden bahsetmiştim. Bu yazıda ise Model dosyasının söz diziminden (syntax) bahsedeceğim.&lt;/p&gt;
&lt;h2 id=&#34;gereklilikler&#34;&gt;Gereklilikler&lt;/h2&gt;
&lt;p&gt;Bu yazıdaki herhangi bir gereklilik bulunmamaktadır. Temel seviyede yazılım ve veritabanı bilgisi konuyu anlamanızı kolaylaştıracaktır.&lt;/p&gt;
&lt;h2 id=&#34;1-dot-giriş&#34;&gt;1. Giriş&lt;/h2&gt;
&lt;p&gt;Model dosyası, uygulamamızdaki katılımcıları, varlıkları ve işlemleri tanımladığımız &lt;strong&gt;.cto&lt;/strong&gt; uzantılı dosyadır. Konuya ilişkin gözden kaçan kavram olmasın diye &lt;a href=&#34;https://hyperledger.github.io/composer/v0.19/reference/cto%5Flanguage.html&#34;&gt;resmi dokümandaki&lt;/a&gt; &lt;strong&gt;modeling language&lt;/strong&gt; tanımını beraber irdeleyelim. Tanıma ilişkin yapacağım açıklamalar büyük oranda yazılım bilgisi yeterli seviyede olmayan kişilere yöneliktir. Bilgi seviyenizin yeterli seviyede olduğuna inanıyorsanız giriş bölümünün bundan sonraki kısmını okumadan diğer bölüme geçebilirsiniz.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;“Hyperledger Composer includes an object-oriented modeling language that is used to define the domain model for a business network definition.”&lt;/p&gt;
&lt;/blockquote&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;object-oriented modeling language&lt;/strong&gt; ifadesi, yazılım dünyasından birçoğumuzun aşina olduğu ve Türkçeye &lt;strong&gt;nesne yönelimli modelleme&lt;/strong&gt; dili olarak çevrilebilecek bir kavram. Modelleme dili zaten adından anlaşılabilecek basitlikte bir kelime. İrdelememiz gereken kısım bu modelleme dilinin nesne yönelimli olması. En net ve kısa ifadeyle yazılım geliştirirken yaptığımız şey genelde dünyadaki bazı olguları koda çevirmektir. Bu çevirme işlemi sırasında nesne yönelimli bir dil kullanıyorsak her şey bizim için bir nesnedir. Her nesnenin bazı özellikleri (attribute) ve davranışları (behaviour) vardır. Biz bu nesnelerin birbiriyle olan ilişkilerini düzenleriz. Yazdığımız kodla yaratacağımız dünyada bakış açımız buna göre olur. Örneğin bir kütüphane otomasyon sistemi yapacaksınız. Kitaplar ve kütüphane üyeleri birer nesnedir. Üyelerin kimlik numarası, isim soyisim, doğrum tarihi gibi bilgileri özellik, kitap ödünç alma, ödünç aldığı kitabı iade etme gibi eylemleri davranıştır. Kitaplar da aynı şekilde nesnelerdir, ISBN numarası, adı, yazar adı, basım yılı gibi özellikleri vardır. Otomasyonda da genellikle yapılacak şey üye nesnesinin kitap nesnesiyle olan ilişkisini kurmak ve düzenlemek olacaktır.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;domain model for a business network definiton&lt;/strong&gt; ifadesindeki &lt;strong&gt;domain model&lt;/strong&gt;, yazılım tasarımının temelidir. Gerçek dünyadaki varlıkları ve bu varlıkların birbiri arasındaki ilişkiyi tanımladığımızda çıkardığımız model &lt;strong&gt;domain model&lt;/strong&gt;’dir. Hyperledger Composer’da bu modeli kurumsal ağ tanımı (business network definition) için yaparız.&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Yukarıda bahsettiğim birkaç kavramı iyice anladıktan sonra tanıma genel bir açıklama getirmekte fayda var. Hyperledger Composer’ın kurumsal ağ tanımına gerçek hayattaki bir modeli, bir problemi anlatmamız gerekiyor. Bu bir tedarik zinciri olabilir veya bir sertifika/belge yönetimi olabilir. Gerçek hayatta bu modelin bazı aktörleri, aktörlerin birbirleri arasındaki ilişkileri ve özellikleri vardır. Bu modeli nesne yönelimli modelleme dili ile Hyperledger’a aktardığımız dosya, model dosyasıdır.&lt;/p&gt;
&lt;p&gt;.cto uzantılı olan bu dosya üç temel bileşenden oluşur:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;namespace&lt;/strong&gt; tanımlaması.&lt;/li&gt;
&lt;li&gt;Uygulamamızdaki kaynakların tanımlaması.
&lt;ul&gt;
&lt;li&gt; Varlıklar (assets)&lt;/li&gt;
&lt;li&gt; İşlemler (transactions)&lt;/li&gt;
&lt;li&gt;Katılımcılar (participants)&lt;/li&gt;
&lt;li&gt; Olaylar (events)&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;(Opsiyonel) Diğer namespace’lerden kaynak almak.(import)&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;2-dot-namespace-tanımlamak&#34;&gt;2. namespace Tanımlamak&lt;/h2&gt;
&lt;p&gt;Uygulamamızda aynı amaç için bir araya getirdiğimiz tüm kaynakların oluşturduğu kümeye namespace denir. Bu namespace içinde tüm kaynaklar eşsiz olarak tanımlanır. Herhangi bir namespace’e ait olan bir kaynağa erişmek için o kaynağı namespace’in adıyla çağırırız. Çünkü aynı isme sahip olan ve farklı namespace’lerde bulunan iki varlık birbirinden farklıdır. Biyolojideki isimlendirmeler gibi düşünebiliriz. Örneğin &lt;strong&gt;mangifera indica&lt;/strong&gt; mango demekken, &lt;strong&gt;apis indica&lt;/strong&gt; bir bal arısı türüdür. Yazımı gayet basittir. Örnek olarak:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;namespace org.hyperledgerturkiye.ornekuygulama
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Burada tanımlamayı istediğiniz şekilde yapabilirsiniz. Fakat genelde org’den sonra organizasyon, şirket veya proje ismi; sonrasında genelden özele doğru inen bir adlandırma tercih ediliyor. Benim verdiğim örnekte org.organizasyonİsmi.projeİsmi şeklinde bir tanımlama var. Birden fazla namespace eklemek isteseydim ona göre tanımlamamı değiştirebilirdim. Örneğin,&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;namespace org.hyperledgerkiye.ornekuygulama.alimSatim
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Bu namespace içindeki bir kaynağa ulaşmak içinse aşağıdaki şekilde bir yazım kullanıyoruz.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;org.hyperledgerturkiye.ornekuygulama.alimSatim.ilan
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Yazım şekline dair bahsedeceklerim bu kadar. İki tane uyarı yapıp bir sonraki bölüme geçelim:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;İnternette, özellikle IBM’in örneklerinde, “org.acme….&amp;quot; şeklinde tanımlamalar görmeniz muhtemeldir. Acme kelimesi başta bir kural veya dile ait bir şey gibi hissettirdiği için kafanız karışabilir. IBM’in bu gibi örnekler verirken kullandığı hayali lojistik firmasının adı Acme Freight’tir. Yani acme yerine kendi organizasyonunuzu yazabilirsiniz. Github’da bu konuda dert yanıp issue açanlar olmuş fakat hala acme örneği yaygın olarak kullanılıyor.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Sizin oluşturduğunuz namespace dışında Hyperledger Composer’ın kendine ait bir namespace’i de vardır. Adı system namespace olan bu namespace, asset, event, participant ve transaction değişkenleri için temel tanımlamaları içerir. Bu tanımlamalar soyut (abstract) tiptedir ve oluşturduğunuz tüm değişkenler bunları extend eder. Bu soyut tanımlamalarda participant ve asset için değer yoktur. Fakat event ve transaction tanımlamalarında&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;eventId&lt;/strong&gt; veya &lt;strong&gt;transactionId&lt;/strong&gt; ve &lt;strong&gt;timestamp&lt;/strong&gt; değişkenleri vardır. Bu demek oluyor ki eğer tanımladığınız herhangi bir participant veya asset içinde bu değişkenler bulunuyorsa silmeniz gerekir. System namespace’in .cto dosyasını Github’da &lt;a href=&#34;https://github.com/hyperledger/composer/blob/master/packages/composer-common/lib/system/org.hyperledger.composer.system.cto&#34;&gt;bulabilirsiniz&lt;/a&gt;.&lt;/p&gt;
&lt;h2 id=&#34;3-dot-kaynakları-tanımlamak&#34;&gt;3. Kaynakları Tanımlamak&lt;/h2&gt;
&lt;h3 id=&#34;3-dot-1-dot-sınıf-tanımlamaları--class-definitions&#34;&gt;3.1. Sınıf Tanımlamaları (Class Definitions)&lt;/h3&gt;
&lt;p&gt;Hyperledger Modelleme dilinde asset, participant, transaction ve event tanımlamaları sınıf tanımlamasıdır. Daha önce belirttiğim gibi ağdaki kaynaklar eşsiz olmak zorundadır. Hepsinin kendine ait eşsiz bir değişkeni vardır. &lt;strong&gt;Event&lt;/strong&gt; ve &lt;strong&gt;transaction&lt;/strong&gt; sınıflarının system namespace’deki soyut (abstract) sınıflarında eventId ve transactionId değişkenleri bulunduğu için onları eşsiz yapan ekstra bir tanımlayıcıya ihtiyaç duymazlar.
Bu yüzden participant ve asset sınıflarını tanımlarken onları eşsiz yapan bir değer belirtmek zorundayız. Aşağıda örnek sınıf tanımlamalarını görebilirsiniz.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;asset Sertifika identified by sertifikaId {
    ...
    ...
    ...
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Yukarıda tanımladığımız Sertifika asset’ini eşsiz yapan değer sertifikaId’dir. Değişken tanımlama kısmına gelmediğimiz için henüz sertifikaId’nin nasıl tanımlanacağını yazmadım. Participant tanımlamasında da aynı söz dizimini kullanılır.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;transaction Onay {
    ...
    ...
    ...
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Yukarıdaki Onay transaction’ınında asset ve participant tanımlamasından farklı olarak yalnızca eşsiz bir değer vermedik. Event tanımlaması da transaction ile aynı formatta olacaktır.&lt;/p&gt;
&lt;p&gt;Son olarak sınıflar arasında kalıtım da sağlanabilir. Yani bir sınıfı başka bir sınıfın alt sınıfı olarak tanımlayıp üst sınıfın sahip olduğu tüm değişkenleri alt sınıfta kullanabiliriz. Bu birçok yazılım dilinde bulunan bir özelliktir. Örneğin:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;asset Telefon identified by imei {
    o String imei
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;asset AkilliTelefon extends Telefon {
    o String marka
    o String model
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Yukarıda iki asset tanımladık. Telefon asset’i AkilliTelefon asset’inin üst sınıfı olduğu için &lt;strong&gt;imei&lt;/strong&gt; değişkeni AkilliTelefon’a kalıtım ile geçmiş oldu. Bunu soyut sınıflarla da yapabiliriz. Soyut sınıfların tek farkı diğer sınıflar gibi nesne oluşturmazlar. Yalnızca kalıtımla değişken veren üst sınıf olarak görev alırlar.&lt;/p&gt;
&lt;h3 id=&#34;3-dot-2-dot-değişken-tanımlamaları--variable-definitions--değişkenler-veya-alanlar--fields--sınıfların-sahip-olduğu-özellikleri-tanımlamaya-yarar-dot&#34;&gt;3.2. Değişken Tanımlamaları (Variable Definitions) Değişkenler, veya alanlar(fields), sınıfların sahip olduğu özellikleri tanımlamaya yarar.&lt;/h3&gt;
&lt;p&gt;Değişkenleri iki şekilde tanımlayabiliriz.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Owned Property (Sahip olunan değişken):&lt;/strong&gt; Başındaki &lt;strong&gt;‘o’&lt;/strong&gt; harfiyle ifade edilen owned property’ler içinde bulunduğu sınıftan türetilen nesnelere ait olur. Yani bu nesne silindiğinde bu değişkenler de o sınıfla beraber silinir.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Related Property (Bağlı Değişken):&lt;/strong&gt; Başlarındaki &amp;ndash;&amp;gt; karakterleriyle ifade edilirler. Bu değişkenler sınıfa ait değildir. Varolan bir değişkenle ilişkilendirilmiş bir alanı ifade eder. Yazılım dillerindeki pointer’ın Hyperledger Composer Modelleme Dilindeki karşılığı olduğu söylenebilir. Yani başında &amp;ndash;&amp;gt; karakterleriyle tanımladığımız değişkenler pratikte içinde veri tutmaz. Yalnızca varolan bir değişkenin adresini tutar. Dolayısıyla bu değişkenleri barındıran sınıflar silindiğinde asıl değişken silinmez.&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Aşağıda modelleme dilindeki olası değişken tiplerini göreceksiniz:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;asset OlasiTumDegiskenler identified by id {

    // Standart UTF8 String değişken.
    o String id;
    // Default değer verebiliyoruz.
    o String paraBirimi default=&amp;#34;TL&amp;#34;
    // Numerik değerlere aralık verebiliyoruz.
    o Integer yas range[18,]

    // Dizi tanımlayabiliriz.
    o Integer[] integerArray
    // 64 bit Double değişken.
    o Double ortalama
    // 64 bit Long değişken.
    o Long not
    // Regex pattern ile kısıtlayabiliriz.
    o String isim regex = [a-zA-Z]
    // Boolean değer.
    o Boolean isTrue
    // Tarih.
    o DateTime createdDate
    // Opsiyonel değişken
    o DateTime updatedDate optional
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;3-dot-2-dot-numaralandırılmış-türler--enumerated-types&#34;&gt;3.2. Numaralandırılmış Türler (Enumerated Types)&lt;/h3&gt;
&lt;p&gt;Yalnızca n adet olası değeri olan tiplerdir. Örneğin haftanın günleri yalnızca 7 tane olabilir. Haftanın günlerine ait enum’ımızı tanımlayalım:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;enum HaftaninGunu {
  o PAZARTESI
  o SALI
  o CARSAMBA
  o PERSEMBE
  o CUMA
  o CUMARTESI
  o PAZAR
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Bu enum’ın sınıf içindeki kullanımı da aşağıdaki gibidir.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;asset Etkinlik identified by id {
  o String id
  o HaftaninGunu etkinlikGunu
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;3-dot-2-dot-konseptler--consepts&#34;&gt;3.2. Konseptler (Consepts)&lt;/h3&gt;
&lt;p&gt;Konseptler, asset, participant veya transaction olmayan soyut sınıflardır. Anlatmak yerine kod üzerinde göstermek daha anlaşılır olacağından iki örnek vereceğim.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;concept AdresBilgisi {
  o String SokakCadde
  o String Mahalle
  o String Sehir
  o String Ilce
  o String Semt
  o String BinaNo
  o String KapiNo
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;participant Personel identified by tc {
  o String tc
  o AdresBilgisi adresBilgisi
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Bu birinci örnek. Diğer örnek de concept’ler arasındaki kalıtım üzerine.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;abstract concept AdresBilgisi {
    o String SokakCadde
    o String Mahalle
    o String Sehir
    o String Ilce
    o String Semt
    o String BinaNo
    o String KapiNo
}

concept YabanciAdres extends AdresBilgisi {
    o String Ulke
}
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;3-dot-3-dot-i̇lişkiler--relationships&#34;&gt;3.3. İlişkiler (Relationships)&lt;/h3&gt;
&lt;p&gt;Composer’da ilişkiler, üç bileşenden oluşan veri gruplarıdır.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Namespace&lt;/li&gt;
&lt;li&gt;Tip adı&lt;/li&gt;
&lt;li&gt;Nesnenin tanımlayıcı (identifier)&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Örneğin&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;org.hyperledgerturkiye.ornekuygulama.alimSatim.Satici#12345678901
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;yazdığımızda&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;org.hyperledgerturkiye.ornekuygulama.alimSatim namespace’inde bulunan,&lt;/li&gt;
&lt;li&gt;Satici participantına ait,&lt;/li&gt;
&lt;li&gt;12345678901 TC Kimlik numaralı kişiyi referans göstermiş oluyoruz.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;4-dot-import&#34;&gt;4. Import&lt;/h2&gt;
&lt;p&gt;Diğer namespace’lerden kaynak almak için import anahtar kelimesini kullanırız. Bunun için .cto dosyamızın başına&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;import org.hyperledgerturkiye.muhasebe.Fatura
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;şeklinde bir tanımlama yaparız. Eğer bir namespace içindeki her şeyi istersek de&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;import org.hyperledgerturkiye.muhasebe.*
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;yazarız.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Kaynaklar&lt;/strong&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://hyperledger.github.io/composer/latest/reference/cto%5Flanguage.html&#34;&gt;Resmi Doküman&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://developer.ibm.com/patterns/unlock-enterprise-data-using-apis/?cm%5Fmmc=github-code-%5F-native-%5F-acme-%5F-journey&amp;amp;cm%5Fmmca1=000019RT&amp;amp;cm%5Fmmca2=10004796&#34;&gt;Acme’nin hayali bir lojistik bir firması olduğuna dair.&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://stackoverflow.com/questions/44410459/different-between-o-and-arrow-symbol-used-in-cto-file&#34;&gt;o ve –&amp;gt; arasındaki farka dair.&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
</description>
        </item>
        
        <item>
            <title>Hyperledger Composer ile Uygulama Geliştirme — 1. Temel Kavramlar</title>
            <link>http://kamer.dev/hyperledger-composer-ile-uygulama-gelistirme-1-temel-kavramlar/</link>
            <pubDate>Fri, 19 Apr 2019 13:01:14 +0000</pubDate>
            
            <guid>http://kamer.dev/hyperledger-composer-ile-uygulama-gelistirme-1-temel-kavramlar/</guid>
            <description>&lt;h2 id=&#34;i̇çerik&#34;&gt;İçerik&lt;/h2&gt;
&lt;p&gt;Bu yazı serisi, Hyperledger Composer’da proje yapmak isteyenlere yönelik olarak hazırlanmıştır. Temel konseptlerde ısınma yapıp sonra örnek bir uygulamayı adım adım beraber geliştireceğiz. Yazımda temel kaynağım Hyperledger Composer’ın resmi dokümanlarıdır.&lt;/p&gt;
&lt;h2 id=&#34;gereklilikler&#34;&gt;Gereklilikler&lt;/h2&gt;
&lt;p&gt;Temel kavramlardan bahsettiğim bu kısımda herhangi bir gereklilik bulunmamaktadır. Sadece daha iyi anlamak açısından Hyperledger’ın ve blokzincir teknolojisinin ne olduğunu bilmek artı olacaktır.&lt;/p&gt;
&lt;h2 id=&#34;temel-kavramlar&#34;&gt;Temel Kavramlar&lt;/h2&gt;
&lt;p&gt;Hyperledger Composer ile geliştirme yaparken bazı kavramlarla karşılaşacaksınız. Yabancılık çekmemeniz açısından kavramların bir kısmını bu başlık altında topladım. Daha önce blokzincir hakkında okumalar yaptıysanız bir kısmına aşina olabilirsiniz.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Varlıklar(Assets):&lt;/strong&gt; Varlıklar, ağda kayıtlarda bulunan mülkleri, servisleri ve eşyaları ifade eder. Varlık tanımı kurumsal ağda birçok şeyi ifade edebilir. Örneğin tapu, satılık bir ev, oy verme sisteminde verilen bir oy, sertifika olabilir. Varlıklar eşsizdir.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Katımcılar(Participants):&lt;/strong&gt; Katılımcılar, tüm işlemleri gerçekleştiren ve varlıklara sahip olan ağ üyeleridir. Bir kişi veya organizasyon katılımcı olabilir. Katılımcılar da varlıklar gibi eşsizdir.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;İşlemler(Transactions):&lt;/strong&gt; Katılımcıların ağ üzerinde yaptığı her faaliyet işlem(transaction) olarak değer kazanır ve ağa kaydedilir. Transactionlar silinemezler ve değiştirilemezler. Dolayısıyla geçmişe yönelik olarak tarama yapabilirsiniz.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;ID Kartları(ID Cards):&lt;/strong&gt; Katılımcıların sahip olduğu eşsiz kimliktir. Hem katılımcıları tanımlamaya hem de ağa daha kolay bir şekilde bağlanmalarını sağlamaya yarar.&lt;/p&gt;
&lt;p&gt;Bu dört kavramı pekiştirmek için bir örnek yeterli olacaktır. Hyperledger Composer ile yapacağınız bir oy verme uygulamasında seçmenler katılımcı, oy verdikleri partiler varlık, verdikleri oylar ise işlem olacaktır. Seçmenleri ağda tanımlanmak için ise kimlik bilgilerini de barındıran bir ID kart kullanılacaktır.&lt;/p&gt;
&lt;h2 id=&#34;kurumsal-ağ-tanımı--business-network-definition&#34;&gt;Kurumsal Ağ Tanımı (Business Network Definition)&lt;/h2&gt;
&lt;p&gt;Kurumsal ağ tanımı dört şeyden oluşur:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Model Dosyası (.cto)&lt;/li&gt;
&lt;li&gt;Script Dosyası (.js)&lt;/li&gt;
&lt;li&gt;Erişim Kontrol Dosyası (Access Control File - .acl)&lt;/li&gt;
&lt;li&gt;Sorgu Dosyası (Query File - .qry)&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id=&#34;model-dosyası--dot-cto&#34;&gt;Model Dosyası(.cto)&lt;/h3&gt;
&lt;p&gt;Model dosyası, Hyperledger Composer Modelleme Dilini kullanan ve ağ katılımcılarını(participants), varlıkları(assets) ve işlemleri(transactions) tanımlamamıza yarayan dosyadır. Kendine ait nesne yönelimli bir söz dizimi ve formatı vardır. Bir sonraki yazıda ayrıntılı olarak değineceğim.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/hyperledger-composer/cto.png&#34;/&gt;
&lt;/figure&gt;

&lt;h3 id=&#34;script-dosyası--dot-js&#34;&gt;Script Dosyası(.js)&lt;/h3&gt;
&lt;p&gt;Script dosyaları, daha önce de belirttiğim üzere, projemizin logic kısmını üstleniyor. Varlıkların transferini script dosyaları ile yapıyoruz. Örneğin katılımcıların herhangi bireyler, varlıkların ise satılık evler olduğu senaryoda bireylerin evi satın alması işlemini js dosyaları ile sağlıyoruz.&lt;/p&gt;
&lt;h3 id=&#34;erişim-kontrol-dosyası--access-control-file-dot-acl&#34;&gt;Erişim Kontrol Dosyası (Access Control File - .acl)&lt;/h3&gt;
&lt;p&gt;Adından tahmin edebileceğiniz üzere kullanıcıların veya grupların ağdaki yetkilerini tanımladığımız dosyadır. Hyperledger, permissioned bir blokzincirdir ve bu özelliğini uyguladığımız yer bu dosyadır. Ağda herkesin yetki kapsamı aynı olmayabilir. Örneğin araba satış ilanları eklediğimiz bir zincirde fiyatları herkes görebilirken fiyat indirimini yalnızca bir kişi yapabilir. Aynı şekilde eğer ilanda uygun olmayan bir yazı girildiyse bunu herkes görebilirken yalnızca ilan sahibi ve bir grup editör düzeltebilir. Bunu yetki kontrolünü .acl dosyası içinde &lt;b&gt;namespace&lt;/b&gt;’ler ile yapıyoruz.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/hyperledger-composer/acl.png&#34;/&gt;
&lt;/figure&gt;

&lt;h3 id=&#34;sorgu-dosyası--query-file-dot-qry&#34;&gt;Sorgu Dosyası (Query File - .qry)&lt;/h3&gt;
&lt;p&gt;Blokzincirde bulunan veriler üzerinde sorgu yapmak için kullandığımız dosyadır. Kendine ait bir formatı vardır fakat daha önceden SQL kullandıysanız yabancılık çekmeyeceğiniz bir formattır. Yazılım dünyasında &lt;strong&gt;“named query”&lt;/strong&gt; olarak geçen terimin Hyperledger karşılığı olduğunu söyleyebiliriz. İsim verdiğimiz bazı hazır sorguları .qry dosyası içine koyarız ve bunu Business Network Definition içinde Fabric’e veririz.
Sonra bu sorgulara Rest API ile ulaşabiliriz.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/hyperledger-composer/qry.png&#34;/&gt;
&lt;/figure&gt;

&lt;h2 id=&#34;kurumsal-ağ-tanımı-ne-i̇şe-yarar&#34;&gt;Kurumsal Ağ Tanımı Ne İşe Yarar?&lt;/h2&gt;
&lt;p&gt;Yukarıda kurumsal ağ tanımının bileşenlerinden bahsettik. Dört temel bileşen ile ağımızı tanımladıktan sonra ağ tanımını .bna uzantılı bir arşiv dosyası olarak alıyoruz. Artık bu .bna dosyasını kullanarak uygulamamızı deploy edebiliriz. İşte tam bu noktada Hyperledger Composer’ın bize sunduğu avantajı hissedebilirsiniz. Hyperledger Composer, resmi dokümanda da yazdığı üzere, blokzincir uygulamalarımızı daha hızlı ve pratik bir şekilde hazırlamamız için bize bir takım araçlar sunan bir proje. Örneğin bu dört bileşeni hazırladıktan sonra oluşturduğumuz .bna dosyası bize doğrudan projemizi deploy edecek yeteneği sağlıyor. Bunu da Hyperledger Fabric ile yapıyoruz. Sonraki yazılarda buna da değineceğim.&lt;/p&gt;
&lt;p&gt;Yukarıda anlattığım şeylerin özetini aşağıdaki diyagramda bulabilirsiniz.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/hyperledger-composer/net-def.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;&lt;strong&gt;Kaynak:&lt;/strong&gt; &lt;a href=&#34;https://hyperledger.github.io/composer/latest/introduction/introduction.html&#34;&gt;https://hyperledger.github.io/composer/latest/introduction/introduction.html&lt;/a&gt;&lt;/p&gt;
</description>
        </item>
        
        <item>
            <title>Başarılı Yazılımcıların 14 Alışkanlığı-1</title>
            <link>http://kamer.dev/basarili-yazilimcilarin-14-aliskanligi-1/</link>
            <pubDate>Tue, 16 Apr 2019 12:53:39 +0000</pubDate>
            
            <guid>http://kamer.dev/basarili-yazilimcilarin-14-aliskanligi-1/</guid>
            <description>&lt;div class=&#34;block-plain&#34;&gt;
  &lt;div&gt;&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;Not:&lt;/strong&gt; Bu yazı bana ait değildir. dev.to sitesinde yayınlanan ve &lt;a href=&#34;https://dev.to/pavlosisaris&#34;&gt;Paul Isaris&lt;/a&gt;’e ait olan &lt;a href=&#34;https://dev.to/pavlosisaris/how-to-transition-from-junior-to-mid-level-developer-part-1-4gig&#34;&gt;“The 14 habits of highly effective developers (Part 1)”&lt;/a&gt; başlıklı yazının çevirisidir. Çeviri için kendisinden izin alınmıştır.&lt;/p&gt;
&lt;/div&gt;
&lt;h2 id=&#34;giriş&#34;&gt;Giriş&lt;/h2&gt;
&lt;p&gt;Bir çok kişi, başarılı bir Junior yazılımcıdan mid-level (orta seviye) bir yazılımcıya geçiş yapmanın zaman ve tecrübe işi olduğunu düşünüyor.&lt;/p&gt;
&lt;p&gt;Aslında bu iki tip yazılımcıyı birbirinden ayıran çizgi ince bir çizgi ve kişiye göre değişkenlik gösteriyor. Bu yazı, hiç bitmeyen “Orta seviye bir yazılımcıyı tam olarak ne tanımlar?” tartışması üzerine daha fazla şey söylemeyecek.&lt;/p&gt;
&lt;p&gt;Dürüst olmak gerekirse birinin düşünce yapısını değiştiren ve Junior seviyeden orta seviyeye geçiren şeyin &lt;strong&gt;alışkanlıklar&lt;/strong&gt; olduğuna sıkı bir şekilde inanıyorum.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Alışkanlıklar, sistematik olarak yaptığımız ve bize garip gelmeyen doğal davranışlardır.&lt;/strong&gt; Kodla ve işle alakalı alışkanlıklar edinmek profesyonel ve kişisel gelişim için kritik öneme sahiptir.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;Uzmanlaştığınızda daha verimli bir şekilde gelişim sağlayacağınız ve bir sonraki seviyeye geçmenize yardım edecek alışkanlıklara bakalım.&lt;/p&gt;
&lt;h2 id=&#34;1-dot-küçük-metotlar-yazın&#34;&gt;1. Küçük metotlar yazın&lt;/h2&gt;
&lt;p&gt;İdeal olanı 20–30 satırdan daha uzun olmamasıdır. (LoC: Line of code) Bu alışkanlık son derece önemlidir. Sizi yalnızca daha derli toplu kod yazmaya zorlamaz, aynı zamanda kodunuzu modülarize etmeye başladığınızda analitik düşünmenize yardımcı olur. İçinde çok fazla &lt;b&gt;if&lt;/b&gt;’in, &lt;b&gt;for&lt;/b&gt; döngüsünün olduğu çok girintili büyük bir metotla uğraşmak tam bir kabus gibidir. Böyle bir metodu yazarken çok kolay ve anlaşılır geliyor olabilir ama birkaç gün sonra bile o metodun ne iş yaptığını anlamanız çok zor olacaktır.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;Üstüne üstlük büyük metotlar çoğunlukla yeniden kullanılabilir değildir. Yalnızca bir projedeki özel bir ihtiyaca hizmet etmek üzere yazılırlar ve başka yerde kullanılmaları zordur.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h2 id=&#34;2-dot-anlamlı-isimler-verin&#34;&gt;2. Anlamlı isimler verin&lt;/h2&gt;
&lt;p&gt;Hem metotlara, hem de değişkenlere anlamlı isimler verin. Mid-level (orta seviye) bir yazılımcının “x”, “xyz” veya “object” gibi isimlere sahip değişkenler yazması makul değildir. Değişkenlerin İngilizce (veya Türkçe) kelimelerle isimlendirilmesinin amacı anlamlı olmalarıdır.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;Kodunuzla iletişim kurmanız dokümanlarla veya comment’lerle iletişim kurmanızdan çok daha önemlidir.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;!--quoteend--&gt;
&lt;blockquote&gt;
&lt;p&gt;Comment’lerin amacı “nasıl”‘ı değil, “neden”‘i cevaplamaktır.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;Anlamlı değişkenlere sahip olmanız kodunuzu okuyan kişiyle daha iyi bir iletişim kurmanıza yardımcı olur ve aynı zamanda haddinden fazla comment yazma ihtiyacınızı azaltmış olursunuz. Bu, hem değişkenler hem de metotlar için geçerlidir. Ayrıca bir metotu isimlendirmek sizi çok uğraştırıyorsa metodu basitleştirmek için kodunuzu refactor etmeyi de düşünün. Çünkü iyi ve temiz yazılmış bir metota isim bulmak, karmaşık bir metota göre daha kolaydır.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;İsimlendirmeyle boğuştuğunuzda bir an için durun ve isimlendirmeye çalıştığınız bileşenin çok karmaşık olduğunu ve refactoring’e ihtiyacı olduğunu düşünün.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h2 id=&#34;3-dot-çok-fazla-parametre-kullanarak-metodunuzu-karmaşıklaştırmayın&#34;&gt;3. Çok fazla parametre kullanarak metodunuzu karmaşıklaştırmayın&lt;/h2&gt;
&lt;p&gt;Metodunuzda çok fazla parametre olması refactoring yapmanız gerektiğine bir işarettir. Bu tarz metotlar yazmak çoğunlukla &lt;a href=&#34;http://devnot.com/2016/single-responsibility-principle-tek-sorumluluk-prensibi-uzerine/&#34;&gt;SRP’ye (Single Responsibility Principle / Tek Sorumluluk Prensibi)&lt;/a&gt; aykırıdır. Yani metodunuzun çok fazla sorumluluğu olur ve çok fazla iş yapar. Etkili ve temiz bir metot, bir işi iyi bir şekilde yapan metottur. &lt;a href=&#34;https://www.goodreads.com/author/show/45372.Robert%5FC%5FMartin&#34;&gt;Uncle Bob&lt;/a&gt;‘a göre bir metot için en fazla üç parametre makul sayılabilir. Bu görüş bu kadar katı olmasa da bir metot için arzu edilen parametre sayısı konusunda size bir fikir verebilir.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;Metodunuzun lokal parametrelerini class field’lara çevirmeyin. Kodunuzu refactor etmeyi veya metodunuzu iki parçaya bölmeyi ve metotlarınıza daha az iş yaptırmayı ihmal etmeyin.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;!--quoteend--&gt;
&lt;blockquote&gt;
&lt;p&gt;Fonksiyonların çok az parametresi olmalı. Parametresiz olması en iyisi, sonra bir parametreli, iki parametreli ve üç parametreli. Üçten fazlası ise güvensizdir ve peşinen uzak durulmalıdır.&lt;/p&gt;
&lt;p&gt;— Robert C. Martin&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h2 id=&#34;4-dot-bir-sınıfta-çok-fazla-metot-tanımlamaktan-kaçının&#34;&gt;4. Bir sınıfta çok fazla metot tanımlamaktan kaçının&lt;/h2&gt;
&lt;p&gt;Parametre sayısının yanısıra bir sınıftaki metot sayısı da önemlidir. Çok fazla metodun olduğu büyük sınıflar genellikle o bileşenin &lt;strong&gt;çok fazla şey bildiğine&lt;/strong&gt; veya &lt;strong&gt;çok fazla şey yaptığına&lt;/strong&gt; işarettir. Bu tarz bileşenlerin yüksek bağlılıklı olarak anti-pattern bir yapıda yazıldığını ifade etmek için &lt;a href=&#34;http://wiki.c2.com/?GodClass&#34;&gt;God Class (Tanrı sınıf)&lt;/a&gt; terimi kullanılır.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;Bir sınıfta çok fazla metodunuz varsa kodun akışı esnasında sınıfın davranışını değiştirmek için o sınıfa kaç kere girmek zorunda olduğunuzu düşünün. Bu durum, Açık-Kapalı prensibine (Open-closed principle) -yani gelişime açık, değişime kapalı ilkesi- aykırı olabilir.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h2 id=&#34;5-dot-üçüncü-parti-kütüphanelerin-lts-stabil-sürümlerini-kullanın&#34;&gt;5. Üçüncü parti kütüphanelerin LTS/stabil sürümlerini kullanın&lt;/h2&gt;
&lt;p&gt;Her zaman sizden sonra kodunuzu kullanacak ve projenizi yeniden derleyecek kişiyi düşünün. Kütüphanelerin LTS (Long Term Support / Uzun Süreli Destek) sürümlerini kullanmak yeni özelliklere sahip olma açısından iyi bir tercih olmasa da gelecekte re-build / re-compile ihtiyaçlarını düşününce daha iyidir.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;Kullandığınız araçların en yeni ve en güzel sürümlerini kullanma isteğinizi bastırın. Her zaman en güvenli ve en stabil sürüme bağlı olun. Gelecekteki kendiniz ve iş arkadaşlarınız size teşekkür edecek!&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h2 id=&#34;6-dot-en-yaygın-tasarım-desenlerini-tanımlamayı-öğrenin&#34;&gt;6. En yaygın tasarım desenlerini tanımlamayı öğrenin&lt;/h2&gt;
&lt;p&gt;Çoğu büyük projenin bir veya birden fazla &lt;a href=&#34;https://medium.com/gokhanyavas/tasar%C4%B1m-desenleri-gof-design-patterns-16e93e54a92d&#34;&gt;tasarım deseni&lt;/a&gt; kullanılarak yapıldığı doğrudur. Tasarım desenleri elemanların açıklamalarını, ilişkilerini ve soyutlama seviyelerini (abstraction level) tanımlar. Hepsini bilmek veya hepsinde iyi olmak zorunda değilsiniz fakat en temel olanları bilmek faydalı olacaktır. Yalnızca düşünme ve tasarlama açısından değil, aynı zamanda code base için tespit etmek açısından da.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;Code base içinde tasarım desenlerini tanımlayabilen kişi, belirli sınıf ve objeler için nereye bakması gerektiğini bildiği için kodu sürdürebilir ve ekstra fonksiyonlar ekleyebilir.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;İyi uygulanmış bir tasarım deseni, projeye dahil olan herkesin aynı tasarım dilini konuşmasını ve kod içinde daha etkili iletişim kurmasını sağlar.&lt;/p&gt;
&lt;h2 id=&#34;7-dot-her-zaman-kendinizden-sonrakini-düşünün&#34;&gt;7. Her zaman kendinizden sonrakini düşünün&lt;/h2&gt;
&lt;p&gt;Bu kişi siz olabilirsiniz, bir iş arkadaşınız olabilir, yeni bir çalışan olabilir, hatta başka bir şirkette çalışan bir yazılımcı da olabilir, ama birileri sizin kodunuzu sürdürmek veya ekstra fonksiyonlar eklemek zorunda kalacaktır.&lt;/p&gt;
&lt;p&gt;Çoğu junior yazılımcı, yalnızca bir kişinin kod yazdığı ve başka kimsenin dahil olmadığı klasik üniversite projesi yaklaşımının olduğu projelerde kullanıldığı için bu maddenin anlaşılması biraz zor.&lt;/p&gt;
&lt;p&gt;Profesyonel bir ortamda durum biraz daha farklı; yıllar önce yazılmış bir projede kod yazmanız istenecek ve kodunuzun birkaç yıl içinde gelecek “sonraki kişi” için hazır olması gerekecek. Yani bir şeyin çalışır hale gelmesi için geçici bir kod yazdığınızda, build sürecinde eklediğiniz şeyi dokümante etmekten kaçındığınızda, refactoring etmekten imtina ettiğinizde, ileride sizden sonra uğraşacak kişi için &lt;a href=&#34;https://www.linkedin.com/pulse/technical-debt-nedir-orhan-kalayci/&#34;&gt;teknik borç (technical debt)&lt;/a&gt; çıkarıyorsunuz.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;Birkaç saatte bir kodunuzu gözden geçirmek için zaman ayırın. README dosyalarına gerekli dokümantasyonu ekleyin, projeye geçici olarak eklediğiniz dosyaları ve kullanılmayan kodları silin. Mimari veya programlama ile ilgili bir konuda karar almanız gerektiğinde zorlanıyorsanız çalışma ortamınızda sizden daha tecrübeli biriyle iletişim kurun. Yalnızca kodunuzun durumunu iyileştirmiş olmayacaksınız, aynı zamanda gelecekte benzer durumların içinde bulunduğunuzda bununla başa çıkmak konusunda kendinizi geliştirmiş olacaksınız ve gururunuzun incinmesine alışacaksınız. (Bu, Junior aşamasını geçtikten sonra sürekli yaşayayacağınız bir şey :) )&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h2 id=&#34;sonuç&#34;&gt;Sonuç&lt;/h2&gt;
&lt;p&gt;Junior seviyesinden mid-level seviyesine geçmek bir gecede olan bir şey değil. Kariyerinizde ilerlemek ve daha iyi bir profesyonel yazılımcı olmak iyi alışkanlıklar edinme işidir. Bu makalede bu geçişe başlamak isteyenler ve Yazılım Geliştirici olarak etki bırakmak isteyenler için en önemli alışkanlıkları sıraladım.&lt;/p&gt;
</description>
        </item>
        
        <item>
            <title>Hyperledger Nedir?</title>
            <link>http://kamer.dev/hyperledger-nedir/</link>
            <pubDate>Fri, 05 Apr 2019 12:50:19 +0000</pubDate>
            
            <guid>http://kamer.dev/hyperledger-nedir/</guid>
            <description>&lt;p&gt;Bilişim veya finans dünyasındaki gelişmeleri az çok takip ediyorsanız blockchain(blokzincir) ve kripto para terimlerini duymuşsunuzdur. Bu yazıda blockhain alanında ses getiren projelerden biri olan Hyperledger’dan bahsedeceğim. Blockchain’i daha önce duymadıysanız ve hakkında bir şeyler öğrenmek isterseniz sayın Mert Susur’un Youtube’da bulunan &lt;a href=&#34;https://youtu.be/06v%5FrIiQQGY&#34;&gt;webinarını&lt;/a&gt; izleyebilirsiniz.&lt;/p&gt;
&lt;p&gt;Blockchain kelimesini duyduğumuzda aklımıza ilk olarak Bitcoin, Ethereum, Ripple, gibi projeler gelse de blockchainin kullanım alanı yalnızca kripto paralar değildir. Kullanım alanını genişleten projelerden biri de adını gün geçtikçe daha sık duyduğumuz/duyacağımız &lt;strong&gt;Hyperledger&lt;/strong&gt;. 2015 Aralık ayında Linux Foundation tarafından duyurulan ve 2016 yılında çıkan Hyperledger, açık kaynak kodlu bir blockchain projesidir. Amaçları, kısaca, iş dünyasında şirket seviyesindeki işlemlerin idare edileceği blockchain framework’leri geliştirmek; bu işlemler için hem ticari hem de teknik yönetimler tarafından desteklenen tarafsız, açık ve tamamen topluluk odaklı altyapılar sağlamak; insanları blockchain fırsatları konusunda eğitmek ve bu projeleri geliştirecek teknik topluluklar kurmak. Yani Hyperledger adını verdiğimiz proje kesinlikle bir kripto para değil. Hatta projenin bir yetkilisi olan Brian Behlendorf kendisine kripto paralar hakkında sorulan bir soruya karşılık olarak &lt;strong&gt;gelecekte asla Hyperledger coin gibi bir proje olmayacağını, global bir para birimi projesinin olası siyasi zorluklarından kaçındıklarını&lt;/strong&gt; söyleyerek bu konuya açıklık getirmiştir.&lt;/p&gt;
&lt;p&gt;Şu anda Hyperledger çatısı altında 12 proje bulunmaktadır. Bu projeler aşağıdaki gibidir:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Burrow&lt;/li&gt;
&lt;li&gt;Fabric&lt;/li&gt;
&lt;li&gt;Grid&lt;/li&gt;
&lt;li&gt;Indy&lt;/li&gt;
&lt;li&gt;Iroha&lt;/li&gt;
&lt;li&gt;Sawtooth&lt;/li&gt;
&lt;li&gt;Caliper&lt;/li&gt;
&lt;li&gt;Cello&lt;/li&gt;
&lt;li&gt;Composer&lt;/li&gt;
&lt;li&gt;Explorer&lt;/li&gt;
&lt;li&gt;Quilt&lt;/li&gt;
&lt;li&gt;Ursa&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Bu projelerden ilk altısı framework, diğer altısı ise tool başlığı altında listelenmektedir.&lt;/p&gt;
&lt;p&gt;Hyperledger üyeleri arasında American Express, Cisco, J.P.Morgan, Intel, IBM, SAP, Digicert, FedEx, Huawei, Oracle gibi devler bulunmaktadır.
Tam listeye ulaşmak için &lt;a href=&#34;https://www.hyperledger.org/members&#34;&gt;tıklayın&lt;/a&gt;.&lt;/p&gt;
&lt;h2 id=&#34;örnek-projeler&#34;&gt;Örnek Projeler&lt;/h2&gt;
&lt;p&gt;Hyperledger ile yapılmış birçok projeye ulaşmak &lt;a href=&#34;https://www.hyperledger.org/resources/publications#case-studies&#34;&gt;mümkün&lt;/a&gt; fakat ben bu yazıda yalnızca üç tanesinden bahsedeceğim.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;IBM Food Trust:&lt;/strong&gt; Gıdaların ilk oluştuğu yerden itibaren masaya gelene kadar geçirdiği tüm süreçleri kayıt altına alarak şeffaflığını ve güvenilirliğini artırmayı hedefleyen bir proje. Food Trust, gıda tedarik zincirindeki tüm aktörlerin değiştirilemez bir veritabanı olarak işlev gören blockchain üzerinde tutulması fikrinin en başarılı örneğidir. Pilot uygulaması Nestlé, Wal-Mart, Tyson Foods ve Golden State Foods ile yapılmaktadır. Proje hakkında ayrıntılı bilgileri yazının sonunda bulabilirsiniz.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Chain-m:&lt;/strong&gt; NIIT Technologies tarafından geliştirilen Chain-m projesi havayolu şirketlerinin biletleme süreçlerinin blockchain üzerinde sürdürüldüğü bir proje. Hyperledger Fabric kullanılarak yapılan bu projede kullanıcıların web tabanlı bir arayüz üzerinden bu süreçlerin kaydını ve takibini şeffaf bir şekilde yapmaları amaçlanıyor. Proje hakkında ayrıntılı bilgileri yazının sonunda bulabilirsiniz.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;ScanTrust:&lt;/strong&gt; Organik kahve satıcısı Cambio Coffe’nin geliştirdiği bu projede kahve çekirdeğinin tüm yolculuğu blockchain üzerine kaydediliyor.&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Kullanıcılar, paketlerin üzerinde yer alan barkodları kullanarak bu yolculuğu görüntüleyebiliyor. Sawtooth ile geliştirilen bu proje hakkındaki ayrıntılı bilgiyi yazının sonunda bulabilirsiniz.&lt;/p&gt;
&lt;h2 id=&#34;neden-hyperledger&#34;&gt;Neden Hyperledger?&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Kimlik Doğrulaması:&lt;/strong&gt;  Kripto para projelerinde çok vurgu yapılan konulardan biri kullanıcıların sistem içinde anonim olması. Fakat bu her zaman gerekli değildir. Bu durumlarda Hyperledger tercih sebebi olabilir. Çünkü Hyperledger,  &lt;em&gt;permissioned&lt;/em&gt;  bir blockchaindir ve identity management modülü ile kimlik doğrulaması konusunda bize yardımcı oluyor.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Veri Gizliliği:&lt;/strong&gt; Bazı projelerde verilerin herkese açık bir ağ üzerinde tutulması ve herkesin erişimine açık olması problemler yaratabilir. Bu sebeple Hyperledger kullanarak belirli bir kullanıcı grubuna özel bazı bilgileri saklayabilirsiniz.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Modüler Mimari:&lt;/strong&gt; Hyperledger’ın modüler mimarisi, geliştiricilerin ihtiyacı olan veya kullanmak istediği modülleri kullanmasına imkan sağlıyor. Örneğin halihazırda kimlik doğrulaması olan bir şirket, projesinin içine kendi kimlik doğrulamasını ekleyebilir.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Dil Seçenekleri:&lt;/strong&gt;  Hyperledger Java, Go ve NodeJS ile geliştirme yapmamıza imkan veriyor.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Ücretsiz:&lt;/strong&gt; İşlem yapmak için veya blockchain üzerine bir veri tutmak için para ödemenize gerek yoktur.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Hız:&lt;/strong&gt;  Public blockchainler, ölçeklenebilirlik problemi sebebiyle yaşanan hız sorunları yüzünden iş dünyasında pek tercih edilmiyor. Bu noktada devreye Hyperledger ve diğer permissioned blockchain’ler giriyor.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Consensus algoritması:&lt;/strong&gt; Hyperledger’ın consensus algoritmasının POW kadar güvenli olduğu düşünülmüyor. Buna karşın herkesin kimliğinin bilindiği bir blockchain’de POW gibi yüksek enerji gerektiren bir algoritmaya gerek olmadığı görüşü de var.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;temel-terimler&#34;&gt;Temel Terimler&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Chaincode:&lt;/strong&gt; Ethereum’dan aşina olduğumuz smart contract’ların Hyperledger’daki adı chaincode’dur.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Channel:&lt;/strong&gt; Channel’lar alt ağlar oluşturmak için kullanılır. Alt ağlar yalnızca belirli kullanıcıların bağlandığı yerlerdir. Böylece belirli kullanıcı grupları gizliliklerini sağlarlar. Her channel’ın kendi ledger’ı vardır ve o channel içinde yapılan tüm transaction’ları channel üyeleri görebilir.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Ledger:&lt;/strong&gt; Yalnızca sondan veri eklemeye izin veren kayıt defteri.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;World State:&lt;/strong&gt; Ağdaki tüm objelerin anlık durumları.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Identity:&lt;/strong&gt;  Ağa katılan tüm kişilerin eşsiz tanımlayacıları.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;yazıda-bahsedilen-linkler&#34;&gt;Yazıda Bahsedilen Linkler&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://www.ibm.com/tr-tr/blockchain/solutions/food-trust&#34;&gt;IBM Food Trust&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.niit-tech.com/news-events/news/niit-technologies-introduces-chain-m-blockchain-powered-solution-airlines-and-its&#34;&gt;Chain-m&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.hyperledger.org/resources/publications/scantrust-case-study&#34;&gt;ScanTrust&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;yararlanılan-kaynaklar&#34;&gt;Yararlanılan Kaynaklar&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://www.hyperledger.org/blog/2018/11/30/six-hyperledger-blockchain-projects-now-in-production&#34;&gt;https://www.hyperledger.org/blog/2018/11/30/six-hyperledger-blockchain-projects-now-in-production&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://developer.ibm.com/tutorials/cl-top-technical-advantages-of-hyperledger-fabric-for-blockchain-networks/&#34;&gt;https://developer.ibm.com/tutorials/cl-top-technical-advantages-of-hyperledger-fabric-for-blockchain-networks/&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.devteam.space/blog/pros-and-cons-of-hyperledger-fabric-for-blockchain-networks/&#34;&gt;https://www.devteam.space/blog/pros-and-cons-of-hyperledger-fabric-for-blockchain-networks/&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://hyperledger.github.io/composer/v0.19/reference/glossary&#34;&gt;https://hyperledger.github.io/composer/v0.19/reference/glossary&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
</description>
        </item>
        
        <item>
            <title>Visual Studio Code Eklenti Tavsiyeleri</title>
            <link>http://kamer.dev/visual-studio-code-eklenti-tavsiyeleri/</link>
            <pubDate>Thu, 31 Jan 2019 12:46:42 +0000</pubDate>
            
            <guid>http://kamer.dev/visual-studio-code-eklenti-tavsiyeleri/</guid>
            <description>&lt;div class=&#34;block-plain&#34;&gt;
  &lt;div&gt;&lt;/div&gt;
&lt;p&gt;Bu yazı Ocak 2019&amp;rsquo;da yazılmıştır. Geçen sürede güncelliğini kaybetmiş olabilir. Okurken bunu göz önünde bulundurmanızı tavsiye ederim.&lt;/p&gt;
&lt;/div&gt;
&lt;p&gt;Merhabalar. Bu yazımda kendim kullanıp faydasını gördüğüm VSCode eklentilerinden bahsedeceğim. Daha önce Brackets, Atom, Sublime editörlerini kısa süreli kullandım ve en sonunda Visual Studio Code kullanmaya karar verdim. Aslında kullandığım diğer editörler de güzeldi fakat ben en çok Visual Studio Code’u beğendim ve uzun süredir yalnızca bunu kullanıyorum. Hemen eklentilere geçelim.&lt;/p&gt;
&lt;h2 id=&#34;auto-close-tag&#34;&gt;Auto Close Tag&lt;/h2&gt;
&lt;p&gt;Html etiketlerinin otomatik olarak kapanması için kullandığım eklenti. Herhangi bir ayar vs. gerekmiyor.&lt;/p&gt;
&lt;h2 id=&#34;duplicate-selection-or-line&#34;&gt;Duplicate selection or line&lt;/h2&gt;
&lt;p&gt;Adından da anlaşılacağı üzere seçili olan bir metni veya satırı kopyalar. &lt;em&gt;Ctrl+d&lt;/em&gt; kısayolunu kullandığınızda eğer seçili olan metin varsa onu, yoksa o satırı kopyalar.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/vscode-plugin/duplicate.gif&#34;/&gt;
&lt;/figure&gt;

&lt;h2 id=&#34;live-server&#34;&gt;Live Server&lt;/h2&gt;
&lt;p&gt;Yaptığınız çalışmaları test etmek için local server kurar. Aynı zamanda editör üzerinden değişiklik yapıp kaydettiğinizde sayfayı günceller. Çalıştırmak için herhangi bir ayar yapmanız gerekmiyor. En kolay çalıştırma şekli  &lt;em&gt;Alt + L + O&lt;/em&gt; kısayoludur. Bunun dışında editörün alt kısmında bulunan status bar’da bulunan Go Live butonunu kullanabilirsiniz. Son olarak  &lt;em&gt;Ctrl + Shift +P&lt;/em&gt;  kısayoluyla commands penceresini açıp Live Server yazıp çıkan listeden Open with Live Server seçeneğiyle de kullanabilirsiniz.&lt;/p&gt;
&lt;h2 id=&#34;polacode&#34;&gt;Polacode&lt;/h2&gt;
&lt;p&gt;Eğer yazılımla alakalı blog tutuyorsanız veya yazdığınız kodları resim olarak kaydetmek istiyorsanız Polacode bu konuda size yardımcı oluyor. Eğer &lt;a href=&#34;http://carbon.now.sh/&#34;&gt;http://carbon.now.sh/&lt;/a&gt; kullandıysanız aşinasınızdır. Kullanımı da oldukça basit.  &lt;em&gt;Ctrl + Shift + P&lt;/em&gt; ile commands penceresini açın ve Polacode yazın. Ekran ikiye bölünecektir. Polacode sekmesine kodunuzu yapıştırın ve aşağıda bulunan butona tıklayın.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/vscode-plugin/polacode.png&#34;/&gt;
&lt;/figure&gt;

&lt;h2 id=&#34;vetur&#34;&gt;Vetur&lt;/h2&gt;
&lt;p&gt;Bu eklenti yalnızca VueJS kullananların ilgisini çekecek bir eklenti. Kod tamamlama, syntax renklendirme, hata kontrolü, hazır kodlar, emmet gibi birçok eklentiyi içinde barındırıyor.&lt;/p&gt;
&lt;h2 id=&#34;image-preview&#34;&gt;Image Preview&lt;/h2&gt;
&lt;p&gt;Kodlarınızda bulunan resim dosyalarına ait path’lerin üzerine geldiğinizde küçük bir önizleme gösteriyor.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/vscode-plugin/image-preview.gif&#34;/&gt;
&lt;/figure&gt;

&lt;h2 id=&#34;path-intellisense&#34;&gt;Path Intellisense&lt;/h2&gt;
&lt;p&gt;Adından da tahmin edileceği üzere path’lerinizi otomatik olarak tamamlar.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/vscode-plugin/path-intellisense.gif&#34;/&gt;
&lt;/figure&gt;

&lt;h2 id=&#34;prettier-code-formatter&#34;&gt;Prettier — Code formatter&lt;/h2&gt;
&lt;p&gt;Bu yazıyı yazdığım sırada 6.3 milyon indirmesi olan bir eklenti. Yazdığınız kodu görsel olarak düzeltiyor. Ekstra bir ayar vs. gerekmiyor. &lt;em&gt;Ctrl + Shift + P&lt;/em&gt; ile commands penceresini açın ve “Format document” yazın. İsterseniz tüm metni, isterseniz de sadece seçili olan bir kısmı düzeltebilirsiniz.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/vscode-plugin/prettier.gif&#34;/&gt;
&lt;/figure&gt;

&lt;h2 id=&#34;code-runner&#34;&gt;Code Runner&lt;/h2&gt;
&lt;p&gt;Yazdığınız bir kod parçacığının çıktısını hızlıca konsoldan görmenize yarar. Sadece çalıştırmak istediğiniz kısmı seçin ve sağ tıklayın, Run Code’a tıkladığınızda konsoldan çıktı görünecektir. Alternatif olarak  &lt;em&gt;Ctrl + Alt + N&lt;/em&gt; kısayolu da kullanılabilir. Desteklemediği dil yok denebilir.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/vscode-plugin/code-runner.gif&#34;/&gt;
&lt;/figure&gt;

&lt;h2 id=&#34;faker--vscode-faker&#34;&gt;Faker (vscode-faker)&lt;/h2&gt;
&lt;p&gt;Aralarında en sevdiğim eklentilerden biri. Fake isim, adres, tarih, şirket ismi, resim gibi şeyler üretiyor. Yalnızca  &lt;em&gt;Ctrl + Shift + P&lt;/em&gt; yazıp faker yazın ve istediğiniz örnek datayı seçin.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/vscode-plugin/faker.gif&#34;/&gt;
&lt;/figure&gt;

</description>
        </item>
        
        <item>
            <title>OOP’nin 4 Ana Prensibi: Encapsulation, Inheritence, Abstraction, Polymorphism</title>
            <link>http://kamer.dev/oopnin-4-ana-prensibi-encapsulation-inheritence-abstraction-polymorphism/</link>
            <pubDate>Thu, 10 Jan 2019 11:59:24 +0000</pubDate>
            
            <guid>http://kamer.dev/oopnin-4-ana-prensibi-encapsulation-inheritence-abstraction-polymorphism/</guid>
            <description>&lt;p&gt;İyi bir kod tasarımı için uyulması gereken bazı prensipler vardır. Prensipler zorunlu değildir fakat uyulduğunda hem dünya çapında standart bir kod yazmış oluruz hem de sürdürülebilirliği yüksek bir iş ortaya çıkar. Aslında herhangi bir programlama dilinde az da olsa bir geçmişiniz varsa bu prensipleri muhtemelen kullanıyorsunuzdur fakat adlarını bilmiyorsunuzdur. Öğrenmesi ve uygulaması çok kolay olan bu prensipler özellikle Junior yazılımcılar tarafından korkuyla yaklaşılan şeyler. Hadi bu prensipleri ve amaçlarını inceleyelim.&lt;/p&gt;
&lt;h2 id=&#34;encapsulation--kapsülleme&#34;&gt;Encapsulation (Kapsülleme)&lt;/h2&gt;
&lt;p&gt;Türkçe’de  &lt;strong&gt;kapsülleme&lt;/strong&gt;  veya  &lt;strong&gt;sarmalama&lt;/strong&gt; olarak bilinen encapsulation prensibi class’ın property’lerini korumaya almasıdır. Bu korumayı sağlamak için private ve protected access modifier’larını (erişim belirteci) kullanırız. Eğer bir property’i tanımlarken private kullanırsak o class dışında hiçbir yerden erişim sağlanamaz. Protected kullanırsak da yalnızca subclass’lar ve aynı package’da bulunan classlar tarafından erişilir. Encapsulation prensibinin maksadı class’a ait property’lere her classın istediği gibi erişmesini ve değiştirmesini engellemektir. Erişim kısıtlanmayacaksa bile erişimi getter/setter methodları gibi yöntemlerle kontrol altına almaktır. Zaten encapsulation prensibine gözümüzün en aşina olduğu yer getter/setter methodlarıdır. Bu prensiple alakalı biri getter/setter methodları olmak üzere iki örnek vereceğim.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;Personel&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Long personelNu&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String isim&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String soyisim&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; String departman&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; Long &lt;span style=&#34;color:#00a000&#34;&gt;getPersonelNu&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; personelNu&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;setPersonelNu&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;Long personelNu&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;this&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;personelNu&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; personelNu&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; String &lt;span style=&#34;color:#00a000&#34;&gt;getIsim&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; isim&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;setIsim&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;String isim&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;this&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;isim&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; isim&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; String &lt;span style=&#34;color:#00a000&#34;&gt;getSoyisim&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; soyisim&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;setSoyisim&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;String soyisim&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;this&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;soyisim&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; soyisim&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; String &lt;span style=&#34;color:#00a000&#34;&gt;getDepartman&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; departman&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;setDepartman&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;String departman&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;this&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;departman&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; departman&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Yukarıdaki örnekte gördüğünüz gibi hiçbir classın Personel property’lerine doğrudan erişim hakkı yoktur. Erişimi yalnızca getter/setter methodlarıyla yapabilirler. Tahmin edileceği gibi getter/setter methodları private olamaz.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;Sayac&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Integer sayac&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;Sayac&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	sayac &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; 1&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; Integer &lt;span style=&#34;color:#00a000&#34;&gt;sayacArtir&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(){&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; sayac&lt;span style=&#34;color:#666&#34;&gt;++;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; Integer &lt;span style=&#34;color:#00a000&#34;&gt;getSayac&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; sayac&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Yukarıda ise örnek bir Sayac classı bulunmakta. Diğer class’lar erişim sağlanmak istediğinde getter methodunu, sayacı artırmak istediğinde ise sayacArtir() methodunu kullanmak zorunda. Yani herhangi bir class’ın  &lt;code&gt;ornekSayac.sayac += 1&lt;/code&gt;  gibi bir şey yazmaya yetkisi yok. Çünkü eğer herhangi bir class bunu yazabilirse sayacı istediği gibi manipüle edebilir. Bu sebeple encapsulation’ı kullanarak Sayac’ın property’sini korumaya almış oluyoruz.&lt;/p&gt;
&lt;h2 id=&#34;inheritence--kalıtım&#34;&gt;Inheritence (Kalıtım)&lt;/h2&gt;
&lt;p&gt;Adından tahmin edilebileceği üzere herhangi bir class’ın üst class’larına ait olan method ve propertyleri kalıtım yoluyla almasıdır. Günlük hayattan bir örnekle anlaması çok daha kolay. Telefon adında bir class düşünelim. Bu class tüm telefonlarda ortak olan bazı property’leri ve method’ları barındıracak. aramaYap(); mesajGonder(); methodları ve imeiNumber property’sini örnek verebiliriz. Bu class’ın tüm alt class’ları bu methodları ve property’leri kullanabilecektir. Böylece AkilliTelefon ve TusluTelefon classlarını tanımlarken kalıtım yoluyla alınan bu property’leri ve method’ları tekrar tanımlamak zorunda kalmayacağız.&lt;/p&gt;
&lt;p&gt;Aşağıda örnek bir Telefon class’ı bulunmakta.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;Telefon&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;protected&lt;/span&gt; String imeiNumber&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;protected&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;aramaYap&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(){&lt;/span&gt;
	System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;println&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Arama yapıldı.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;protected&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;mesajGonder&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(){&lt;/span&gt;
	System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;println&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Mesaj gönderildi.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; String &lt;span style=&#34;color:#00a000&#34;&gt;getImeiNumber&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;return&lt;/span&gt; imeiNumber&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;setImeiNumber&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;String imeiNumber&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;this&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;imeiNumber&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; imeiNumber&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Şimdi de bu class’ın iki subclass’ını tanımlayalım.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;AkilliTelefon&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;extends&lt;/span&gt; Telefon &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;protected&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;interneteBaglan&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;println&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;İnternete bağlandı.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;TusluTelefon&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;extends&lt;/span&gt; Telefon &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;protected&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;yilanOyununuAc&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(){&lt;/span&gt;
	System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;println&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Yılan oyunu açıldı.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Şimdi de Test class’ını yazalım.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;Test&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;static&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;main&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;[]&lt;/span&gt; args&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	AkilliTelefon akilliTelefon &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; AkilliTelefon&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
	akilliTelefon&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;setImeiNumber&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;354816220461203&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	akilliTelefon&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;aramaYap&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
	akilliTelefon&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;interneteBaglan&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;

	TusluTelefon tusluTelefon &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; TusluTelefon&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
	tusluTelefon&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;setImeiNumber&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;354816221162234&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	tusluTelefon&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;mesajGonder&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
	tusluTelefon&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;yilanOyununuAc&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Yukarıdaki örnekte görüldü üzere AkilliTelefon ve TusluTelefon class’larının instance’ları hem Telefon class’ına ait olan  &lt;em&gt;aramaYap()&lt;/em&gt;  ve  &lt;em&gt;mesajGonder()&lt;/em&gt;  methodlarını ve  &lt;em&gt;imeiNumber&lt;/em&gt;  property’sini  &lt;strong&gt;inheritence (kalıtım)&lt;/strong&gt;  yoluyla alıp kullanıyor hem de kendi class’larına ait olan  &lt;em&gt;interneteBaglan()&lt;/em&gt;  ve  &lt;em&gt;yilanOyunuAc()&lt;/em&gt; methodlarını kullanıyor.&lt;/p&gt;
&lt;h2 id=&#34;abstraction--soyutlama&#34;&gt;Abstraction (Soyutlama)&lt;/h2&gt;
&lt;p&gt;Bu prensibe doğrudan bir örnekle başlıyoruz. Aşağıdaki kod parçacığının ne yaptığını, ne işe yaradığını biliyor musunuz? Biraz incelerseniz ne iş yaptığını tahmin edeceksiniz ama buna hiç gerek yok. Ben değil, abstraction prensibi söylüyor bunu. Aşağıdaki kod parçacığı IDE’nizi her açtığınızda en az bir kere kullandığınız &lt;code&gt;System.out.println();&lt;/code&gt;  methodunun arkaplanda yaptığı işlerin bir kısmı. Fakat siz &lt;code&gt;System.out.println();&lt;/code&gt; yazarken arka planda neler döndüğünü bilmeden yazıyorsunuz. Bunun sebebi abstraction prensibi. Daha derli toplu bir ifadeyle objelerin ayrıntılarıyla uğraşmak yerine yalnızca girdi ve çıktılarına odaklanarak tasarımı daha iyi oluşturmayı ve anlamayı sağlamaktır.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;try&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
      &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;synchronized&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;this&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	  ensureOpen&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
	  textOut&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;write&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;s&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
	  textOut&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;flushBuffer&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
	  charOut&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;flushBuffer&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
	  &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;if&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;autoFlush &lt;span style=&#34;color:#666&#34;&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;s&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;indexOf&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#39;\n&amp;#39;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;&amp;gt;=&lt;/span&gt; 0&lt;span style=&#34;color:#666&#34;&gt;))&lt;/span&gt;
	      out&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;flush&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;catch&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;InterruptedIOException x&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
    Thread&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;currentThread&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;().&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;interrupt&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;catch&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;IOException x&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
    trouble &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;true&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Bu prensibe araba kullanmak örneği de verilebilir. Araba kullanan birinin gaz pedalına ve frene bastığında veya vites değiştirdiğinde neler olduğunu bilmesine gerek yok. Yalnızca girdi ve çıktıları öğrenerek rahatça araba kullanabilir.&lt;/p&gt;
&lt;h2 id=&#34;polymorphism--çok-biçimlilik&#34;&gt;Polymorphism (Çok Biçimlilik)&lt;/h2&gt;
&lt;p&gt;Polymorphism, (çok biçimlilik) methodların objeye göre farklı çıktılar üretmesi veya farklı işler yapmasıdır. Yani alışageldiğimiz gibi methodlara sabit görevler vermek yerine onlara çok biçimli (polimorf) davranacak şekilde bir esneklik vermektir.&lt;/p&gt;
&lt;h3 id=&#34;polymorphism-örnek-1--method-overriding&#34;&gt;Polymorphism Örnek 1 (Method Overriding)&lt;/h3&gt;
&lt;p&gt;İlk vereceğim örnek klişe ama -bence- konuyu en iyi anlatan örnek.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;Hayvan&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;sesCikar&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(){&lt;/span&gt;

	System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;println&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Hayvan sesi.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;Kedi&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;extends&lt;/span&gt; Hayvan &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;sesCikar&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;println&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Miyav&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;Kopek&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;extends&lt;/span&gt; Hayvan &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;sesCikar&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;println&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Hav Hav&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Yukarıda Hayvan class’ı ve Kedi — Kopek subclass’ları var. Hayvan class’ının sesCikar metodu olmasına rağmen Kedi ve Kopek subclass’ları için özel sesCikar metodu tanımladık. Aşağıda ise Hayvan tipindeki değişkene Kedi instance’ı verince kedi sesi, Kopek instance’ı verince köpek sesi çıkaracak.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;Test&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;static&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;main&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;String&lt;span style=&#34;color:#666&#34;&gt;[]&lt;/span&gt; args&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	Hayvan hayvan &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; Hayvan&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
	hayvan&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;sesCikar&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;

	System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;println&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;-------&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	hayvan &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; Kedi&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
	hayvan&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;sesCikar&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;

	System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;println&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;-------&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

	hayvan &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; Kopek&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
	hayvan&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;sesCikar&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;

    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Yukarıdaki testin çıktısı aşağıdaki gibi olacaktır.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-plain&#34; data-lang=&#34;plain&#34;&gt;Hayvan sesi.
— — — –
Miyav
— — –
Hav Hav
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;polymorphism-örnek-2--method-overloading&#34;&gt;Polymorphism Örnek 2 (Method Overloading)&lt;/h3&gt;
&lt;p&gt;Bu örnekte ise aynı isimde iki method var. Bu iki method’un biri iki Integer değeri alıyor, diğeri ise bir Integer değeri alıyor. Biz kaç parametre göndererek çağırırsak o method çalışacaktır.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;yemekYe&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;Integer hamburgerSayisi&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; Integer kolaSayisi&lt;span style=&#34;color:#666&#34;&gt;){&lt;/span&gt;
      System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;println&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(((&lt;/span&gt;hamburgerSayisi&lt;span style=&#34;color:#666&#34;&gt;*&lt;/span&gt;261&lt;span style=&#34;color:#666&#34;&gt;)+(&lt;/span&gt;kolaSayisi&lt;span style=&#34;color:#666&#34;&gt;*&lt;/span&gt;168&lt;span style=&#34;color:#666&#34;&gt;))&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;+&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34; kalori alındı.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
  &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

  &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;yemekYe&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;Integer hamburgerSayisi&lt;span style=&#34;color:#666&#34;&gt;){&lt;/span&gt;
      System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;println&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;((&lt;/span&gt;hamburgerSayisi&lt;span style=&#34;color:#666&#34;&gt;*&lt;/span&gt;261&lt;span style=&#34;color:#666&#34;&gt;)+&lt;/span&gt; &lt;span style=&#34;color:#b44&#34;&gt;&amp;#34; kalori alındı.&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
  &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;

  &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;test&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

      yemekYe&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;2&lt;span style=&#34;color:#666&#34;&gt;,&lt;/span&gt; 1&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
      yemekYe&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;2&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;

&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;</description>
        </item>
        
        <item>
            <title>Spring Initialzr ile Proje Oluşturma</title>
            <link>http://kamer.dev/spring-initialzr-ile-proje-olusturma/</link>
            <pubDate>Fri, 06 Jul 2018 11:47:32 +0000</pubDate>
            
            <guid>http://kamer.dev/spring-initialzr-ile-proje-olusturma/</guid>
            <description>&lt;p&gt;Merhaba, bu yazıda Spring Initializr kullanarak basit bir HelloWorld projesi yapmayı anlatacağım.  &lt;em&gt;Spring Initialzr&lt;/em&gt;, istediğimiz gerekliliklere göre bize temel konfigürasyonları hazır bir Spring projesi üretip veren bir araçtır. Benim bildiğim 3 farklı kullanım şekli var:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;http://start.spring.io/&#34;&gt;http://start.spring.io/&lt;/a&gt; adresinden indirerek.&lt;/li&gt;
&lt;li&gt;IDE Pluginleri ile&lt;/li&gt;
&lt;li&gt;Spring CLI kullanarak.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Ben bu yazıda doğrudan internet sitesi üzerinden anlatacağım. Öncelikle yukarıda verdiğim Spring Initialzr linkine tıklayın.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/spring-initialzr-tutorial/initialzr.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Bu sayfada proje adını, Spring ve Java sürümlerini, Maven/Gradle tercihini ve gereklilikleri seçiyoruz. Ben yalnızca Web gerekliliğini seçip bir proje oluşturuyorum. Tüm gereklilikleri girip Generate Project’e tıklayıp projeyi indirdikten sonra arşivden çıkarın. Sonra (Eclipse için) Project Explorer kısmından Import seçeneğine tıklayıp açılan menüde Existing Maven Project’i seçin ve arşivden çıkardığınız projeyi Import edin.&lt;/p&gt;
&lt;p&gt;Finish seçeneğine tıkladıktan sonra ortalama 3–5 saniye projeyi gerekliliklerini indirmesi sürüyor. Projenin son hali aşağıdaki gibi oluyor.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/spring-initialzr-tutorial/hierarchy.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Bu proje yapısını biraz inceleyelim.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Spring Elements&lt;/strong&gt;  kısmında Spring’e ait olan Bean, Controller, Repository gibi bileşenlerin kopyası bulunuyor.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;src/main/java&lt;/strong&gt;  kısmında java classlarımız bulunuyor.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;src/main/resources&lt;/strong&gt;  application.properties dosyasının bulunduğu dizin. Aynı zamanda html, css dosyalarımızı da burada tutuyoruz.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;src/test/java&lt;/strong&gt; kısmı test için kullanılıyor.&lt;/li&gt;
&lt;li&gt;Altında JRE ve Maven bağımlılıkları bulunuyor.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Projemiz bu haliyle çalışmaya hazır. Sağ tıklayıp Run As &amp;gt; Spring Boot App diyerek çalıştırabiliriz.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/spring-initialzr-tutorial/console-output.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Çalıştırdığımızda Console’da buna benzer bir çıktı alacaksınız. Burada aşama aşama neler yaptığını yazıyor. Şimdilik burada yazanlar bizim için önemsiz fakat ileride kullanacağız. Şimdilik önemli olan kısım  &lt;em&gt;“Started HelloWorldApplication in …”&lt;/em&gt;  yazan kısım ve  &lt;em&gt;“Tomcat started on port(s): 8080 (http)…”&lt;/em&gt; yazan kısım. Uygulamamızın default port olan 8080 portunda başarılı bir şekilde çalıştırıldığını buradan görüyoruz. Henüz isteklerimize cevap verecek bir bileşen olmadığından dolayı localhost:8080 adresine gittiğinizde error sayfası ile karşılaşacaksınız. Son olarak bir Hello World çıktısı alıp bu yazıyı bitirelim.&lt;/p&gt;
&lt;p&gt;&lt;code&gt;src/main/java&lt;/code&gt; kısmına gelin ve &lt;code&gt;HelloWorld&lt;/code&gt; paketinin altında yeni bir paket oluşturun. Ben adını &lt;code&gt;com.kamer.helloworld.controllers&lt;/code&gt; olarak veriyorum. Burada önemli bir noktaya değinmekte fayda var. Siz projeyi çalıştırdığınızda Spring, Controller, Repository, RestController gibi bileşenleri taramak için main method’un bulunduğu paketin altındaki paketleri tarayacak. Bu yüzden eğer oluşturacağınız herhangi bir component bu paketin alt katmanlarından birinde olmazsa hata alırsınız. Spring’e başka bir yeri taraması için bir ayar yapabiliriz fakat şimdilik bu şekilde devam ediyorum.&lt;/p&gt;
&lt;p&gt;Sonra bu paketin içinde HelloController adında bir sınıf yaratıp sınıfın hemen üstüne &lt;code&gt;@RestController&lt;/code&gt; anotasyonunu ekleyin. Sonra aşağıdaki gibi bir method oluşturun.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/spring-initialzr-tutorial/controller.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Yukarıda yaptığımız işlemi açıklayayım. Öncelikle anotasyonlar Spring Framework ile iletişim kurma şeklimiz. Yani bazı şeyleri Spring’e söyleyip ondan sonra kalan şeyleri serinin ilk yazısında açıkladığım IoC prensibine bırakıyoruz. Öncelikle bu sınıfın RestController olduğunu, yani yapılan HTTP isteklerine cevap verecek bir controller olduğunu söyledik. Altındaki method’da ise ilk restful endpoint’imizi yarattık. GET isteklerine cevap vereceğini, “/” dizinine gelecek istekleri dinleyeceğini söyledik. Biz uygulamamızı çalıştırdığımızda Spring öncelikle bu anotasyonları okuyacak, eğer biz aksi bir şey söylemezsek Main metodun bulunduğu paketin altındaki her yere bakıp bunları ‘map’leyecek. Ondan sonra gelen isteklere bizim istediğimiz şekilde cevap verilmesini sağlayacak. Bu sınıfı yazdıktan sonra Relaunch yaparak uygulamamızı tekrar çalıştırıyoruz. Bu sefer konsolda farklı bir şey yazıyor.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/spring-initialzr-tutorial/map-log.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Burada paketleri tararken bizim yazdığımız &lt;code&gt;@RequestMapping&lt;/code&gt; anotasyonunu gördüğünü, &lt;code&gt;home()&lt;/code&gt; methodunu çalıştırmak için “/” dizinine gelecek bir GET isteği beklediğini bize söylüyor. Bu aşamadan sonra ister Postman gibi bir programla, ister curl ile, isterseniz de tarayıcınızla localhost:8080 adresine GET isteği göndererek Hello World! çıktısını görebilirsiniz.&lt;/p&gt;
</description>
        </item>
        
        <item>
            <title>İngilizce Öğrenme Üzerine Tavsiyeler</title>
            <link>http://kamer.dev/ingilizce-ogrenme-uzerine-tavsiyeler/</link>
            <pubDate>Sat, 30 Jun 2018 21:56:04 +0000</pubDate>
            
            <guid>http://kamer.dev/ingilizce-ogrenme-uzerine-tavsiyeler/</guid>
            <description>&lt;p&gt;Aşağıda sıraladığım tavsiyeler yalnızca kendi tecrübelerimdir.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;İnternette tonlarca set, yöntem, iddia vs. var. Bunların hemen hemen çoğundan uzak durmanız gerekiyor. Aklıma gelenlerden bahsedeyim:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Uyurken İngilizce:&lt;/strong&gt;  Bu iddia safsatadır. Bilimsel bir açıklaması yoktur. Aldous Huxley’in Cesur Yeni Dünya kitabından esinlenilmiştir. Günümüz teknolojisinde kimse size uykuda İngilizce öğretemez.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;X Günde İngilizce:&lt;/strong&gt;  Eğer maksadınız İngilizce öğrenmekse bundan da uzak durmalısınız. Zira çevrenize bakarsanız saçma sapan dil kursları bu işi iyice abarttı ve gün konusunda birbirleriyle yarışan reklamlar yapıyorlar. 15 günde, 30 günde dil öğrenilmez. Bu kursta size ezberletecekleri cümle kalıplarını 5 TL’ye alacağınız bir konuşma kılavuzuyla da yaparsınız zaten.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;“Yeni bir teknik buldum, mükemmel” diyenlerin bir kısmı&lt;/strong&gt; — Daha web sayfalarında ne Türkçe’yi ne de İngilizce’yi doğru düzgün ifade edemeyen kimseler ilginç iddialarla safsatalarını sunuyorlar. Kendi kitapları, yöntemleri vs. var. Sonuçta sizden yine bir ton para alıp karşılığında hüsran veriyorlar. (Aralarında muhakkak ki iyileri vardır ama bir kısmı maalesef böyle)&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Konuşma kılavuzları:&lt;/strong&gt;  Maksadınız İngilizce öğrenmekse hiç bulaşmayın. Sizin için yalnızca zaman kaybıdır. Ama seyahat için kullanacaksanız ve acil bir şeyler lazımsa elbette güzel bir çözümdür.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Dile Maruz Kalmak:&lt;/strong&gt;  Bu kavram dil öğrenimi açısından önemlidir. İlk tercih tabi ki öğrendiğiniz dilin konuşulduğu ülkeye gitmektir fakat böyle bir imkân yoksa çevrenizde bu ortamı yaratmanız gerekiyor. Bu, kullandığınız telefondan tutun da izlediğiniz filmlere, okuduğunuz kitaplara ya da dinlediğiniz şeylere kadar her şeyin mümkün olduğunda sizi dil konusunda sizi desteklemesi demektir.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Hikaye Kitapları:&lt;/strong&gt;  Seviyeniz A1 de olsa B2 de olsa İngilizce okuyun. Düşük seviyelerde olanlar için kitapçılarda “stage kitapları” olarak geçen kitapları almak çooook faydalıdır. Zorlansanız bile okumaya çabalarsanız ve bu okumaları da gelişiminizle orantılı olarak artırırsanız faydasını göreceksiniz. Bununla alakalı olarak Türk yayınevlerinden çıkan kitapları tavsiye etmiyorum. Sadeleştirilirken veya çevrilirken özenilmediği için içeriği yanıltıcı olabiliyor. Oxford Press gibi yayınlar da pahalı oluyor ama ikinci el kitapçılarda (Ankara’da Adilhan’da, İstanbul’da Akmar’da mesela) 3–4 TL’ye bulunuyor.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Dinleme ve Konuşma:&lt;/strong&gt;  Eğer yalnızca kitaptan çalışıyorsanız muhtemelen bu iki becerinizde problem vardır. Ama dili yalnızca okuyarak ve yazarak kullanmayacağınız için bu becerilerinizi de başlangıç seviyelerinden itibaren dile maruz kalma sürecine dahil ederek geliştirmeniz gerekmektedir. Çünkü telaffuzunuzda bir eksiklik varsa o dili tekrar öğreniyor gibi olursunuz. Öğrenecekseniz bir kere öğrenin.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Kelime Öğrenimi:&lt;/strong&gt;  Bununla alakalı son zamanlarda popüler olan birçok uygulama/site var. Deneme şansı bulduklarım arasında en beğendiğim memrise oldu. Ama arada bir aklınıza geldikçe bakıyorsanız çok faydalı bir seçenek değil. Şahsen ben bu programlarda devamlılık sağlayamadığım için kullanmadım. Kelime ile bildiğim birçok şeyi çeviriye borçluyum. Çeviri derken kastım kendi kendinize çeviri yapmanız. Okuduğunuz bir öyküyü, izlediğiniz programdan bir repliği, tabelaları, film afişlerini, aklınıza gelebilecek her şeyi çevirin. Çünkü bunları yapmak için ihtiyaç duyacağınız en önemli şey kelime. (Bunu kendi kendinize oynadığınız bir oyun gibi düşünebilirsiniz.)&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Mektup arkadaşı, Skype arkadaşı:&lt;/strong&gt;  Dile maruz kalma etmenlerinden biri olarak kabul edebiliriz bunu. Sandığınızdan daha iyi sonuçlar alabileceğiniz bir yöntemdir. Eskiden omegle gibi bir seçenek vardı bunun için ama artık amacından sapmış bir site konumunda. Bunun için önereceğim ilk site &lt;a href=&#34;https://howdoyou.do/&#34;&gt;https://howdoyou.do/&lt;/a&gt; Bunun dışında penpal gibi sitelerden de faydalanabilir, basit bir Google araştırmasıyla güzel siteler bulabilirsiniz.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Yazın:&lt;/strong&gt;  Akılda kalmaz satırda kalır sözünün doğruluğuna inananlardanım. Bu yüzden mutlaka defterleriniz olsun. Bu sadece not tutmakla sınırlı değil. Günlük, köşe yazarı gibi en az 200–300 kelime yazın. Bu, dil kullanımına aşina olmak için çok güzel bir yöntem.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Kelime Kartları:&lt;/strong&gt;  Kelime kartı hazırlamak çok basit ve etkilidir. Excel’den hazırlayacağınız bir tabloyu, karton kağıda çıktı almak bu işlem için yeterlidir. Diğer bir seçenek ise 16. maddede bahsettiğim web sitelerinden biri olan Quizlet.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Partner:&lt;/strong&gt;  İngilizce öğrenen bir arkadaşınızın olması ve İngilizce konusunda paslaşmanız ikiniz için de faydalı. İkinizin de hangi seviyede olduğunun önemi yok. Yalnızca ortak bir birikim oluşturmak ve biri bıraktığında diğerinin motive edebilmesi için.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Utangaç olmayın:&lt;/strong&gt;  Konuşurken İngilizler gibi “errr…” yaptığınızca veya ağzınızı açarak telaffuz etmeye çalıştığınızda komik olmuyorsunuz. Bu yüzden konuşmaktan ve doğru telaffuz etmekten korkmayın. İstanbul gibi bir şehirde yaşıyorsanız turistler bu konuda çok iyi bir avantajdır. Ama sakın gidip de hiçbir turiste “Hello! Sorry for my bad English. I’m learning English. I want to practice.” demeyin. Ya sizi umursamayacaktır ya da İngilizce’yi iyi bilmediğinizi bildiği için doğallıktan uzaklaşacaktır. Bunun yerine adres sorun, tişörtünün çok şık olduğunu falan söyleyin.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Sözlük:&lt;/strong&gt;  Türkçe sözlükleri mümkün olduğunda az kullanmaya çalışın. İngilizce-İngilizce sözlük kullanmak daha faydalı olur.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Dizi/Film izleyin:&lt;/strong&gt;  Altyazılı dizi/film izlemek dinleme yapmak açısından faydalıdır fakat izlediğiniz 5 sezon dizide karakterlerin hiç yüzünü görmediyseniz yanlış yapıyorsunuz demektir. Dizi izleyip dinlemeye çalışın, sadece okumayın. Aksi takdirde pek bir faydası olmuyor.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Telaffuz-Ağız Şekilleri:&lt;/strong&gt;  Telaffuz konusunda ilk tavsiyem şu: eğer native-like bir telaffuzu ve konuşmayı hedefliyorsanız yabancı dizileri ve filmleri izlerken konuşanların ağızlarına bakın. Zira İngilizce konuşurken ağzınızın şekli doğru değilse native-like bir konuşma elde edemezsiniz. Ağız şekillerinden kastım ise harfler ağızdan çıkarken ağzın aldığı şekiller. En bariz örneğini “e” harfinde görürsünüz zaten.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Telaffuz-Altyazı:&lt;/strong&gt;  Dizi ve filmleri internetten indirip İngilizce altyazıyı programla kendiniz ekleyin. Her programda altyazı senkronizesi vardır. Videonun üstünde sağ tıkladığınız zaman altyazı geciktirmesi veya altyazı senkronizesi olarak geçer. Altyazıyı -0.5 saniye yapın ve filmi izlerken altyazıyı sesli okuyun, hatta taklit edin. -0.5 saniyede okursanız sesle hemen hemen eş zamanlı bir seslendirme olacaktır. Bu sayede hatalarınızı daha o saniyede fark edeceksiniz. (Bu işlem için tavsiyem BSPlayer’dır. İzlediğiniz dizi/film ismini BSPlayer veritabanından ve diğer büyük altyazı sitelerinden arar ve otomatik olarak altyazılı açar. Size sadece Türkçe ve İngilizce seçimini yapmak düşer. Hatta ikincil bir altyazı açıp. Altyazı olarak İngilizce, üstyazı olarak Türkçe de yapabilirsiniz.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Telaffuz-Kendinizi dinleyin:&lt;/strong&gt;  Elinize herhangi bir makale, yazı vs. alın ve sesli okurken bunu kaydedin. Sonra kendiniz tekrar bu kaydı dinleyin. Bunu kendi kendinize yapmanızın manası ise şu: günümüzde oyunlar, diziler, filmler aracılığıyla hepimiz İngilizce duymaya aşinayız. Hemen hemen bütün kelimelerin okunuşu bilinçaltınızda var ve sıkıntı bunu pratiğe dökmekte. Bu nedenle kendi yaptığınız ve doğru olduğunu düşündüğünüz kaydı tekrar dinlediğinizde sahip olduğunuz kulak doygunluğu size hatalarınızı gösterecek.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;En yaygın kullanılan kelimeler:&lt;/strong&gt;  Okuduğunuz, dinlediğiniz İngilizce’yi anlamak için en çok ihtiyacınız olan şey kelimeler. Bu yüzden belirli seviyede İngilizce birikiminiz olmalı. Bence bunun için en önemi kaynak en çok kullanılan kelimelerdir. Bunun için internette hazır bulunan her kaynağı tavsiye etmiyorum. En çok kullanılan kelimeler dizi-film altyazılarından analiz edilmiş olmalıdır. Ancak böyle doğru sonuçlara ulaşabilir. Birçok dil için bu verilere bu &lt;a href=&#34;https://en.wiktionary.org/wiki/Wiktionary:Frequency%5Flists&#34;&gt;linkten&lt;/a&gt; ulaşabilirsiniz.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Kendim kullandığım ve faydalandığım sitelerden aklıma gelenleri de şöyle sıralıyorum:&lt;/strong&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://www.vocabulary.com/&#34;&gt;https://www.vocabulary.com/&lt;/a&gt; -&amp;gt; Sözlük ve kelime quizi için kullanılabilecek sitenin en önemli işlevi okuduğunuz parçaların kelimelerini sizin yerinize çıkarması. Metin verdiğinizde tüm kelimeleri çıkarıyor ve size bir liste veriyor. Sizin aralarından seçtiklerinizi bir liste olarak anlamlarıyla veriyor ve öğrendiğinizi test etmek için quize girebiliyorsunuz. (Ücretli android uygulaması da var.)&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.voscreen.com/&#34;&gt;https://www.voscreen.com/&lt;/a&gt; -&amp;gt; Bunu bir çoğunuz duymuştur muhtemelen. İlk çıktığında tesadüfen görmüştüm, üstüne sürekli bir şeyler katarak ilerleyen enfes bir site. Genellikle filmlerden/dizilerden kesitler sunuluyor ve anlamı soruluyor. Tabii bu kesitler çok kısa. Genellikle 1–2 cümlelik şeyler oluyor.&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.ted.com/&#34;&gt;https://www.ted.com/&lt;/a&gt; -&amp;gt; Burada yüzlerce konu hakkında, çoğu 50–60 farklı dilde altyazıya sahip, binlerce konuşma videosu var. Ücretsiz mp3 veya mp4 olarak indirme seçeneği ve konuşmanın her dilde yazılı hâlini indirme seçeneği de mevcut.&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.engvid.com/&#34;&gt;https://www.engvid.com/&lt;/a&gt; -&amp;gt;  Bu site belirli bir seviyeye gelmiş arkadaşlar için. İngilizce öğretmenleri İngilizce olarak birçok konuyu anlatıyor. Esprili dilleri konuları daha zevkli kılıyor. (James favorim)&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;http://lyricstraining.com/&#34;&gt;http://lyricstraining.com/&lt;/a&gt; -&amp;gt; Şarkı sözleri ile İngilizce.&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;http://www.ozdic.com/&#34;&gt;http://www.ozdic.com/&lt;/a&gt; -&amp;gt;  Merriam Webster ile kullandığım sözlük. Pek bilinmediği için buradan veriyorum. (Collocation dictionary)&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;http://fraze.it/&#34;&gt;http://fraze.it/&lt;/a&gt; -&amp;gt; Girdiğiniz kelimeyi cümle içinde kullanımlarıyla gösteriyor.&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.grammarly.com/&#34;&gt;https://www.grammarly.com/&lt;/a&gt; -&amp;gt; Yazdığınız cümlenin/metnin grammer incelemesini yapıyor ve size doğrusunu öneriyor. Başarılı bir proje.&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://quizlet.com/&#34;&gt;https://quizlet.com/&lt;/a&gt; -&amp;gt; Kelime kartları oluşturmak için kullanılan bir site. Girdiğiniz kelime kartlarına ses ekleme, mobil cihazlardan bu kartlara çalışma, pdf çıktısı alma, oyunlar kullanarak öğrenme veya word, excel gibi kaynaklardan kopyaladığınız 1000’lerce kelimeyi 5 saniyede ekleme gibi özellikleri var.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Youtube Kanalları&lt;/strong&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Speak English With Misterduncan&lt;/li&gt;
&lt;li&gt;Luke’s English Podcast&lt;/li&gt;
&lt;li&gt;English With Lucy&lt;/li&gt;
&lt;li&gt;Jade Joddle&lt;/li&gt;
&lt;li&gt;Go Natural English&lt;/li&gt;
&lt;li&gt;Simple English Videos&lt;/li&gt;
&lt;li&gt;podEnglish&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Podcastler:&lt;/strong&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;British Council&lt;/li&gt;
&lt;li&gt;Stuff They Don’t Want You to Know&lt;/li&gt;
&lt;li&gt;Serial&lt;/li&gt;
&lt;li&gt;Rationally Speaking&lt;/li&gt;
&lt;li&gt;Radiolab&lt;/li&gt;
&lt;li&gt;A History Of The World In 100 Object&lt;/li&gt;
&lt;li&gt;In Our Time&lt;/li&gt;
&lt;li&gt;Ted Radio Hour&lt;/li&gt;
&lt;li&gt;Answer Me This&lt;/li&gt;
&lt;li&gt;Spark&lt;/li&gt;
&lt;li&gt;Comedian’s Comedian&lt;/li&gt;
&lt;li&gt;Comedians Telling Stuff&lt;/li&gt;
&lt;li&gt;This American Life&lt;/li&gt;
&lt;li&gt;Stuff You Should Know&lt;/li&gt;
&lt;li&gt;Revisionist History&lt;/li&gt;
&lt;li&gt;Myths and Legends&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ol&gt;
</description>
        </item>
        
        <item>
            <title>Spring Framework | IoC Container</title>
            <link>http://kamer.dev/spring-framework-ioc-container/</link>
            <pubDate>Thu, 14 Jun 2018 11:40:12 +0000</pubDate>
            
            <guid>http://kamer.dev/spring-framework-ioc-container/</guid>
            <description>&lt;p&gt;IoC ve DI prensiplerini anlattığım bir önceki yazıda IoC’yi interface kullanarak kendimiz yapmayı anlatmıştım.Spring Framework’de ise bu prensip IoC containerlar ile sağlanır. IoC containerların temel görevi beanleri yönetmektir. Yönetmek kelimesinin kapsamı ise geniştir. Beanleri oluşturmak, birbirleriyle uyumunu sağlamak, ayarlarını yapılandırmak, yaşam döngülerini kontrol etmek gibi işler yönetmek kelimesinin kapsamına girer. Bu noktada “bean nedir?” sorusunun da cevabını vermem gerekiyor. Bean standartları belirlenmiş bir Java classıdır. Normal classtan üç farkı vardır:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;Tüm değişkenleri private olmak zorunda. (Getter/Setter kullanmanız gerekiyor.)&lt;/li&gt;
&lt;li&gt;Parametresiz bir public constructor’ı olmak zorunda.&lt;/li&gt;
&lt;li&gt;Serializable interface’ini implemente etmek zorunda.&lt;/li&gt;
&lt;/ol&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/ioc/diagram.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Yukarıdaki klasik bir IoC Container akış diyagramı var. Diyagram üzerinde çalışma akışı şöyledir:&lt;/p&gt;
&lt;p&gt;Container, hazırladığımız POJO classlarını alır. Sonra bu POJO classlarını yönetmek ve konfigüre etmek için xml dosyalarından, anotasyonlardan ve beanlere yönelik hazırlanmış kodlardan gerekli metadatayı alır. Artık elinde hem POJO’lar hem de bu POJO’ları nasıl yöneceğinin bilgisi vardır. Bunun sonucunda IoC, programda kullanıma hazır beanleri yaratır. Bu beanleri yaratırken de IoC prensibini sağlamak için bir önceki yazıda bahsettiğimiz DI prensibini kullanır. Gerekli bağımlılıkları framework tarafındaki aktör olarak kendisi verir.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/ioc/diagram2.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Spring container’ın ne işe yaradığını öğrendikten sonra irdelemeye devam edelim. İki tip Spring container vardır.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;BeanFactory Container&lt;/li&gt;
&lt;li&gt;ApplicationContextContainer&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;BeanFactory&lt;/strong&gt;
Spring Container’a DI desteği sağlayan en temel interface’tir. Beanleri oluşturmanın dışında konfigürasyonlarını yapar ve bağımlılıklarla birbirine bağlar. ApplicationContext’e göre biraz daha ilkel olduğu söylenebilir. Bu sebeple BeanFactory’i kısa kesip ApplicationContext’e geçiyorum.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;ApplicationContext&lt;/strong&gt;
ApplicationContext, BeanFactory’nin tüm özelliklerini barındıran ve bunun yanında ekstra yetenekleri olan container’dır. Bu sebeple BeanFactory’e oranla daha çok kullanılıyor. Spring’in kendi dokümanı da bu tercihi destekliyor. Eğer gerçekten kullanmak için iyi bir sebebiniz yoksa ApplicationContext kullanın şeklinde bir ifade geçiyor. Bu sebebe örnek olarak ise kilobayt seviyesinde performans hassasiyeti sağlamanız gereken projeleri örnek verebiliriz. Onun dışında ApplicationContext kullanmak ve sunduğu ekstra özelliklerden faydalanmak daha doğru bir yaklaşım. ApplicationContext’in sunduğu ekstra özellikler bu aşamada biraz daha üst seviye sayılabileceği için bunu konuyu daha sonraki yazılarımdan birine erteleyip ApplicationContext’in farklı kullanım şekillerinden bahsediyorum.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;FileSystemXmlApplicationContext&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Bu kullanımda ApplicationContext, bean tanımlarını bir xml dosyasından alır. XML dosyası &lt;strong&gt;tam dizin&lt;/strong&gt;i ile birlikte constructor’a verilir.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/ioc/filesystem.png&#34;/&gt;
&lt;/figure&gt;

&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;ClassPathXmlApplicationContext&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Bu kullanımda ise XML dosyasının tam dizinini vermeye gerek yoktur. XML dosyasının projenin  &lt;strong&gt;classpath&lt;/strong&gt;’inde olması yeterlidir.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/ioc/classpath.png&#34;/&gt;
&lt;/figure&gt;

&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;XmlWebApplicationContext&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Bu kullanımda ise tüm beanler web uygulamasının içinde tanımlanır.&lt;/p&gt;
&lt;p&gt;İnternette karşılaştığım diğer derslerde ApplicationContext tanımlarını anlatırken getBean() metodu ile beanlerin doğrudan xml konfigürasyonlarına göre elle oluşturulduğunu gördüm. Fakat bunun IoC’ye aykırı olduğunu düşündüğüm için öyle bir girişimde bulunmadım. Gözünüzün veya elinizin yanlış bir şeye alışmasındansa bu kısmın biraz daha soyut kalması daha doğru diye düşünüyorum. Tabii ki tercih ederseniz internette bu örnekleri bulabilirsiniz. Son olarak basit bir bean.xml dosyası göstereceğim.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/ioc/bean.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Yukarıda örnek bir SelamVer class’ı var. Bu classı bean olarak konfigüre etmek istiyorum. Aşağıdaki xml dosyası bunu sağlıyor.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/ioc/xml.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;En üstteki dört satır xml, versiyonunu, web-app versiyonunu seçtiğimiz ve kullanacağımız namespace’leri eklediğimiz kısım. Buralar genellikle sabit olur. Aşağıdaki kısımda ise id yazan yerde bean’in adını, class kısmında SelamVer classının yerini verdik. Property kısmında ise örnek olarak selam değişkeninin değerini verdik.&lt;/p&gt;
&lt;p&gt;Spring containerlar’la alakalı yazım bu kadar. Yazının başında da söylediğim gibi, anlattığım bu kavramların biraz soyut kalması gayet normal. En azından bir fikriniz olursa somut olarak bir şeyler yapmaya başladığınızda bu bilgilere ihtiyaç duyacaksınız.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Yararlandığım Kaynaklar:&lt;/strong&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://www.quora.com/Why-is-a-spring-container-known-as-an-IOC-container&#34;&gt;https://www.quora.com/Why-is-a-spring-container-known-as-an-IOC-container&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://docs.spring.io/spring/docs/3.0.x/spring-framework-reference/html/beans.html&#34;&gt;https://docs.spring.io/spring/docs/3.0.x/spring-framework-reference/html/beans.html&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;http://www.baeldung.com/inversion-control-and-dependency-injection-in-spring&#34;&gt;http://www.baeldung.com/inversion-control-and-dependency-injection-in-spring&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.quora.com/What-is-IOC-Container-in-Spring&#34;&gt;https://www.quora.com/What-is-IOC-Container-in-Spring&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://adnjavainterview.blogspot.com/2018/01/what-is-ioc-container-in-spring.html&#34;&gt;https://adnjavainterview.blogspot.com/2018/01/what-is-ioc-container-in-spring.html&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
</description>
        </item>
        
        <item>
            <title>Spring Framework | IoC ve DI</title>
            <link>http://kamer.dev/spring-framework-ioc-ve-di/</link>
            <pubDate>Mon, 11 Jun 2018 11:32:16 +0000</pubDate>
            
            <guid>http://kamer.dev/spring-framework-ioc-ve-di/</guid>
            <description>&lt;p&gt;Merhaba. Bu yazıda IoC ve DI olarak kısaltılan inversion of control ve dependency injection prensiplerinden ve bunların avantajlarından bahsedeceğim. Bu yazıyı ve Spring ile alakalı diğer yazıları yazarken kullanacağım birincil kaynak spring.io adresinden ulaşabileceğiniz gayet açıklayıcı hazırlanmış dokümantasyon olacaktır. Diğer kullandığım kaynaklar ise yazıların sonlarında istisnasız belirtilecektir.&lt;/p&gt;
&lt;h2 id=&#34;ioc--inversion-of-control--ve-di--dependency-injection&#34;&gt;IoC (Inversion of Control) ve DI (Dependency Injection)&lt;/h2&gt;
&lt;p&gt;Öncelikle bu kelimelerin sözlük anlamlarını irdeleyelim. Inversion of Control prensibi, kontrolün tersine dönmesi şeklinde ifade edilebilir. Dependency injection ise bağımlılıkları enjekte etmek demektir. Peki bu iki garip kelime grubu bize yazılım geliştirirken nasıl bir fayda sağlıyor?&lt;/p&gt;
&lt;p&gt;Bu prensipleri ve kelime manalarını bir kenara bırakıp kendi tecrübelerinizle düşünün. Bir yazılım geliştirirken programın kontrolü kimdedir? Mesela veritabanı bağlantıları, kullandığınız JDK sürümü, veritabanı bağlantısı açmak için kullandığınız driverlar… Genellikle bir XML dosyası kullanarak veya başka yöntemler kullanarak akışa etki edecek tüm parametreleri belirler ve o şekilde çalıştırırız. Daha farklı bir ifadeyle lineer bir program akışı hazırlarız. Hatta tüm bunlar bir yana String tipinde nesne oluşturma kontrolü bile sizdedir.  &lt;b&gt;IoC prensibi&lt;/b&gt;nin hedeflediği şey ise bundan biraz daha farklıdır. Bu akışın doğrudan programcıdan alınıp başka aktörlere devredilmesini amaçlar. Bu aktörler bir framework, servis veya başka herhangi bir bileşen olabilir. Ama temelinde hepsi program akışının lineer olmaması amacını güder. Peki kontrolü devrettiğimizde bunun bize nasıl bir faydası var? Bu prensip, yazılımda ‘loose-coupling’ olarak geçen başka bir prensibi başarmamızı sağlar.  &lt;strong&gt;Loose-coupling&lt;/strong&gt; Türkçe’de “gevşek bağlaşım” olarak karşılaştığım bir terim. Bir nesne yaratırken yaratılan bu nesnenin class’lara veya diğer başka bileşenlere olan bağımlılığının en aza indirilmesi prensibidir. Böylece daha esnek bir kod yazma imkânı elde edilir ve modülerlik sağlanır.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Dependency Injection&lt;/strong&gt; kavramı ise birçok yerde IoC ile eş anlamlı olarak geçse de kapsam bakımından IoC’den daha dardır. IoC’yi uygulamanın birçok yolu vardır, DI ise bunlardan biridir.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/ioc-di/diagram.jpeg&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;DI yaklaşımında ise temel prensip kodumuzda birbirine bağımlı olan bileşenleri tespit edip, bu bağımlılıkları birbirinden ayırıp bağımsız hale getirmek ve bağımlılıklarını dışarıdan enjekte etmektir. Şimdi yukarıda örnekler vererek anlattığım şeyi bir paragrafta kısaca toparlayayım.&lt;/p&gt;
&lt;p&gt;Yazılım geliştirme süreçlerinde modülerliği sağlamak için birçok prensip kullanırız. IoC bunlardan biridir. Kontrolü kodu yazan kişiden alıp başka bir aktöre (mesela framework) teslim etmek demektir. Biz kontrolü teslim ettiğimizde loose-coupling sağlarız. Yani bir nesneyi yaratırken bağımlılıklarını minimuma indirmeyi ve bu bağımlılıklarını da gevşek bağlı yapmaya çalışırız. Peki bu prensipleri uygulamak için ne yaparız sorusunun cevaplarından biri ise dependency injection. Yani bağımlılıkları tespit edip ayırmak ve bu bağlılıkları dışarıdan enjekte etmek. Gördüğünüz üzere birbiriyle iç içe geçmiş üç ayrı kavramdır ve kapsamlarını iyi bilmek gerekir. Şimdi bu soyut tanımları biraz daha somulaştıralım.&lt;/p&gt;
&lt;p&gt;IHayvan adında bir interface’imiz olsun. Bu interface yalnızca hayvan sesi çıkarmak için kullanılan sesCikar() metodunun imzasını barındırsın.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;interface&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;IHayvan&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;sesCikar&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Köpek ve Kedi hayvanlarına ait iki tane de class tanımlayalım.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;Kopek&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;implements&lt;/span&gt; IHayvan &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;sesCikar&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;println&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Hav hav hav&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;Kedi&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;implements&lt;/span&gt; IHayvan &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

    &lt;span style=&#34;color:#a2f&#34;&gt;@Override&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;sesCikar&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	System&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;out&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;println&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;&amp;#34;Miyavv&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;);&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Hayvan seslerini kullanmak için de bir tane servis tanımlayalım.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;HayvanService&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; Kopek hayvan1 &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; Kopek&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;HayvanService&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	hayvan1&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;sesCikar&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Yukarıda görmüş olduğunuz tasarımda Kopek class’ına ait olan hayvan1 nesnesi tight coupled olarak tanımlanmış. Yani hayvan1 nesnesinin kedi olmasını istesek doğrudan kodda değişiklik yapmamız gerekecek. Bu bize esnek bir yazılım ortamı sunmuyor. Şimdi bu servisi DI ile loose-coupled yapalım.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;class&lt;/span&gt; &lt;span style=&#34;color:#00f&#34;&gt;HayvanService&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
    IHayvan hayvan1&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

    &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;public&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;HayvanService&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;(&lt;/span&gt;IHayvan hayvan1&lt;span style=&#34;color:#666&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;
	&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;this&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;hayvan1&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; hayvan1&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;
	hayvan1&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;sesCikar&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
    &lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Değişikliği, yaptığımız DI tanımıyla şöyle açıklayabiliriz. İlk serviste hayvan1 nesnesi Kopek class’ına bağımlıydı. sesCikar() metodunun çağırılması için bu nesnenin Kopek classının sesCikar() metodunu bilmesi gerekiyordu. İkinci örnekte ise bu bağımlılığı tespit edip kaldırdık. Yerine iki classı da kapsayacak olan “private IHayvan hayvan1” tanımlaması yaptık. Dolayısıyla şimdi istersek Kedi, istersek de Kopek classını gönderip sesCikar() metodunu çağırabiliriz.&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre style=&#34;background-color:#f8f8f8;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-java&#34; data-lang=&#34;java&#34;&gt;&lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;private&lt;/span&gt; &lt;span style=&#34;color:#0b0;font-weight:bold&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#00a000&#34;&gt;testiGerceklestir&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#666&#34;&gt;{&lt;/span&gt;

	&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;// Bir hayvan tanımladık ama
&lt;/span&gt;&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;&lt;/span&gt;	&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;//ne olduğunu seçmedik.
&lt;/span&gt;&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;&lt;/span&gt;	IHayvan hayvan1&lt;span style=&#34;color:#666&#34;&gt;;&lt;/span&gt;

	&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;// Hayvanı burada kedi olarak seçtim.
&lt;/span&gt;&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;&lt;/span&gt;	hayvan1 &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; Kedi&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
	hayvan1&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;sesCikar&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;

	&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;// Burada ise köpek.
&lt;/span&gt;&lt;span style=&#34;color:#080;font-style:italic&#34;&gt;&lt;/span&gt;	hayvan1 &lt;span style=&#34;color:#666&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#a2f;font-weight:bold&#34;&gt;new&lt;/span&gt; Kopek&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;
	hayvan1&lt;span style=&#34;color:#666&#34;&gt;.&lt;/span&gt;&lt;span style=&#34;color:#b44&#34;&gt;sesCikar&lt;/span&gt;&lt;span style=&#34;color:#666&#34;&gt;();&lt;/span&gt;

&lt;span style=&#34;color:#666&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Bu kodun çıktısı aşağıdaki gibi olacaktır:&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/ioc-di/output.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;&lt;strong&gt;Kodların GitHub linki:&lt;/strong&gt; &lt;a href=&#34;https://github.com/kamer/IoCveDI&#34;&gt;https://github.com/kamer/IoCveDI&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Yararlandığım Kaynaklar&lt;/strong&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://stackoverflow.com/questions/226977/what-is-loose-coupling-please-provide-examples#227334&#34;&gt;https://stackoverflow.com/questions/226977/what-is-loose-coupling-please-provide-examples#227334&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://dzone.com/tutorials/java/spring/spring-ioc-1.html&#34;&gt;https://dzone.com/tutorials/java/spring/spring-ioc-1.html&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://docs.spring.io/spring/docs/3.2.x/spring-framework-reference/html/beans.html#beans-factory-collaborators&#34;&gt;https://docs.spring.io/spring/docs/3.2.x/spring-framework-reference/html/beans.html#beans-factory-collaborators&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Bu yazı ilk olarak &lt;a href=&#34;https://medium.com/topluluk/spring-framework-1-ioc-ve-di-3e2da31bc0e5&#34;&gt;https://medium.com/topluluk/spring-framework-1-ioc-ve-di-3e2da31bc0e5&lt;/a&gt; adresinde yayınlanmıştır.&lt;/p&gt;
</description>
        </item>
        
        <item>
            <title>Apache JMeter ile REST API Testi</title>
            <link>http://kamer.dev/apache-jmeter-ile-rest-api-testi/</link>
            <pubDate>Sun, 10 Jun 2018 22:07:38 +0000</pubDate>
            
            <guid>http://kamer.dev/apache-jmeter-ile-rest-api-testi/</guid>
            <description>&lt;p&gt;Bu yazımda Apache JMeter kullanarak basit bir REST API testinin nasıl yapıldığını anlatacağım.&lt;/p&gt;
&lt;h2 id=&#34;gereklilikler&#34;&gt;Gereklilikler&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;HTTP methodları hakkında bilgi sahibi olmak.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;1-dot-kurulum&#34;&gt;1. Kurulum&lt;/h2&gt;
&lt;p&gt;JMeter’ı indirmek için &lt;a href=&#34;http://ftp.itu.edu.tr/Mirror/Apache//jmeter/&#34;&gt;http://ftp.itu.edu.tr/Mirror/Apache//jmeter/&lt;/a&gt; bağlantısına gidin. İndirdikten sonra arşivden çıkarın. Karşınıza şöyle bir klasör yapısı çıkacak.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/apache-jmeter-ile-rest-api-testi/folder.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;/bin dizinine giderek “ApacheJMeter.jar” veya “jmeter.bat” dosyalarından birini çalıştırarak programı açıyoruz.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/apache-jmeter-ile-rest-api-testi/jmeter-overall.png&#34;/&gt;
&lt;/figure&gt;

&lt;h2 id=&#34;2-dot-http-i̇steği-göndermek&#34;&gt;2. HTTP İsteği Göndermek&lt;/h2&gt;
&lt;p&gt;Programı açtıktan sonra ekran görüntüsünde olduğu gibi Test Plan’e sağ tıklayıp Add -&amp;gt; Thread (Users) -&amp;gt; Thread Group seçeneğine tıklayın. İsteğe bağlı olarak isim verebilirsiniz. Ben bu şekilde devam ediyorum.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/apache-jmeter-ile-rest-api-testi/jmeter1.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Yapacağımız istek Thread Group üzerinde çalışacağı için Thread Group’a sağ tıklayıp Add -&amp;gt; Sampler -&amp;gt; HTTP Request seçeneğine tıklayın.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/apache-jmeter-ile-rest-api-testi/jmeter2.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Ben bu anlatımı test için &lt;a href=&#34;https://jsonplaceholder.typicode.com/comments?postId=1&#34;&gt;https://jsonplaceholder.typicode.com/comments?postId=1&lt;/a&gt; üzerinden yapacağım.&lt;/p&gt;
&lt;p&gt;Aşağıdaki ekran görüntüsündeki formu şu şekilde dolduruyorsunuz.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Procol&lt;/strong&gt;: Örneğimizde https. &lt;br /&gt;
&lt;strong&gt;Server Name or IP:&lt;/strong&gt;  jsonplaceholder.typicode.com &lt;br /&gt;
&lt;strong&gt;Path:&lt;/strong&gt;  Server Name veya IP’den itibaren soru işaretine kadar olan kısım. (/comments) &lt;br /&gt;
&lt;strong&gt;Method:&lt;/strong&gt; Kullanacağınız HTTP metodu. &lt;br /&gt;
&lt;strong&gt;Send Parameters With The Request:&lt;/strong&gt;  Örneğimizde parametre de göndereceğimiz için burayı da kullanıyoruz. Parametre ise soru işaretinden sonraki kısım, yani “postId=1”.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/apache-jmeter-ile-rest-api-testi/jmeter3.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Son olarak listener ekleyip yaptığımız isteği dinliyoruz. HTTP Request’e sağ tıklayın. Add -&amp;gt; Listener -&amp;gt; View Result Tree seçeneği ile listener’ı oluşturun.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/apache-jmeter-ile-rest-api-testi/jmeter4.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Buraya kadar geldikten sonra ilk testimizi yapalım. Yukarıdaki Start butonuna basarak isteği gönderiyoruz.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/apache-jmeter-ile-rest-api-testi/jmeter5.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;Test planını daha sonra kullanmak üzere kaydetmek isteyip istemediğimizi soruyor. Yes diyerek devam ediyorum.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/apache-jmeter-ile-rest-api-testi/jmeter6.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;1 numaralı sekmedeki yeşil onay işareti başarılı bir istek atıp cevap aldığınız gösteriyor. &lt;br /&gt;
2 numaralı sekmede gönderilen/alınan veri boyutu, bağlantı süresi gibi sonuçlar, &lt;br /&gt;
3 numaralı sekmede gönderdiğiniz isteğe dair ayrıntılar, &lt;br /&gt;
4 numaralı sekmede size gelen cevap yer alıyor.&lt;/p&gt;
&lt;h2 id=&#34;3-dot-toplu-i̇stek-gönderme&#34;&gt;3. Toplu İstek Gönderme&lt;/h2&gt;
&lt;p&gt;Kullandığınız API’nın ne kadar isteğe cevap verebileceğini test etmek isteyebilirsiniz. Bu durumda ise Loop Controller kullanıyorsunuz. Thread Group’a sağ tıklayıp Add -&amp;gt; Logic Controller -&amp;gt; Loop Controller seçeği ile controller oluşturup HTTP Requesti sürükleyip controllerın içine koyuyorsunuz. Eğer bu isteklerin belirli bir gecikmeyle yapılmasını istiyorsanız da Controller’a sağ tıklayıp Add -&amp;gt; Timer -&amp;gt; Constant Timer seçeneğini kullanıyorsunuz. Oraya gecikme süresini ms cinsinde yazdıktan sonra yaptığınız istekler timerda yazan değer kadar gecikmeli olarak loop içinde yazan değer kadar yapılır. Eğer baştan itibaren yazıyı takip ettiyseniz nihai test plan yapısı aşağıdaki şekilde oluyor.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/apache-jmeter-ile-rest-api-testi/jmeter7.png&#34;/&gt;
&lt;/figure&gt;

&lt;h2 id=&#34;4-dot-xml-csv-sonuç-alma&#34;&gt;4. XML/CSV Sonuç Alma&lt;/h2&gt;
&lt;p&gt;Yaptığınız isteklere dair sonuç dokümanı almak için View Result Tree içinde bulunan “Write results to file /Read from the file” yazısının altında bulunan yere kaydetmek istediğiniz yolu ve dosya adını giriyorsunuz. Sağ tarafta bulunan configure seçeneğine tıklayarak doküman içeriğinde neler olmasını istediğinizi yazıyorsunuz. Sonra siz thread’e start dediğinizde dokümanı oluşturup belirlediğiniz yere kaydediyor.&lt;/p&gt;
&lt;figure&gt;&lt;img src=&#34;http://kamer.dev/images/posts/apache-jmeter-ile-rest-api-testi/jmeter8.png&#34;/&gt;
&lt;/figure&gt;

&lt;p&gt;JMeter programının kullanımı bu şekilde. Daha birçok özelliği ve test/sonuç şekilleri var fakat en genel kullanım alanı bu şekilde olduğu için yazıyı burada bitiriyorum. Eğer talep olursa biraz daha ayrıntıya indiğim bir yazı daha yazabilirim. Sorularınızı, katkılarınızı ve eleştirilerinizi bekliyorum.&lt;/p&gt;
&lt;p&gt;Bu yazı ilk olarak &lt;a href=&#34;https://medium.com/topluluk/apache-jmeter-i%CC%87le-rest-api-testi-617d9d377ad8&#34;&gt;https://medium.com/topluluk/apache-jmeter-i%CC%87le-rest-api-testi-617d9d377ad8&lt;/a&gt; adresinde yayınlanmıştır.&lt;/p&gt;
</description>
        </item>
        
    </channel>
</rss>