Shared utilities, form contracts, and UI configuration helpers that back OpenSRP Android form workflows and other reusable components.
- Toolchain: Gradle 8.7 · Android Gradle Plugin 8.6.0 · Java (JDK 17) · Kotlin not required (Java-only module)
- Modules:
opensrp-utils(library),app(sample/demo shell) - Continuous integration: Travis CI configuration present (
.travis.yml); verify against your current CI pipeline - Current branch:
master; latest tag:v0.0.7
- Contracts that define how client forms are stored, served, and rendered (
ClientFormContract) - Exhaustive JSON form constants used across OpenSRP-native form rendering (
JsonFormConstants) - A configurable
Formdomain model for branding, navigation, and button behaviors in wizard-style flows
- JDK: 17 (Temurin/OpenJDK recommended)
- Gradle: Wrapper pinned to 8.7 (run via
./gradlew) - Android Gradle Plugin: 8.6.0
- Kotlin: Not required (Java sources only)
- Android SDK:
compileSdk/targetSdk35,minSdk28, Build Tools 35.0.0 - Android Studio: Giraffe or newer recommended for AGP 8.6
Add the dependency from Maven Central (replace <version> with the latest release version).
Groovy DSL
repositories {
mavenCentral()
}
dependencies {
implementation 'io.github.bluecodesystems:opensrp-client-utils:<version>' // see Releases for versions
}Kotlin DSL
repositories {
mavenCentral()
}
dependencies {
implementation("io.github.bluecodesystems:opensrp-client-utils:<version>") // see Releases for versions
}If you consume this repository as a multi-module project, you can instead depend on
project(":opensrp-utils").
No global initialization hook is required. Add the dependency and exercise the APIs directly in your feature modules.
Configure a form shell for a native JSON workflow:
import org.smartregister.client.utils.domain.Form;
Form registration = new Form();
registration.setName("household_registration");
registration.setWizard(true);
registration.setNextLabel("Next");
registration.setPreviousLabel("Back");
registration.setGreyOutSaveWhenFormInvalid(true);Build JSON field definitions with shared constants:
import org.json.JSONObject;
import org.smartregister.client.utils.constants.JsonFormConstants;
JSONObject householdName = new JSONObject()
.put(JsonFormConstants.KEY, "household_name")
.put(JsonFormConstants.TYPE, JsonFormConstants.EDIT_TEXT)
.put(JsonFormConstants.HINT, "Household name");Implement a lightweight DAO for client forms:
import java.util.ArrayList;
import java.util.List;
import org.smartregister.client.utils.contract.ClientFormContract;
public class InMemoryClientFormDao implements ClientFormContract.Dao {
private final List<ClientFormContract.Model> cache = new ArrayList<>();
@Override
public void addOrUpdate(ClientFormContract.Model clientForm) {
cache.removeIf(existing -> existing.getId() == clientForm.getId());
cache.add(clientForm);
}
@Override
public ClientFormContract.Model getActiveClientFormByIdentifier(String identifier) {
return cache.stream()
.filter(ClientFormContract.Model::isActive)
.filter(model -> identifier.equals(model.getIdentifier()))
.findFirst()
.orElse(null);
}
// Implement other contract methods to persist forms to disk, SQLCipher, etc.
}The app/ module acts as a minimal harness. To install it on a connected device or emulator:
./gradlew :app:installDebugYou can also open the project in Android Studio and use the standard run configurations targeting the app module.
- Assemble all variants:
./gradlew clean assemble - Run unit tests (includes the library placeholder test suite):
./gradlew test - Generate Jacoco coverage for the library:
./gradlew :opensrp-utils:jacocoTestReport
Binary releases and changelogs are published under GitHub Releases. Check the latest tag before updating <version> in your build.
Issues and pull requests are welcome. Please:
- Use JDK 17, Gradle 8.7, and AGP 8.6.0 when building locally
- Run
./gradlew clean assemble testbefore submitting a PR - Follow existing code style and package structure for contracts and constants
If you add significant features or fixes, update this README with new guidance.
Apache License 2.0 — see LICENSE for the full terms.