title: @Transactional doesn't rollback by calling an External method that throw an RuntimeException
body: <p>I'm playing with Spring and the <code>@Transactional</code> annotation. I'm doing a simple experiment to test the behaviour of this annotation. These are my super simple java classes:</p>
  <p>my domain:</p>
  <pre><code>package com.xxx.springdemo.transactionalAnnotation.domain;
  
  import lombok.Data;
  
  import javax.persistence.Entity;
  import javax.persistence.Id;
  
  @Data
  @Entity
  public class Counter {
  
      @Id
      int id;
      int count = 0;
  
  }
  </code></pre>
  <p>my service:</p>
  <pre><code>package com.xxx.springdemo.transactionalAnnotation.services;
  
  import com.xxx.springdemo.transactionalAnnotation.domain.Counter;
  import org.springframework.stereotype.Service;
  import org.springframework.transaction.annotation.Transactional;
  
  @Service
  @Transactional
  public class TransactionalService {
  
      public void throwException(Counter counter) {
          counter.setCount(1);
          throw new RuntimeException(&quot;Runtime exception&quot;);
      }
  
      public void dontThrowException(Counter counter) {
          counter.setCount(2);
      }
  }
  </code></pre>
  <p>and my controller:</p>
  <pre><code>package com.xxx.springdemo.transactionalAnnotation.controllers;
  
  import com.xxx.springdemo.transactionalAnnotation.domain.Counter;
  import com.xxx.springdemo.transactionalAnnotation.services.TransactionalService;
  import lombok.RequiredArgsConstructor;
  import org.springframework.web.bind.annotation.GetMapping;
  import org.springframework.web.bind.annotation.RestController;
  
  @RestController
  @RequiredArgsConstructor
  public class TransactionController {
  
      private final TransactionalService transactionalService;
  
      @GetMapping(&quot;test-transactional&quot;)
      public void testTransactional() {
          Counter counter = new Counter();
          try {
              transactionalService.throwException(counter);
          } catch (Exception e) {
              System.out.println(&quot;Exception caught: &quot; + e.getMessage());
          }
          System.out.println(&quot;Variable hasn't changed (counter = &quot; + counter.getCount() + &quot;)&quot;);
      }
  
      @GetMapping(&quot;test-transactional-2&quot;)
      public void testTransactionalWithoutException() {
          Counter counter = new Counter();
          try {
              transactionalService.dontThrowException(counter);
          } catch (Exception e) {
              System.out.println(&quot;Exception caught: &quot; + e.getMessage());
          }
          System.out.println(&quot;Variable changed (counter = &quot; + counter.getCount() + &quot;)&quot;);
      }
  }
  </code></pre>
  <p>The code should be self-explanatory. I expect to have printed:</p>
  <blockquote>
  <p>Variable hasn't changed (counter = 0)</p>
  </blockquote>
  <p>in case the <code>test-transactional</code> endpoint is called. What I get instead is:</p>
  <blockquote>
  <p>Variable hasn't changed (counter = 1)</p>
  </blockquote>
  <p>This means that in the service method <code>throwException</code> the count property isn't rollbacked after the exception is thrown.</p>
  <p>P.S. this is my build.gradle file:</p>
  <pre><code>plugins {
      id 'org.springframework.boot' version '2.6.2'
      id 'io.spring.dependency-management' version '1.0.11.RELEASE'
      id 'java'
  }
  
  group = 'com.example'
  version = '0.0.1-SNAPSHOT'
  sourceCompatibility = '11'
  
  configurations {
      compileOnly {
          extendsFrom annotationProcessor
      }
  }
  
  repositories {
      mavenCentral()
  }
  
  dependencies {
      implementation 'org.springframework.boot:spring-boot-starter-web'
      implementation 'org.springframework.boot:spring-boot-starter-data-jpa'
      implementation 'org.springframework.boot:spring-boot-starter-actuator'
      implementation 'io.micrometer:micrometer-registry-prometheus'
  
      developmentOnly 'org.springframework.boot:spring-boot-devtools'
      runtimeOnly 'com.h2database:h2'
      compileOnly 'org.projectlombok:lombok'
      annotationProcessor 'org.projectlombok:lombok'
      testImplementation 'org.springframework.boot:spring-boot-starter-test'
  }
  
  test {
      useJUnitPlatform()
  }
  </code></pre>