Skip to content

Commit

Permalink
Initial commit
Browse files Browse the repository at this point in the history
  • Loading branch information
bibekaryal86 authored Oct 14, 2024
0 parents commit 87c88b1
Show file tree
Hide file tree
Showing 28 changed files with 1,014 additions and 0 deletions.
5 changes: 5 additions & 0 deletions .gitattributes
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
#
# https://help.github.com/articles/dealing-with-line-endings/
#
# These are explicitly windows files and should use crlf
*.bat text eol=crlf
12 changes: 12 additions & 0 deletions .github/dependabot.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
# To get started with Dependabot version updates, you'll need to specify which
# package ecosystems to update and where the package manifests are located.
# Please see the documentation for all configuration options:
# https://help.github.com/github/administering-a-repository/configuration-options-for-dependency-updates

version: 2
updates:
- package-ecosystem: "gradle" # See documentation for possible values
directory: "app/" # Location of package manifests
schedule:
interval: "weekly"
day: "saturday"
75 changes: 75 additions & 0 deletions .github/workflows/codeql-analysis.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
# For most projects, this workflow file will not need changing; you simply need
# to commit it to your repository.
#
# You may wish to alter this file to override the set of languages analyzed,
# or to provide custom queries or build logic.
#
# ******** NOTE ********
# We have attempted to detect the languages in your repository. Please check
# the `language` matrix defined below to confirm you have the correct set of
# supported CodeQL languages.
#
name: "CodeQL"

on:
push:
branches: [ main ]
pull_request:
# The branches below must be a subset of the branches above
branches: [ main ]
schedule:
- cron: '0 0 * * 5'

jobs:
analyze:
name: Analyze
runs-on: ubuntu-latest
permissions:
actions: read
contents: read
security-events: write

strategy:
fail-fast: false
matrix:
language: [ 'java' ]
# CodeQL supports [ 'cpp', 'csharp', 'go', 'java', 'javascript', 'python', 'ruby' ]
# Learn more about CodeQL language support at https://git.io/codeql-language-support

steps:
- name: Checkout repository
uses: actions/checkout@v4
- name: Setup Java
uses: actions/setup-java@v4
with:
distribution: temurin
java-version: 21

# Initializes the CodeQL tools for scanning.
- name: Initialize CodeQL
uses: github/codeql-action/init@v2
with:
languages: ${{ matrix.language }}
# If you wish to specify custom queries, you can do so here or in a config file.
# By default, queries listed here will override any specified in a config file.
# Prefix the list here with "+" to use these queries and those in the config file.
# queries: ./path/to/local/query, your-org/your-repo/queries@main

# Autobuild attempts to build any compiled languages (C/C++, C#, or Java).
# If this step fails, then you should remove it and run the build manually (see below)
- name: Autobuild
uses: github/codeql-action/autobuild@v2

# ℹ️ Command-line programs to run using the OS shell.
# 📚 https://git.io/JvXDl

# ✏️ If the Autobuild fails above, remove it and uncomment the following three lines
# and modify them (or add more) to build your code if your project
# uses a compiled language

#- run: |
# make bootstrap
# make release

- name: Perform CodeQL Analysis
uses: github/codeql-action/analyze@v2
34 changes: 34 additions & 0 deletions .github/workflows/gradle.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
# This workflow will build a Java project with Gradle
# For more information see: https://help.github.com/actions/language-and-framework-guides/building-and-testing-java-with-gradle

name: Java CI with Gradle

on:
push:
branches: [ main ]
pull_request:
branches: [ main ]

jobs:
build:

runs-on: ubuntu-latest

steps:
- name: Checkout repository
uses: actions/checkout@v4

- name: Set up Java
uses: actions/setup-java@v4
with:
distribution: temurin
java-version: 21

- name: Setup Gradle
uses: gradle/actions/setup-gradle@v4

- name: Build with Gradle
run: ./gradlew clean build

- name: Test with Gradle
run: ./gradlew clean test
14 changes: 14 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
# Ignore Gradle project-specific cache directory
.gradle

# Ignore Gradle build output directory
build

# Ignore IntelliJ config directory
.idea

# Ignore Jar Files in gcp folder
gcp/*.jar

# Ignore credentials to be committed
gcp/app-credentials.yaml
17 changes: 17 additions & 0 deletions Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
# Build
FROM gradle:8.10.2-jdk21-alpine AS build
WORKDIR /app
COPY app/build.gradle .
COPY app/src /app/src
RUN gradle --no-daemon clean build

# Deploy
FROM eclipse-temurin:21-jre-alpine
RUN addgroup -S springdocker
RUN adduser -S springdocker -G springdocker
USER springdocker:springdocker
WORKDIR /app
COPY --from=build /app/build/libs/spring-service-skeleton.jar .
EXPOSE 8080
ENTRYPOINT ["java","-jar", "spring-service-skeleton.jar"]
# provide environment variables in docker-compose
47 changes: 47 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
# spring-service-skeleton

* This is a template Repository to create a new Spring Boot REST Service
* Things to update:
* Refactor the package name from `spring.service.skeleton.app` to as desired
* keep it 3 words if possible, eg: `xxx.xxx.xxx.app`
* `settings.gradle`
* `rootProject.name`
* `build.gradle`
* Add/Remove dependencies as necessary
* `springVersion`, and version in buildscript and plugin as necessary
* `archiveFileName` in `bootJar`
* `mainClass` in `application`
* gradle wrapper version as necessary
* `application.yml` as necessary
* at least need to replace `spring-service-skeleton` with application name
* `logback.xml` as necessary
* avoid LOG_FILE as much as possible, prefer console logging
* replace `spring-service-skeleton` with application name in `LOG_PATTERN` and `LOG_FILE`
* remove `traceId` and `spanId` if `spring-cloud-started-sleuth` is not used in `build.gradle`
* `Dockerfile` as necessary
* esp `JAR_FILE`, `COPY` and environment variables in `ENTRYPOINT`
* GCP configurations, in `gcp` folder as necessary
* esp `app-credentials.yaml` and `app-credentials_DUMMY.yaml`
* `README.md` i.e. this file to add the program's readme
* `.gitignore` if necessary
* Things to add:
* `DatasourceConfig` if using MONGO/JPA/JDBC
* See: `pets-database-layer` for MongoDB example
* https://github.com/bibekaryal86/pets-database-layer
* See: `health-data-java` for JPA example
* https://github.com/bibekaryal86/health-data-java
* For JDBC, only need to set `Datasource` from above examples
* `RestTemplateConfig` if using `RestTemplate`
* See: `pets-service-layer` for example
* https://github.com/bibekaryal86/pets-service-layer
* `SwaggerConfig` if using SwaggerUI
* See: `pets-service-layer` / `pets-database-layer` for example
* https://github.com/bibekaryal86/pets-service-layer
* https://github.com/bibekaryal86/pets-database-layer
* Also, will have to update `SecurityConfig` to allow SwaggerUI
* Things to remove:
* If not using cache
* Remove `CacheConfig` from config package
* Remove `spring-boot-starter-cache` dependency from `build.gradle`
* GitHub workflows
* Remove `dependabot.yml` in the new app until automated merge is figured out
93 changes: 93 additions & 0 deletions app/build.gradle
Original file line number Diff line number Diff line change
@@ -0,0 +1,93 @@
/*
* This file was generated by the Gradle 'init' task.
*
* This generated file contains a sample Java application project to get you started.
* For more details take a look at the 'Building Java & JVM projects' chapter in the Gradle
* User Manual available at https://docs.gradle.org/7.3.1/userguide/building_java_projects.html
*/

plugins {
id 'application'
id 'java'
id 'io.freefair.lombok' version '8.10.2'
id 'org.springframework.boot' version '3.3.4'
id 'com.diffplug.spotless' version '6.25.0'
}

java {
sourceCompatibility = JavaVersion.VERSION_21
targetCompatibility = JavaVersion.VERSION_21
toolchain {
languageVersion = JavaLanguageVersion.of(21)
}
}

repositories {
mavenCentral()
}

bootJar {
archiveFileName = 'spring-service-skeleton.jar'
}

dependencies {
def springVersion = "3.3.4"
def junitVersion = "5.11.2"

implementation "org.springframework.boot:spring-boot-starter-actuator:$springVersion"
implementation "org.springframework.boot:spring-boot-starter-web:$springVersion"
implementation "org.springframework.boot:spring-boot-starter-security:$springVersion"
implementation "org.springframework.boot:spring-boot-starter-cache:$springVersion"

implementation 'ch.qos.logback:logback-classic:1.5.10'

// FOR ClassNotFoundException javax.xml.bind.JAXBException
implementation 'javax.xml.bind:jaxb-api:2.3.1'

// FOR REST TEMPLATE
implementation 'org.apache.httpcomponents.client5:httpclient5:5.4'
implementation 'com.fasterxml.jackson.core:jackson-databind:2.18.0'

// IF USING JPA
implementation "org.springframework.boot:spring-boot-starter-data-jpa:$springVersion"

// IF USING JDBC
implementation "org.springframework.boot:spring-boot-starter-data-jdbc:$springVersion"

// IF USING MONGO
implementation "org.springframework.boot:spring-boot-starter-data-mongodb:$springVersion"
implementation "org.springframework.boot:spring-boot-starter-data-rest:$springVersion"

// IF USING SWAGGER
implementation 'org.springdoc:springdoc-openapi-starter-webmvc-ui:2.6.0'

// IF USING APP IN A MICROSERVICES CLUSTER WITH GATEWAY, THIS WILL LOG TRACE/SPAN
implementation 'io.micrometer:micrometer-tracing-bridge-otel:1.3.4'

// FOR TESTING
testImplementation("org.springframework.boot:spring-boot-starter-test:$springVersion") {
exclude group: 'org.junit.vintage', module: 'junit-vintage-engine'
}
testImplementation "org.junit.jupiter:junit-jupiter-api:$junitVersion"
testRuntimeOnly "org.junit.jupiter:junit-jupiter-engine:$junitVersion"

// IF USING ELK STACK OR OTHER JSON LOGGING DRIVER
// ALSO UPDATE LOGBACK.XML
implementation 'net.logstash.logback:logstash-logback-encoder:8.0'
}

application {
mainClass = 'spring.service.skeleton.App'
}

configurations {
implementation.exclude module: 'spring-boot-starter-logging'
implementation.exclude group: 'org.apache.logging.log4j', module: 'log4j-to-slf4j'
}

spotless {
java {
removeUnusedImports()
googleJavaFormat()
}
}
26 changes: 26 additions & 0 deletions app/src/main/java/spring/service/skeleton/App.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
/*
* This Java source file was generated by the Gradle 'init' task.
*/
package spring.service.skeleton;

import static java.util.Collections.singletonMap;
import static spring.service.skeleton.app.util.CommonUtils.getSystemEnvProperty;
import static spring.service.skeleton.app.util.ConstantUtils.SERVER_PORT;

import lombok.extern.slf4j.Slf4j;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

@Slf4j
@SpringBootApplication
public class App {

public static void main(String[] args) {
log.info("Begin application initialization...");
SpringApplication app = new SpringApplication(App.class);
app.setDefaultProperties(
singletonMap("server.port", getSystemEnvProperty(SERVER_PORT, "8080")));
app.run(args);
log.info("End application initialization...");
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
package spring.service.skeleton.app.config;

import static java.util.Objects.requireNonNull;

import lombok.extern.slf4j.Slf4j;
import org.springframework.cache.CacheManager;
import org.springframework.cache.annotation.EnableCaching;
import org.springframework.context.annotation.Configuration;
import org.springframework.scheduling.annotation.EnableScheduling;
import org.springframework.scheduling.annotation.Scheduled;

@Slf4j
@Configuration
@EnableCaching
@EnableScheduling // so that @Scheduled will be registered
public class CacheConfig {

private final CacheManager cacheManager;

public CacheConfig(CacheManager cacheManager) {
this.cacheManager = cacheManager;
}

@Scheduled(cron = "0 0 0 * * *")
protected void putAllCache() {
log.info("Firing Cache Evict!!!");
cacheManager
.getCacheNames()
.forEach(cacheName -> requireNonNull(cacheManager.getCache(cacheName)).clear());

log.info("Firing All Cache!!!");
// call methods that set to cache here
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
package spring.service.skeleton.app.config;

import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
import spring.service.skeleton.app.util.InterceptorUtilsLogging;

@Configuration
public class InterceptorConfig implements WebMvcConfigurer {

@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(new InterceptorUtilsLogging());
}
}
Loading

0 comments on commit 87c88b1

Please sign in to comment.