• Stars
    star
    605
  • Rank 74,072 (Top 2 %)
  • Language
    Java
  • License
    MIT License
  • Created about 6 years ago
  • Updated 10 months ago

Reviews

There are no reviews yet. Be the first to send feedback to the community and the maintainers!

Repository Details

Your First Full Stack Application with Angular and Spring Boot

Your First Full Stack Application with Angular and Spring Boot

Image

Take your first steps towards becoming a Full Stack Developer with Angular and Spring Boot

Angular is a complete front end framework with a wide range of features

  • Strong Module System
  • Strong Component System
  • Forms Handling
  • Routing System
  • Dependency Injection
  • HTTP Requests

Spring Boot is an awesome framework to build RESTful API and Microservices.

In this course, lets combine these awesome frameworks to create your first full stack web application.

Installation Guides

Our Recommendations

  • Use latest version of Java
  • Use latest version of "Eclipse IDE for Enterprise Java Developers"
  • Remember: Spring Boot 3+ works only with Java 17+
  • Node v8+ for npm
  • Visual Studio Code - Latest Version

Installing Java

Troubleshooting

Installing Eclipse

Troubleshooting

Installing Node Js (npm) & Visual Studio Code

Troubleshooting Installations

Getting Started with Spring, Spring Boot and JPA

Course Overview

Introduction

Developing your first full stack application with Angular and Spring Boot is fun.

In this course, you will learn the basics of full stack development developing a Basic Todo Management Application using Angular, Spring Boot and Spring Security Frameworks.

You will build the application step by step - in more than 50 steps. This course would be a perfect first step as an introduction to Angular and Full Stack Development.

You will be using Angular (Frontend Framework), TypeScript Basics, Angular Cli(To create Angular projects), Spring Boot (REST API Framework), Spring (Dependency Management), Spring Security (Authentication and Authorization - Basic and JWT), BootStrap (Styling Pages), Maven (dependencies management), Node (npm), Visual Studio Code (TypeScript IDE), Eclipse (Java IDE) and Tomcat Embedded Web Server. We will help you set up each one of these.

What You will learn

  • You will develop your first full stack application with Angular and Spring Boot
  • You will learn the basic of Angular - Angular Modules, Components, Data Binding and Routing
  • You will learn basics of building awesome frontend applications with Angular
  • You will be introduced to building great RESTful APIs with Spring Boot
  • You will learn to use Spring Security to configure Basic Authentication and JWT
  • You will learn to solve the challenges of connecting an Angular Frontend to a RESTful API
  • You will learn to connect REST API to JPA/Hibernate with Spring Boot
  • You will learn to use a wide variety of Spring Boot Starter Projects - Spring Boot Web, and Spring Boot Data JPA
  • You will understand the best practices in designing RESTful web services
  • You will develop a Todo Management Full Stack Application step by step with login and logout functionalities
  • You will learn the magic of Spring Boot - Auto Configuration, Spring Initializr and Starter Projects
  • You will understand how to make best use of Spring Boot Actuator and Spring Boot Developer Tools
  • You will understand and use the embedded servlet container options provided by Spring Boot

Requirements

  • You should have prior experience with Java, Basic JavaScript and Spring Framework.
  • You should have Chrome browser installed.
  • We will help you install Eclipse, Visual Studio Code and Node JS(for npm)
  • We will help you install Chrome Restlet Client Plugin
  • We will help you learn the basics of Modern JavaScript, TypeScript, Spring Boot and JPA.

Step Wise Details

Quick Overview

  • Step 01 - Understanding Full Stack Application Architecture
  • Step 02 - Quick Overview of Modern JavaScript and TypeScript
  • Step 03 - Installing Angular CLI - Awesome Tool to create Angular Projects
  • Step 04 - Creating and Launching Angular Application with Angular CLI
  • Step 05 - Importing Angular App into Visual Studio Code
  • Step 06 - Exploring Angular CLI Commands - test, lint, e2e, serve, build
  • Step 07 - Exploring Angular CLI Project Structure

Getting Hands on With Angular

  • Step 08 - Introduction to Angular Components - Basics
  • Step 09 - Introduction to Angular Components - Playing with AppComponent
  • Step 10 - Generating Welcome Component with ng generate
  • Step 11 - Language Variations With an Example - Java, JavaScript and TypeScript
  • Step 12 - Generating and Setting up Login Component
  • Step 13 - Understanding Event Binding - Adding click event on Login Page
  • Step 14 - Using ngModel with 2 Way Data Binding in Login Page
  • Step 15 - Quick Review of Data Binding Approaches
  • Step 16 - Adding Hardcoded Authentication to Logic Component - ngIf directive
  • Step 17 - Implementing Routes for Login, Welcome and Error Components
  • Step 18 - Implementing Routing from Login to Welcome Component
  • Step 19 - Adding Route Parameter for Welcome Component
  • Step 20 - Create List Todos Component with ng generate
  • Step 21 - Create a Link to Todos in Welcome Component
  • Step 22 - Best Practice - Create a Todo Class
  • Step 23 - Quick Introduction to Angular Modules
  • Step 24 - Understanding Bootstrapping of Angular App with Root Module and Component
  • Step 25 - Quick Review - Angular Modules and Components
  • Step 26 - Overview of Next Few Steps - Bootstrap, Menu, Footer and Refactoring
  • Step 27 - Adding Bootstrap Framework and Creating Components for Menu and Footer
  • Step 28 - Using Bootstrap to Create a Menu with Navigation Links
  • Step 29 - Styling Footer and Other Components with CSS and Bootstrap
  • Step 30 - Good Practice - Use RouterLink instead of href for Routes
  • Step 31 - Creating an Independent Authentication Service Component
  • Step 32 - Using Session Storage to Store User Authentication Token
  • Step 33 - Enabling Menu Links Based on User Authentication Token
  • Step 34 - Implementing Logout to remove User Authentication Token
  • Step 35 - Securing Components using Route Guards - Part 1
  • Step 36 - Securing Components using Route Guards - Part 2
  • Step 37 - Quick Review - Authentication Service, Dependency Injection and Route Guards

Introduction to Web Services and REST

  • Step 41 - What is a Web Service?
  • Step 42 - Important How Questions related to Web Services
  • Step 43 - Web Services - Key Terminology
  • Step 44 - Introduction to RESTful Web Services

Getting Up and Running with REST and Spring Boot

  • Step 45 - Initializing a RESTful Services Project with Spring Boot
  • Step 46 - Creating a Hello World Service
  • Step 47 - Enhancing the Hello World Service to return a Bean
  • Step 48 - Quick Review of Spring Boot Auto Configuration and Dispatcher Servlet - What's happening in the background?
  • Step 49 - Enhancing the Hello World Service with a Path Variable

Connecting Angular Frontend to Spring Boot Restful Services

  • Step 50 - Connecting Angular Frontend with Restful API - 1 - Creating Data Service
  • Step 51 - Connecting Angular Frontend with Restful API - 2 - HttpClientModule and HttpClient
  • Step 52 - Connecting Angular Frontend with Restful API - 3 - Understanding Observable
  • Step 53 - Connecting Angular Frontend with Restful API - 4 - Understanding Subscribe
  • Step 54 - Connecting Angular Frontend with Restful API - 5 - Handling Error Responses
  • Step 55 - Calling Welcome HTTP Service with Path Variables
  • Step 56 - Designing RESTful Services for Todo Resource
  • Step 57 - Creating REST API for retrieving Todo List
  • Step 58 - Connecting Angular Frontend with Todo List RESTful Service
  • Step 59 - Creating REST API to delete a Todo - DELETE Request Method
  • Step 60 - Adding Delete Todo Feature to Angular Frontend
  • Step 61 - Creating Todo Component and Handle Routing
  • Step 62 - Designing Todo Page with Bootstrap Framework
  • Step 63 - Creating Retrieve Tod0 Service and Connect Angular Frontend
  • Step 64 - Improve Todo Page Appearance
  • Step 65 - Creating REST API for Updating Todo - PUT Request Method
  • Step 66 - Creating REST API for Creating a Todo - POST Request Method
  • Step 67 - Implementing Update Todo Feature in Angular Frontend
  • Step 68 - Implementing New Todo Feature in Angular Frontend
  • Step 69 - Improving Todo Form - Validation and Form Submit on Enter - ngSubmit
  • Step 70 - Enhancing Validation Messages on Todo Page

Implementing Spring Security with Basic Authentication

  • Step 71 - Overview of Security with Basic Auth and JWT
  • Step 72 - Setting up Spring Security
  • Step 73 - Configure standard userid and password
  • Step 74 - Enhancing Angular Welcome Data Service to use Basic Auth
  • Step 75 - Configure Spring Security to disable CSRF and enable OPTION Requests
  • Step 76 - Creating Angular HttpInterceptor to add Basic Auth Header
  • Step 77 - Configure HttpInterceptor as Provider in App Module
  • Step 78 - Create Basic Authentication RESTful Service in Spring Boot
  • Step 79 - Create Angular Basic Authentication Service
  • Step 80 - Connect Login Page to Basic Authentication Service - Part 1
  • Step 81 - Connect Login Page to Basic Authentication Service - Part 2
  • Step 82 - Refactoring Angular Basic Authentication Service
  • Step 83 - Refactoring HttpInterceptor to use Basic Authentication Token
  • Step 84 - Best Practice - Use Constants for URLs and Tokens

Connecting Spring Security with JWT

  • Step 85 - Introduction to JWT
  • Step 86 - Importing JWT Framework into Eclipse
  • Step 87 - Quick Tip - Resolving JWT Compilation Errors
  • Step 88 - Executing JWT Resources - Get Token and Refresh Token
  • Step 89 - Understanding JWT Spring Security Framework Setup
  • Step 90 - Creating a New User with Encoded Password
  • Step 91 - Using JWT Token in Angular Frontend

Connecting REST API With JPA and Hibernate

  • Step 92 - Setting up Todo Entity and Populating Data
  • Step 93 - Connecting GET REST APIs to JPA Repository
  • Step 94 - Connecting POST, PUT and DELETE REST APIs to JPA Repository

Spring Boot in 10 Steps

  • Introduction to Spring Boot in 10 Steps
  • Step 01 - Introduction to Spring Boot - Goals and Important Features
  • Step 02 - Developing Spring Applications before Spring Boot
  • Step 03 - Using Spring Initializr to create a Spring Boot Application
  • Step 04 - Creating a Simple REST Controller
  • Step 05 - What is Spring Boot Auto Configuration?
  • Step 06 - Spring Boot vs Spring vs Spring MVC
  • Step 07 - Spring Boot Starter Projects - Starter Web and Starter JPA
  • Step 08 - Overview of different Spring Boot Starter Projects
  • Step 09 - Spring Boot Actuator
  • Step 10 - Spring Boot Developer Tools

First 10 Steps in JPA with H2 in-memory database

  • Introduction to JPA in 10 Steps
  • Step 01 - Object Relational Impedence Mismatch - Understanding the problem that JPA solves
  • Step 02 - World before JPA - JDBC, Spring JDBC and myBatis
  • Step 03 - Introduction to JPA
  • Step 04 - Creating a JPA Project using Spring Initializr
  • Step 05 - Defining a JPA Entity - User
  • Step 06 - Defining a Service to manage the Entity - UserService and EntityManager
  • Step 07 - Using a Command Line Runner to save the User to database.
  • Step 08 - Magic of Spring Boot and In Memory Database H2
  • Step 09 - Introduction to Spring Data JPA
  • Step 10 - More JPA Repository - findById and findAll

Code Snippets

Core JWT Components - Spring Boot 3

package com.in28minutes.rest.webservices.restfulwebservices.jwt;

public record JwtTokenRequest(String username, String password) {}


package com.in28minutes.rest.webservices.restfulwebservices.jwt;

public record JwtTokenResponse(String token) {}


package com.in28minutes.rest.webservices.restfulwebservices.jwt;

import java.time.Instant;
import java.time.temporal.ChronoUnit;
import java.util.stream.Collectors;

import org.springframework.security.core.Authentication;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.oauth2.jwt.JwtClaimsSet;
import org.springframework.security.oauth2.jwt.JwtEncoder;
import org.springframework.security.oauth2.jwt.JwtEncoderParameters;
import org.springframework.stereotype.Service;

@Service
public class JwtTokenService {
    
    private final JwtEncoder jwtEncoder;

    public JwtTokenService(JwtEncoder jwtEncoder) {
        this.jwtEncoder = jwtEncoder;
    }

    public String generateToken(Authentication authentication) {

        var scope = authentication
                        .getAuthorities()
                        .stream()
                        .map(GrantedAuthority::getAuthority)
                        .collect(Collectors.joining(" "));

        var claims = JwtClaimsSet.builder()
                        .issuer("self")
                        .issuedAt(Instant.now())
                        .expiresAt(Instant.now().plus(90, ChronoUnit.MINUTES))
                        .subject(authentication.getName())
                        .claim("scope", scope)
                        .build();

        return this.jwtEncoder
                .encode(JwtEncoderParameters.from(claims))
                .getTokenValue();
    }
}


package com.in28minutes.rest.webservices.restfulwebservices.jwt;

import org.springframework.http.ResponseEntity;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RestController;

@RestController
public class JwtAuthenticationController {
    
    private final JwtTokenService tokenService;
    
    private final AuthenticationManager authenticationManager;

    public JwtAuthenticationController(JwtTokenService tokenService, 
            AuthenticationManager authenticationManager) {
        this.tokenService = tokenService;
        this.authenticationManager = authenticationManager;
    }

    @PostMapping("/authenticate")
    public ResponseEntity<JwtTokenResponse> generateToken(
            @RequestBody JwtTokenRequest jwtTokenRequest) {
        
        var authenticationToken = 
                new UsernamePasswordAuthenticationToken(
                        jwtTokenRequest.username(), 
                        jwtTokenRequest.password());
        
        var authentication = 
                authenticationManager.authenticate(authenticationToken);
        
        var token = tokenService.generateToken(authentication);
        
        return ResponseEntity.ok(new JwtTokenResponse(token));
    }
}


package com.in28minutes.rest.webservices.restfulwebservices.jwt;

import java.security.KeyPair;
import java.security.KeyPairGenerator;
import java.security.interfaces.RSAPrivateKey;
import java.security.interfaces.RSAPublicKey;
import java.util.UUID;

import org.springframework.boot.autoconfigure.security.servlet.PathRequest;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.http.HttpMethod;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.authentication.ProviderManager;
import org.springframework.security.authentication.dao.DaoAuthenticationProvider;
import org.springframework.security.config.Customizer;
import org.springframework.security.config.annotation.method.configuration.EnableMethodSecurity;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configurers.AbstractHttpConfigurer;
import org.springframework.security.config.annotation.web.configurers.oauth2.server.resource.OAuth2ResourceServerConfigurer;
import org.springframework.security.config.http.SessionCreationPolicy;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.oauth2.jwt.JwtDecoder;
import org.springframework.security.oauth2.jwt.JwtEncoder;
import org.springframework.security.oauth2.jwt.NimbusJwtDecoder;
import org.springframework.security.oauth2.jwt.NimbusJwtEncoder;
import org.springframework.security.provisioning.InMemoryUserDetailsManager;
import org.springframework.security.web.SecurityFilterChain;
import org.springframework.web.servlet.handler.HandlerMappingIntrospector;

import com.nimbusds.jose.JOSEException;
import com.nimbusds.jose.jwk.JWKSet;
import com.nimbusds.jose.jwk.RSAKey;
import com.nimbusds.jose.jwk.source.JWKSource;
import com.nimbusds.jose.proc.SecurityContext;

@Configuration
@EnableWebSecurity
@EnableMethodSecurity
public class JwtSecurityConfig {

    @Bean
    public SecurityFilterChain securityFilterChain(HttpSecurity httpSecurity, HandlerMappingIntrospector introspector) throws Exception {
        
        // h2-console is a servlet 
        // https://github.com/spring-projects/spring-security/issues/12310
        return httpSecurity
                .authorizeHttpRequests(auth -> auth
                    .requestMatchers("/authenticate").permitAll()
                    .requestMatchers(PathRequest.toH2Console()).permitAll() // h2-console is a servlet and NOT recommended for a production
                    .requestMatchers(HttpMethod.OPTIONS,"/**")
                    .permitAll()
                    .anyRequest()
                    .authenticated())
                .csrf(AbstractHttpConfigurer::disable)
                .sessionManagement(session -> session.
                    sessionCreationPolicy(SessionCreationPolicy.STATELESS))
                .oauth2ResourceServer(
                        (oauth2) -> oauth2.jwt(withDefaults()))
                .httpBasic(
                        Customizer.withDefaults())
                .headers(headers -> headers.frameOptions(frameOptionsConfig-> frameOptionsConfig.disable()))
                .build();
    }

    @Bean
    public AuthenticationManager authenticationManager(
            UserDetailsService userDetailsService) {
        var authenticationProvider = new DaoAuthenticationProvider();
        authenticationProvider.setUserDetailsService(userDetailsService);
        return new ProviderManager(authenticationProvider);
    }

    @Bean
    public UserDetailsService userDetailsService() {
        UserDetails user = User.withUsername("in28minutes")
                                .password("{noop}dummy")
                                .authorities("read")
                                .roles("USER")
                                .build();

        return new InMemoryUserDetailsManager(user);
    }

    @Bean
    public JWKSource<SecurityContext> jwkSource() {
        JWKSet jwkSet = new JWKSet(rsaKey());
        return (((jwkSelector, securityContext) 
                        -> jwkSelector.select(jwkSet)));
    }

    @Bean
    JwtEncoder jwtEncoder(JWKSource<SecurityContext> jwkSource) {
        return new NimbusJwtEncoder(jwkSource);
    }

    @Bean
    JwtDecoder jwtDecoder() throws JOSEException {
        return NimbusJwtDecoder
                .withPublicKey(rsaKey().toRSAPublicKey())
                .build();
    }
    
    @Bean
    public RSAKey rsaKey() {
        
        KeyPair keyPair = keyPair();
        
        return new RSAKey
                .Builder((RSAPublicKey) keyPair.getPublic())
                .privateKey((RSAPrivateKey) keyPair.getPrivate())
                .keyID(UUID.randomUUID().toString())
                .build();
    }

    @Bean
    public KeyPair keyPair() {
        try {
            var keyPairGenerator = KeyPairGenerator.getInstance("RSA");
            keyPairGenerator.initialize(2048);
            return keyPairGenerator.generateKeyPair();
        } catch (Exception e) {
            throw new IllegalStateException(
                    "Unable to generate an RSA Key Pair", e);
        }
    }
    
}

Core JWT Components

jwt.signing.key.secret=mySecret
jwt.get.token.uri=/authenticate
jwt.refresh.token.uri=/refresh
jwt.http.request.header=Authorization
jwt.token.expiration.in.seconds=604800
package com.in28minutes.todoservices.jwt;

import java.util.ArrayList;
import java.util.List;
import java.util.Optional;

import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.stereotype.Service;

@Service
public class JwtInMemoryUserDetailsService implements UserDetailsService {

  static List<JwtUserDetails> inMemoryUserList = new ArrayList<>();

  static {
    inMemoryUserList.add(new JwtUserDetails(1L, "in28minutes",
        "$2a$10$3zHzb.Npv1hfZbLEU5qsdOju/tk2je6W6PnNnY.c1ujWPcZh4PL6e", "ROLE_USER_2"));
  }

  @Override
  public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
    Optional<JwtUserDetails> findFirst = inMemoryUserList.stream()
        .filter(user -> user.getUsername().equals(username)).findFirst();

    if (!findFirst.isPresent()) {
      throw new UsernameNotFoundException(String.format("USER_NOT_FOUND '%s'.", username));
    }

    return findFirst.get();
  }

}


@Component
public class JwtTokenAuthorizationOncePerRequestFilter extends OncePerRequestFilter {

    private final Logger logger = LoggerFactory.getLogger(this.getClass());

    @Autowired
    private UserDetailsService jwtInMemoryUserDetailsService;
    
    @Autowired
    private JwtTokenUtil jwtTokenUtil;
    
    @Value("${jwt.http.request.header}")
    private String tokenHeader;

    @Override
    protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain chain) throws ServletException, IOException {
        logger.debug("Authentication Request For '{}'", request.getRequestURL());

        final String requestTokenHeader = request.getHeader(this.tokenHeader);

        String username = null;
        String jwtToken = null;
        if (requestTokenHeader != null && requestTokenHeader.startsWith("Bearer ")) {
            jwtToken = requestTokenHeader.substring(7);
            try {
                username = jwtTokenUtil.getUsernameFromToken(jwtToken);
            } catch (IllegalArgumentException e) {
                logger.error("JWT_TOKEN_UNABLE_TO_GET_USERNAME", e);
            } catch (ExpiredJwtException e) {
                logger.warn("JWT_TOKEN_EXPIRED", e);
            }
        } else {
            logger.warn("JWT_TOKEN_DOES_NOT_START_WITH_BEARER_STRING");
        }

        logger.debug("JWT_TOKEN_USERNAME_VALUE '{}'", username);
        if (username != null && SecurityContextHolder.getContext().getAuthentication() == null) {

            UserDetails userDetails = this.jwtInMemoryUserDetailsService.loadUserByUsername(username);

            if (jwtTokenUtil.validateToken(jwtToken, userDetails)) {
                UsernamePasswordAuthenticationToken usernamePasswordAuthenticationToken = new UsernamePasswordAuthenticationToken(userDetails, null, userDetails.getAuthorities());
                usernamePasswordAuthenticationToken.setDetails(new WebAuthenticationDetailsSource().buildDetails(request));
                SecurityContextHolder.getContext().setAuthentication(usernamePasswordAuthenticationToken);
            }
        }

        chain.doFilter(request, response);
    }
}


@Component
public class JwtTokenUtil implements Serializable {

  static final String CLAIM_KEY_USERNAME = "sub";
  static final String CLAIM_KEY_CREATED = "iat";
  private static final long serialVersionUID = -3301605591108950415L;
  private Clock clock = DefaultClock.INSTANCE;

  @Value("${jwt.signing.key.secret}")
  private String secret;

  @Value("${jwt.token.expiration.in.seconds}")
  private Long expiration;

  public String getUsernameFromToken(String token) {
    return getClaimFromToken(token, Claims::getSubject);
  }

  public Date getIssuedAtDateFromToken(String token) {
    return getClaimFromToken(token, Claims::getIssuedAt);
  }

  public Date getExpirationDateFromToken(String token) {
    return getClaimFromToken(token, Claims::getExpiration);
  }

  public <T> T getClaimFromToken(String token, Function<Claims, T> claimsResolver) {
    final Claims claims = getAllClaimsFromToken(token);
    return claimsResolver.apply(claims);
  }

  private Claims getAllClaimsFromToken(String token) {
    return Jwts.parser().setSigningKey(secret).parseClaimsJws(token).getBody();
  }

  private Boolean isTokenExpired(String token) {
    final Date expiration = getExpirationDateFromToken(token);
    return expiration.before(clock.now());
  }

  private Boolean ignoreTokenExpiration(String token) {
    // here you specify tokens, for that the expiration is ignored
    return false;
  }

  public String generateToken(UserDetails userDetails) {
    Map<String, Object> claims = new HashMap<>();
    return doGenerateToken(claims, userDetails.getUsername());
  }

  private String doGenerateToken(Map<String, Object> claims, String subject) {
    final Date createdDate = clock.now();
    final Date expirationDate = calculateExpirationDate(createdDate);

    return Jwts.builder().setClaims(claims).setSubject(subject).setIssuedAt(createdDate)
        .setExpiration(expirationDate).signWith(SignatureAlgorithm.HS512, secret).compact();
  }

  public Boolean canTokenBeRefreshed(String token) {
    return (!isTokenExpired(token) || ignoreTokenExpiration(token));
  }

  public String refreshToken(String token) {
    final Date createdDate = clock.now();
    final Date expirationDate = calculateExpirationDate(createdDate);

    final Claims claims = getAllClaimsFromToken(token);
    claims.setIssuedAt(createdDate);
    claims.setExpiration(expirationDate);

    return Jwts.builder().setClaims(claims).signWith(SignatureAlgorithm.HS512, secret).compact();
  }

  public Boolean validateToken(String token, UserDetails userDetails) {
    JwtUserDetails user = (JwtUserDetails) userDetails;
    final String username = getUsernameFromToken(token);
    return (username.equals(user.getUsername()) && !isTokenExpired(token));
  }

  private Date calculateExpirationDate(Date createdDate) {
    return new Date(createdDate.getTime() + expiration * 1000);
  }
}

@Component
public class JwtUnAuthorizedResponseAuthenticationEntryPoint implements AuthenticationEntryPoint, Serializable {

  private static final long serialVersionUID = -8970718410437077606L;

  @Override
  public void commence(HttpServletRequest request, HttpServletResponse response,
      AuthenticationException authException) throws IOException {
    response.sendError(HttpServletResponse.SC_UNAUTHORIZED,
        "You would need to provide the Jwt Token to Access This resource");
  }
}


public class JwtUserDetails implements UserDetails {

  private static final long serialVersionUID = 5155720064139820502L;

  private final Long id;
  private final String username;
  private final String password;
  private final Collection<? extends GrantedAuthority> authorities;

  public JwtUserDetails(Long id, String username, String password, String role) {
    this.id = id;
    this.username = username;
    this.password = password;

    List<SimpleGrantedAuthority> authorities = new ArrayList<SimpleGrantedAuthority>();
    authorities.add(new SimpleGrantedAuthority(role));

    this.authorities = authorities;
  }

  @JsonIgnore
  public Long getId() {
    return id;
  }

  @Override
  public String getUsername() {
    return username;
  }

  @JsonIgnore
  @Override
  public boolean isAccountNonExpired() {
    return true;
  }

  @JsonIgnore
  @Override
  public boolean isAccountNonLocked() {
    return true;
  }

  @JsonIgnore
  @Override
  public boolean isCredentialsNonExpired() {
    return true;
  }

  @JsonIgnore
  @Override
  public String getPassword() {
    return password;
  }

  @Override
  public Collection<? extends GrantedAuthority> getAuthorities() {
    return authorities;
  }

  @Override
  public boolean isEnabled() {
    return true;
  }

}


@Configuration
@EnableWebSecurity
@EnableGlobalMethodSecurity(prePostEnabled = true)
public class JWTWebSecurityConfig extends WebSecurityConfigurerAdapter {

    @Autowired
    private JwtUnAuthorizedResponseAuthenticationEntryPoint jwtUnAuthorizedResponseAuthenticationEntryPoint;

    @Autowired
    private UserDetailsService jwtInMemoryUserDetailsService;

    @Autowired
    private JwtTokenAuthorizationOncePerRequestFilter jwtAuthenticationTokenFilter;

    @Value("${jwt.get.token.uri}")
    private String authenticationPath;

    @Autowired
    public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
        auth
            .userDetailsService(jwtInMemoryUserDetailsService)
            .passwordEncoder(new BCryptPasswordEncoder());
    }

    //@Bean
    //public PasswordEncoder passwordEncoderBean() {
    //    return new BCryptPasswordEncoder();
    //}

    @Bean
    @Override
    public AuthenticationManager authenticationManagerBean() throws Exception {
        return super.authenticationManagerBean();
    }

    @Override
    protected void configure(HttpSecurity httpSecurity) throws Exception {
        httpSecurity
            .csrf().disable()
            .exceptionHandling().authenticationEntryPoint(jwtUnAuthorizedResponseAuthenticationEntryPoint).and()
            .sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS).and()
            .authorizeRequests()
            .anyRequest().authenticated();

       httpSecurity
            .addFilterBefore(jwtAuthenticationTokenFilter, UsernamePasswordAuthenticationFilter.class);
        
        httpSecurity
            .headers()
            .frameOptions().sameOrigin()  //H2 Console Needs this setting
            .cacheControl(); //disable caching
    }

    @Override
    public void configure(WebSecurity webSecurity) throws Exception {
        webSecurity
            .ignoring()
            .antMatchers(
                HttpMethod.POST,
                authenticationPath
            )
            .antMatchers(HttpMethod.OPTIONS, "/**")
            .and()
            .ignoring()
            .antMatchers(
                HttpMethod.GET,
                "/" //Other Stuff You want to Ignore
            )
            .and()
            .ignoring()
            .antMatchers("/h2-console/**/**");//Should not be in Production!
    }
}

@RestController
@CrossOrigin(origins="http://localhost:4200")
public class JwtAuthenticationRestController {

  @Value("${jwt.http.request.header}")
  private String tokenHeader;

  @Autowired
  private AuthenticationManager authenticationManager;

  @Autowired
  private JwtTokenUtil jwtTokenUtil;

  @Autowired
  private UserDetailsService jwtInMemoryUserDetailsService;

  @RequestMapping(value = "${jwt.get.token.uri}", method = RequestMethod.POST)
  public ResponseEntity<?> createAuthenticationToken(@RequestBody JwtTokenRequest authenticationRequest)
      throws AuthenticationException {

    authenticate(authenticationRequest.getUsername(), authenticationRequest.getPassword());

    final UserDetails userDetails = jwtInMemoryUserDetailsService.loadUserByUsername(authenticationRequest.getUsername());

    final String token = jwtTokenUtil.generateToken(userDetails);

    return ResponseEntity.ok(new JwtTokenResponse(token));
  }

  @RequestMapping(value = "${jwt.refresh.token.uri}", method = RequestMethod.GET)
  public ResponseEntity<?> refreshAndGetAuthenticationToken(HttpServletRequest request) {
    String authToken = request.getHeader(tokenHeader);
    final String token = authToken.substring(7);
    String username = jwtTokenUtil.getUsernameFromToken(token);
    JwtUserDetails user = (JwtUserDetails) jwtInMemoryUserDetailsService.loadUserByUsername(username);

    if (jwtTokenUtil.canTokenBeRefreshed(token)) {
      String refreshedToken = jwtTokenUtil.refreshToken(token);
      return ResponseEntity.ok(new JwtTokenResponse(refreshedToken));
    } else {
      return ResponseEntity.badRequest().body(null);
    }
  }

  @ExceptionHandler({ AuthenticationException.class })
  public ResponseEntity<String> handleAuthenticationException(AuthenticationException e) {
    return ResponseEntity.status(HttpStatus.UNAUTHORIZED).body(e.getMessage());
  }

  private void authenticate(String username, String password) {
    Objects.requireNonNull(username);
    Objects.requireNonNull(password);

    try {
      authenticationManager.authenticate(new UsernamePasswordAuthenticationToken(username, password));
    } catch (DisabledException e) {
      throw new AuthenticationException("USER_DISABLED", e);
    } catch (BadCredentialsException e) {
      throw new AuthenticationException("INVALID_CREDENTIALS", e);
    }
  }
}

public class AuthenticationException extends RuntimeException {
    public AuthenticationException(String message, Throwable cause) {
        super(message, cause);
    }
}

public class  JwtTokenRequest implements Serializable {
  
  private static final long serialVersionUID = -5616176897013108345L;

  private String username;
    private String password;

    public JwtTokenRequest() {
        super();
    }

    public JwtTokenRequest(String username, String password) {
        this.setUsername(username);
        this.setPassword(password);
    }

    public String getUsername() {
        return this.username;
    }

    public void setUsername(String username) {
        this.username = username;
    }

    public String getPassword() {
        return this.password;
    }

    public void setPassword(String password) {
        this.password = password;
    }
}

public class JwtTokenResponse implements Serializable {

  private static final long serialVersionUID = 8317676219297719109L;

  private final String token;

    public JwtTokenResponse(String token) {
        this.token = token;
    }

    public String getToken() {
        return this.token;
    }
}

Course Recording Notes

Preview Video

  • Welcome to course on *** in ** simple steps.
  • I'm Ranga Karanam. I've so and so much experience with ... I've been using this framework for ...
  • At in28minutes, we ask one question everyday - How to create more effective courses? All our success - *** students on Udemy and *** subscribers on Youtube - is a result of this pursuit of excellence.
  • You will develop *** and *** using ***
  • You will learn the basics like *** and move on to the advanced concepts like ***.
  • You will use
    • ... todo ...
    • Maven for dependency management, building and running the application in tomcat.
    • Eclipse IDE
  • All the code for this course and the step by step details are in our Github repository.
  • We have an awesome installation guide to help you install Maven and Eclipse. You are NOT expected to have any experience with Eclipse, Maven, or Tomcat.
  • What are we waiting for? Lets have some fun with *** in *** steps. We had a lot of fun creating this course for you and We are confident that you will have a lot of fun. I hope you are as excited as we are to learn more. Go ahead and enroll for the course. Or take a test drive with a free preview. See you in the course.

Course Intro Video

  • Welcome to this course on ***. We are excited to teach you how to build awesome ***.
  • In this video, we introduce you to the different sections of the course. By the end of the video you should have a clear idea of how to make the best use of the course.
  • We have organized this course into 6 different sections. We have designed each section to be independent of each other. That means, you have the flexibility of customizing the course based on your skills and your needs.
  • If you have experience with Spring and Spring Boot, you can skip these sections.
  • Lets get a quick overview of each of the sections now:
    • Section I is an one hour introduction to Spring
    • Section II is an one hour introduction to Spring Boot..
  • In summary this is your course. Feel free to create your own path and tailor it to your needs.
  • I will see you in the next video where we introduce you to our github repository

Overview of the Github Repository

  • Welcome Back. In this video, we give you an overview of how our github repository for this course is organized.
  • Github repository for this course is at ****.
  • Home page of the github repository has an overview of the course and installation guide
  • For each hands-on section of the course, we have a seperate folder in the repository. You can see these five folders for *** different sections
    • Folder 1 contains ...
    • Folder 2 contains ...
    • Folder 3 contains ...
  • Each of these folders contain
    • Step by Step details of the sections
    • Complete code example at the end of the section
    • Intermediate backups at different stages of the section
    • Useful Links
  • For example, let's look at the folder for ***. Home page of the folder contains
    • Step by step details : What are we going to do in each step
    • Useful Links : Different links that would be useful during the course
    • Complete Code, Snippets and Examples : Example code that your can use during the section. For example, If you are using a class and you do not know the package of the class, you can search here and quickly find what you would need.
    • Intermediate Backups : You can download any of these zips and import them into Eclipse as maven projects. File > Import > Existing Maven Projects.
    • Understanding our github repository is key part of making best use of this course. I recommend to spend some time with our github repository and I will see you in the next video.

Installation of Tools Video

  • In this video, we will help you install all the basic tools to get you started with the course
  • We use
    • Maven for Dependency Management
    • Eclipse as IDE
    • ..
  • Step by step details to install Java, Eclipse and Maven are in the installation guide present here. Also included are links to 5 videos that will help you to install and trouble shoot installations.
  • If you have any problems during the course, we recommend you to look at the troubleshooting section of the installation playlist.
  • Get your tools ready and I will see you in the course

Each Section Introduction

  • Why is this section important to the course?
  • What is discussed in this section?
  • What is the github folder for this section?
  • Can a student skip this sections?
  • Is there a trouble shooting guide?
  • What are the backups available?
  • Are examples in this section dependent on any other section?

Conclusion Video

  • Congratulations! You have successfully completed the course on ... We covered a wide range of topics starting from Spring, Spring Boot to ..... I'm sure you had a lot of fun doing this course. If you loved this course, we would love to hear from you. Do not forget to leave us a review. Until we see you in another in28minutes course, here's bye from the team here at in28minutes.
  • To find out more about *** use these References

Templates

Welcome Message


## ADD A FEW SAMPLE REVIEWS AFter a couple of months
## ADD A FEW SAMPLE REVIEWS - in the description of the course 

Congratulations on joining this course from in28Minutes. 

We have 14,000+ 5 Star reviews on our courses.  

I hope that by the time you are prompted to leave a review, that you think this course is an amazing course and can write a few sentences about what you like about the course for future students to see.

There are three things you need to understand before you start this course!

1...... Listen + See + Do Hands-on + Repeat = 90% Retention
For the first 2 hours, we repeat a few concepts to help you retain them. .

2...... Set Yourself a Goal
Set 1 hour aside every day for the next week for this course! No exceptions allowed :) 

3...... Udemy asks you for a review very early in the course! If you are not ready for giving a review, you can skip giving a review.

Thank you and enjoy the course,
Ranga

Thank You for completing the course message

Congratulations on completing the course from in28Minutes.

We have 14,000+ 5 Star reviews on our courses. We hope you think this course is an amazing course and can write a few sentences about what you like about the course for future students to see.

Good Luck for your future.

Ranga from in28Minutes

Bonus Lectures

TITLE : Bonus Lecture : Coupons for My Best-Selling Courses

I hope you enjoyed it! 

Connect and share yourΒ success (Course Completion Certificate) on Linked In -Β https://www.linkedin.com/in/rangakaranam/

Here are coupons for many of my best-selling courses. Please click the images/courses below to watch the course video previews (all of these courses have 30-day 100% money back guarantees):

- Copy relevant courses from https://github.com/in28minutes/learn

Other Courses

About in28Minutes

  • At in28Minutes, we ask ourselves one question everyday. How do we help you learn effectively - that is more quickly and retain more of what you have learnt?
  • We use Problem-Solution based Step-By-Step Hands-on Approach With Practical, Real World Application Examples.
  • Our success on Udemy and Youtube (2 Million Views & 12K Subscribers) speaks volumes about the success of our approach.
  • While our primary expertise is on Development, Design & Architecture Java & Related Frameworks (Spring, Struts, Hibernate) we are expanding into the front-end world (Bootstrap, JQuery, Angular JS).

Our Beliefs

  • Best Courses are interactive and fun.
  • Foundations for building high quality applications are best laid down while learning.

Our Approach

  • Problem Solution based Step by Step Hands-on Learning
  • Practical, Real World Application Examples.
  • We use 80-20 Rule. We discuss 20% things used 80% of time in depth. We touch upon other things briefly equipping you with enough knowledge to find out more on your own.
  • We will be developing a demo application in the course, which could be reused in your projects, saving hours of your effort.
  • We love open source and therefore, All our code is open source too and available on Github.

Troubleshooting

Rangas-MacBook-Pro:04-10-2018 rangaraokaranam$ node -v

Rangas-MacBook-Pro:04-10-2018 rangaraokaranam$ npm -v
6.4.1

#Global
npm uninstall -g angular-cli
npm cache verify
npm install -g @angular/[email protected]

#Inside the project - If you had an earlier version of angular cli
rm -rf node_modules
npm uninstall --save-dev angular-cli
npm install --save-dev @angular/cli@latest
npm install

What You will Learn?

Big Picture

  • What is the High Level Architecture of our Full Stack Application?
  • What is an SPA?
  • What is Angular?

TypeScript and JavaScript

  • I'm new to TypeScript. Will I be able to adapt to it?
  • How does a JavaScript Class compare to a Java Class?
    • Packages vs Modules
    • import statements
    • Decorator vs Annotation
  • What is a JavaScript Module?
  • What does TypeScript add on top of JavaScript?
  • How does JavaScript Syntax compare to Java Syntax?
    • Arrays - Filtering, Spread Operator and Functional Stuff
    • Custom Objects

Angular Basics

  • What is Angular Component?
  • How is Angular Component implemented?
    • Play with Selector, Template and Styles
  • What are the conventions for file extensions in Angular Projects?
  • What is Angular Module? Why do we need Modules? What are inbuilt Modules in Angular? How are they different from JavaScript Modules?
  • How is an Angular Module implemented?
  • How can I use a component which is built into another module?
  • How do you build forms in Angular? How do you do Form Validation?
  • What is Data Binding?
  • What is Routing?
  • How do you implement Routing in Angular?
  • How do you call HTTP Services in Angular?
  • What is Dependency Injection?
  • What is a Service?
  • Where do you store static content in Angular Projects? src\assets folder

Running Angular Applications

  • What is 'ng serve'? What does it enable for developers?
  • What is Root Module? What are Bootstrap Components? How is the Angular Application Bootstrapped? \src\index.html, \src\main.ts, AppModule, AppComponent
  • Do Browsers understand TypeScript? How does TypeScript code get converted to JavaScript code? \tsconfig.json, \src\tsconfig.app.json, \src\tsconfig.spec.json
  • What are angular.json, package.json, ```\node_modules?

Automated Tests and Code Quality

  • What are unit tests? How are unit tests organized in Angular? How is different from Java?
  • How can you run tests? \src\karma.conf.ts
  • What are coding standards? How can you check coding standards for Angular Cli Project? What is Lint? What is Linting? Is there a Standard Style Guide for Angular? \tslint.json
  • How can I run coding standards check for Angular Projects?
  • What are end to end tests? How are end to end tests organized in Angular? How can you run end to end tests? e2e folder

Course Details

Request URLs and Examples

Common Headers

Origin - http://localhost:4200
Content-Type - application/json
Authorization 
- Bearer *** or
- Basic *****

Retrieve all todos for a user

[
  {
    id: 1,
    username: "in28minutes",
    description: "Learn to Dance 2",
    targetDate: "2018-11-09T12:05:18.647+0000",
   : false,
  },
  {
    id: 2,
    username: "in28minutes",
    description: "Learn about Microservices 2",
    targetDate: "2018-11-09T12:05:18.647+0000",
   : false,
  },
  {
    id: 3,
    username: "in28minutes",
    description: "Learn about Angular",
    targetDate: "2018-11-09T12:05:18.647+0000",
   : false,
  },
]

Retrieve a specific todo

{
  id: 1,
  username: "in28minutes",
  description: "Learn to Dance 2",
  targetDate: "2018-11-09T12:05:18.647+0000",
 : false,
}

Creating a new todo

{
  "username": "in28minutes",
  "description": "Learn to Drive a Car",
  "targetDate": "2018-11-09T10:49:23.566+0000",
  "done": false
}

Updating a new todo

{
  "id": 1
  "username": "in28minutes",
  "description": "Learn to Drive a Car",
  "targetDate": "2018-11-09T10:49:23.566+0000",
  "done": false
}

Delete todo

JWT Authenticate

{
  "username":"ranga",
  "password":"password@!23@#!"
}

Response

{
"token": "eyJhbGciOiJIUzUxMiJ9.eyJzdWIiOiJyYW5nYSIsImV4cCI6MTU0MjQ3MjA3NCwiaWF0IjoxNTQxODY3Mjc0fQ.kD6UJQyxjSPMzAhoTJRr-Z5UL-FfgsyxbdseWQvk0fLi7eVXAKhBkWfj06SwH43sY_ZWBEeLuxaE09szTboefw"
}

Other URLS

Useful Links

Connection to MySQL

create sequence hibernate_sequence start with 1 increment by 1

create table todo (
    id bigint not null, 
    description varchar(255), 
    is_done boolean not null, 
    target_date timestamp, 
    username varchar(255), 
    primary key (id))


launch.json

{
    // Use IntelliSense to learn about possible attributes.
    // Hover to view descriptions of existing attributes.
    // For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387
    "version": "0.2.0",
    "configurations": [
        {
            "type": "chrome",
            "request": "launch",
            "name": "Launch Chrome against localhost",
            "url": "http://localhost:4200",//Line Changed
            "webRoot": "${workspaceFolder}"
        }
    ]
}
npm install @angular/material @angular/cdk
<link href="https://fonts.googleapis.com/icon?family=Material+Icons" rel="stylesheet">
npm install @angular/flex-layout rxjs-compat

Diagrams


graph architecture {
node[style=filled,color="#59C8DE"]
//node [style=filled,color="#D14D28", fontcolor=white];
rankdir = TB;
node[shape=record]

FRONTEND[label=<Angular Application<BR />
   <FONT POINT-SIZE="9">TypeScript</FONT>>];

REST[label=<RESTFUL API<BR />
   <FONT POINT-SIZE="9">Spring Boot on Java</FONT>>];

DB[label=<Database>];

FRONTEND -- REST -- DB
DB[shape=cylinder]
}


digraph architecture {
node[style=filled,color="#59C8DE"]
//node [style=filled,color="#D14D28", fontcolor=white];
rankdir = TB;
node[shape=record]

FRONTEND[label=<Angular Application<BR />
   <FONT POINT-SIZE="9">TypeScript</FONT>>];

NGMODULE0[label=<Login Angular Module>];

NGMODULE1[label=<Todo Angular Module>];

NGMODULE2[label=<Common Angular Module>];

NGMODULE3[label=<Builtin Angular Modules<BR />
   <FONT POINT-SIZE="9">BrowserModule, FormsModule, HttpClientModule, etc</FONT>>];

NGMODULE3[label=<Builtin Angular Modules<BR />
   <FONT POINT-SIZE="9">BrowserModule, FormsModule, HttpClientModule, etc</FONT>>];

COMPONENT01[label=<Login Component>];
COMPONENT11[label=<List Todo Component>];
COMPONENT12[label=<Todo Component>];

FRONTEND -> NGMODULE0
FRONTEND -> NGMODULE1
FRONTEND -> NGMODULE2
FRONTEND -> NGMODULE3

NGMODULE0 -> COMPONENT01

NGMODULE1 -> COMPONENT11
NGMODULE1 -> COMPONENT12

}

graph architecture {

node[style=filled,color="#59C8DE"]
//node [style=filled,color="#D14D28", fontcolor=white];
rankdir = TB;
node[shape=record]

COMPONENT[label=<Component>];

TEMPLATE[label=<Template<BR />
   <FONT POINT-SIZE="9">HTML .component.html</FONT>>];

STYLE[label=<Style<BR />
   <FONT POINT-SIZE="9">CSS .component.css</FONT>>];

CODE[label=<Code<BR />
   <FONT POINT-SIZE="9">TypeScript  .component.ts</FONT>>];

COMPONENT -- TEMPLATE
COMPONENT -- STYLE
COMPONENT -- CODE
}

digraph architecture {
node[style=filled,color="#59C8DE"]
//node [style=filled,color="#D14D28", fontcolor=white];
rankdir = TB;
node[shape=record]

APP[label=<Angular Application  <BR />
   <FONT POINT-SIZE="9">1</FONT>>];

MODULES[label=<Angular Modules<BR />
   <FONT POINT-SIZE="9">@NgModule 1..N incl. Builtin</FONT>>];

COMPONENTS[label=<Angular Components<BR />
   <FONT POINT-SIZE="9">@Component 0..N</FONT>>];

APP -> MODULES -> COMPONENTS

}

digraph architecture {
node[style=filled,color="#59C8DE"]
//node [style=filled,color="#D14D28", fontcolor=white];
rankdir = LR;
node[shape=record]
COMPONENT[label=<Business Logic <BR />(Component)<BR />
   <FONT POINT-SIZE="10">TypeScript .component.ts</FONT>>];

VIEW[label=<DOM <BR />(HTML/View)>];


//VIEW -> COMPONENT [label=<<FONT POINT-SIZE="25">Event Binding  </FONT> (event)="event handler" >]
//COMPONENT -> VIEW [label=<<FONT POINT-SIZE="25">Interpolation </FONT> {{value}} >]
//COMPONENT -> VIEW [label=<<FONT POINT-SIZE="25">Property Binding  </FONT> [property]=value >]
VIEW -> COMPONENT [label = ""]
COMPONENT -> VIEW  [label=<<FONT POINT-SIZE="25">2 Way Data Binding  </FONT> [(ngModel)]="model.attribute" >]
}   

graph architecture {

node[style=filled,color="#59C8DE"]
//node [style=filled,color="#D14D28", fontcolor=white];
rankdir = TB;
node[shape=record]

Angular -- Basics
Basics -- Components
Basics -- DataBinding
Basics -- Routing
Basics -- Modules
Angular -- Features
Features -- Forms
Features -- RestAPICalls
Features -- DependencyInjection

DependencyInjection[label=<Dependency Injection>]
DataBinding[label=<Data Binding>]
RestAPICalls[label=<Rest API Calls>]
Forms[label=<Forms and Validation>]

}

graph architecture {

node[style=filled,color="#59C8DE"]
//node [style=filled,color="#D14D28", fontcolor=white];
rankdir = TB;
node[shape=record]

Tools[label=<Angular CLI Project>]

Tools -- PackageManagment
Tools -- BuildAndRun
BuildAndRun -- Transpilation
BuildAndRun -- Serve
Tools -- BuildOptimizations
BuildOptimizations -- Bundling
BuildOptimizations -- Minification
BuildOptimizations -- Uglification
Tools -- CodeQuality
CodeQuality -- EditorConfig
CodeQuality -- Lint
Tools -- AutomationTests
AutomationTests -- Karma
AutomationTests -- Protractor

}
  

Next Steps

Troubleshooting

Youtube Playlists - 500+ Videos

Click here - 30+ Playlists with 500+ Videos on Spring, Spring Boot, REST, Microservices and the Cloud

Keep Learning in28Minutes

in28Minutes is creating amazing solutions for you to learn Spring Boot, Full Stack and the Cloud - Docker, Kubernetes, AWS, React, Angular etc. - Check out all our courses here

More Repositories

1

devops-master-class

Devops Tutorial for Beginners - Learn Docker, Kubernetes, Terraform, Ansible, Jenkins and Azure Devops
Java
2,203
star
2

spring-microservices

Microservices using Spring Boot, Spring Cloud, Docker and Kubernetes
Java
1,770
star
3

java-tutorial-for-beginners

Java Tutorial For Beginners with 500 Code Examples
1,312
star
4

java-best-practices

Best practices in Coding, Designing and Architecting Java Applications
1,254
star
5

master-spring-and-spring-boot

Spring and Spring Boot Tutorial For Absolute Beginners - 10-in-1 - Spring to Spring Boot to REST API to Full Stack to Containers to Cloud
Java
1,226
star
6

spring-boot-examples

Code Examples for everything thats written on www.springboottutorial.com
Java
1,207
star
7

spring-master-class

An updated introduction to the Spring Framework 5. Become an Expert understanding the core features of Spring In Depth. You would write Unit Tests, AOP, JDBC and JPA code during the course. Includes introductions to Spring Boot, JPA, Eclipse, Maven, JUnit and Mockito.
Java
1,142
star
8

java-a-course-for-beginners

Java Programming Tutorial for Beginners
JavaScript
1,044
star
9

JavaInterviewQuestionsAndAnswers

Java Interview Questions and Answers
Java
973
star
10

spring-boot-master-class

Understand and love the power of Spring Boot - All its features are illustrated developing a web application managing todos and a basic API for survey questionnaire. Also covers unit testing, mocking and integration testing.
Java
965
star
11

course-material

Course Material for in28minutes courses on Java, Spring Boot, DevOps, AWS, Google Cloud, and Azure.
947
star
12

SpringMvcStepByStep

Spring MVC Tutorial for beginners - In 25 Small Steps
Java
828
star
13

spring-microservices-v2

Microservices + Spring Boot 2 + Spring Cloud + Docker + Kubernetes - https://www.udemy.com/course/microservices-with-spring-boot-and-spring-cloud/. Latest Repo - http://github.com/in28minutes/spring-microservices-v3
JavaScript
714
star
14

learn

How do you achieve your career objectives? Complete career paths with amazing Cloud, Full Stack and Microservice Courses and Videos from in28Minutes
685
star
15

SpringIn28Minutes

Spring Tutorial For Beginners
Java
657
star
16

spring-interview-guide

200+ Questions and Answers on Spring, Spring Boot and Spring MVC
JavaScript
642
star
17

MockitoTutorialForBeginners

Mockito Tutorial for Beginners
Java
632
star
18

jpa-with-hibernate

Master JPA using Hibernate as the implementation. Learn the basics of JPA - entities, relationships, entity manager, annotations, JPQL and Criteria API. Take a step into the advanced world of JPA - caching, performance tuning(n + 1 queries), mapping inheritance hierarchies. Get a peek into the magic of Spring Data JPA & Spring Data Rest.
Java
630
star
19

SpringBootForBeginners

Spring Boot Tutorial For Beginners
Java
609
star
20

full-stack-with-react-and-spring-boot

Your First Full Stack Application with React and Spring Boot
Java
606
star
21

in28minutes-initiatives

All initiatives to build a connect between industry, instructors and learners
596
star
22

java-cheat-sheet

Java Tutorial For Beginners - Companion Reference
588
star
23

JavaWebApplicationStepByStep

JSP Servlets Tutorial For Beginners - in 25 Steps
Java
534
star
24

spring-web-services

Spring Web Services - SOAP and RESTful
Java
532
star
25

spring-unit-testing-with-junit-and-mockito

Spring Unit Testing with JUnit and Mockito
Java
359
star
26

docker-crash-course

Docker for beginners - with Java and Spring Boot Applications and Microservices
Java
350
star
27

functional-programming-with-java

Learn Functional Programming with Java using a Hands-on Step by Step Approach
Java
340
star
28

kubernetes-crash-course

Learn Kubernetes and Docker with Google Kubernetes Engine deploying Spring Boot Microservices
Java
327
star
29

interview-guide

Java interview guide - 200+ Question and Answers
297
star
30

deploy-spring-microservices-to-aws-ecs-fargate

Take your first steps towards cloud with AWS ECS Fargate. Deploy REST APIs and Microservices with Spring Boot and Docker Containers to the cloud.
Java
265
star
31

SpringBootWebApplicationStepByStep

Develop your first web application with Spring Boot Magic
Java
256
star
32

spring-boot-react-fullstack-examples

All full stack examples with Spring Boot and React for articles on our website http://www.springboottutorial.com
JavaScript
255
star
33

roadmaps

Roadmaps of in28minutes courses!
245
star
34

spring-microservices-v3

JavaScript
228
star
35

JUnitIn28Minutes

JUNIT Tutorial For Beginners
Java
216
star
36

automation-testing-with-java-and-selenium

Learn Automation Testing with Java and Selenium
HTML
193
star
37

MavenIn28Minutes

Maven Tutorial for Beginners with Examples
Java
193
star
38

python-tutorial-for-beginners

Python Tutorial for Beginners with 500 Code Examples
182
star
39

in28minutes.github.io

Spring Boot Tutorials
HTML
171
star
40

deploy-spring-boot-aws-eb

Deploying Spring Boot Apps to AWS using Elastic Beanstalk
Java
160
star
41

getting-started-in-5-steps

How to install and get started with Java, Eclipse, Maven, JUnit, Mockito & Spring in 5 easy steps
JavaScript
154
star
42

clean-code

Learn to Write Clean Code with Java. Get Hands-on with 20+ Code Examples involving 4 principles of Simple Design, Refactoring and TDD.
JavaScript
153
star
43

first-steps-to-software-architect

How to start your journey towards software architecture?
136
star
44

MockitoIn28Minutes

Learn Mockito from In28Minutes
Java
121
star
45

learning-paths-cloud-and-devops

How to learn Cloud and DevOps
119
star
46

spring-boot-angular-fullstack-examples

All full stack examples with Spring Boot and Angular for articles on our website http://www.springboottutorial.com
TypeScript
109
star
47

in28Minutes-Course-Roadmap

A Roadmap for our Courses. Remember we focus on Java, Microservices, Web Applications and are big Spring Shop - Spring, Spring MVC, Spring Boot, Spring Cloud...
104
star
48

docker

Docker for Beginners - Learn Docker in 5 Steps
Java
101
star
49

pcf-crash-course-with-spring-boot

PCF Crash Course for Java, Spring and Spring Boot Developers - Deploy Spring Boot REST API, Full Stack Applications and Microservices to Pivotal Cloud Foundry (PCF)
Java
98
star
50

azure-devops-kubernetes-terraform-pipeline

https://github.com/in28minutes/devops-master-class
Java
87
star
51

deploy-spring-boot-to-azure

Deploy Spring Boot Applications to Azure Web Apps
Java
82
star
52

camel

Learn Enterprise Integration Patterns with Apache Camel
JavaScript
80
star
53

Design-Patterns-For-Beginners

Design Patterns for Beginners
80
star
54

JavaObjectOrientedProgramming

Learn basics of object oriented programming with Java
Java
69
star
55

learn-programming-with-python-

learn-programming-with-python​
Python
67
star
56

10-Steps-to-High-Quality-Java-Developer

You Key to Becoming a High Quality Java Developer
61
star
57

java-to-python-in-100-steps

Learn Python using your Java Knowledge
Python
58
star
58

java-technology-for-beginners

In my 15 years of designing and developing more than 100 java web applications, there are a number of terminologies, standards, frameworks, tools that I have used. I know how difficult it is for a beginner to understand them. And imagine the trouble non techies face - the business, testing teams and others. So, this guide is to demystify these terms! Enough talk. Let's Rock and Roll......
58
star
59

spring-boot-vuejs-fullstack-examples

All full stack examples with Spring Boot and Vue JS for articles on our website http://www.springboottutorial.com
Java
57
star
60

EclipseIn28Minutes

Eclipse Tutorial for Beginners - From in28Minutes
53
star
61

jenkin-devops-microservice

https://github.com/in28minutes/devops-master-class
Java
49
star
62

spring-complete-career-path

Level 1 covers Basics of Spring Developing a web application with Spring MVC Basics of Spring Boot - Autoconfiguration, Starter Projects Basic Todo Management Application with Login/Logout Model, Controllers, ViewResolver and Filters Forms - DataBinding, Validation Bootstrap to style the page Spring Security Exception Handling Level 2 (coming soon) will cover Rest APIs with Spring Boot SOAP Web Services with Spring Boot. Level 3 (coming soon) will cover Spring Cloud Microservices
Java
44
star
63

go-serverless

Go Serverless with AWS Lambda and Azure Functions - Udemy Course https://www.udemy.com/course/serverless-tutorial-aws-lambda-and-azure-functions
JavaScript
41
star
64

Tips-Database

Tips about Web Services, APIs, Microservices, Spring, Spring Boot, Maven, Eclipse etc
37
star
65

TDDin28Minutes

TDD Tutorial For Beginners - from in28Minutes
Java
31
star
66

spring-boot-to-cloud

Spring Boot to Cloud (AWS, Azure, GCP and PCF) with Docker and Kubernetes
Java
30
star
67

JavaTutorialForBeginners

Java Tutorial for Beginners with examples
Java
29
star
68

BasicWebServletsIn28Minutes

Java
28
star
69

campus-interview-guide

60 Day Learning Challenges for Campus Interviews
28
star
70

CTutorialForBeginners

C Tutorial for Beginners
27
star
71

Java-EE-Design-Patterns

26
star
72

HibernateJPAStepByStep

Hibernate Tutorial For Beginners - Step by Step with Examples
22
star
73

in28minutes.com

Awesome Courses from the Best Selling Instructor
HTML
22
star
74

RealWorldWebApplicationWithServletsAndJspIn28Minutes

Learn to Develop your first web application with Servlets and JSP
Java
20
star
75

cloud.in28minutes.com

cloud.in28minutes.com
HTML
20
star
76

jenkins-pipeline

Java
18
star
77

spring-boot-rest-api-playground

Java
18
star
78

spring-microservices-v3-old

JavaScript
16
star
79

microservice-reference-archetype

Java
14
star
80

hello-world-rest-api-aws-ecs-codepipeline

Java
14
star
81

Struts2StepByStep

Learn Struts 2 Step By Step
Java
11
star
82

jshell-for-java-programmers

An introduction to JShell for Java Programmers
11
star
83

hello-world-rest-api-azure-pipelines

Java
10
star
84

in28minutes

9
star
85

getting-started-for-beginners-v2

Updated Getting Started Guides for Beginners Recorded with Spring Boot 3 - Spring, Spring Boot, JUnit, Mockito, JPA, Hibernate ....
Java
9
star
86

spring-boot-todo-rest-api-h2-aws-codepipeline

Java
8
star
87

In28MinutesTemplate

Serves as template for my new courses
8
star
88

todo-app

Java
6
star
89

automatewithselenium.com

Learn how to automate your tests with Selenium - Java, Python, C# and JavaScript - automatewithselenium.com
CSS
6
star
90

dev-config-server-test

4
star
91

config-server

2
star
92

programmingabc.com

Master Content for our Programming Website - programmingabc.com
CSS
2
star
93

Future-Course-Preparation

1
star
94

hello-world-playground

Java
1
star