<?xml version="1.0" encoding="UTF-8"?><rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:atom="http://www.w3.org/2005/Atom" version="2.0" xmlns:cc="http://cyber.law.harvard.edu/rss/creativeCommonsRssModule.html">
    <channel>
        <title><![CDATA[Stories by Eymen Eruyar on Medium]]></title>
        <description><![CDATA[Stories by Eymen Eruyar on Medium]]></description>
        <link>https://medium.com/@eruyareymen?source=rss-44db768b0377------2</link>
        <image>
            <url>https://cdn-images-1.medium.com/fit/c/150/150/0*xHZozIQnLJ1if3t1</url>
            <title>Stories by Eymen Eruyar on Medium</title>
            <link>https://medium.com/@eruyareymen?source=rss-44db768b0377------2</link>
        </image>
        <generator>Medium</generator>
        <lastBuildDate>Sun, 24 May 2026 03:44:07 GMT</lastBuildDate>
        <atom:link href="https://medium.com/@eruyareymen/feed" rel="self" type="application/rss+xml"/>
        <webMaster><![CDATA[yourfriends@medium.com]]></webMaster>
        <atom:link href="http://medium.superfeedr.com" rel="hub"/>
        <item>
            <title><![CDATA[What is the Inversion of Control (IoC) and Dependency Injection (DI) ?]]></title>
            <link>https://medium.com/@eruyareymen/what-is-the-inversion-of-control-ioc-and-dependency-injection-di-61280379c93f?source=rss-44db768b0377------2</link>
            <guid isPermaLink="false">https://medium.com/p/61280379c93f</guid>
            <category><![CDATA[spring]]></category>
            <category><![CDATA[java]]></category>
            <category><![CDATA[dependency-injection]]></category>
            <category><![CDATA[inversion-of-control]]></category>
            <dc:creator><![CDATA[Eymen Eruyar]]></dc:creator>
            <pubDate>Sun, 05 Mar 2023 14:56:58 GMT</pubDate>
            <atom:updated>2023-03-05T14:56:58.917Z</atom:updated>
            <content:encoded><![CDATA[<h3><strong>What is the Inversion of Control (IoC) and Dependency Injection (DI) ?</strong></h3><h3><strong>Inversion of Control (IoC)</strong></h3><p>Inversion of Control (IoC) is not a design pattern, is a software principle. The main purpose of IoC is to minimize dependencies and manage object instances. IoC often uses with dependency injection. However, dependency injection is just an implementation of IoC. One of the best examples of using IoC is Spring Framework.</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/968/1*GtkzBnxXOc5zAPuntz8jiw.png" /></figure><p>There are 2 IoC containers in Spring Framework, BeanFactory, and ApplicationContext. These container structures manage the components that make up the application using the dependency injection principle. Objects get about information such as XML, Java Code, and Java Annotation. It also provides convenience to the developer by adjusting the lifecycles of the objects themselves.</p><h3>Dependency Injection (DI)</h3><p>Dependency injection is a programming principle that allows an object to receive its dependencies (objects it needs to function) from an external source, rather than creating them itself. It realizes this transaction by decoupling the usage of an object from its creation. Thus, it will carry out dependency inversion and single responsibility from SOLID principles. As everyone knows, SOLID principles increase the reusability of our code, and its aim is to decrease what you need to change in a class. Dependency injection supports these goals by separating the usage and creation of an object. Please note that the creation of an object is more costly than the usage of that object.</p><p>The dependency injection principle is an alternative to the service locator pattern. Most popular frameworks implement dependency injection in their structure. So that, we can focus to be done business logic instead of the technical infrastructure. Some frameworks that use the dependency injection principle are as follows.</p><p>1. Spring Framework: Spring is a popular Java-based framework that provides comprehensive infrastructure support for building enterprise applications. It provides a built-in dependency injection mechanism.</p><p>2. Google Guice: Guice is a lightweight dependency injection framework for Java.</p><p>3. Dagger: Dagger is a dependency injection framework for Android and Java.</p><p>4. PicoContainer: PicoContainer is a lightweight Java-based dependency injection container.</p><p>5. AngularJS: AngularJS is a JavaScript-based framework for building web applications. It uses dependency injection to make components and services available to other components in the application.</p><p>6. React-Redux: React-Redux is a popular JavaScript library for building user interfaces with the React JavaScript library. It uses dependency injection to provide the store to the React components.</p><p>These are just a few examples of frameworks that use dependency injection. There are many other frameworks and libraries that use dependency injection in different programming languages.</p><p>Let’s do an example together now. Let’s say we have a class called DesktopComputerService that has a start method. It is defined as follows.</p><pre>public class DesktopComputerService {<br><br>    public void start(String computerAccountName){<br>        System.out.println(&quot;Welcome to &quot; + computerAccountName);<br>    }<br><br>}</pre><p>This class shows a message when we turn on the computer. Our application code will be like below.</p><pre>public class MyComputer {<br><br>    Laptop laptop;<br>    public MyComputer(Laptop laptop) {<br>        this.laptop = laptop;<br>    }<br><br>    public void startComputer(String accountName){<br>        laptop.start(accountName);<br>    }<br><br>}</pre><p>Our client code that will use MyComputer class to start computer will be like below.</p><pre>public static void main(String[] args) {<br>        MyComputer computer = new MyComputer();<br>        computer.startComputer(&quot;Alex Donnie&quot;);<br>}</pre><p>Although everything seems normal in the code at first glance, some restrictions and difficulties will arise as the code grows.</p><p>· As is seen in the code, MyComputer class depends on DesktopComputerService class. This means that any future changes you make to the DesktopComputerService class will affect the MyComputer class.</p><p>· If we want to add new computer types as Laptop, Gaming, we will have to write other application for these.</p><p>· On the other hand, testing this application is very difficult because there is no way to mock it in the test class.</p><p>We have talked about what kind of difficulties we will encounter when we write a program without dependency injection. Let’s recode and expand the application using the dependency injection principle.</p><p>Firstly, we should use interfaces to use effectively classes and methods. By defining an interface called ComputerService, we include common methods for computer types.</p><pre>public interface ComputerService {<br><br>    void start(String accountName);<br><br>    void logOut(String accountName);<br><br>}</pre><p>Thus we can use the Laptop class as an implementation of ComputerService.</p><pre>public class Laptop implements ComputerService{<br><br>    @Override<br>    public void start(String accountName) {<br>        System.out.println(&quot;Welcome to &quot; + accountName);<br>    }<br><br>    @Override<br>    public void logOut(String accountName) {<br>        System.out.println(&quot;Logging out &quot; + accountName);<br>    }<br><br>}</pre><p>Finally, we create a class ourselves that is named “MyComputer”. We want to create an object from the Laptop class and use the class properties. We create an object from the Laptop class using dependency injection. There are three ways to implement dependency injection:</p><p>1. Constructor Injection</p><p>2. Setter Injection</p><p>3. Interface Injection</p><p>In summary, using dependency injection we created and managed objects. Many frameworks as Spring, manage self the dependency injection process. See you in another article. Stay with Java.</p><h4>References</h4><p><a href="https://martinfowler.com/articles/injection.html#InterfaceInjection">Inversion of Control Containers and the Dependency Injection pattern</a></p><p><a href="https://www.digitalocean.com/community/tutorials/java-dependency-injection-design-pattern-example-tutorial">https://www.digitalocean.com/community/tutorials/java-dependency-injection-design-pattern-example-tutorial</a></p><img src="https://medium.com/_/stat?event=post.clientViewed&referrerSource=full_rss&postId=61280379c93f" width="1" height="1" alt="">]]></content:encoded>
        </item>
        <item>
            <title><![CDATA[Spring Batch Nedir?]]></title>
            <link>https://medium.com/@eruyareymen/spring-batch-nedir-6a313fef2c4c?source=rss-44db768b0377------2</link>
            <guid isPermaLink="false">https://medium.com/p/6a313fef2c4c</guid>
            <category><![CDATA[spring-batch]]></category>
            <category><![CDATA[java]]></category>
            <category><![CDATA[spring-framework]]></category>
            <category><![CDATA[spring-boot]]></category>
            <category><![CDATA[batch-processing]]></category>
            <dc:creator><![CDATA[Eymen Eruyar]]></dc:creator>
            <pubDate>Sat, 10 Dec 2022 22:07:11 GMT</pubDate>
            <atom:updated>2022-12-10T22:07:11.672Z</atom:updated>
            <content:encoded><![CDATA[<p>Programlamanın derinliklerine indikçe her gün yepyeni kavramlarla karşılaşıyoruz. İleri seviyelerde karşılaştığımız en sık kavramlardan birisi ise “Batch”. Peki batch dediğimiz şey tam olarak nedir ve ne işe yarar? En basit tanımıyla batch; herhangi bir kullanıcı müdahelesi olmadan, belirlenen zaman dilimlerinde çalışan programlardır. Örneğin, her gün binlerce verinin geldiğini ve gelen verilerin bir veri tabanında tutulduğunu düşünelim. Gün geçtikçe veri tabanı dolacak ve bir süre sonra işlem hızımız yavaşlayacaktır. Bu olayı engellemek için arşiv veri tabanı yapabilir ve düzenli olarak verileri taşıyabiliriz. Tam bu noktada batch yapısı hayatımızı kurtaracaktır. Yazacağımız batch’ler belirlediğimiz saatlerde çalışarak otomatik yedekleme yapacak ve böylece asıl veri tabanımız daha hızlı çalışacaktır.</p><p>Spring batch, güçlü batch uygulamaları geliştirmek için tasarlanan açık kaynak bir araçtır. Spring batch sayesinde geniş hacimli verilerin işlenmesi, kayıtların takibi (logging/tracking), yapılan işlerin istatistikleri (job processing statistics), kaynak yönetimi (resource management) gibi konularda büyük kolaylıklar sağlar.</p><figure><img alt="" src="https://cdn-images-1.medium.com/max/583/1*Cvfop3dDHn5P6tCBoBuYUw.png" /><figcaption>Spring Batch Workflow</figcaption></figure><p>Yukarıdaki şemada spring batch yapısının genel işleyişini basit şekilde görebiliriz. <strong>Reader, </strong>verileri bir veri tabanından, dosyadan ya da kuyruktan okur. Okunan veriler <strong>processor </strong>yapısına iletilerek işlenir. <strong>Writer </strong>adımında ise işlenen veriler veri tabanına ya da dosyaya yazılarak süreç tamamlanmış olur. Bütün bu sürece (Reader -&gt; Processor -&gt; Writer) <strong>step </strong>denir. Oluşturulan bu step’ler ise <strong>Job </strong>dediğimiz yapılarla çalışır. Bir job birden fazla step çalıştırabileceği gibi bir programda birden fazla job da olabilir. Gelin şimdi hep beraber spring batch’in mimarisine bakalım.</p><h3><strong>Spring Batch Architecture</strong></h3><figure><img alt="" src="https://cdn-images-1.medium.com/max/444/1*gaScMMxUSY1uNYhys-cMWg.png" /><figcaption>Spring Batch Layered Architecture</figcaption></figure><p>Spring batch’in katmanlı mimarisi 3 önemli komponentten oluşmaktadır.</p><p><strong>Application </strong>katmanı, geliştiriciler tarafından yazılan bütün job’ları ve özel kodları içerir.</p><p><strong>Batch core </strong>katmanı, job’ları başlatmak ve kontrol etmek için gerekli olan ana sınıfları içerir. Ayrıca JobLauncher, Job ve Step gibi adımların implemetasyonları yapılır.</p><p><strong>Batch infrastructure </strong>katmanı, hem geliştiriciler<strong> </strong>(ItemReader ve ItemWriter) hem de framework tarafından kullanılan (RetryTemplate) reader ve writer methodları içerir.</p><h3><strong>Spring Batch Example</strong></h3><p>Spring hakkında genel bir fikir edindik, şimdi adım adım bir batch uygulaması yazalım. Bu örnek kapsamında haber raporlarını içeren veri seti kullandım. Excel formatında ki bu veri setini okuyarak tablolara yazacağız.</p><p>İlk olarak gerekli dependency’lerimiz pom.xml dosyamıza ekleyerek başlıyoruz. Proje kapsamında postgresql ve spring data jpa kullanacağız. Farklı bir veri tabanı ile çalışmak isterseniz maven repository’den <strong>(</strong><a href="https://mvnrepository.com/"><strong>https://mvnrepository.com/</strong></a><strong>)</strong> gerekli dependency’leri indirebilirsiniz.</p><pre>        &lt;dependency&gt;<br>            &lt;groupId&gt;org.springframework.boot&lt;/groupId&gt;<br>            &lt;artifactId&gt;spring-boot-starter-batch&lt;/artifactId&gt;<br>        &lt;/dependency&gt;<br>        &lt;dependency&gt;<br>            &lt;groupId&gt;org.springframework.boot&lt;/groupId&gt;<br>            &lt;artifactId&gt;spring-boot-starter-data-jpa&lt;/artifactId&gt;<br>        &lt;/dependency&gt;<br>        &lt;dependency&gt;<br>            &lt;groupId&gt;org.postgresql&lt;/groupId&gt;<br>            &lt;artifactId&gt;postgresql&lt;/artifactId&gt;<br>            &lt;scope&gt;runtime&lt;/scope&gt;<br>        &lt;/dependency&gt;<br>        &lt;dependency&gt;<br>            &lt;groupId&gt;org.projectlombok&lt;/groupId&gt;<br>            &lt;artifactId&gt;lombok&lt;/artifactId&gt;<br>            &lt;optional&gt;true&lt;/optional&gt;<br>        &lt;/dependency&gt;<br>        &lt;dependency&gt;<br>            &lt;groupId&gt;org.slf4j&lt;/groupId&gt;<br>            &lt;artifactId&gt;slf4j-api&lt;/artifactId&gt;<br>            &lt;version&gt;1.7.36&lt;/version&gt;<br>        &lt;/dependency&gt;</pre><p>application.properties dosyasında veri tabanı bağlantı ayarlarımızı ve batch’e ait bazı konfigürasyonları yapıyoruz. Eğer program ayağa kalkar kalkmaz batch’in çalışmasını istemiyorsak <strong>spring.batch.job.enabled </strong>özelliğini <strong>false </strong>olarak güncellemeliyiz.</p><pre><br>spring.datasource.driver-class-name=org.postgresql.Driver<br>spring.datasource.url=jdbc:postgresql://localhost:5432/demoBatch<br>spring.datasource.username=postgres<br>spring.datasource.password=postgres<br><br>spring.jpa.hibernate.ddl-auto=update<br>spring.batch.jdbc.initialize-schema=always<br>spring.jpa.show-sql=true<br><br><br>#disabled job run at startup<br>spring.batch.job.enabled=false<br>spring.main.allow-bean-definition-overriding=true</pre><p><strong>Entity ve Repository</strong></p><p>Csv dosyasından okunacak olan verileri NewsReport entity sınıfı temsil etmektedir. Haberler gerçekliğe göre ayrılırken ise RealNews ve FakeNews sınıfları kullanılmıştır. Her entity sınıfına ait repository interface’leri bulunmaktadır. Benzer yapıda oldukları için aşağıda sadece RealNews ve RealNewsRepository kodlarına yer verilmiştir.</p><pre>@Data<br>@Entity<br>@Table(name = &quot;REAL_NEWS&quot;)<br>public class RealNews {<br><br>    @Id<br>    @GeneratedValue<br>    private Long id;<br><br>    @Column(columnDefinition = &quot;text&quot;, name = &quot;TITLE&quot;)<br>    private String title;<br><br>    @Column(columnDefinition = &quot;text&quot;, name = &quot;NEWS_URL&quot;)<br>    private String url;<br><br>    @Column(name = &quot;SOURCE_DOMAIN&quot;)<br>    private String sourceDomain;<br><br>    @Column(name = &quot;TWEET_NUM&quot;)<br>    private int tweetNum;<br><br>}</pre><p>Program için ön hazırlığımızı yaptığımıza göre artık batch kısmına girebiliriz. Yukarıda da bahsettiğim gibi veriler bir dosya, veri tabanı ya da kuyruktan okunabilir. Bu dosya üzerinden ve veri tabanından veri okuyacağız.</p><pre>public interface RealNewsRepository extends JpaRepository&lt;RealNews,Long&gt; {<br>}</pre><p><strong>Reader</strong></p><p>İlk aşamada .csv formatta bir dosyadan veri okuyacağımız için <strong>FlatFileItemReaderBuilder </strong>kullandık. FlatFileItemReaderBuilder’ın ayrıntıları için dökümana (<a href="https://docs.spring.io/spring-batch/docs/current/api/org/springframework/batch/item/file/builder/FlatFileItemReaderBuilder.html">https://docs.spring.io/spring-batch/docs/current/api/org/springframework/batch/item/file/builder/FlatFileItemReaderBuilder.html</a>) bakabilirsiniz. Burada ki önemli nokta dosyadan okunan verilerin oluşturmuş olduğumuz entity sınıfı ile eşleşebilmesidir. Bunun için csv dosyasında bulunan kolon isimleri ile entity sınıfında yapılan tanımlar aynı olmalıdır.</p><pre>@Bean(name = &quot;readerNewsReportCSVFile&quot;)<br>public ItemReader&lt;NewsReport&gt; readerNewsReportCSVFile(){<br>    return new FlatFileItemReaderBuilder&lt;NewsReport&gt;()<br>         .name(&quot;readerNewsReportCSVFile&quot;)<br>         .resource(new FileSystemResource(&quot;dataset/FakeNewsNet.csv&quot;))<br>         .linesToSkip(1)<br>         .delimited()<br>         .names(&quot;title&quot;,&quot;news_url&quot;,&quot;source_domain&quot;,&quot;tweet_num&quot;,&quot;real&quot;)<br>         .targetType(NewsReport.class)<br>         .build();<br>}</pre><p>Çeşitli işlemleri gerçekleştirebilmek için farklı Reader sınıfları vardır. Örneğin dosya üzerinden <strong>FlatFileItemReader </strong>ile okuma işlemi yapılabilirken, RepositoryItemReader sınıfı veri tabanından okuma yapar. Daha detaylı bilgi için <a href="https://docs.spring.io/spring-batch/docs/current/reference/html/readersAndWriters.html#repositoryItemReader">https://docs.spring.io/spring-batch/docs/current/reference/html/readersAndWriters.html#repositoryItemReader</a> adresini ziyaret edebilirsiniz.</p><pre>@Bean(name = &quot;readerNewsReportByRealStatus&quot;)<br>public RepositoryItemReader&lt;NewsReport&gt; readerNewsReportByRealStatus(){<br>    RepositoryItemReader&lt;NewsReport&gt; reader = new RepositoryItemReader&lt;&gt;();<br>    reader.setRepository(newsReportRepository);<br>    reader.setMethodName(&quot;findByReal&quot;);<br>    List&lt;Object&gt; queryMethodArguments = new ArrayList&lt;&gt;();<br>    queryMethodArguments.add(&quot;1&quot;);<br>    reader.setArguments(queryMethodArguments);<br>    Map&lt;String, Sort.Direction&gt; sorts = new LinkedHashMap&lt;&gt;();<br>    sorts.put(&quot;id&quot;, Sort.Direction.ASC);<br>    reader.setSort(sorts);<br>    return reader;<br>}</pre><p><strong>Processor</strong></p><p>Reader ve Writer adımları birçok işimizi tamamlamak için yeterlidir. Ancak bazı durumlarda writer adımına geçmeden önce business logic ekleme ihtiyacımız olabilir. Bu durumlarda akışa process ekleyerek ara işlemlerimizi gerçekleştirebiliriz.</p><pre>@Slf4j<br>@Component<br>public class RealNewsProcessor implements ItemProcessor&lt;NewsReport, RealNews&gt;{<br><br>    @Override<br>    public RealNews process(NewsReport newsReport) throws Exception {<br>        log.info(&quot;Processing real news.....{}&quot;, newsReport);<br>        RealNews realNews = new RealNews();<br>        realNews.setUrl(newsReport.getNews_url());<br>        realNews.setTitle(newsReport.getTitle());<br>        realNews.setTweetNum(Integer.parseInt(newsReport.getTweet_num()));<br>        realNews.setSourceDomain(newsReport.getSource_domain());<br>        return realNews;<br>    }<br><br>}</pre><p>Burada csv dosyasından okunan haber verilerinin gerçeklik durumuna göre ayrıştırılmasını process adımlarında sağladık. Ayrıştırılan gerçek haberleri <strong>RealNews </strong>nesnesi ile <strong>Writer </strong>adımına aktarıyoruz.</p><p><strong>Writer</strong></p><p>Writer adımında ise Process adımından geriye dönen nesne veri tabanı veya dosyaya yazılır.</p><pre>@Bean(name = &quot;writerRealNewsReportTable&quot;)<br>public RepositoryItemWriter&lt;RealNews&gt; writerRealNewsReportTable(){<br>    RepositoryItemWriter&lt;RealNews&gt; writer = new RepositoryItemWriter&lt;&gt;();<br>    writer.setRepository(realNewsRepository);<br>    writer.setMethodName(&quot;save&quot;);<br>    return writer;<br>}</pre><p><strong>Step</strong></p><p>Step adımını, şu zamana kadar yapmış olduğumuz Reader, Process ve Writer adımlarının toparlandığı bölüm olarak düşünebiliriz. Listener ile step’den önce ve sonraki hareketleri kontrol edebiliriz.</p><pre>@Bean<br>public Step stepRealNewsReport(@Qualifier(&quot;readerNewsReportByRealStatus&quot;) ItemReader&lt;NewsReport&gt; itemReader, @Qualifier(&quot;writerRealNewsReportTable&quot;) ItemWriter&lt;RealNews&gt; itemWriter, StepCompletionNotificationListener listener){<br>    return stepBuilderFactory<br>           .get(&quot;stepRealNewsReport&quot;)<br>           .listener(listener)<br>           .&lt;NewsReport, RealNews&gt;chunk(50)<br>           .reader(itemReader)<br>           .processor(realNewsProcessor())<br>           .writer(itemWriter)<br>           .build();<br>}</pre><p>Step’ler chunk ve tasklet olmak üzere 2 farklı şekilde oluşturulabilirler. Chunk yapısı ile hangi veri tipinden, tek transactionda kaç adet veri okunup işleneceği verilir. Chunk’da verilen ilk parametre okunan verinin hangi tipte olduğunu ikinci parametre ise hangi tipte yazılacağını temsil etmektedir. Chunksize ise transaction başına kaç verinin işleneceğini belirler. Tasklet, bir kaynaktan dosya silme veya bir kaynağa dosya yüklemek gibi tek işin gerçekleştirildiği yapılardır. Bu örnekte chunk processing tercih edilmiştir.</p><p><strong>Job</strong></p><p>Job adımı ile beraber oluşturmuş olduğumuz step’leri sırasıyla çalıştırıyoruz. Step adımında olduğu gibi Job’larda da listener yapıları kullanılabilir. Böylece Job’ların çalışmadan önce ve sonraki durumları kontrol edilebilir.</p><pre>@Bean<br>public Job job(JobCompletionNotificationListener listener,Step stepNewsReport,Step stepRealNewsReport,Step stepFakeNewsReport){<br>    return jobBuilderFactory<br>           .get(&quot;job&quot;)<br>           .incrementer(new RunIdIncrementer())<br>           .listener(listener)<br>           .start(stepNewsReport)<br>           .next(stepRealNewsReport)<br>           .next(stepFakeNewsReport)<br>           .build();<br>}</pre><p>Job’lar için listener’ın yanında farklı konfigürasyonlarda yapılabilir. Örneğin, bir job tekrardan başlatılması istenmiyorsa <strong>preventRestart() </strong>ile bu engellenebilir.</p><p>Kaynak kodlara erişmek için <a href="https://github.com/eymeneruyar/Spring-Batch-NewsReport"><strong>https://github.com/eymeneruyar/Spring-Batch-NewsReport</strong></a></p><h3>Referanslar</h3><p><a href="https://www.tutorialsbuddy.com/spring-batch-with-mysql-example">https://www.tutorialsbuddy.com/spring-batch-with-mysql-example</a></p><p><a href="https://docs.spring.io/spring-batch/docs/current/reference/html/index.html">Spring Batch - Reference Documentation</a></p><p><a href="https://www.kaggle.com/">https://www.kaggle.com/</a></p><img src="https://medium.com/_/stat?event=post.clientViewed&referrerSource=full_rss&postId=6a313fef2c4c" width="1" height="1" alt="">]]></content:encoded>
        </item>
    </channel>
</rss>