Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .factorypath
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
<factorypath>
<factorypathentry kind="VARJAR" id="M2_REPO/org/projectlombok/lombok/1.18.36/lombok-1.18.36.jar" enabled="true" runInBatchMode="false"/>
<factorypathentry kind="VARJAR" id="M2_REPO/org/projectlombok/lombok/1.18.30/lombok-1.18.30.jar" enabled="true" runInBatchMode="false"/>
<factorypathentry kind="VARJAR" id="M2_REPO/org/mapstruct/mapstruct-processor/1.2.0.Final/mapstruct-processor-1.2.0.Final.jar" enabled="true" runInBatchMode="false"/>
</factorypath>
78 changes: 69 additions & 9 deletions pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
</parent>
<groupId>com.wipro.fhir.r4</groupId>
<artifactId>fhir-api</artifactId>
<version>3.1.0</version>
<version>3.6.1</version>
<packaging>war</packaging>
<name>FHIR-API</name>
<description>FHIR_NDHM standard integration in AMRIT</description>
Expand Down Expand Up @@ -53,6 +53,30 @@
</properties>

<dependencies>
<dependency>
<groupId>co.elastic.logging</groupId>
<artifactId>logback-ecs-encoder</artifactId>
<version>1.3.2</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-elasticsearch</artifactId>
</dependency>
<dependency>
<groupId>co.elastic.clients</groupId>
<artifactId>elasticsearch-java</artifactId>
<version>8.11.0</version>
</dependency>

<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-elasticsearch</artifactId>
</dependency>
<dependency>
<groupId>co.elastic.clients</groupId>
<artifactId>elasticsearch-java</artifactId>
<version>8.11.0</version>
</dependency>

<dependency>
<groupId>org.springframework.boot</groupId>
Expand Down Expand Up @@ -186,39 +210,74 @@
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-core</artifactId>
<version>2.14.2</version>
<version>2.15.2</version>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.14.2</version>
<version>2.15.2</version>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-annotations</artifactId>
<version>2.14.2</version>
<version>2.15.2</version>
</dependency>

<!--
https://mvnrepository.com/artifact/ca.uhn.hapi.fhir/hapi-fhir-structures-r4 -->
<dependency>
<groupId>ca.uhn.hapi.fhir</groupId>
<artifactId>hapi-fhir-structures-r4</artifactId>
<version>8.4.0</version>
</dependency>

<!--
https://mvnrepository.com/artifact/ca.uhn.hapi.fhir/hapi-fhir-validation -->
<dependency>
<groupId>ca.uhn.hapi.fhir</groupId>
<artifactId>hapi-fhir-validation</artifactId>
<version>8.4.0</version>
</dependency>

<!-- https://mvnrepository.com/artifact/ca.uhn.hapi.fhir/hapi-fhir-structures-r4 -->
<!--
https://mvnrepository.com/artifact/ca.uhn.hapi.fhir/hapi-fhir-structures-r4 -->
<dependency>
<groupId>ca.uhn.hapi.fhir</groupId>
<artifactId>hapi-fhir-structures-r4</artifactId>
<version>6.10.0</version>
<version>8.4.0</version>
</dependency>


<!-- Choose a HAPI version that matches the rest of your modules -->
<dependency>
<groupId>ca.uhn.hapi.fhir</groupId>
<artifactId>hapi-fhir-caching-caffeine</artifactId>
<version>8.4.0</version> <!-- example; align with your HAPI version -->
</dependency>



<dependency>
<groupId>ca.uhn.hapi</groupId>
<artifactId>hapi-base</artifactId>
<version>2.6.0</version>
</dependency>

<!-- https://mvnrepository.com/artifact/ca.uhn.hapi.fhir/org.hl7.fhir.utilities -->
<!--
https://mvnrepository.com/artifact/ca.uhn.hapi.fhir/org.hl7.fhir.utilities -->
<dependency>
<groupId>ca.uhn.hapi.fhir</groupId>
<artifactId>org.hl7.fhir.utilities</artifactId>
<version>6.5.18</version>
</dependency>

<!--
https://mvnrepository.com/artifact/ca.uhn.hapi.fhir/hapi-fhir-validation-resources-r4 -->
<dependency>
<groupId>ca.uhn.hapi.fhir</groupId>
<artifactId>hapi-fhir-validation-resources-r4</artifactId>
<version>8.4.0</version>
</dependency>

<!-- lombok -->
<dependency>
<groupId>org.projectlombok</groupId>
Expand Down Expand Up @@ -368,7 +427,8 @@
${target-properties} and
${source-properties}
</echo>
<concat destfile="${target-properties}" append="yes"
<concat destfile="${target-properties}"
append="yes"
force="yes">
<fileset file="${source-properties}">
</fileset>
Expand Down
16 changes: 16 additions & 0 deletions src/main/environment/common_ci.properties
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,10 @@ webLoginAbhaRequestOtp = @env.ABDM_PHR_URL@/login/abha/request/otp
webLoginAbhaVerify = @env.ABDM_PHR_URL@/login/abha/verify
webLoginPhrCard = @env.ABDM_PHR_URL@/login/profile/abha/phr-card

## ABDM V3 M2 APIs
generateTokenForLinkCareContext = @env.ABDM_HIECM_BASE_URL@/api/hiecm/v3/token/generate-token
linkCareContext = @env.ABDM_HIECM_BASE_URL@/api/hiecm/hip/v3/link/carecontext

x-CM-ID=@env.X_CM_ID@
abhaMode=@env.ABHA_MODE@

Expand All @@ -120,3 +124,15 @@ springdoc.swagger-ui.enabled=@env.SWAGGER_DOC_ENABLED@
spring.redis.host=@env.REDIS_HOST@

cors.allowed-origins=@env.CORS_ALLOWED_ORIGINS@

hipSystemUrl= @env.HIP_SYSTEM_URL@

# Elasticsearch Configuration
elasticsearch.host=@env.ELASTICSEARCH_HOST@
elasticsearch.port=@env.ELASTICSEARCH_PORT@
elasticsearch.username=@env.ELASTICSEARCH_USERNAME@
elasticsearch.password=@env.ELASTICSEARCH_PASSWORD@
elasticsearch.index.beneficiary=@env.ELASTICSEARCH_INDEX_BENEFICIARY@

# Enable/Disable ES (for gradual rollout)
elasticsearch.enabled=@env.ELASTICSEARCH_ENABLED@
20 changes: 19 additions & 1 deletion src/main/environment/common_docker.properties
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,10 @@ webLoginAbhaRequestOtp = ${ABDM_PHR_URL}/login/abha/request/otp
webLoginAbhaVerify = ${ABDM_PHR_URL}/login/abha/verify
webLoginPhrCard = ${ABDM_PHR_URL}/login/profile/abha/phr-card

## ABDM V3 M2 APIs
generateTokenForLinkCareContext = @env.ABDM_HIECM_BASE_URL@/api/hiecm/v3/token/generate-token
linkCareContext = @env.ABDM_HIECM_BASE_URL@/api/hiecm/hip/v3/link/carecontext
Comment on lines +101 to +103
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | πŸ”΄ Critical

Inconsistent placeholder syntax will cause runtime failure.

Lines 102-103 use @env.ABDM_HIECM_BASE_URL@ (Maven resource filtering syntax), while all other properties in this file use ${VARIABLE} (Spring property placeholder syntax). This inconsistency will likely result in the literal string @env.ABDM_HIECM_BASE_URL@ being used at runtime instead of the resolved value.

πŸ› Proposed fix
 ## ABDM V3 M2 APIs 
-generateTokenForLinkCareContext = `@env.ABDM_HIECM_BASE_URL`@/api/hiecm/v3/token/generate-token
-linkCareContext = `@env.ABDM_HIECM_BASE_URL`@/api/hiecm/hip/v3/link/carecontext
+generateTokenForLinkCareContext = ${ABDM_HIECM_BASE_URL}/api/hiecm/v3/token/generate-token
+linkCareContext = ${ABDM_HIECM_BASE_URL}/api/hiecm/hip/v3/link/carecontext
πŸ“ Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
## ABDM V3 M2 APIs
generateTokenForLinkCareContext = @env.ABDM_HIECM_BASE_URL@/api/hiecm/v3/token/generate-token
linkCareContext = @env.ABDM_HIECM_BASE_URL@/api/hiecm/hip/v3/link/carecontext
## ABDM V3 M2 APIs
generateTokenForLinkCareContext = ${ABDM_HIECM_BASE_URL}/api/hiecm/v3/token/generate-token
linkCareContext = ${ABDM_HIECM_BASE_URL}/api/hiecm/hip/v3/link/carecontext
πŸ€– Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/main/environment/common_docker.properties` around lines 101 - 103, The
two properties generateTokenForLinkCareContext and linkCareContext use
Maven-style placeholders (`@env.ABDM_HIECM_BASE_URL`@) which will not be resolved
at runtime; update both to use the same Spring-style placeholder used elsewhere
(e.g., replace `@env.ABDM_HIECM_BASE_URL`@ with ${ABDM_HIECM_BASE_URL}) so the
values are resolved consistently at runtime.


x-CM-ID=${X_CM_ID}
abhaMode=${ABHA_MODE}

Expand All @@ -117,4 +121,18 @@ springdoc.api-docs.enabled=${SWAGGER_DOC_ENABLED}
springdoc.swagger-ui.enabled=${SWAGGER_DOC_ENABLED}

# Redis IP
spring.redis.host=${REDIS_HOST}
spring.redis.host=${REDIS_HOST}


hipSystemUrl= ${HIP_SYSTEM_URL}

# Elasticsearch Configuration
elasticsearch.host=${ELASTICSEARCH_HOST}
elasticsearch.port=${ELASTICSEARCH_PORT}
elasticsearch.username=${ELASTICSEARCH_USERNAME}
elasticsearch.password=${ELASTICSEARCH_PASSWORD}
elasticsearch.index.beneficiary=${ELASTICSEARCH_INDEX_BENEFICIARY}

# Enable/Disable ES (for gradual rollout)
elasticsearch.enabled=${ELASTICSEARCH_ENABLED}

19 changes: 18 additions & 1 deletion src/main/environment/common_example.properties
Original file line number Diff line number Diff line change
Expand Up @@ -100,6 +100,10 @@
webLoginAbhaVerify = https://abhasbx.abdm.gov.in/abha/api/v3/phr/web/login/abha/verify
webLoginPhrCard = https://abhasbx.abdm.gov.in/abha/api/v3/phr/web/login/profile/abha/phr-card

## ABDM V3 M2 APIs
generateTokenForLinkCareContext = https://dev.abdm.gov.in/api/hiecm/v3/token/generate-token
linkCareContext = https://dev.abdm.gov.in/api/hiecm/hip/v3/link/carecontext

x-CM-ID= sbx
abhaMode=sbx

Expand All @@ -113,4 +117,17 @@
logging.path=logs/
logging.file.name=logs/fhir-api.log

cors.allowed-origins=http://localhost:*
cors.allowed-origins=http://localhost:*

hipSystemUrl= <Enter HIP request URL>

# Elasticsearch Configuration
elasticsearch.host=localhost
elasticsearch.port=9200
elasticsearch.username=elastic
elasticsearch.password=piramalES

Check warning on line 128 in src/main/environment/common_example.properties

View check run for this annotation

SonarQubeCloud / SonarCloud Code Analysis

Make sure these credentials get revoked, changed, and removed from the code.

See more on https://sonarcloud.io/project/issues?id=PSMRI_FHIR-API&issues=AZ0FvWKQu5_pCbq7Y7sk&open=AZ0FvWKQu5_pCbq7Y7sk&pullRequest=141

Check notice

Code scanning / SonarCloud

Credentials should not be hard-coded Low

Make sure these credentials get revoked, changed, and removed from the code. See more on SonarQube Cloud
elasticsearch.index.beneficiary=beneficiary_index

# Enable/Disable ES (for gradual rollout)
elasticsearch.enabled=true

2 changes: 2 additions & 0 deletions src/main/java/com/wipro/fhir/FhirApiApplication.java
Original file line number Diff line number Diff line change
Expand Up @@ -30,10 +30,12 @@
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.serializer.Jackson2JsonRedisSerializer;
import org.springframework.data.redis.serializer.StringRedisSerializer;
import org.springframework.scheduling.annotation.EnableAsync;

import com.wipro.fhir.data.users.User;

@SpringBootApplication
@EnableAsync
public class FhirApiApplication {

public static void main(String[] args) {
Expand Down
5 changes: 3 additions & 2 deletions src/main/java/com/wipro/fhir/config/CorsConfig.java
Original file line number Diff line number Diff line change
Expand Up @@ -19,8 +19,9 @@ public void addCorsMappings(CorsRegistry registry) {
Arrays.stream(allowedOrigins.split(","))
.map(String::trim)
.toArray(String[]::new))
.allowedMethods("GET", "POST", "PUT", "DELETE", "OPTIONS")
.allowedHeaders("Content-Type", "Authorization")
.allowedMethods("GET", "POST", "PUT", "PATCH", "DELETE", "OPTIONS")
.allowedHeaders("Authorization", "Content-Type", "Accept", "Jwttoken",
"serverAuthorization", "ServerAuthorization", "serverauthorization", "Serverauthorization")
.exposedHeaders("Authorization")
.allowCredentials(true)
.maxAge(3600);
Expand Down
104 changes: 104 additions & 0 deletions src/main/java/com/wipro/fhir/config/ElasticsearchConfig.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,104 @@
package com.wipro.fhir.config;

import co.elastic.clients.elasticsearch.ElasticsearchClient;
import co.elastic.clients.json.jackson.JacksonJsonpMapper;
import co.elastic.clients.transport.ElasticsearchTransport;
import co.elastic.clients.transport.rest_client.RestClientTransport;
import org.apache.http.HttpHost;
import org.apache.http.auth.AuthScope;
import org.apache.http.auth.UsernamePasswordCredentials;
import org.apache.http.impl.client.BasicCredentialsProvider;
import org.apache.http.impl.nio.reactor.IOReactorConfig;
import org.elasticsearch.client.RestClient;
import org.elasticsearch.client.RestClientBuilder;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.scheduling.annotation.EnableAsync;
import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;

import java.util.concurrent.Executor;

@Configuration
@EnableAsync
public class ElasticsearchConfig {

@Value("${elasticsearch.host}")
private String esHost;

@Value("${elasticsearch.port}")
private int esPort;

@Value("${elasticsearch.username}")
private String esUsername;

@Value("${elasticsearch.password}")
private String esPassword;

@Value("${elasticsearch.connection.timeout:10000}")
private int connectionTimeout;

@Value("${elasticsearch.socket.timeout:120000}")
private int socketTimeout;

@Value("${elasticsearch.max.connections:200}")
private int maxConnections;

@Value("${elasticsearch.max.connections.per.route:100}")
private int maxConnectionsPerRoute;

@Bean
public ElasticsearchClient elasticsearchClient() {
BasicCredentialsProvider credentialsProvider = new BasicCredentialsProvider();
credentialsProvider.setCredentials(
AuthScope.ANY,
new UsernamePasswordCredentials(esUsername, esPassword)
);

RestClientBuilder builder = RestClient.builder(
new HttpHost(esHost, esPort, "http")
);

// Apply timeout configurations
builder.setRequestConfigCallback(requestConfigBuilder ->
requestConfigBuilder
.setConnectTimeout(connectionTimeout)
.setSocketTimeout(socketTimeout)
.setConnectionRequestTimeout(connectionTimeout)
);

// Apply connection pool settings
builder.setHttpClientConfigCallback(httpClientBuilder ->
httpClientBuilder
.setDefaultCredentialsProvider(credentialsProvider)
.setMaxConnTotal(maxConnections)
.setMaxConnPerRoute(maxConnectionsPerRoute)
.setDefaultIOReactorConfig(
IOReactorConfig.custom()
.setSoTimeout(socketTimeout)
.build()
)
);

RestClient restClient = builder.build();

ElasticsearchTransport transport = new RestClientTransport(
restClient,
new JacksonJsonpMapper()
);

return new ElasticsearchClient(transport);
}

@Bean(name = "esAsyncExecutor")
public Executor asyncExecutor() {
ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();
executor.setCorePoolSize(5);
executor.setMaxPoolSize(20);
executor.setQueueCapacity(500);
executor.setThreadNamePrefix("es-sync-");
executor.setRejectedExecutionHandler(new java.util.concurrent.ThreadPoolExecutor.CallerRunsPolicy());
executor.initialize();
return executor;
}
}
Loading
Loading