Skip to content
Open
Show file tree
Hide file tree
Changes from 6 commits
Commits
Show all changes
21 commits
Select commit Hold shift + click to select a range
c94352f
fixing checkstyle issues, configuring pom to run checkstyle:check
markiantorno Jul 31, 2025
228674c
changing checks to run CHECKSTYLE over all modules
markiantorno Jul 31, 2025
191835d
checkstyle now runs on every PR across every module, and fails fast
markiantorno Jul 31, 2025
ae18caa
Merge branch 'hapifhir:master' into master
markiantorno Jul 31, 2025
1ceafe2
checkstyle profile now unified instead of having a checkstyle and che…
markiantorno Jul 31, 2025
bf5ae1c
need to build checkstyle first
markiantorno Jul 31, 2025
45164b0
need to move checkstyle to after the cache build job
markiantorno Jul 31, 2025
672244b
applying spotless changes
markiantorno Jul 31, 2025
24110e0
checkstyle will not block pipeline from running
markiantorno Jul 31, 2025
a6470b4
checkstyle now a reusable action
markiantorno Jul 31, 2025
eff0292
adding debug
markiantorno Jul 31, 2025
3c002ab
The pipeline should now work correctly because Maven will find the c…
markiantorno Jul 31, 2025
a884757
moving to local branch to test caching
markiantorno Aug 1, 2025
8b2332c
wip
markiantorno Aug 1, 2025
5dd53a8
wip
markiantorno Aug 7, 2025
d2913dd
wip
markiantorno Aug 8, 2025
5dd2efa
Merge pull request #2 from markiantorno/actions_temp
markiantorno Aug 8, 2025
8d3af98
Merge branch 'hapifhir:master' into master
markiantorno Aug 8, 2025
3f3e7d2
fixing r4 test
markiantorno Aug 8, 2025
2fca433
Merge pull request #3 from markiantorno/actions_temp
markiantorno Aug 8, 2025
7d2f62d
test fix error code
markiantorno Aug 11, 2025
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
30 changes: 29 additions & 1 deletion .github/workflows/pull-request.yml
Original file line number Diff line number Diff line change
Expand Up @@ -28,8 +28,36 @@ jobs:
outputs:
ignored_modules: ${{ steps.load_config.outputs.ignored_modules }}

checkstyle:
runs-on: ubuntu-latest
steps:
- name: Checkout repository
uses: actions/checkout@v4

- name: Set up JDK
uses: actions/setup-java@v4
with:
distribution: 'temurin'
java-version: '17'
cache: 'maven'

- name: Build checkstyle module
run: |
echo "Building hapi-fhir-checkstyle module first as it's required for cross-module validation..."
mvn clean install -pl hapi-fhir-checkstyle --batch-mode --no-transfer-progress

- name: Run cross-module checkstyle validation
run: |
echo "Running cross-module checkstyle validation to detect duplicate error codes and other violations..."
echo "This step ensures that HAPI FHIR error codes (Msg.code) are unique across all modules."
echo "If this step fails, it means there are checkstyle violations that must be fixed before the build can proceed."
echo ""
mvn validate -P CHECKSTYLE --batch-mode --no-transfer-progress

run-parallel-build:
needs: load-config-and-run
needs:
- load-config-and-run
- checkstyle
uses: ./.github/workflows/parallel-pipeline-build.yml
with:
ignored_modules: ${{ needs.load-config-and-run.outputs.ignored_modules }}
Expand Down
2 changes: 1 addition & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -170,6 +170,6 @@ Snap.*
/database*/
/activemq-data/
/.run/
/CLAUDE.md
**/CLAUDE.md

**/.claude/settings.local.json
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,8 @@
*/
package org.hl7.fhir.instance.model.api;

import ca.uhn.fhir.i18n.Msg;

public interface IBaseReference extends ICompositeType {

IBaseResource getResource();
Expand All @@ -38,7 +40,7 @@ default boolean hasIdentifier() {
}

default IBaseReference setIdentifier(ICompositeType theIdentifier) {
throw new UnsupportedOperationException("This reference does not support identifiers");
throw new UnsupportedOperationException(Msg.code(2759) + "This reference does not support identifiers");
}

default ICompositeType getIdentifier() {
Expand Down
34 changes: 0 additions & 34 deletions hapi-fhir-checkstyle/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -99,39 +99,5 @@
</plugins>
</build>
</profile>
<profile>
<id>CHECKSTYLE</id>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-checkstyle-plugin</artifactId>
<configuration>
<excludes>**/osgi/**/*, **/.mvn/**/*, **/.mvn_/**/*</excludes>
<includeTestSourceDirectory>true</includeTestSourceDirectory>
<!--suppress UnresolvedMavenProperty -->
<configLocation>checkstyle/hapi-base-checkstyle.xml</configLocation>
<!--suppress UnresolvedMavenProperty -->
<suppressionsLocation>checkstyle/hapi-base-checkstyle-suppression.xml</suppressionsLocation>
<inputEncoding>UTF-8</inputEncoding>
<consoleOutput>true</consoleOutput>
</configuration>
<executions>
<execution>
<id>checkstyle-across-all-modules</id>
<phase>install</phase>
<goals>
<goal>check</goal>
</goals>
</execution>
<execution>
<id>hapi-single-module-checkstyle</id>
<phase>none</phase>
</execution>
</executions>
</plugin>
</plugins>
</build>
</profile>
</profiles>
</project>
Original file line number Diff line number Diff line change
Expand Up @@ -103,7 +103,8 @@ private byte[] loadFileAsByteArray(String theFileName) throws ParseException {
input = IOUtils.toByteArray(new FileInputStream(new File(theFileName)));
} catch (IOException e) {
throw new ParseException(
Msg.code(1615) + "Failed to load file '" + theFileName + "' - Error: " + e.toString());
// Msg.code(1615) + "Failed to load file '" + theFileName + "' - Error: " + e.toString());
Msg.code(2478) + "Failed to load file '" + theFileName + "' - Error: " + e.toString());
}
return input;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -566,7 +566,7 @@ private String encodeAsString(IBaseResource theResource) {
} else if (myDstu2Hl7OrgContext.getVersion().getVersion().equals(version)) {
return myDstu2Hl7OrgContext.newJsonParser().encodeResourceToString(theResource);
} else {
throw new IllegalArgumentException("Cannot encode resource with version: %s".formatted(version));
throw new IllegalArgumentException(Msg.code(2777) + "Cannot encode resource with version: %s".formatted(version));
}
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -126,7 +126,7 @@ public void run() {

} catch (Exception theE) {
ourLog.error("Hibernate SQL log filters not refreshed. Exception: {} \n{}", theE, theE.getStackTrace());
throw new RuntimeException(Msg.code(2478) + theE);
throw new RuntimeException(Msg.code(2778) + theE);
} finally {
myRefreshDoneLatch.countDown();
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
*/
package ca.uhn.fhir.jpa.cache;

import ca.uhn.fhir.i18n.Msg;
import ca.uhn.fhir.jpa.config.util.ResourceTypeUtil;
import ca.uhn.fhir.jpa.dao.data.IResourceTypeDao;
import ca.uhn.fhir.jpa.dao.tx.IHapiTransactionService;
Expand Down Expand Up @@ -119,7 +120,7 @@ protected ResourceTypeEntity createResourceType(String theResourceType) {
myResourceTypeDao.flush();
} catch (DataIntegrityViolationException e) {
if (e.getMessage().contains("Value too long for column")) {
throw new InternalErrorException("Resource type name is too long: " + theResourceType, e);
throw new InternalErrorException(Msg.code(2764) + "Resource type name is too long: " + theResourceType, e);
}
// This can happen if the resource type already exists in the database
ourLog.info("Resource type already exists: {}", theResourceType);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
package ca.uhn.fhir.jpa.packages;

import ca.uhn.fhir.context.FhirContext;
import ca.uhn.fhir.i18n.Msg;
import ca.uhn.fhir.parser.IParser;
import ca.uhn.fhir.rest.server.exceptions.InternalErrorException;
import ca.uhn.fhir.util.BundleBuilder;
Expand All @@ -45,7 +46,7 @@ public static IBaseBundle bundleAdditionalResources(
try {
npmPackage = NpmPackage.fromPackage(new ByteArrayInputStream(packageInstallationSpec.getPackageContents()));
} catch (IOException e) {
throw new InternalErrorException(e);
throw new InternalErrorException(Msg.code(2765) + e);
}
List<IBaseResource> resources = getAdditionalResources(additionalResources, npmPackage, fhirContext);

Expand Down Expand Up @@ -73,15 +74,15 @@ public static List<IBaseResource> getAdditionalResources(
.flatMap(Collection::stream)
.collect(Collectors.toList());
} catch (IOException e) {
throw new InternalErrorException(e.getMessage(), e);
throw new InternalErrorException(Msg.code(2766) + e.getMessage(), e);
}

resources.addAll(fileNames.stream()
.map(fileName -> {
try {
return new String(folder.fetchFile(fileName));
} catch (IOException e) {
throw new InternalErrorException(e.getMessage(), e);
throw new InternalErrorException(Msg.code(2767) + e.getMessage(), e);
}
})
.map(parser::parseResource)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -113,7 +113,7 @@ private Condition createPredicateSourceContains(JpaStorageSettings theStorageSet
return BinaryCondition.like(upperFunction, generatePlaceholder(containsLikeExpression));
} else {
throw new MethodNotAllowedException(
Msg.code(getContainsModifierDisabledCode()) + ":contains modifier is disabled on this server");
Msg.code(2768) + ":contains modifier is disabled on this server");
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,6 @@
import org.hl7.fhir.instance.model.api.IIdType;

import java.util.function.Supplier;
import javax.annotation.Nullable;

/**
* This is a request object containing a request to extract the FullText index data from
Expand All @@ -35,10 +34,10 @@
*/
public class FullTextExtractionRequest {

@Nullable
@Nonnull
private final IIdType myResourceId;

@Nullable
@Nonnull
private final IBaseResource myResource;

@Nonnull
Expand All @@ -51,8 +50,8 @@ public class FullTextExtractionRequest {
* Constructor
*/
public FullTextExtractionRequest(
@Nullable IIdType theResourceId,
@Nullable IBaseResource theResource,
@Nonnull IIdType theResourceId,
@Nonnull IBaseResource theResource,
@Nonnull String theResourceType,
@Nonnull Supplier<String> theDefaultSupplier) {
myResourceId = theResourceId;
Expand All @@ -71,15 +70,15 @@ public boolean isDelete() {
/**
* @return Returns the ID of the resource being indexed. This may be <code>null</code> if a new resource is being created, and a type isn't assigned yet
*/
@Nullable
@Nonnull
public IIdType getResourceId() {
return myResourceId;
}

/**
* @return Returns the resource being indexed. May be <code>null</code> if the operation is a resource deletion.
*/
@Nullable
@Nonnull
public IBaseResource getResource() {
return myResource;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@
*/
package ca.uhn.fhir.jpa.searchparam.fulltext;

import javax.annotation.Nullable;
import jakarta.annotation.Nonnull;

/**
* This is a response object containing the FullText index data which should be stored during
Expand Down Expand Up @@ -72,7 +72,7 @@ public static FullTextExtractionResponse doNotIndex() {
*
* @param thePayload The fulltext payload string. May be <code>null</code> if no payload should be specified for the given resource.
*/
public static FullTextExtractionResponse indexPayload(@Nullable String thePayload) {
public static FullTextExtractionResponse indexPayload(@Nonnull String thePayload) {
return new FullTextExtractionResponse(false, false, thePayload);
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -71,7 +71,7 @@ public void validate(IIdType theSubscriptionId, ResourceDeliveryMessage theResou
case OFF:
case NULL:
default:
throw new SubscriptionInactiveException(Msg.code(2668) + "Attempting to deliver "
throw new SubscriptionInactiveException(Msg.code(2762) + "Attempting to deliver "
+ theResourceDeliveryMessage.getPayloadId() + " to disabled subscription "
+ subscription.getIdElementString() + ". Aborting delivery.");
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package ca.uhn.fhir.repository.impl;

import ca.uhn.fhir.context.BaseRuntimeElementDefinition;
import ca.uhn.fhir.i18n.Msg;
import ca.uhn.fhir.model.primitive.IdDt;
import ca.uhn.fhir.repository.IRepository;
import ca.uhn.fhir.rest.api.Constants;
Expand Down Expand Up @@ -82,8 +83,8 @@ public <B extends IBaseBundle> B processTransaction(B theTransactionBundle) {
case POST -> processPost(e, now);
case PUT -> processPut(e, now);
case DELETE -> processDelete(e, now);
default -> throw new NotImplementedOperationException(
"Transaction stub only supports POST, PUT, or DELETE");
default -> throw new NotImplementedOperationException(Msg.code(2769) +
"Transaction stub only supports POST, PUT, or DELETE");
};
bundleBuilder.addEntry(myResponseEntryBuilder.apply(responseEntry));
}
Expand Down Expand Up @@ -120,7 +121,7 @@ private static void validateNoLogicalUrl(BundleEntryParts theBundleEntryParts) {
String url = theBundleEntryParts.getUrl();
Validate.notNull(url, "request url must not be null: entry %s", theBundleEntryParts.getFullUrl());
if (url.contains("?")) {
throw new UnprocessableEntityException("Conditional urls are not supported");
throw new UnprocessableEntityException(Msg.code(2770) + "Conditional urls are not supported");
}
}

Expand All @@ -129,7 +130,7 @@ protected BundleResponseEntryParts processPost(
BundleEntryParts theBundleEntryParts, IPrimitiveType<Date> theInstant) {
// we assume POST is always "create", not an operation invocation
if (theBundleEntryParts.getConditionalUrl() != null) {
throw new UnprocessableEntityException("Conditional create urls are not supported");
throw new UnprocessableEntityException(Msg.code(2771) + "Conditional create urls are not supported");
}

var responseOutcome = myRepository.create(theBundleEntryParts.getResource());
Expand Down Expand Up @@ -197,7 +198,8 @@ protected static String statusCodeToStatusLine(int theResponseStatusCode) {
case Constants.STATUS_HTTP_409_CONFLICT -> "409 Conflict";
case Constants.STATUS_HTTP_204_NO_CONTENT -> "204 No Content";
case Constants.STATUS_HTTP_404_NOT_FOUND -> "404 Not Found";
default -> throw new IllegalArgumentException("Unsupported response status code: " + theResponseStatusCode);
default -> throw new IllegalArgumentException(Msg.code(2776) + "Unsupported response status code: "
+ theResponseStatusCode);
};
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package ca.uhn.fhir.repository.impl.memory;

import ca.uhn.fhir.context.FhirContext;
import ca.uhn.fhir.i18n.Msg;
import ca.uhn.fhir.model.api.IQueryParameterType;
import ca.uhn.fhir.repository.IRepository;
import ca.uhn.fhir.repository.impl.NaiveRepositoryTransactionProcessor;
Expand Down Expand Up @@ -121,7 +122,7 @@ private String formatResource(IBaseResource theResource) {
@Override
public synchronized <I extends IIdType, P extends IBaseParameters> MethodOutcome patch(
I theId, P thePatchParameters, Map<String, String> theHeaders) {
throw new NotImplementedOperationException("The PATCH operation is not currently supported");
throw new NotImplementedOperationException(Msg.code(2772) + "The PATCH operation is not currently supported");
}

@Override
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package ca.uhn.fhir.repository.impl.memory;

import ca.uhn.fhir.context.FhirContext;
import ca.uhn.fhir.i18n.Msg;
import ca.uhn.fhir.model.api.IQueryParameterType;
import ca.uhn.fhir.model.primitive.IdDt;
import ca.uhn.fhir.rest.param.ReferenceParam;
Expand Down Expand Up @@ -127,8 +128,8 @@ IdDt normalizeIdParamToIdPart(IQueryParameterType theIdParam) {
} else if (theIdParam instanceof StringParam stringParam) {
return new IdDt(stringParam.getValue());
} else {
throw new IllegalArgumentException(
"Unsupported _id parameter type: " + theIdParam.getClass().getName());
throw new IllegalArgumentException(Msg.code(2773) +
"Unsupported _id parameter type: " + theIdParam.getClass().getName());
}
}

Expand All @@ -138,8 +139,8 @@ Predicate<IBaseResource> matchPredicate(Multimap<String, List<IQueryParameterTyp
return Predicates.alwaysTrue();
} else {
// SOMEDAY Apply the rest of the params with a matcher
throw new UnsupportedOperationException(
"NaiveSearching does not support search parameters other than _id. Received: "
throw new UnsupportedOperationException(Msg.code(2780) +
"NaiveSearching does not support search parameters other than _id. Received: "
+ theSearchParameters.keys());
}
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package ca.uhn.fhir.repository.impl.memory;

import ca.uhn.fhir.i18n.Msg;
import ca.uhn.fhir.model.primitive.IdDt;
import ca.uhn.fhir.rest.server.exceptions.ResourceNotFoundException;
import jakarta.annotation.Nonnull;
Expand Down Expand Up @@ -90,7 +91,8 @@ private static IIdType normalizeIdForLookup(IIdType theId, String resourceTypeNa
}

if (!resourceTypeName.equals(unqualifiedVersionless.getResourceType())) {
throw new IllegalArgumentException("Resource type mismatch: resource is " + resourceTypeName
throw new IllegalArgumentException(Msg.code(2775) + "Resource type mismatch: resource is "
+ resourceTypeName
+ " but id type is " + unqualifiedVersionless.getResourceType());
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -341,10 +341,10 @@ private static IPrimitiveType<String> getStringPrimitiveFromParametersParameter(
} else if (value instanceof IBaseReference patientReference) {
return patientReference.getReferenceElement();
} else {
throw new InvalidRequestException("Unsupported type.");
throw new InvalidRequestException(Msg.code(2763) + "Unsupported type.");
}
} catch (Exception e) {
throw new InvalidRequestException("Invalid patient parameter.", e);
throw new InvalidRequestException(Msg.code(2779) + "Invalid patient parameter.", e);
}
}

Expand Down
Loading
Loading