diff --git a/.gitattributes b/.gitattributes
index 00a51aff5..022b84144 100644
--- a/.gitattributes
+++ b/.gitattributes
@@ -3,4 +3,3 @@
#
# These are explicitly windows files and should use crlf
*.bat text eol=crlf
-
diff --git a/.github/workflows/lint-pr.yml b/.github/workflows/lint-pr.yml
index bce134066..a3c228ef4 100644
--- a/.github/workflows/lint-pr.yml
+++ b/.github/workflows/lint-pr.yml
@@ -18,6 +18,6 @@ jobs:
name: Validate PR title
runs-on: ubuntu-latest
steps:
- - uses: amannn/action-semantic-pull-request@40166f00814508ec3201fc8595b393d451c8cd80
+ - uses: amannn/action-semantic-pull-request@069817c298f23fab00a8f29a2e556a5eac0f6390
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
diff --git a/.github/workflows/merge.yml b/.github/workflows/merge.yml
index 338a0985c..8c978f625 100644
--- a/.github/workflows/merge.yml
+++ b/.github/workflows/merge.yml
@@ -9,35 +9,39 @@ name: on-merge
on:
push:
- branches: [ master, main ]
+ branches:
+ - main
permissions:
contents: read
jobs:
build:
-
+ environment: publish
runs-on: ubuntu-latest
steps:
- - uses: actions/checkout@85e6279cec87321a52edac9c87bce653a07cf6c2
- - name: Set up JDK 8
- uses: actions/setup-java@3a4f6e1af504cf6a31855fa899c6aa5355ba6c12
+ - uses: actions/checkout@1af3b93b6815bc44a9784bd300feb67ff0d1eeb3
+ with:
+ fetch-depth: 0
+ submodules: recursive
+ - name: Set up JDK 17
+ uses: actions/setup-java@46c56d6f92c88cf540acf95a12a4a41197499222
with:
- java-version: '8'
+ java-version: '17'
distribution: 'temurin'
cache: maven
- server-id: ossrh
- server-username: ${{ secrets.OSSRH_USERNAME }}
- server-password: ${{ secrets.OSSRH_PASSWORD }}
+ server-id: central
+ server-username: ${{ secrets.CENTRAL_USERNAME }}
+ server-password: ${{ secrets.CENTRAL_PASSWORD }}
- name: Cache local Maven repository
- uses: actions/cache@36f1e144e1c8edb0a652766b484448563d8baf46
+ uses: actions/cache@0057852bfaa89a56745cba8c7296529d2fc39830
with:
path: ~/.m2/repository
- key: ${{ runner.os }}-maven-${{ hashFiles('**/pom.xml') }}
+ key: ${{ runner.os }}-17-maven-${{ hashFiles('**/pom.xml') }}
restore-keys: |
- ${{ runner.os }}-maven-
+ ${{ runner.os }}-17-maven-
- name: Configure GPG Key
run: |
@@ -49,7 +53,7 @@ jobs:
run: mvn --batch-mode --update-snapshots verify
- name: Upload coverage to Codecov
- uses: codecov/codecov-action@v5.3.1
+ uses: codecov/codecov-action@v5.5.1
with:
token: ${{ secrets.CODECOV_TOKEN }} # not required for public repos
flags: unittests # optional
@@ -60,11 +64,11 @@ jobs:
# Add -SNAPSHOT before deploy
- name: Add SNAPSHOT
run: mvn versions:set -DnewVersion='${project.version}-SNAPSHOT'
-
+
- name: Deploy
run: |
mvn --batch-mode \
- --settings release/m2-settings.xml clean deploy
+ --settings release/m2-settings.xml -DskipTests clean deploy
env:
- OSSRH_USERNAME: ${{ secrets.OSSRH_USERNAME }}
- OSSRH_PASSWORD: ${{ secrets.OSSRH_PASSWORD }}
+ CENTRAL_USERNAME: ${{ secrets.CENTRAL_USERNAME }}
+ CENTRAL_PASSWORD: ${{ secrets.CENTRAL_PASSWORD }}
diff --git a/.github/workflows/pullrequest.yml b/.github/workflows/pullrequest.yml
index d7ade6207..7e815801d 100644
--- a/.github/workflows/pullrequest.yml
+++ b/.github/workflows/pullrequest.yml
@@ -7,36 +7,49 @@ permissions:
jobs:
build:
- runs-on: ubuntu-latest
+ strategy:
+ matrix:
+ os: [ubuntu-latest]
+ build:
+ - java: 17
+ profile: codequality
+ - java: 11
+ profile: java11
+ name: with Java ${{ matrix.build.java }}
+ runs-on: ${{ matrix.os}}
steps:
- name: Check out the code
- uses: actions/checkout@85e6279cec87321a52edac9c87bce653a07cf6c2
+ uses: actions/checkout@1af3b93b6815bc44a9784bd300feb67ff0d1eeb3
+ with:
+ fetch-depth: 0
+ submodules: recursive
- - name: Set up JDK 8
- uses: actions/setup-java@3a4f6e1af504cf6a31855fa899c6aa5355ba6c12
+ - name: Set up JDK ${{ matrix.build.java }}
+ uses: actions/setup-java@46c56d6f92c88cf540acf95a12a4a41197499222
with:
- java-version: '8'
- distribution: 'temurin'
- cache: maven
+ java-version: ${{ matrix.build.java }}
+ distribution: 'temurin'
+ cache: maven
- name: Initialize CodeQL
- uses: github/codeql-action/init@0701025a8b1600e416be4f3bb5a830b1aa6af01e
+ uses: github/codeql-action/init@ce729e4d353d580e6cacd6a8cf2921b72e5e310a
with:
languages: java
- name: Cache local Maven repository
- uses: actions/cache@36f1e144e1c8edb0a652766b484448563d8baf46
+ uses: actions/cache@0057852bfaa89a56745cba8c7296529d2fc39830
with:
- path: ~/.m2/repository
- key: ${{ runner.os }}-maven-${{ hashFiles('**/pom.xml') }}
- restore-keys: |
- ${{ runner.os }}-maven-
+ path: ~/.m2/repository
+ key: ${{ runner.os }}${{ matrix.build.java }}-maven-${{ hashFiles('**/pom.xml') }}
+ restore-keys: |
+ ${{ runner.os }}${{ matrix.build.java }}-maven-
- name: Verify with Maven
- run: mvn --batch-mode --update-snapshots --activate-profiles e2e verify
+ run: mvn --batch-mode --update-snapshots --activate-profiles e2e,${{ matrix.build.profile }} verify
- - name: Upload coverage to Codecov
- uses: codecov/codecov-action@v5.3.1
+ - if: matrix.build.java == '17'
+ name: Upload coverage to Codecov
+ uses: codecov/codecov-action@v5.5.1
with:
token: ${{ secrets.CODECOV_TOKEN }} # not required for public repos
flags: unittests # optional
@@ -45,4 +58,4 @@ jobs:
verbose: true # optional (default = false)
- name: Perform CodeQL Analysis
- uses: github/codeql-action/analyze@0701025a8b1600e416be4f3bb5a830b1aa6af01e
+ uses: github/codeql-action/analyze@ce729e4d353d580e6cacd6a8cf2921b72e5e310a
diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml
index 7342889db..841441307 100644
--- a/.github/workflows/release.yml
+++ b/.github/workflows/release.yml
@@ -12,46 +12,56 @@ permissions: # added using https://github.com/step-security/secure-workflows
jobs:
release-please:
- permissions:
- contents: write # for google-github-actions/release-please-action to create release commit
- pull-requests: write # for google-github-actions/release-please-action to create release PR
runs-on: ubuntu-latest
+ permissions:
+ contents: write # for googleapis/release-please-action to create release commit
+ pull-requests: write # for googleapis/release-please-action to create release PR
+ issues: write # for googleapis/release-please-action to create labels
# Release-please creates a PR that tracks all changes
steps:
- - uses: google-github-actions/release-please-action@e4dc86ba9405554aeba3c6bb2d169500e7d3b4ee
+ - uses: googleapis/release-please-action@v4
id: release
with:
- token: ${{secrets.GITHUB_TOKEN}}
- default-branch: main
-
- # These steps are only run if this was a merged release-please PR
- - name: checkout
- if: ${{ steps.release.outputs.release_created }}
- uses: actions/checkout@85e6279cec87321a52edac9c87bce653a07cf6c2
- - name: Set up JDK 8
- if: ${{ steps.release.outputs.release_created }}
- uses: actions/setup-java@3a4f6e1af504cf6a31855fa899c6aa5355ba6c12
+ token: ${{secrets.RELEASE_PLEASE_ACTION_TOKEN}}
+ outputs:
+ release_created: ${{ fromJSON(steps.release.outputs.paths_released)[0] != null }} # if we have a single release path, do the release
+
+ publish:
+ environment: publish
+ runs-on: ubuntu-latest
+ permissions:
+ contents: read
+ needs: release-please
+ if: ${{ fromJSON(needs.release-please.outputs.release_created || false) }}
+
+ steps:
+ - name: Checkout Repository
+ uses: actions/checkout@1af3b93b6815bc44a9784bd300feb67ff0d1eeb3
+ with:
+ fetch-depth: 0
+ submodules: recursive
+
+ - name: Set up JDK 17
+ uses: actions/setup-java@46c56d6f92c88cf540acf95a12a4a41197499222
with:
- java-version: '8'
+ java-version: '17'
distribution: 'temurin'
cache: maven
- server-id: ossrh
- server-username: ${{ secrets.OSSRH_USERNAME }}
- server-password: ${{ secrets.OSSRH_PASSWORD }}
+ server-id: central
+ server-username: ${{ secrets.CENTRAL_USERNAME }}
+ server-password: ${{ secrets.CENTRAL_PASSWORD }}
- name: Configure GPG Key
- if: ${{ steps.release.outputs.release_created }}
run: |
echo -n "$GPG_SIGNING_KEY" | base64 --decode | gpg --import
env:
GPG_SIGNING_KEY: ${{ secrets.GPG_SIGNING_KEY }}
- name: Deploy
- if: ${{ steps.release.outputs.release_created }}
run: |
mvn --batch-mode \
- --settings release/m2-settings.xml clean deploy
+ --settings release/m2-settings.xml -DskipTests clean deploy
env:
- OSSRH_USERNAME: ${{ secrets.OSSRH_USERNAME }}
- OSSRH_PASSWORD: ${{ secrets.OSSRH_PASSWORD }}
\ No newline at end of file
+ CENTRAL_USERNAME: ${{ secrets.CENTRAL_USERNAME }}
+ CENTRAL_PASSWORD: ${{ secrets.CENTRAL_PASSWORD }}
diff --git a/.github/workflows/static-code-scanning.yaml b/.github/workflows/static-code-scanning.yaml
index 8e6d4ed29..c2de02806 100644
--- a/.github/workflows/static-code-scanning.yaml
+++ b/.github/workflows/static-code-scanning.yaml
@@ -29,16 +29,16 @@ jobs:
steps:
- name: Checkout repository
- uses: actions/checkout@85e6279cec87321a52edac9c87bce653a07cf6c2
+ uses: actions/checkout@1af3b93b6815bc44a9784bd300feb67ff0d1eeb3
# Initializes the CodeQL tools for scanning.
- name: Initialize CodeQL
- uses: github/codeql-action/init@0701025a8b1600e416be4f3bb5a830b1aa6af01e
+ uses: github/codeql-action/init@ce729e4d353d580e6cacd6a8cf2921b72e5e310a
with:
languages: java
- name: Autobuild
- uses: github/codeql-action/autobuild@0701025a8b1600e416be4f3bb5a830b1aa6af01e
+ uses: github/codeql-action/autobuild@ce729e4d353d580e6cacd6a8cf2921b72e5e310a
- name: Perform CodeQL Analysis
- uses: github/codeql-action/analyze@0701025a8b1600e416be4f3bb5a830b1aa6af01e
+ uses: github/codeql-action/analyze@ce729e4d353d580e6cacd6a8cf2921b72e5e310a
diff --git a/.gitignore b/.gitignore
index a7575d545..dfc5642e5 100644
--- a/.gitignore
+++ b/.gitignore
@@ -10,6 +10,7 @@ target
# vscode stuff - we may want to use a more specific pattern later if we'd like to suggest editor configurations
.vscode/
+.cursor
# used for spec compliance tooling
java-report.json
diff --git a/.mvn/wrapper/maven-wrapper.properties b/.mvn/wrapper/maven-wrapper.properties
index d58dfb70b..44f3cf2c1 100644
--- a/.mvn/wrapper/maven-wrapper.properties
+++ b/.mvn/wrapper/maven-wrapper.properties
@@ -1,19 +1,2 @@
-# Licensed to the Apache Software Foundation (ASF) under one
-# or more contributor license agreements. See the NOTICE file
-# distributed with this work for additional information
-# regarding copyright ownership. The ASF licenses this file
-# to you under the Apache License, Version 2.0 (the
-# "License"); you may not use this file except in compliance
-# with the License. You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing,
-# software distributed under the License is distributed on an
-# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-# KIND, either express or implied. See the License for the
-# specific language governing permissions and limitations
-# under the License.
-wrapperVersion=3.3.2
distributionType=only-script
-distributionUrl=https://repo.maven.apache.org/maven2/org/apache/maven/apache-maven/3.9.9/apache-maven-3.9.9-bin.zip
+distributionUrl=https://repo.maven.apache.org/maven2/org/apache/maven/apache-maven/3.9.11/apache-maven-3.9.11-bin.zip
diff --git a/.release-please-manifest.json b/.release-please-manifest.json
index e2d18dc18..f386789e1 100644
--- a/.release-please-manifest.json
+++ b/.release-please-manifest.json
@@ -1 +1 @@
-{".":"1.14.0"}
\ No newline at end of file
+{".":"1.18.2"}
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 3f7000d46..cbb4c6135 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,5 +1,448 @@
# Changelog
+## [1.18.2](https://github.com/open-feature/java-sdk/compare/v1.18.1...v1.18.2) (2025-10-06)
+
+
+### ๐ Bug Fixes
+
+* deployment failure because no tests were run by VMLens ([#1634](https://github.com/open-feature/java-sdk/issues/1634)) ([f6cb985](https://github.com/open-feature/java-sdk/commit/f6cb98556be3dacdb4e8d7770014dc2e7df65b6b))
+* **deps:** update dependency io.cucumber:cucumber-bom to v7.29.0 ([#1624](https://github.com/open-feature/java-sdk/issues/1624)) ([d0f9647](https://github.com/open-feature/java-sdk/commit/d0f9647fd09a8602ee47aae7778dbf7534c3fbd5))
+* **deps:** update dependency io.cucumber:cucumber-bom to v7.30.0 ([#1649](https://github.com/open-feature/java-sdk/issues/1649)) ([07bda4a](https://github.com/open-feature/java-sdk/commit/07bda4a99127e2c35d1e5323516c59f5beed20f8))
+* **deps:** update dependency org.junit:junit-bom to v5.14.0 ([#1646](https://github.com/open-feature/java-sdk/issues/1646)) ([2da33d6](https://github.com/open-feature/java-sdk/commit/2da33d60bc51ff9adadc3113d53106162e42f4b7))
+* **deps:** update dependency org.junit:junit-bom to v6 ([#1647](https://github.com/open-feature/java-sdk/issues/1647)) ([8893bf3](https://github.com/open-feature/java-sdk/commit/8893bf3817053e416d0d8656890441095357411b))
+* **deps:** update dependency org.projectlombok:lombok to v1.18.42 ([#1616](https://github.com/open-feature/java-sdk/issues/1616)) ([6dcd21f](https://github.com/open-feature/java-sdk/commit/6dcd21f559477c1b473cd30e459ca7241c4f7210))
+* for [#1611](https://github.com/open-feature/java-sdk/issues/1611) ([f6cb985](https://github.com/open-feature/java-sdk/commit/f6cb98556be3dacdb4e8d7770014dc2e7df65b6b))
+* improve vmlens handling ([#1628](https://github.com/open-feature/java-sdk/issues/1628)) ([fb3144a](https://github.com/open-feature/java-sdk/commit/fb3144a0b5e2f02e8af33d746fb6c426724adede))
+
+
+### โจ New Features
+
+* add hook data support ([#1620](https://github.com/open-feature/java-sdk/issues/1620)) ([52c7f99](https://github.com/open-feature/java-sdk/commit/52c7f9906672320d08ad6e840dbaf4978d5fb6e2))
+
+
+### ๐งน Chore
+
+* **deps:** update actions/cache digest to 0057852 ([#1631](https://github.com/open-feature/java-sdk/issues/1631)) ([c1944d2](https://github.com/open-feature/java-sdk/commit/c1944d2b1c1a85efb3b4f76a5836dfc0e1c9124b))
+* **deps:** update amannn/action-semantic-pull-request digest to e49f57c ([#1648](https://github.com/open-feature/java-sdk/issues/1648)) ([badac4f](https://github.com/open-feature/java-sdk/commit/badac4f6aaf8fb1a71f4a50f906b4c74603f10ae))
+* **deps:** update dependency com.diffplug.spotless:spotless-maven-plugin to v3 ([#1632](https://github.com/open-feature/java-sdk/issues/1632)) ([0596ada](https://github.com/open-feature/java-sdk/commit/0596adac7dde1d9b5bf0da3763799d965870e828))
+* **deps:** update dependency com.google.guava:guava to v33.5.0-jre ([#1615](https://github.com/open-feature/java-sdk/issues/1615)) ([3ef41f5](https://github.com/open-feature/java-sdk/commit/3ef41f5225b93ca9d4b975c265d4ec41dbd91717))
+* **deps:** update dependency com.puppycrawl.tools:checkstyle to v11.1.0 ([#1640](https://github.com/open-feature/java-sdk/issues/1640)) ([b686932](https://github.com/open-feature/java-sdk/commit/b686932fa86138e02bddaab0be79d61f39946a02))
+* **deps:** update dependency com.vmlens:api to v1.2.15 ([#1636](https://github.com/open-feature/java-sdk/issues/1636)) ([9bffa0a](https://github.com/open-feature/java-sdk/commit/9bffa0a45aaea6fb5ecf7b489c02cd502fc2d93c))
+* **deps:** update dependency com.vmlens:api to v1.2.16 ([#1642](https://github.com/open-feature/java-sdk/issues/1642)) ([4c18cc4](https://github.com/open-feature/java-sdk/commit/4c18cc4ee502030935796e98272fd45b6c394c11))
+* **deps:** update dependency com.vmlens:vmlens-maven-plugin to v1.2.15 ([#1637](https://github.com/open-feature/java-sdk/issues/1637)) ([139c9b2](https://github.com/open-feature/java-sdk/commit/139c9b21b73717e52fde4970561009cbd27addaa))
+* **deps:** update dependency com.vmlens:vmlens-maven-plugin to v1.2.16 ([#1643](https://github.com/open-feature/java-sdk/issues/1643)) ([01ce26a](https://github.com/open-feature/java-sdk/commit/01ce26afc9b8a4bc098dc3406e65c483fd940d15))
+* **deps:** update dependency maven-wrapper to v3.3.4 ([#1638](https://github.com/open-feature/java-sdk/issues/1638)) ([69a87a8](https://github.com/open-feature/java-sdk/commit/69a87a81e8f4796c5d4a895b9379c0103765ba3d))
+* **deps:** update dependency org.apache.maven.plugins:maven-compiler-plugin to v3.14.1 ([#1625](https://github.com/open-feature/java-sdk/issues/1625)) ([55c344a](https://github.com/open-feature/java-sdk/commit/55c344a8323fa94f4b890d5a119976e879bbb43c))
+* **deps:** update dependency org.apache.maven.plugins:maven-dependency-plugin to v3.9.0 ([#1651](https://github.com/open-feature/java-sdk/issues/1651)) ([bb42184](https://github.com/open-feature/java-sdk/commit/bb4218456e87391ae4ad96999e6cb49f78eab0aa))
+* **deps:** update dependency org.apache.maven.plugins:maven-javadoc-plugin to v3.12.0 ([#1623](https://github.com/open-feature/java-sdk/issues/1623)) ([eeda099](https://github.com/open-feature/java-sdk/commit/eeda09980cc85a538f0c41fef10bf285b0829761))
+* **deps:** update dependency org.assertj:assertj-core to v3.27.5 ([#1619](https://github.com/open-feature/java-sdk/issues/1619)) ([d4beca7](https://github.com/open-feature/java-sdk/commit/d4beca71bb60359b88e739153ff96ffc11aa74ef))
+* **deps:** update dependency org.assertj:assertj-core to v3.27.6 ([#1627](https://github.com/open-feature/java-sdk/issues/1627)) ([14f550f](https://github.com/open-feature/java-sdk/commit/14f550fd4ff9223437cc36d6cc1b248125a68e3c))
+* **deps:** update dependency org.codehaus.mojo:exec-maven-plugin to v3.6.0 ([#1645](https://github.com/open-feature/java-sdk/issues/1645)) ([261ea5d](https://github.com/open-feature/java-sdk/commit/261ea5dfa6b73d6e538388315719b0f06f417927))
+* **deps:** update dependency org.codehaus.mojo:exec-maven-plugin to v3.6.1 ([#1653](https://github.com/open-feature/java-sdk/issues/1653)) ([71dfb08](https://github.com/open-feature/java-sdk/commit/71dfb08a096a03fb02e44be4ada796e99b053cf0))
+* **deps:** update dependency org.mockito:mockito-core to v5.20.0 ([#1622](https://github.com/open-feature/java-sdk/issues/1622)) ([857fb9d](https://github.com/open-feature/java-sdk/commit/857fb9d78c509ee9c1087c355eb0fdb4ffdb668e))
+* **deps:** update dependency org.sonatype.central:central-publishing-maven-plugin to v0.9.0 ([#1630](https://github.com/open-feature/java-sdk/issues/1630)) ([014e82a](https://github.com/open-feature/java-sdk/commit/014e82af10ae478596c65c80d2cf92fc843339ed))
+* **deps:** update github/codeql-action digest to 0337c4c ([#1621](https://github.com/open-feature/java-sdk/issues/1621)) ([6cf64d6](https://github.com/open-feature/java-sdk/commit/6cf64d6b0c0ae351a707d70257380f2bce81a82e))
+* **deps:** update github/codeql-action digest to 065c6cf ([#1652](https://github.com/open-feature/java-sdk/issues/1652)) ([fe44e51](https://github.com/open-feature/java-sdk/commit/fe44e519c9de5dbc00b25aeaa6f1bf31809688f0))
+* **deps:** update github/codeql-action digest to 12dda79 ([#1618](https://github.com/open-feature/java-sdk/issues/1618)) ([17d0e48](https://github.com/open-feature/java-sdk/commit/17d0e487f31864facc0e69ee76352cab82b6b6b7))
+* **deps:** update github/codeql-action digest to 21a7ba3 ([#1650](https://github.com/open-feature/java-sdk/issues/1650)) ([1de446d](https://github.com/open-feature/java-sdk/commit/1de446d38ee2abdc3149f8eff374c617c26462fb))
+* **deps:** update github/codeql-action digest to 36adfa7 ([#1641](https://github.com/open-feature/java-sdk/issues/1641)) ([2155cc9](https://github.com/open-feature/java-sdk/commit/2155cc94371a0147fafc3246e7d4e4b9d9b7a5a3))
+* **deps:** update github/codeql-action digest to 6a87ebe ([#1639](https://github.com/open-feature/java-sdk/issues/1639)) ([58b6575](https://github.com/open-feature/java-sdk/commit/58b6575410b75760d5402f3f927dc8a2e62e9654))
+* **deps:** update github/codeql-action digest to 80cb6b5 ([#1644](https://github.com/open-feature/java-sdk/issues/1644)) ([6b922a2](https://github.com/open-feature/java-sdk/commit/6b922a2a6107cff7f951dcaf9e1c09609aeade83))
+* **deps:** update github/codeql-action digest to 94a9b7a ([#1635](https://github.com/open-feature/java-sdk/issues/1635)) ([f9796e8](https://github.com/open-feature/java-sdk/commit/f9796e8e1623bdac0ec52b7102e11759d3e449d8))
+* **deps:** update github/codeql-action digest to e4b85ab ([#1626](https://github.com/open-feature/java-sdk/issues/1626)) ([99a997d](https://github.com/open-feature/java-sdk/commit/99a997dcc594e06662cc3509e9c8698611893567))
+
+## [1.18.1](https://github.com/open-feature/java-sdk/compare/v1.18.0...v1.18.1) (2025-09-17)
+
+
+### ๐ Bug Fixes
+
+* **deps:** update dependency com.fasterxml.jackson:jackson-bom to v2.20.0 ([#1604](https://github.com/open-feature/java-sdk/issues/1604)) ([b693390](https://github.com/open-feature/java-sdk/commit/b69339067a75a524911dded9798a06e58d628bce))
+* **deps:** update dependency com.github.spotbugs:spotbugs to v4.9.6 ([#1609](https://github.com/open-feature/java-sdk/issues/1609)) ([45ff89f](https://github.com/open-feature/java-sdk/commit/45ff89f530e8c73636618676b9db46c61235df57))
+* revert hook data to resolve bytecode incompatibility ([#1613](https://github.com/open-feature/java-sdk/issues/1613)) ([9845601](https://github.com/open-feature/java-sdk/commit/984560196d4a34fb21c8946d1dc675cf6565e90f))
+
+
+### ๐งน Chore
+
+* **deps:** update actions/setup-java digest to ead9eaa ([#1608](https://github.com/open-feature/java-sdk/issues/1608)) ([a40667e](https://github.com/open-feature/java-sdk/commit/a40667e9cb635f9ba31f6975ba72bc5932fca094))
+* **deps:** update dependency com.github.spotbugs:spotbugs-maven-plugin to v4.9.6.0 ([#1612](https://github.com/open-feature/java-sdk/issues/1612)) ([fa23e96](https://github.com/open-feature/java-sdk/commit/fa23e960ff9dc52b5c44b56e521485ca03e0e650))
+* **deps:** update dependency com.vmlens:vmlens-maven-plugin to v1.2.14 ([#1606](https://github.com/open-feature/java-sdk/issues/1606)) ([a92a367](https://github.com/open-feature/java-sdk/commit/a92a367fef71cc9ec26f6b1b6609fb8e6b2543bc))
+* **deps:** update dependency dev.cel:cel to v0.11.0 ([#1603](https://github.com/open-feature/java-sdk/issues/1603)) ([e792221](https://github.com/open-feature/java-sdk/commit/e7922212d8cd964a8a24dacc518ff31c77fcfae6))
+* **deps:** update github/codeql-action digest to 573acd9 ([#1600](https://github.com/open-feature/java-sdk/issues/1600)) ([6fb139f](https://github.com/open-feature/java-sdk/commit/6fb139f8425fb76368b1e1baa745aa182f8c13f7))
+* fix checkout ([#1614](https://github.com/open-feature/java-sdk/issues/1614)) ([fbf2a75](https://github.com/open-feature/java-sdk/commit/fbf2a752647817d3e25d4f8b67893ba5e8f89b7a))
+* relax coverage ([69c5a12](https://github.com/open-feature/java-sdk/commit/69c5a1244283d22af0119f534270726a8c520367))
+
+## [1.18.0](https://github.com/open-feature/java-sdk/compare/v1.17.0...v1.18.0) (2025-09-16)
+
+
+### ๐ Bug Fixes
+
+* **deps:** update dependency com.github.spotbugs:spotbugs to v4.9.4 ([#1548](https://github.com/open-feature/java-sdk/issues/1548)) ([f2fef65](https://github.com/open-feature/java-sdk/commit/f2fef65eb580b1960ad15b2c46ebe40855551be3))
+* **deps:** update dependency com.github.spotbugs:spotbugs to v4.9.5 ([#1598](https://github.com/open-feature/java-sdk/issues/1598)) ([5474c73](https://github.com/open-feature/java-sdk/commit/5474c736f711ed06cbca2bd0d4d0cfd458a54d10))
+* **deps:** update dependency io.cucumber:cucumber-bom to v7.27.1 ([#1562](https://github.com/open-feature/java-sdk/issues/1562)) ([508bdac](https://github.com/open-feature/java-sdk/commit/508bdac4f075e2cd374dd1728919cfc1619d0097))
+* **deps:** update dependency io.cucumber:cucumber-bom to v7.27.2 ([#1566](https://github.com/open-feature/java-sdk/issues/1566)) ([8a9f251](https://github.com/open-feature/java-sdk/commit/8a9f25177f2d4bab1b5215f172bbb8ed1a5ad788))
+* **deps:** update dependency io.cucumber:cucumber-bom to v7.28.2 ([#1593](https://github.com/open-feature/java-sdk/issues/1593)) ([ca72b19](https://github.com/open-feature/java-sdk/commit/ca72b19d33985dfaae1cda009afd6795c5752259))
+* **deps:** update dependency org.projectlombok:lombok to v1.18.40 ([#1597](https://github.com/open-feature/java-sdk/issues/1597)) ([e181276](https://github.com/open-feature/java-sdk/commit/e1812767b684b21d417e31dadc8d031cd64cdab1))
+* javadoc error on-merge action ([#1599](https://github.com/open-feature/java-sdk/issues/1599)) ([c126bdb](https://github.com/open-feature/java-sdk/commit/c126bdb2d772a85417dbb77b92079a8a2107b8b6))
+* make builder visible for javadocs, move javadoc gen to codequality profile ([c126bdb](https://github.com/open-feature/java-sdk/commit/c126bdb2d772a85417dbb77b92079a8a2107b8b6))
+
+
+### โจ New Features
+
+* add hook data ([#1587](https://github.com/open-feature/java-sdk/issues/1587)) ([1b08e3d](https://github.com/open-feature/java-sdk/commit/1b08e3db42635bbe79c61437db2359bd74a98348))
+
+
+### ๐งน Chore
+
+* **deps:** update actions/cache digest to 0400d5f ([#1544](https://github.com/open-feature/java-sdk/issues/1544)) ([050379b](https://github.com/open-feature/java-sdk/commit/050379be110b7a980cf5cc02ddf23e00a7ee7202))
+* **deps:** update actions/cache digest to 358a730 ([#1541](https://github.com/open-feature/java-sdk/issues/1541)) ([6efc2ee](https://github.com/open-feature/java-sdk/commit/6efc2ee1e701daf38e3efc2f115dc93025a0e2e2))
+* **deps:** update actions/cache digest to 638ed79 ([#1549](https://github.com/open-feature/java-sdk/issues/1549)) ([7f487ee](https://github.com/open-feature/java-sdk/commit/7f487ee7ecd1c69a63d22eca140bc422a0afc963))
+* **deps:** update actions/checkout digest to 08c6903 ([#1550](https://github.com/open-feature/java-sdk/issues/1550)) ([527e3f8](https://github.com/open-feature/java-sdk/commit/527e3f836f664ecace1018de84502592ee75007c))
+* **deps:** update actions/checkout digest to ff7abcd ([#1554](https://github.com/open-feature/java-sdk/issues/1554)) ([35fe5b4](https://github.com/open-feature/java-sdk/commit/35fe5b41bc971f8bc41b82b8c0ef50d719071301))
+* **deps:** update actions/setup-java digest to 0913e9a ([#1572](https://github.com/open-feature/java-sdk/issues/1572)) ([58c82de](https://github.com/open-feature/java-sdk/commit/58c82de9656562f137feafb9e6eff20521695803))
+* **deps:** update actions/setup-java digest to a7ab372 ([#1589](https://github.com/open-feature/java-sdk/issues/1589)) ([a08ff4d](https://github.com/open-feature/java-sdk/commit/a08ff4d96ccf9236ad882892280b600a05409394))
+* **deps:** update actions/setup-java digest to dded088 ([#1574](https://github.com/open-feature/java-sdk/issues/1574)) ([d332224](https://github.com/open-feature/java-sdk/commit/d33222439e84435baeb0a49d33651208e659ad27))
+* **deps:** update amannn/action-semantic-pull-request digest to 24e6f01 ([#1568](https://github.com/open-feature/java-sdk/issues/1568)) ([c8d48e1](https://github.com/open-feature/java-sdk/commit/c8d48e1a739f02b25e7980dcd5652851756729f2))
+* **deps:** update amannn/action-semantic-pull-request digest to 677b895 ([#1570](https://github.com/open-feature/java-sdk/issues/1570)) ([fb6ab35](https://github.com/open-feature/java-sdk/commit/fb6ab353b403542a1f7e6ccafb07e25ae1d5e2be))
+* **deps:** update amannn/action-semantic-pull-request digest to a46a7c8 ([#1563](https://github.com/open-feature/java-sdk/issues/1563)) ([47af527](https://github.com/open-feature/java-sdk/commit/47af5279d6abd0080eae16d630bd202976f9a4b1))
+* **deps:** update amannn/action-semantic-pull-request digest to e7d011b ([#1577](https://github.com/open-feature/java-sdk/issues/1577)) ([532ad2f](https://github.com/open-feature/java-sdk/commit/532ad2f3d404753189a529cdc262ba6ef8d3d586))
+* **deps:** update amannn/action-semantic-pull-request digest to fdd4d3d ([#1553](https://github.com/open-feature/java-sdk/issues/1553)) ([8a6c796](https://github.com/open-feature/java-sdk/commit/8a6c79627a492eb61ed35ffa91035b0737598b64))
+* **deps:** update codecov/codecov-action action to v5.5.0 ([#1573](https://github.com/open-feature/java-sdk/issues/1573)) ([2c2b380](https://github.com/open-feature/java-sdk/commit/2c2b380e13d2be5a988b70212ea243efdb60999b))
+* **deps:** update codecov/codecov-action action to v5.5.1 ([#1591](https://github.com/open-feature/java-sdk/issues/1591)) ([e47913a](https://github.com/open-feature/java-sdk/commit/e47913a07ee064fe340db978250710a7cb17795d))
+* **deps:** update dependency com.github.spotbugs:spotbugs-maven-plugin to v4.9.4.0 ([#1576](https://github.com/open-feature/java-sdk/issues/1576)) ([894165d](https://github.com/open-feature/java-sdk/commit/894165ddd7216dc30c1ca4c9f43c0a4c21970f17))
+* **deps:** update dependency com.github.spotbugs:spotbugs-maven-plugin to v4.9.4.2 ([#1592](https://github.com/open-feature/java-sdk/issues/1592)) ([8b3f7f0](https://github.com/open-feature/java-sdk/commit/8b3f7f07f4aa555301d484544939fa5a0b4de746))
+* **deps:** update dependency com.github.spotbugs:spotbugs-maven-plugin to v4.9.5.0 ([#1601](https://github.com/open-feature/java-sdk/issues/1601)) ([a7964be](https://github.com/open-feature/java-sdk/commit/a7964beda575c46eddc15f44d21c23b5a52802c7))
+* **deps:** update dependency com.puppycrawl.tools:checkstyle to v11 ([#1543](https://github.com/open-feature/java-sdk/issues/1543)) ([d2f85d5](https://github.com/open-feature/java-sdk/commit/d2f85d5a9e42c0e336546684b27a1e77edc4c620))
+* **deps:** update dependency com.puppycrawl.tools:checkstyle to v11.0.1 ([#1585](https://github.com/open-feature/java-sdk/issues/1585)) ([8dd40fa](https://github.com/open-feature/java-sdk/commit/8dd40fabcae6a90ee7abe1b0a0d8f55f345e3331))
+* **deps:** update dependency maven-wrapper to v3.3.3 ([#1584](https://github.com/open-feature/java-sdk/issues/1584)) ([cba90dd](https://github.com/open-feature/java-sdk/commit/cba90dd227514464fd90bd605f73c358748c09e1))
+* **deps:** update dependency net.bytebuddy:byte-buddy to v1.17.7 ([#1560](https://github.com/open-feature/java-sdk/issues/1560)) ([124c26f](https://github.com/open-feature/java-sdk/commit/124c26f6ea2d20cebb7520afcd94ab6b6c8c8e7b))
+* **deps:** update dependency net.bytebuddy:byte-buddy-agent to v1.17.7 ([#1561](https://github.com/open-feature/java-sdk/issues/1561)) ([84887bf](https://github.com/open-feature/java-sdk/commit/84887bfc86eb4905f52bce4641c35a8909f2c463))
+* **deps:** update dependency org.apache.maven.plugins:maven-failsafe-plugin to v3.5.4 ([#1596](https://github.com/open-feature/java-sdk/issues/1596)) ([3606154](https://github.com/open-feature/java-sdk/commit/3606154aa7ded57f41c324559268335531606b6c))
+* **deps:** update dependency org.apache.maven.plugins:maven-javadoc-plugin to v3.11.3 ([#1559](https://github.com/open-feature/java-sdk/issues/1559)) ([6fbc9d6](https://github.com/open-feature/java-sdk/commit/6fbc9d6cca5716b7477f84ff4093ccc6af06d4e6))
+* **deps:** update dependency org.apache.maven.plugins:maven-surefire-plugin to v3.5.4 ([#1595](https://github.com/open-feature/java-sdk/issues/1595)) ([a17bd3a](https://github.com/open-feature/java-sdk/commit/a17bd3a388927781b86e91064748a71670bb2a2a))
+* **deps:** update dependency org.assertj:assertj-core to v3.27.4 ([#1546](https://github.com/open-feature/java-sdk/issues/1546)) ([c4fe7d2](https://github.com/open-feature/java-sdk/commit/c4fe7d2e81510db4eaa13a4d0046827efecd8a79))
+* **deps:** update dependency org.mockito:mockito-core to v5.19.0 ([#1557](https://github.com/open-feature/java-sdk/issues/1557)) ([dff5412](https://github.com/open-feature/java-sdk/commit/dff54123ab38fd3ad59809e5f863b6ace17e4da4))
+* **deps:** update github/codeql-action digest to 02ab253 ([#1583](https://github.com/open-feature/java-sdk/issues/1583)) ([080fc6e](https://github.com/open-feature/java-sdk/commit/080fc6e9a60c15eb748891245258c9c5378e4248))
+* **deps:** update github/codeql-action digest to 0d33fd9 ([#1590](https://github.com/open-feature/java-sdk/issues/1590)) ([9e4881f](https://github.com/open-feature/java-sdk/commit/9e4881fdcb577a693cfe587b58dce5a74fb3caf4))
+* **deps:** update github/codeql-action digest to 2330521 ([#1558](https://github.com/open-feature/java-sdk/issues/1558)) ([f1165da](https://github.com/open-feature/java-sdk/commit/f1165da1b910efda6dbe486a21eb7985cccf11ae))
+* **deps:** update github/codeql-action digest to 4474150 ([#1547](https://github.com/open-feature/java-sdk/issues/1547)) ([09b3138](https://github.com/open-feature/java-sdk/commit/09b31383e3b7e693ec43d6016486e3ededf8c2de))
+* **deps:** update github/codeql-action digest to 5b49155 ([#1575](https://github.com/open-feature/java-sdk/issues/1575)) ([d9c1df0](https://github.com/open-feature/java-sdk/commit/d9c1df0c5ec247f64c37648128d56b7e83444ca9))
+* **deps:** update github/codeql-action digest to 6dee5bc ([#1569](https://github.com/open-feature/java-sdk/issues/1569)) ([907b75d](https://github.com/open-feature/java-sdk/commit/907b75d3481e71621249b0246e0ca67c42c9a890))
+* **deps:** update github/codeql-action digest to 6ec994e ([#1564](https://github.com/open-feature/java-sdk/issues/1564)) ([19c2a12](https://github.com/open-feature/java-sdk/commit/19c2a1272a34040f3ac2b603c2bcb645f3707a82))
+* **deps:** update github/codeql-action digest to 6fe50b2 ([#1545](https://github.com/open-feature/java-sdk/issues/1545)) ([866235e](https://github.com/open-feature/java-sdk/commit/866235e494c229b3d47df80146199db4204b2ece))
+* **deps:** update github/codeql-action digest to 777f917 ([#1556](https://github.com/open-feature/java-sdk/issues/1556)) ([03a8018](https://github.com/open-feature/java-sdk/commit/03a8018098bbced558e157b60e7ba3ff18527db6))
+* **deps:** update github/codeql-action digest to 7eb43b0 ([#1555](https://github.com/open-feature/java-sdk/issues/1555)) ([88ded5d](https://github.com/open-feature/java-sdk/commit/88ded5d9290b3c008a597cf55bb1e1f4c05e40ec))
+* **deps:** update github/codeql-action digest to a880e53 ([#1581](https://github.com/open-feature/java-sdk/issues/1581)) ([5efac69](https://github.com/open-feature/java-sdk/commit/5efac69dae28ff26227e5a9e83c6edbea9b9b6b5))
+* **deps:** update github/codeql-action digest to aa90e97 ([#1594](https://github.com/open-feature/java-sdk/issues/1594)) ([5df4317](https://github.com/open-feature/java-sdk/commit/5df4317caa97bdd055ec1f809d2b5e49642b5312))
+* **deps:** update github/codeql-action digest to b1228d0 ([#1540](https://github.com/open-feature/java-sdk/issues/1540)) ([bc58780](https://github.com/open-feature/java-sdk/commit/bc587809341d60eeb575b0d58d75b35972b92053))
+* **deps:** update github/codeql-action digest to bbfff2f ([#1538](https://github.com/open-feature/java-sdk/issues/1538)) ([6056877](https://github.com/open-feature/java-sdk/commit/60568776c471e7c01f8cee6b198fe6df70fc2ca5))
+* **deps:** update github/codeql-action digest to c6dcdfa ([#1551](https://github.com/open-feature/java-sdk/issues/1551)) ([ce2b6e8](https://github.com/open-feature/java-sdk/commit/ce2b6e88313ea500c2b71f0b4c06ad4a12522f3e))
+* **deps:** update github/codeql-action digest to db69a51 ([#1571](https://github.com/open-feature/java-sdk/issues/1571)) ([fc7ec65](https://github.com/open-feature/java-sdk/commit/fc7ec6511fd92c872e55e2b4f96f1dc6215ed029))
+* **deps:** update github/codeql-action digest to e2b6f0f ([#1542](https://github.com/open-feature/java-sdk/issues/1542)) ([7ccbb71](https://github.com/open-feature/java-sdk/commit/7ccbb714b305deb9fa0e31ace1bd7f044c8c57ed))
+* **deps:** update github/codeql-action digest to e96e340 ([#1565](https://github.com/open-feature/java-sdk/issues/1565)) ([ea23114](https://github.com/open-feature/java-sdk/commit/ea23114d424ce042681d6b42cdc6b2e2086ccbf8))
+* **deps:** update github/codeql-action digest to eef4c44 ([#1552](https://github.com/open-feature/java-sdk/issues/1552)) ([4bae329](https://github.com/open-feature/java-sdk/commit/4bae3294b20f19550a878f331cba2377df14f7c1))
+
+## [1.17.0](https://github.com/open-feature/java-sdk/compare/v1.16.0...v1.17.0) (2025-08-01)
+
+
+### ๐ Bug Fixes
+
+* **deps:** update dependency io.cucumber:cucumber-bom to v7.24.0 ([#1510](https://github.com/open-feature/java-sdk/issues/1510)) ([4881966](https://github.com/open-feature/java-sdk/commit/488196656ad0fbca5211e270bfc55e3d83fa9a2f))
+* **deps:** update dependency io.cucumber:cucumber-bom to v7.25.0 ([#1514](https://github.com/open-feature/java-sdk/issues/1514)) ([bf68cbd](https://github.com/open-feature/java-sdk/commit/bf68cbdedf6ce7218fadfe3a39df38019da8bcbb))
+* **deps:** update dependency io.cucumber:cucumber-bom to v7.26.0 ([#1516](https://github.com/open-feature/java-sdk/issues/1516)) ([1d3fab6](https://github.com/open-feature/java-sdk/commit/1d3fab6184b4ba45b3e4cee420e24be722c76946))
+* **deps:** update dependency io.cucumber:cucumber-bom to v7.27.0 ([#1530](https://github.com/open-feature/java-sdk/issues/1530)) ([c06d6d5](https://github.com/open-feature/java-sdk/commit/c06d6d588d529ae52d763a8dcf414b7aa1025d81))
+* **deps:** update dependency org.junit:junit-bom to v5.13.4 ([#1524](https://github.com/open-feature/java-sdk/issues/1524)) ([db47b7e](https://github.com/open-feature/java-sdk/commit/db47b7e8233970b0bf37dbb5679227d1917e15b7))
+
+
+### โจ New Features
+
+* Allow Access to ImmutableMetadata Map as unmodifiable Map ([#1534](https://github.com/open-feature/java-sdk/issues/1534)) ([09e3c3f](https://github.com/open-feature/java-sdk/commit/09e3c3faf8fe6c3e8c4d46c6fa3e3a7a2dd8f146))
+
+
+### ๐งน Chore
+
+* **deps:** update actions/checkout digest to 8edcb1b ([#1529](https://github.com/open-feature/java-sdk/issues/1529)) ([074a5ec](https://github.com/open-feature/java-sdk/commit/074a5ec52d7591e5b06801782415d1f2c930086e))
+* **deps:** update actions/setup-java digest to ae2b61d ([#1518](https://github.com/open-feature/java-sdk/issues/1518)) ([1382b36](https://github.com/open-feature/java-sdk/commit/1382b367d934feaa5effe851f8b03b02bb2482c1))
+* **deps:** update actions/setup-java digest to c190c18 ([#1508](https://github.com/open-feature/java-sdk/issues/1508)) ([908755c](https://github.com/open-feature/java-sdk/commit/908755c2c2e3abcef84f29728fd19092a9d66646))
+* **deps:** update actions/setup-java digest to e9343db ([#1535](https://github.com/open-feature/java-sdk/issues/1535)) ([7cca589](https://github.com/open-feature/java-sdk/commit/7cca589a7e2de6f3a9ec2d803dd9564205af722a))
+* **deps:** update dependency com.diffplug.spotless:spotless-maven-plugin to v2.45.0 ([#1509](https://github.com/open-feature/java-sdk/issues/1509)) ([62738f7](https://github.com/open-feature/java-sdk/commit/62738f7f16b783eabb7325bed3ac26be086b35e4))
+* **deps:** update dependency com.diffplug.spotless:spotless-maven-plugin to v2.46.0 ([#1522](https://github.com/open-feature/java-sdk/issues/1522)) ([844f6df](https://github.com/open-feature/java-sdk/commit/844f6df33542b927d38627f9a8ee5f9371e47aca))
+* **deps:** update dependency com.diffplug.spotless:spotless-maven-plugin to v2.46.1 ([#1526](https://github.com/open-feature/java-sdk/issues/1526)) ([91e451b](https://github.com/open-feature/java-sdk/commit/91e451b29b10031a9697156194af1d209ee5fec6))
+* **deps:** update dependency com.google.guava:guava to v33.4.8-jre ([#1382](https://github.com/open-feature/java-sdk/issues/1382)) ([1e8f5c8](https://github.com/open-feature/java-sdk/commit/1e8f5c880c1a0e8f0ccaa7c4b7452a051973f2b6))
+* **deps:** update dependency maven to v3.9.11 ([#1519](https://github.com/open-feature/java-sdk/issues/1519)) ([cbf7a58](https://github.com/open-feature/java-sdk/commit/cbf7a5862286dc36023095208c3e865b058dacb0))
+* **deps:** update github/codeql-action digest to 03a2a17 ([#1520](https://github.com/open-feature/java-sdk/issues/1520)) ([ecc8f7e](https://github.com/open-feature/java-sdk/commit/ecc8f7e3ade314c050c67710ae96a182534b9692))
+* **deps:** update github/codeql-action digest to 0d17ea4 ([#1517](https://github.com/open-feature/java-sdk/issues/1517)) ([5b3e365](https://github.com/open-feature/java-sdk/commit/5b3e3656f6efad1f9020937bc3ea18078c4defc8))
+* **deps:** update github/codeql-action digest to 624d0bc ([#1507](https://github.com/open-feature/java-sdk/issues/1507)) ([26716a5](https://github.com/open-feature/java-sdk/commit/26716a51cfc720bdb294b50ff3759f8ae41fe410))
+* **deps:** update github/codeql-action digest to 6f936b5 ([#1515](https://github.com/open-feature/java-sdk/issues/1515)) ([006ae75](https://github.com/open-feature/java-sdk/commit/006ae75e2b1c745476dfda35113a06fc7fbceafb))
+* **deps:** update github/codeql-action digest to 701df0e ([#1528](https://github.com/open-feature/java-sdk/issues/1528)) ([b5e335c](https://github.com/open-feature/java-sdk/commit/b5e335c3ee7865f26bcd688953204280affe2834))
+* **deps:** update github/codeql-action digest to 7273f08 ([#1537](https://github.com/open-feature/java-sdk/issues/1537)) ([4addf64](https://github.com/open-feature/java-sdk/commit/4addf6458dacbc00bb599a758d87478e6d97d369))
+* **deps:** update github/codeql-action digest to 76bf77d ([#1527](https://github.com/open-feature/java-sdk/issues/1527)) ([c05757e](https://github.com/open-feature/java-sdk/commit/c05757e4895253053e49982dbe8f16ef501fd038))
+* **deps:** update github/codeql-action digest to 7710ed1 ([#1521](https://github.com/open-feature/java-sdk/issues/1521)) ([ac3344c](https://github.com/open-feature/java-sdk/commit/ac3344c7f6293ac72523a5d0c5e61d4304c0a8b1))
+* **deps:** update github/codeql-action digest to acdac9e ([#1531](https://github.com/open-feature/java-sdk/issues/1531)) ([15aaf58](https://github.com/open-feature/java-sdk/commit/15aaf5800f0fb2b8d22415fa5d9b61dacc651932))
+* **deps:** update github/codeql-action digest to b9b3b12 ([#1533](https://github.com/open-feature/java-sdk/issues/1533)) ([477d7ce](https://github.com/open-feature/java-sdk/commit/477d7ce752ecbc5b3ad13753888d5ee6b650c390))
+* **deps:** update github/codeql-action digest to eefe1b5 ([#1523](https://github.com/open-feature/java-sdk/issues/1523)) ([66215ef](https://github.com/open-feature/java-sdk/commit/66215efaf3a18eeeb4c244775d6a72725a274097))
+* **deps:** update github/codeql-action digest to f53ec7c ([#1512](https://github.com/open-feature/java-sdk/issues/1512)) ([aa05693](https://github.com/open-feature/java-sdk/commit/aa0569379bd85d11a5f91bd1078cd9f2b3b311b4))
+
+## [1.16.0](https://github.com/open-feature/java-sdk/compare/v1.15.1...v1.16.0) (2025-07-07)
+
+
+### ๐ Bug Fixes
+
+* **deps:** update dependency io.cucumber:cucumber-bom to v7.23.0 ([#1466](https://github.com/open-feature/java-sdk/issues/1466)) ([50a6b16](https://github.com/open-feature/java-sdk/commit/50a6b168a7de40337aa51ef3d79d122030956cb9))
+* **deps:** update dependency org.junit:junit-bom to v5.13.1 ([#1475](https://github.com/open-feature/java-sdk/issues/1475)) ([545d6aa](https://github.com/open-feature/java-sdk/commit/545d6aac09dbc74c00a0a4e5c26f4ef80be22379))
+* **deps:** update dependency org.junit:junit-bom to v5.13.2 ([#1492](https://github.com/open-feature/java-sdk/issues/1492)) ([34b22e8](https://github.com/open-feature/java-sdk/commit/34b22e8d93a986fdb81500ab539b4d2fe038b618))
+* **deps:** update dependency org.junit:junit-bom to v5.13.3 ([#1505](https://github.com/open-feature/java-sdk/issues/1505)) ([957c0d1](https://github.com/open-feature/java-sdk/commit/957c0d1ba38ecc758c1ec164e40070ac93a01d68))
+* **deps:** update junit5 monorepo ([#1467](https://github.com/open-feature/java-sdk/issues/1467)) ([f8260a1](https://github.com/open-feature/java-sdk/commit/f8260a1c3a345c877eba95bfe41184ad11f6555e))
+* Reduce locking and concurrency issues ([#1478](https://github.com/open-feature/java-sdk/issues/1478)) ([ebea0fd](https://github.com/open-feature/java-sdk/commit/ebea0fdf1cf3e6f4d2e8aebf2dcb7c7e1f31acc2))
+
+
+### โจ New Features
+
+* add means of awaiting event emission, fix flaky build ([#1463](https://github.com/open-feature/java-sdk/issues/1463)) ([3dd7d5d](https://github.com/open-feature/java-sdk/commit/3dd7d5d4262f1f4461e13c13a7d64d2fa8bfd764)), closes [#1449](https://github.com/open-feature/java-sdk/issues/1449)
+
+
+### ๐งน Chore
+
+* **deps:** update actions/cache digest to 640a1c2 ([#1485](https://github.com/open-feature/java-sdk/issues/1485)) ([7c2af57](https://github.com/open-feature/java-sdk/commit/7c2af57a362ee11f757a431ee17eff3ee448bf6c))
+* **deps:** update actions/checkout digest to 09d2aca ([#1473](https://github.com/open-feature/java-sdk/issues/1473)) ([b5d873e](https://github.com/open-feature/java-sdk/commit/b5d873e44d3c41b42f11569b0fafccc0a002ebdd))
+* **deps:** update actions/setup-java digest to 67aec00 ([#1504](https://github.com/open-feature/java-sdk/issues/1504)) ([08f549a](https://github.com/open-feature/java-sdk/commit/08f549afd1fd26581b2a8e063832ec986c5e3267))
+* **deps:** update actions/setup-java digest to ebb356c ([#1490](https://github.com/open-feature/java-sdk/issues/1490)) ([e67f598](https://github.com/open-feature/java-sdk/commit/e67f5983573afff805a56ef18584d1a7291ccafc))
+* **deps:** update codecov/codecov-action action to v5.4.3 ([#1454](https://github.com/open-feature/java-sdk/issues/1454)) ([e337939](https://github.com/open-feature/java-sdk/commit/e3379395e6bfb0ce811d8372761a3cb015ad2cde))
+* **deps:** update dependency com.diffplug.spotless:spotless-maven-plugin to v2.44.5 ([#1462](https://github.com/open-feature/java-sdk/issues/1462)) ([40b319c](https://github.com/open-feature/java-sdk/commit/40b319c5de0461bec13f76978ae09edc958310cd))
+* **deps:** update dependency com.github.spotbugs:spotbugs-maven-plugin to v4.9.3.1 ([#1493](https://github.com/open-feature/java-sdk/issues/1493)) ([b64efe8](https://github.com/open-feature/java-sdk/commit/b64efe82d993defe070dfeb9aa60e740ccf757cd))
+* **deps:** update dependency com.github.spotbugs:spotbugs-maven-plugin to v4.9.3.2 ([#1496](https://github.com/open-feature/java-sdk/issues/1496)) ([fc430c3](https://github.com/open-feature/java-sdk/commit/fc430c3e1d57a532d8c0c879c3e7e25c46d4ad84))
+* **deps:** update dependency com.puppycrawl.tools:checkstyle to v10.24.0 ([#1458](https://github.com/open-feature/java-sdk/issues/1458)) ([dcbfd26](https://github.com/open-feature/java-sdk/commit/dcbfd265a3875271695af760fce9870e53c69f13))
+* **deps:** update dependency com.puppycrawl.tools:checkstyle to v10.25.0 ([#1468](https://github.com/open-feature/java-sdk/issues/1468)) ([1558a86](https://github.com/open-feature/java-sdk/commit/1558a862497c0e133d11d53ff6d7f28437653d43))
+* **deps:** update dependency com.puppycrawl.tools:checkstyle to v10.25.1 ([#1489](https://github.com/open-feature/java-sdk/issues/1489)) ([312b6df](https://github.com/open-feature/java-sdk/commit/312b6df5d2c891ac758bf398f8399ecd25b7597e))
+* **deps:** update dependency com.puppycrawl.tools:checkstyle to v10.26.0 ([#1494](https://github.com/open-feature/java-sdk/issues/1494)) ([300a705](https://github.com/open-feature/java-sdk/commit/300a705e0af959da7ed0e88e9975379ff6fc4138))
+* **deps:** update dependency com.puppycrawl.tools:checkstyle to v10.26.1 ([#1498](https://github.com/open-feature/java-sdk/issues/1498)) ([2e3b479](https://github.com/open-feature/java-sdk/commit/2e3b479cb1e8b0b65652ee813eaa2e1940d53c8e))
+* **deps:** update dependency maven to v3.9.10 ([#1474](https://github.com/open-feature/java-sdk/issues/1474)) ([4481537](https://github.com/open-feature/java-sdk/commit/4481537cebc213dcfe19bb8cd9b70a4c91a682b2))
+* **deps:** update dependency net.bytebuddy:byte-buddy to v1.17.6 ([#1482](https://github.com/open-feature/java-sdk/issues/1482)) ([8e51e6f](https://github.com/open-feature/java-sdk/commit/8e51e6fe101882184a5d09be31fa65563d82c673))
+* **deps:** update dependency net.bytebuddy:byte-buddy-agent to v1.17.6 ([#1483](https://github.com/open-feature/java-sdk/issues/1483)) ([936ff60](https://github.com/open-feature/java-sdk/commit/936ff60fac471a83a7c14412d2e825b2a7f9704c))
+* **deps:** update dependency org.apache.maven.plugins:maven-gpg-plugin to v3.2.8 ([#1501](https://github.com/open-feature/java-sdk/issues/1501)) ([0515ad5](https://github.com/open-feature/java-sdk/commit/0515ad54c4f71863373eb1b7f429393923b27d90))
+* **deps:** update dependency org.codehaus.mojo:exec-maven-plugin to v3.5.1 ([#1461](https://github.com/open-feature/java-sdk/issues/1461)) ([b6ceff2](https://github.com/open-feature/java-sdk/commit/b6ceff2ecb0e34be2ccdb83f7f37c1177de6f27e))
+* **deps:** update dependency org.mockito:mockito-core to v5.18.0 ([#1457](https://github.com/open-feature/java-sdk/issues/1457)) ([e17b0b2](https://github.com/open-feature/java-sdk/commit/e17b0b29758ae7cdbdac9ddb2178382c55eb1277))
+* **deps:** update github/codeql-action digest to 075e08a ([#1470](https://github.com/open-feature/java-sdk/issues/1470)) ([6597de7](https://github.com/open-feature/java-sdk/commit/6597de7a98e0fae10a541a8a9b60837623c133a8))
+* **deps:** update github/codeql-action digest to 33f8489 ([#1502](https://github.com/open-feature/java-sdk/issues/1502)) ([0fd9d3d](https://github.com/open-feature/java-sdk/commit/0fd9d3dcfb1fd65197a42885b12d40a1cc152d3b))
+* **deps:** update github/codeql-action digest to 396fd27 ([#1456](https://github.com/open-feature/java-sdk/issues/1456)) ([b45a937](https://github.com/open-feature/java-sdk/commit/b45a9370173e3d3b97c78449dfc99225fb572228))
+* **deps:** update github/codeql-action digest to 3de706a ([#1481](https://github.com/open-feature/java-sdk/issues/1481)) ([99a3006](https://github.com/open-feature/java-sdk/commit/99a3006de878ab0ba1f0e61a4cb5432914425795))
+* **deps:** update github/codeql-action digest to 466d6ce ([#1477](https://github.com/open-feature/java-sdk/issues/1477)) ([0b57bca](https://github.com/open-feature/java-sdk/commit/0b57bcafc14b946000feb4a3421d73b9616e83cb))
+* **deps:** update github/codeql-action digest to 4a00331 ([#1469](https://github.com/open-feature/java-sdk/issues/1469)) ([376f81f](https://github.com/open-feature/java-sdk/commit/376f81f5c3b66d7e3e298aac30ac7544b84e7362))
+* **deps:** update github/codeql-action digest to 4c57370 ([#1497](https://github.com/open-feature/java-sdk/issues/1497)) ([49214b7](https://github.com/open-feature/java-sdk/commit/49214b7282ddde1ee16cf80f92c11cc90ef7612a))
+* **deps:** update github/codeql-action digest to 510dfa3 ([#1450](https://github.com/open-feature/java-sdk/issues/1450)) ([d9a72d2](https://github.com/open-feature/java-sdk/commit/d9a72d2aafd787a1814132f000897ad1c94181e4))
+* **deps:** update github/codeql-action digest to 57eebf6 ([#1455](https://github.com/open-feature/java-sdk/issues/1455)) ([36eed06](https://github.com/open-feature/java-sdk/commit/36eed065e763bbfa0f8f97d704202bbd219332ca))
+* **deps:** update github/codeql-action digest to 66d7255 ([#1487](https://github.com/open-feature/java-sdk/issues/1487)) ([c3eaecd](https://github.com/open-feature/java-sdk/commit/c3eaecdb8b34d3b33946bd205ee92d49584602bd))
+* **deps:** update github/codeql-action digest to 7b0fb5a ([#1459](https://github.com/open-feature/java-sdk/issues/1459)) ([6a95c00](https://github.com/open-feature/java-sdk/commit/6a95c008e975dd3c7328c32f1d7cf626bbaecfa6))
+* **deps:** update github/codeql-action digest to 7cb9b16 ([#1476](https://github.com/open-feature/java-sdk/issues/1476)) ([6cca721](https://github.com/open-feature/java-sdk/commit/6cca721be5bc6f5926fe64668a7c03728cab3cb0))
+* **deps:** update github/codeql-action digest to 7fd6215 ([#1464](https://github.com/open-feature/java-sdk/issues/1464)) ([f10aaaa](https://github.com/open-feature/java-sdk/commit/f10aaaa357581b573895f4d6e2329abb705582aa))
+* **deps:** update github/codeql-action digest to 8ef1782 ([#1495](https://github.com/open-feature/java-sdk/issues/1495)) ([86a5916](https://github.com/open-feature/java-sdk/commit/86a5916f0dc6116b5b9e5dc897ff4b8705ac01e3))
+* **deps:** update github/codeql-action digest to 9b02dc2 ([#1491](https://github.com/open-feature/java-sdk/issues/1491)) ([6f67b06](https://github.com/open-feature/java-sdk/commit/6f67b06f712c461f331681a76f5cb2c3ddb0d36b))
+* **deps:** update github/codeql-action digest to ac30a39 ([#1488](https://github.com/open-feature/java-sdk/issues/1488)) ([8fad544](https://github.com/open-feature/java-sdk/commit/8fad544b17ee08b4280d7975073d00a874c374db))
+* **deps:** update github/codeql-action digest to b1e4dc3 ([#1471](https://github.com/open-feature/java-sdk/issues/1471)) ([2dcd6a1](https://github.com/open-feature/java-sdk/commit/2dcd6a1dd0c80ee676b9860afd6a6002d0ea4aea))
+* **deps:** update github/codeql-action digest to b694213 ([#1503](https://github.com/open-feature/java-sdk/issues/1503)) ([a5d1cbc](https://github.com/open-feature/java-sdk/commit/a5d1cbced4658fadb63f362b4512bdbd68ae7d6a))
+* **deps:** update github/codeql-action digest to b86edfc ([#1453](https://github.com/open-feature/java-sdk/issues/1453)) ([b667aa3](https://github.com/open-feature/java-sdk/commit/b667aa325136b78c01867d40342f81eeb7e16f46))
+* **deps:** update github/codeql-action digest to bc02a25 ([#1460](https://github.com/open-feature/java-sdk/issues/1460)) ([5e922cf](https://github.com/open-feature/java-sdk/commit/5e922cf3efc156135563707de92e508b0a4d19f3))
+* **deps:** update github/codeql-action digest to be30325 ([#1479](https://github.com/open-feature/java-sdk/issues/1479)) ([844d5e2](https://github.com/open-feature/java-sdk/commit/844d5e244b02703b624cf75e5bf8448c07e62d3d))
+* **deps:** update github/codeql-action digest to dcc1a66 ([#1499](https://github.com/open-feature/java-sdk/issues/1499)) ([69519b1](https://github.com/open-feature/java-sdk/commit/69519b1ef7274ceae39d6746c5a5a98dc69f562f))
+* **deps:** update github/codeql-action digest to ef36b69 ([#1484](https://github.com/open-feature/java-sdk/issues/1484)) ([8bf777a](https://github.com/open-feature/java-sdk/commit/8bf777a7e99be4dfac8917b8e61cb6c23385b8ce))
+* **deps:** update io.cucumber.version to v7.23.0 ([#1465](https://github.com/open-feature/java-sdk/issues/1465)) ([2de7616](https://github.com/open-feature/java-sdk/commit/2de76166764bacd34883b13220dd0bad824c8b1a))
+* improvements to release workflow ([#1451](https://github.com/open-feature/java-sdk/issues/1451)) ([1714efe](https://github.com/open-feature/java-sdk/commit/1714efe81aa6ae025f4f8b12c9c042561498d25e))
+* migrate to new publish ([5425a34](https://github.com/open-feature/java-sdk/commit/5425a34a12baa04f9583b83fd1bfdd7e2a6ab5e8))
+* remove unneeded version information ([#1428](https://github.com/open-feature/java-sdk/issues/1428)) ([3ed65cf](https://github.com/open-feature/java-sdk/commit/3ed65cfb0cb5ee5b70793cd68a27909c81cd4fab))
+* skip tests on publish ([6194186](https://github.com/open-feature/java-sdk/commit/6194186b3e791f3cb28da24f5acb3ff96788d65e))
+* update publish env vars ([85d89ee](https://github.com/open-feature/java-sdk/commit/85d89ee79a52d960322731fb786c0f60245f0d75))
+
+## [1.15.1](https://github.com/open-feature/java-sdk/compare/v1.14.2...v1.15.1) (2025-05-14)
+
+
+### NOTABLE CHANGES
+
+* Raise required Java version to 11 ([#1393](https://github.com/open-feature/java-sdk/issues/1393))
+
+### ๐ Bug Fixes
+
+* **deps:** update dependency io.cucumber:cucumber-bom to v7.22.0 ([#1411](https://github.com/open-feature/java-sdk/issues/1411)) ([e251819](https://github.com/open-feature/java-sdk/commit/e25181982af8e5d37be4876b71b337ca86e8454b))
+* **deps:** update dependency io.cucumber:cucumber-bom to v7.22.1 ([#1427](https://github.com/open-feature/java-sdk/issues/1427)) ([1c4d2ef](https://github.com/open-feature/java-sdk/commit/1c4d2efafdebb562f099ba1ec3a6a29eabc8ff91))
+* **deps:** update dependency io.cucumber:cucumber-bom to v7.22.2 ([#1442](https://github.com/open-feature/java-sdk/issues/1442)) ([e568f3a](https://github.com/open-feature/java-sdk/commit/e568f3a4f560187586d5473aa7bc12a673340e24))
+* **deps:** update dependency org.projectlombok:lombok to v1.18.38 ([#1403](https://github.com/open-feature/java-sdk/issues/1403)) ([ef32f11](https://github.com/open-feature/java-sdk/commit/ef32f11571de4d3a981efec4f61113eb8b0d7d9d))
+* **deps:** update junit5 monorepo ([#1418](https://github.com/open-feature/java-sdk/issues/1418)) ([97b442e](https://github.com/open-feature/java-sdk/commit/97b442ed6e8f2b99ca949ffd63e5cbf57718c796))
+
+
+### โจ New Features
+
+* add logging on provider state transitions ([#1444](https://github.com/open-feature/java-sdk/issues/1444)) ([e2813b2](https://github.com/open-feature/java-sdk/commit/e2813b2e5df8e548caf16e3e425b35962045ca6c))
+* add telemetry helper utils ([#1346](https://github.com/open-feature/java-sdk/issues/1346)) ([d0ae548](https://github.com/open-feature/java-sdk/commit/d0ae5482771f4d1701bce25381cdf4e92e2d4882))
+* Raise required Java version to 11 ([#1393](https://github.com/open-feature/java-sdk/issues/1393)) ([4dc988b](https://github.com/open-feature/java-sdk/commit/4dc988b637a9e9c377edf7df7b29bf6407319f16))
+
+
+### ๐งน Chore
+
+* add DCO to release please ([45ec4b1](https://github.com/open-feature/java-sdk/commit/45ec4b1b7734c9117f43abf8fe5105c2903c3986))
+* add DCO to release please ([#1429](https://github.com/open-feature/java-sdk/issues/1429)) ([32137bf](https://github.com/open-feature/java-sdk/commit/32137bfa82e9c0391c999bf0be2a36f201620931))
+* add publish env ([#1420](https://github.com/open-feature/java-sdk/issues/1420)) ([665dd51](https://github.com/open-feature/java-sdk/commit/665dd51eb2b3b79d3ffccb6cef64d544aa5e7206))
+* **deps:** update actions/setup-java digest to 148017a ([#1404](https://github.com/open-feature/java-sdk/issues/1404)) ([f834e11](https://github.com/open-feature/java-sdk/commit/f834e11acc7ecf903e972d80e9dab324be97847e))
+* **deps:** update actions/setup-java digest to c5195ef ([#1415](https://github.com/open-feature/java-sdk/issues/1415)) ([a578903](https://github.com/open-feature/java-sdk/commit/a5789038acc36cb2b0ddf12e534a1317e1c9b8e8))
+* **deps:** update actions/setup-java digest to f4f1212 ([#1421](https://github.com/open-feature/java-sdk/issues/1421)) ([a3e2a59](https://github.com/open-feature/java-sdk/commit/a3e2a59aebee051ae8c7eb1c5769a04dc9da8de3))
+* **deps:** update amannn/action-semantic-pull-request digest to 3352882 ([#1434](https://github.com/open-feature/java-sdk/issues/1434)) ([62ba6db](https://github.com/open-feature/java-sdk/commit/62ba6db457358d759fe83f23318b1cf4200756ac))
+* **deps:** update codecov/codecov-action action to v5.4.2 ([#1419](https://github.com/open-feature/java-sdk/issues/1419)) ([a6389e8](https://github.com/open-feature/java-sdk/commit/a6389e89f60aa7f4871f47d78fedd27a7f9991b4))
+* **deps:** update dependency com.diffplug.spotless:spotless-maven-plugin to v2.44.4 ([#1414](https://github.com/open-feature/java-sdk/issues/1414)) ([e066d3f](https://github.com/open-feature/java-sdk/commit/e066d3f749c09bb1ef79e3bcace1d205a39787df))
+* **deps:** update dependency com.h3xstream.findsecbugs:findsecbugs-plugin to v1.14.0 ([#1422](https://github.com/open-feature/java-sdk/issues/1422)) ([495da27](https://github.com/open-feature/java-sdk/commit/495da271bee976a942973cd23012f60db895bf24))
+* **deps:** update dependency com.puppycrawl.tools:checkstyle to v10 ([#103](https://github.com/open-feature/java-sdk/issues/103)) ([3403510](https://github.com/open-feature/java-sdk/commit/34035105154b7945c02de2a88fe83eb2414526ef))
+* **deps:** update dependency com.tngtech.archunit:archunit-junit5 to v1.4.1 ([#1440](https://github.com/open-feature/java-sdk/issues/1440)) ([78657ee](https://github.com/open-feature/java-sdk/commit/78657ee79efdc94018387cdf8263a73d4abf7191))
+* **deps:** update dependency net.bytebuddy:byte-buddy to v1.17.5 ([#1400](https://github.com/open-feature/java-sdk/issues/1400)) ([1f2d071](https://github.com/open-feature/java-sdk/commit/1f2d0715087ebd4554826d8552b250e4b8b950c8))
+* **deps:** update dependency net.bytebuddy:byte-buddy-agent to v1.17.5 ([#1401](https://github.com/open-feature/java-sdk/issues/1401)) ([07301bd](https://github.com/open-feature/java-sdk/commit/07301bda3f5b65550eff1e025fc9c0bec3c25275))
+* **deps:** update dependency org.apache.maven.plugins:maven-failsafe-plugin to v3.5.3 ([#1398](https://github.com/open-feature/java-sdk/issues/1398)) ([1fcf0e7](https://github.com/open-feature/java-sdk/commit/1fcf0e77d956c88c54e10942d96d2afd4d79315c))
+* **deps:** update dependency org.apache.maven.plugins:maven-surefire-plugin to v3.5.3 ([#1399](https://github.com/open-feature/java-sdk/issues/1399)) ([d6ebc16](https://github.com/open-feature/java-sdk/commit/d6ebc161a93ad703e25592abdb0bf0fd9e281bbc))
+* **deps:** update dependency org.jacoco:jacoco-maven-plugin to v0.8.13 ([#1407](https://github.com/open-feature/java-sdk/issues/1407)) ([e19ccaa](https://github.com/open-feature/java-sdk/commit/e19ccaa35d9ac4d89d72ea58a70d416d202078db))
+* **deps:** update dependency org.mockito:mockito-core to v5.17.0 ([#1409](https://github.com/open-feature/java-sdk/issues/1409)) ([345cdcf](https://github.com/open-feature/java-sdk/commit/345cdcfa10da64c61d769746f335f38ac564e9ad))
+* **deps:** update github/codeql-action digest to 15bce5b ([#1443](https://github.com/open-feature/java-sdk/issues/1443)) ([bc10bac](https://github.com/open-feature/java-sdk/commit/bc10bacb5a68d0d2e498cb41c087505490f19de8))
+* **deps:** update github/codeql-action digest to 2a8cbad ([#1423](https://github.com/open-feature/java-sdk/issues/1423)) ([6b6849f](https://github.com/open-feature/java-sdk/commit/6b6849f3a3ee8a7b66d859c8e522bc101d1ccd44))
+* **deps:** update github/codeql-action digest to 362ef4c ([#1408](https://github.com/open-feature/java-sdk/issues/1408)) ([ca160ca](https://github.com/open-feature/java-sdk/commit/ca160cab7ccd71527e06a0851502353ac50b8d0d))
+* **deps:** update github/codeql-action digest to 40e16ed ([#1437](https://github.com/open-feature/java-sdk/issues/1437)) ([f965cbc](https://github.com/open-feature/java-sdk/commit/f965cbcb37d20724e15b76c15842a88574810b1a))
+* **deps:** update github/codeql-action digest to 4c3e536 ([#1417](https://github.com/open-feature/java-sdk/issues/1417)) ([0c77c84](https://github.com/open-feature/java-sdk/commit/0c77c8446032eaac7e068d48901e1423c21db326))
+* **deps:** update github/codeql-action digest to 4ffa236 ([#1425](https://github.com/open-feature/java-sdk/issues/1425)) ([a7828e7](https://github.com/open-feature/java-sdk/commit/a7828e73a8f2e30f71bd2d9d4da180b2fa436424))
+* **deps:** update github/codeql-action digest to 56dd02f ([#1416](https://github.com/open-feature/java-sdk/issues/1416)) ([4607c62](https://github.com/open-feature/java-sdk/commit/4607c62f15f7ee572207b8ec012ad4b3626e0184))
+* **deps:** update github/codeql-action digest to 5eb3ed6 ([#1439](https://github.com/open-feature/java-sdk/issues/1439)) ([f2348ea](https://github.com/open-feature/java-sdk/commit/f2348ea370412351389c60eef390f36edbea68b0))
+* **deps:** update github/codeql-action digest to 83605b3 ([#1435](https://github.com/open-feature/java-sdk/issues/1435)) ([7e74f2a](https://github.com/open-feature/java-sdk/commit/7e74f2aa3ad2dc8f7a3e4ad398e7705b3e3db364))
+* **deps:** update github/codeql-action digest to 97a2bfd ([#1438](https://github.com/open-feature/java-sdk/issues/1438)) ([85b200a](https://github.com/open-feature/java-sdk/commit/85b200a08b9f8a71de3b5a19eaa057ec04e0801e))
+* **deps:** update github/codeql-action digest to 9f45e74 ([#1396](https://github.com/open-feature/java-sdk/issues/1396)) ([37d76be](https://github.com/open-feature/java-sdk/commit/37d76be697e83f524250a82b2a67cdb4a953d7bc))
+* **deps:** update github/codeql-action digest to d26c46a ([#1413](https://github.com/open-feature/java-sdk/issues/1413)) ([5b327ee](https://github.com/open-feature/java-sdk/commit/5b327eeb770d0a4222f3599be79543b7bed9abc2))
+* **deps:** update github/codeql-action digest to dab8a02 ([#1405](https://github.com/open-feature/java-sdk/issues/1405)) ([5b2f151](https://github.com/open-feature/java-sdk/commit/5b2f1513ab75ef6692978830e59eba87ffa494d5))
+* **deps:** update github/codeql-action digest to e13fe0d ([#1406](https://github.com/open-feature/java-sdk/issues/1406)) ([e211397](https://github.com/open-feature/java-sdk/commit/e211397d517e1263e1251f9c99093bf05cecd93f))
+* **deps:** update github/codeql-action digest to ed51cb5 ([#1436](https://github.com/open-feature/java-sdk/issues/1436)) ([b09e887](https://github.com/open-feature/java-sdk/commit/b09e88798fed529161c61b96c20a8f257d355d3c))
+* **deps:** update github/codeql-action digest to efffb48 ([#1402](https://github.com/open-feature/java-sdk/issues/1402)) ([384953d](https://github.com/open-feature/java-sdk/commit/384953d30ecff83d60a2e5b9790e8228d1a52ac7))
+* **deps:** update github/codeql-action digest to f843d94 ([#1432](https://github.com/open-feature/java-sdk/issues/1432)) ([99faaf8](https://github.com/open-feature/java-sdk/commit/99faaf88aa07bd45fc473db5bafce3b8eafaf9e0))
+* **deps:** update io.cucumber.version to v7.22.0 ([#1410](https://github.com/open-feature/java-sdk/issues/1410)) ([3c69f2f](https://github.com/open-feature/java-sdk/commit/3c69f2f36c4e975d690ecc2e790df632a33001ba))
+* **deps:** update io.cucumber.version to v7.22.1 ([#1426](https://github.com/open-feature/java-sdk/issues/1426)) ([844374a](https://github.com/open-feature/java-sdk/commit/844374a42b94deffab6856e978766354a6f46576))
+* **deps:** update io.cucumber.version to v7.22.2 ([#1441](https://github.com/open-feature/java-sdk/issues/1441)) ([58454b4](https://github.com/open-feature/java-sdk/commit/58454b4eaabfd3327f7ceaff4bf335a5a839ed41))
+* **main:** release 1.15.0 ([#1431](https://github.com/open-feature/java-sdk/issues/1431)) ([7182a7f](https://github.com/open-feature/java-sdk/commit/7182a7fc4197e70218e829971dae2cff09f948c9))
+* update boostrap sha for release please ([f6bd30d](https://github.com/open-feature/java-sdk/commit/f6bd30db93e37e596d211d899315a62d9f810199))
+* update codeowners to give global maintainers code ownership ([#1412](https://github.com/open-feature/java-sdk/issues/1412)) ([498fd38](https://github.com/open-feature/java-sdk/commit/498fd382659669315b0db61db5f19ce054467bc9))
+* update release please action ([#1430](https://github.com/open-feature/java-sdk/issues/1430)) ([1cc851b](https://github.com/open-feature/java-sdk/commit/1cc851b293008a8dd273e904e4c77a650ad71146))
+* use PAT for release please ([014f8a5](https://github.com/open-feature/java-sdk/commit/014f8a59da8f1e976e440ed1ea17e85561f98e2d))
+
+
+### ๐ Documentation
+
+* add try-catch example for setProviderAndWait usage ([#1433](https://github.com/open-feature/java-sdk/issues/1433)) ([96cf9c7](https://github.com/open-feature/java-sdk/commit/96cf9c7f5463e4e0de394117845aebdd9a69425f))
+
+## [1.14.2](https://github.com/open-feature/java-sdk/compare/v1.14.1...v1.14.2) (2025-03-27)
+
+
+### ๐ Bug Fixes
+
+* **deps:** update dependency org.slf4j:slf4j-api to v2.0.17 ([#1348](https://github.com/open-feature/java-sdk/issues/1348)) ([2ec7c6c](https://github.com/open-feature/java-sdk/commit/2ec7c6c7ff704380fdfd8116378adf78734e4f2b))
+* **deps:** update junit5 monorepo ([#1344](https://github.com/open-feature/java-sdk/issues/1344)) ([d95e270](https://github.com/open-feature/java-sdk/commit/d95e2706532259bd5739e5b4ea4813ef9f2196a6))
+* **deps:** update junit5 monorepo ([#1373](https://github.com/open-feature/java-sdk/issues/1373)) ([6b65e26](https://github.com/open-feature/java-sdk/commit/6b65e26c7439895652c3f64f2b4a7307a7ca582e))
+* equals and hashcode of several classes ([69b571e](https://github.com/open-feature/java-sdk/commit/69b571eda73b6f43c99864420b8663ae54ebf0ad))
+* equals and hashcode of several classes ([#1364](https://github.com/open-feature/java-sdk/issues/1364)) ([69b571e](https://github.com/open-feature/java-sdk/commit/69b571eda73b6f43c99864420b8663ae54ebf0ad))
+* hooks not run in NOT_READY/FATAL ([#1392](https://github.com/open-feature/java-sdk/issues/1392)) ([24ef9dd](https://github.com/open-feature/java-sdk/commit/24ef9dd2903d01ec029b70cd1e39e71ffe327499))
+
+
+### ๐งน Chore
+
+* **deps:** update actions/cache digest to 5a3ec84 ([#1380](https://github.com/open-feature/java-sdk/issues/1380)) ([8359ef1](https://github.com/open-feature/java-sdk/commit/8359ef13bb935ac1d144787cfd7181814a0b286c))
+* **deps:** update actions/cache digest to 7921ae2 ([#1337](https://github.com/open-feature/java-sdk/issues/1337)) ([3920c63](https://github.com/open-feature/java-sdk/commit/3920c638a49caddfb07041f812cc6bc0bf3101f9))
+* **deps:** update actions/cache digest to d4323d4 ([#1353](https://github.com/open-feature/java-sdk/issues/1353)) ([5901797](https://github.com/open-feature/java-sdk/commit/59017977a487a36c8a39f63b83299bc657134c0d))
+* **deps:** update actions/setup-java digest to 3b6c050 ([#1391](https://github.com/open-feature/java-sdk/issues/1391)) ([7536679](https://github.com/open-feature/java-sdk/commit/753667925a8803b3b227f762936ae397dde95484))
+* **deps:** update actions/setup-java digest to 799ee7c ([#1359](https://github.com/open-feature/java-sdk/issues/1359)) ([31444d6](https://github.com/open-feature/java-sdk/commit/31444d6c8f30f0dd35debacc9dab8da7397e11ed))
+* **deps:** update actions/setup-java digest to b8ebb8b ([#1381](https://github.com/open-feature/java-sdk/issues/1381)) ([2239f05](https://github.com/open-feature/java-sdk/commit/2239f054b90734dde6cdd4a23daec1c1daa96f07))
+* **deps:** update amannn/action-semantic-pull-request digest to 04501d4 ([#1390](https://github.com/open-feature/java-sdk/issues/1390)) ([87c06d9](https://github.com/open-feature/java-sdk/commit/87c06d9edd935287daf7ebc8db1e7da4831531de))
+* **deps:** update codecov/codecov-action action to v5.4.0 ([#1351](https://github.com/open-feature/java-sdk/issues/1351)) ([b133c2f](https://github.com/open-feature/java-sdk/commit/b133c2fa527a0dddb6de7f7781a00fc84feaa813))
+* **deps:** update dependency com.diffplug.spotless:spotless-maven-plugin to v2.44.3 ([#1341](https://github.com/open-feature/java-sdk/issues/1341)) ([5de33c0](https://github.com/open-feature/java-sdk/commit/5de33c02a675db6ca5966bfa3f58d99c8e53e36b))
+* **deps:** update dependency com.github.spotbugs:spotbugs-maven-plugin to v4.9.1.0 ([#1332](https://github.com/open-feature/java-sdk/issues/1332)) ([cdcdc14](https://github.com/open-feature/java-sdk/commit/cdcdc143ea5ad2f003cb3f5450ec78314e619ea3))
+* **deps:** update dependency com.github.spotbugs:spotbugs-maven-plugin to v4.9.2.0 ([#1360](https://github.com/open-feature/java-sdk/issues/1360)) ([ecea9df](https://github.com/open-feature/java-sdk/commit/ecea9df932ee4874613f219b73640fe964c99593))
+* **deps:** update dependency com.github.spotbugs:spotbugs-maven-plugin to v4.9.3.0 ([#1375](https://github.com/open-feature/java-sdk/issues/1375)) ([de3e213](https://github.com/open-feature/java-sdk/commit/de3e213ac8b8931121904a3d12929405512e74dd))
+* **deps:** update dependency net.bytebuddy:byte-buddy to v1.17.2 ([#1355](https://github.com/open-feature/java-sdk/issues/1355)) ([2a1adca](https://github.com/open-feature/java-sdk/commit/2a1adca8c2ed8d61d51530969290793a5d3d15f3))
+* **deps:** update dependency net.bytebuddy:byte-buddy to v1.17.3 ([#1384](https://github.com/open-feature/java-sdk/issues/1384)) ([b6becac](https://github.com/open-feature/java-sdk/commit/b6becac2c4e0f98a8651cc2f77d4c0b081548991))
+* **deps:** update dependency net.bytebuddy:byte-buddy to v1.17.4 ([#1387](https://github.com/open-feature/java-sdk/issues/1387)) ([cb574d9](https://github.com/open-feature/java-sdk/commit/cb574d93b6210c89a188aa104ef4f1db68daf1c0))
+* **deps:** update dependency net.bytebuddy:byte-buddy-agent to v1.17.2 ([#1356](https://github.com/open-feature/java-sdk/issues/1356)) ([dd83114](https://github.com/open-feature/java-sdk/commit/dd83114c4d9389753575392fafcd56585d7178ae))
+* **deps:** update dependency net.bytebuddy:byte-buddy-agent to v1.17.3 ([#1385](https://github.com/open-feature/java-sdk/issues/1385)) ([4125ae8](https://github.com/open-feature/java-sdk/commit/4125ae83801a9f485059a9edaca090ee47b7632f))
+* **deps:** update dependency net.bytebuddy:byte-buddy-agent to v1.17.4 ([#1388](https://github.com/open-feature/java-sdk/issues/1388)) ([d8f6514](https://github.com/open-feature/java-sdk/commit/d8f6514598d53f43cb084ee746742a59d271363b))
+* **deps:** update dependency org.apache.maven.plugins:maven-compiler-plugin to v3.14.0 ([#1342](https://github.com/open-feature/java-sdk/issues/1342)) ([88a778c](https://github.com/open-feature/java-sdk/commit/88a778cc03e112d45756428d1f0ae1ef0fe02c84))
+* **deps:** update dependency org.awaitility:awaitility to v4.3.0 ([#1343](https://github.com/open-feature/java-sdk/issues/1343)) ([1504d0f](https://github.com/open-feature/java-sdk/commit/1504d0f7982757a2b413eda593ce7057b90519e5))
+* **deps:** update dependency org.mockito:mockito-core to v5.15.2 ([#1339](https://github.com/open-feature/java-sdk/issues/1339)) ([4817864](https://github.com/open-feature/java-sdk/commit/4817864fd7ae70c1e19c3c09e82e1fb03dd88942))
+* **deps:** update dependency org.mockito:mockito-core to v5.16.0 ([#1358](https://github.com/open-feature/java-sdk/issues/1358)) ([30b6d00](https://github.com/open-feature/java-sdk/commit/30b6d004aaf3464547805f7eda6fad0e122de4f9))
+* **deps:** update dependency org.mockito:mockito-core to v5.16.1 ([#1376](https://github.com/open-feature/java-sdk/issues/1376)) ([9750f75](https://github.com/open-feature/java-sdk/commit/9750f75d04beb8339fc2e972f0ee97120eaff354))
+* **deps:** update github/codeql-action digest to 1bb15d0 ([#1336](https://github.com/open-feature/java-sdk/issues/1336)) ([e163ce1](https://github.com/open-feature/java-sdk/commit/e163ce1c060d0dc8812e4a8a3b37f52b0156324d))
+* **deps:** update github/codeql-action digest to 486ab5a ([#1389](https://github.com/open-feature/java-sdk/issues/1389)) ([85fd5e0](https://github.com/open-feature/java-sdk/commit/85fd5e0997ff1a5e5d7226d8bbfe2775769a6ca6))
+* **deps:** update github/codeql-action digest to 56b25d5 ([#1365](https://github.com/open-feature/java-sdk/issues/1365)) ([959e675](https://github.com/open-feature/java-sdk/commit/959e675e4c2363e5fd80d1d2f1edbfab11794fc8))
+* **deps:** update github/codeql-action digest to 608ccd6 ([#1361](https://github.com/open-feature/java-sdk/issues/1361)) ([67b34f8](https://github.com/open-feature/java-sdk/commit/67b34f84a373512013ab2f7649faaddfd2d61048))
+* **deps:** update github/codeql-action digest to 6349095 ([#1378](https://github.com/open-feature/java-sdk/issues/1378)) ([dbf92df](https://github.com/open-feature/java-sdk/commit/dbf92df33bf5657d50dc3b2f129207b0097c1f27))
+* **deps:** update github/codeql-action digest to 6a151cd ([#1377](https://github.com/open-feature/java-sdk/issues/1377)) ([7065655](https://github.com/open-feature/java-sdk/commit/706565581d78856dd73605b1a16b131f974c0731))
+* **deps:** update github/codeql-action digest to 70df9de ([#1372](https://github.com/open-feature/java-sdk/issues/1372)) ([d233480](https://github.com/open-feature/java-sdk/commit/d233480912f1d5e095f5034f36a838535d1ecdff))
+* **deps:** update github/codeql-action digest to 7254660 ([#1368](https://github.com/open-feature/java-sdk/issues/1368)) ([d54c68a](https://github.com/open-feature/java-sdk/commit/d54c68a8e9e4a0f67c99e7d76621a1c5724e4cd1))
+* **deps:** update github/codeql-action digest to 80f9930 ([#1357](https://github.com/open-feature/java-sdk/issues/1357)) ([6c03e5d](https://github.com/open-feature/java-sdk/commit/6c03e5d84aacee11f5b8e608a6114c11fced72b8))
+* **deps:** update github/codeql-action digest to 8392354 ([#1352](https://github.com/open-feature/java-sdk/issues/1352)) ([989f4ae](https://github.com/open-feature/java-sdk/commit/989f4ae54263b46ca2c81561acc70b39918c382d))
+* **deps:** update github/codeql-action digest to 8c1551c ([#1333](https://github.com/open-feature/java-sdk/issues/1333)) ([859a36c](https://github.com/open-feature/java-sdk/commit/859a36cbfafc94d4601b87d304237e6ddf97c08d))
+* **deps:** update github/codeql-action digest to 8c69433 ([#1347](https://github.com/open-feature/java-sdk/issues/1347)) ([6987568](https://github.com/open-feature/java-sdk/commit/698756856ba40e98d91ccf661dab409798861aa5))
+* **deps:** update github/codeql-action digest to 97aac9b ([#1350](https://github.com/open-feature/java-sdk/issues/1350)) ([7df9565](https://github.com/open-feature/java-sdk/commit/7df9565691731d164b534116b8a6b933b171d103))
+* **deps:** update github/codeql-action digest to a8849fb ([#1345](https://github.com/open-feature/java-sdk/issues/1345)) ([de64edd](https://github.com/open-feature/java-sdk/commit/de64eddfb3a6cc117bb108dbcf167830e9f6729d))
+* **deps:** update github/codeql-action digest to acadfed ([#1335](https://github.com/open-feature/java-sdk/issues/1335)) ([5436eb0](https://github.com/open-feature/java-sdk/commit/5436eb0d5db3a0e9bd9289fbef57b9eeada0a667))
+* **deps:** update github/codeql-action digest to b2e6519 ([#1366](https://github.com/open-feature/java-sdk/issues/1366)) ([d00e4b5](https://github.com/open-feature/java-sdk/commit/d00e4b5b24621aa55085827fbe6ea982491376de))
+* **deps:** update github/codeql-action digest to b46b37a ([#1367](https://github.com/open-feature/java-sdk/issues/1367)) ([c550d59](https://github.com/open-feature/java-sdk/commit/c550d597227bfc1e0e17357139f1fd8a87593be0))
+* **deps:** update github/codeql-action digest to bd1d9ab ([#1383](https://github.com/open-feature/java-sdk/issues/1383)) ([922e17e](https://github.com/open-feature/java-sdk/commit/922e17e677e15690e3df2fe93a961f16f21ff283))
+* **deps:** update github/codeql-action digest to c50c157 ([#1379](https://github.com/open-feature/java-sdk/issues/1379)) ([d61c33e](https://github.com/open-feature/java-sdk/commit/d61c33e466336c7120b870ca5e3843eba5f7175c))
+* **deps:** update github/codeql-action digest to d99c7e8 ([#1338](https://github.com/open-feature/java-sdk/issues/1338)) ([4e535fd](https://github.com/open-feature/java-sdk/commit/4e535fd10fac742ca472faa62c941fa51b282ca7))
+* **deps:** update github/codeql-action digest to dc49dca ([#1369](https://github.com/open-feature/java-sdk/issues/1369)) ([f8df5fb](https://github.com/open-feature/java-sdk/commit/f8df5fb84a765af917587dd509f9cec38103f787))
+* **deps:** update github/codeql-action digest to e0ea141 ([#1386](https://github.com/open-feature/java-sdk/issues/1386)) ([387e5f2](https://github.com/open-feature/java-sdk/commit/387e5f2e3bd24ccea6691b0d6dbfe542cfd05b52))
+* **deps:** update github/codeql-action digest to ff79de6 ([#1340](https://github.com/open-feature/java-sdk/issues/1340)) ([50b45b2](https://github.com/open-feature/java-sdk/commit/50b45b2be442bb89a431c9bcc45d825f63bd93a6))
+* update build and tooling to utilize new java version ([#1321](https://github.com/open-feature/java-sdk/issues/1321)) ([90217b2](https://github.com/open-feature/java-sdk/commit/90217b2083a2ba92c623365dc450326d49b46fab))
+
+## [1.14.1](https://github.com/open-feature/java-sdk/compare/v1.14.0...v1.14.1) (2025-02-14)
+
+
+### ๐ Bug Fixes
+
+* **deps:** update dependency io.cucumber:cucumber-bom to v7.21.0 ([#1312](https://github.com/open-feature/java-sdk/issues/1312)) ([208411e](https://github.com/open-feature/java-sdk/commit/208411e72338e37bf477ac0b784bbbbe0309b922))
+* **deps:** update dependency io.cucumber:cucumber-bom to v7.21.1 ([#1317](https://github.com/open-feature/java-sdk/issues/1317)) ([b797883](https://github.com/open-feature/java-sdk/commit/b7978832b786fe081169ff0efeb702218300c622))
+* possible event-related deadlocks with some providers ([#1314](https://github.com/open-feature/java-sdk/issues/1314)) ([c33ac2d](https://github.com/open-feature/java-sdk/commit/c33ac2d9b2e91b85fffb3c21653912fe82006351))
+* TrackingEventDetails interface to include numeric getValue() call ([#1328](https://github.com/open-feature/java-sdk/issues/1328)) ([08c38fb](https://github.com/open-feature/java-sdk/commit/08c38fb553d82a42682c3eb9239329f770063898))
+
+
+### ๐งน Chore
+
+* **deps:** update actions/cache digest to 9fa7e61 ([#1324](https://github.com/open-feature/java-sdk/issues/1324)) ([69cdc77](https://github.com/open-feature/java-sdk/commit/69cdc772a639470dd223bf70ef6e9f8bc4d93dea))
+* **deps:** update actions/checkout digest to 85e6279 ([#1287](https://github.com/open-feature/java-sdk/issues/1287)) ([640e35e](https://github.com/open-feature/java-sdk/commit/640e35e85375e3098f61b7397432d80a95502bdd))
+* **deps:** update actions/setup-java digest to 28b532b ([#1296](https://github.com/open-feature/java-sdk/issues/1296)) ([874e86d](https://github.com/open-feature/java-sdk/commit/874e86df5c22a1e5771ca16c76aa13039b5f9b65))
+* **deps:** update actions/setup-java digest to 3a4f6e1 ([#1306](https://github.com/open-feature/java-sdk/issues/1306)) ([ba9cc4b](https://github.com/open-feature/java-sdk/commit/ba9cc4b85a1082d638d49b9d2d0a4ed5a45f09ee))
+* **deps:** update actions/setup-java digest to 51ab6d2 ([#1288](https://github.com/open-feature/java-sdk/issues/1288)) ([c69d3a4](https://github.com/open-feature/java-sdk/commit/c69d3a4bd137c1d6baa47c14228bfe8f96555676))
+* **deps:** update actions/setup-java digest to 99d3141 ([#1285](https://github.com/open-feature/java-sdk/issues/1285)) ([32a3933](https://github.com/open-feature/java-sdk/commit/32a39335de8e61650905fc96dc1a73e65f1fe9f8))
+* **deps:** update codecov/codecov-action action to v5.2.0 ([#1298](https://github.com/open-feature/java-sdk/issues/1298)) ([531fc38](https://github.com/open-feature/java-sdk/commit/531fc385b662c5b7b334fee298fc9fe1283c78fb))
+* **deps:** update codecov/codecov-action action to v5.3.0 ([#1301](https://github.com/open-feature/java-sdk/issues/1301)) ([f7f6586](https://github.com/open-feature/java-sdk/commit/f7f6586d72e3f112a7dafc8f77de273ed49ccc4b))
+* **deps:** update codecov/codecov-action action to v5.3.1 ([#1303](https://github.com/open-feature/java-sdk/issues/1303)) ([f9fa54b](https://github.com/open-feature/java-sdk/commit/f9fa54be493e1d0843b709008eb0f047e7580d47))
+* **deps:** update dependency net.bytebuddy:byte-buddy to v1.16.0 ([#1289](https://github.com/open-feature/java-sdk/issues/1289)) ([0b5b423](https://github.com/open-feature/java-sdk/commit/0b5b423bdd378bb1db3e10fe5da7fa2c937a4610))
+* **deps:** update dependency net.bytebuddy:byte-buddy to v1.16.1 ([#1292](https://github.com/open-feature/java-sdk/issues/1292)) ([0af9f29](https://github.com/open-feature/java-sdk/commit/0af9f2901f88b5ef9bed0c570d426939a55af3cf))
+* **deps:** update dependency net.bytebuddy:byte-buddy to v1.17.0 ([#1309](https://github.com/open-feature/java-sdk/issues/1309)) ([cda3405](https://github.com/open-feature/java-sdk/commit/cda34053f7e39318205a181ef93c825bab2ed9fc))
+* **deps:** update dependency net.bytebuddy:byte-buddy to v1.17.1 ([#1329](https://github.com/open-feature/java-sdk/issues/1329)) ([9ab2618](https://github.com/open-feature/java-sdk/commit/9ab26182eae4974b60d166777c51dfcb07957150))
+* **deps:** update dependency net.bytebuddy:byte-buddy-agent to v1.16.0 ([#1290](https://github.com/open-feature/java-sdk/issues/1290)) ([6c4205a](https://github.com/open-feature/java-sdk/commit/6c4205a00817af260ef9b90f54ce878cad33f75a))
+* **deps:** update dependency net.bytebuddy:byte-buddy-agent to v1.16.1 ([#1293](https://github.com/open-feature/java-sdk/issues/1293)) ([6071932](https://github.com/open-feature/java-sdk/commit/6071932cb4207dc83cdedfa67c8a69ed71d9c26a))
+* **deps:** update dependency net.bytebuddy:byte-buddy-agent to v1.17.0 ([#1310](https://github.com/open-feature/java-sdk/issues/1310)) ([40fa173](https://github.com/open-feature/java-sdk/commit/40fa1733382f4c476a1228c6499044ad83c8f3c4))
+* **deps:** update dependency net.bytebuddy:byte-buddy-agent to v1.17.1 ([#1330](https://github.com/open-feature/java-sdk/issues/1330)) ([4ba5695](https://github.com/open-feature/java-sdk/commit/4ba5695eeea6a7ab2fe1d2c595fa482d4b7868dc))
+* **deps:** update dependency org.assertj:assertj-core to v3.27.3 ([#1291](https://github.com/open-feature/java-sdk/issues/1291)) ([a5eb21d](https://github.com/open-feature/java-sdk/commit/a5eb21d1a2e6945a4455cacde898bc913bddb96d))
+* **deps:** update github/codeql-action digest to 0701025 ([#1311](https://github.com/open-feature/java-sdk/issues/1311)) ([9a1e9ab](https://github.com/open-feature/java-sdk/commit/9a1e9abd64220c8d8706f2a64e041ef3f37e1a43))
+* **deps:** update github/codeql-action digest to 08bc0cf ([#1313](https://github.com/open-feature/java-sdk/issues/1313)) ([37ed6a4](https://github.com/open-feature/java-sdk/commit/37ed6a424cdc013ed74c9881826cc56c93ae8228))
+* **deps:** update github/codeql-action digest to 0a35e8f ([#1316](https://github.com/open-feature/java-sdk/issues/1316)) ([26e1d7f](https://github.com/open-feature/java-sdk/commit/26e1d7fff342a32880542efa87b017aec506667e))
+* **deps:** update github/codeql-action digest to 0f1559a ([#1286](https://github.com/open-feature/java-sdk/issues/1286)) ([882d2dd](https://github.com/open-feature/java-sdk/commit/882d2dd5bdac007e8a3783efc54fa45faed22054))
+* **deps:** update github/codeql-action digest to 10a3f07 ([#1280](https://github.com/open-feature/java-sdk/issues/1280)) ([a3854d6](https://github.com/open-feature/java-sdk/commit/a3854d6ab1dba99f4db18f868e89fcc04418e306))
+* **deps:** update github/codeql-action digest to 1c15a48 ([#1325](https://github.com/open-feature/java-sdk/issues/1325)) ([3baf0df](https://github.com/open-feature/java-sdk/commit/3baf0df966f8212864aa7e57bc3d3d09d324fe11))
+* **deps:** update github/codeql-action digest to 1efc6bb ([#1281](https://github.com/open-feature/java-sdk/issues/1281)) ([8a1ab7e](https://github.com/open-feature/java-sdk/commit/8a1ab7ea18aff4ee5a6a2fdd1f805b08e51a50a3))
+* **deps:** update github/codeql-action digest to 24e1c2d ([#1315](https://github.com/open-feature/java-sdk/issues/1315)) ([46903c6](https://github.com/open-feature/java-sdk/commit/46903c6f275e5f9dc8884acf3f76f76efcfc58bd))
+* **deps:** update github/codeql-action digest to 3b4f4d9 ([#1282](https://github.com/open-feature/java-sdk/issues/1282)) ([b390d5f](https://github.com/open-feature/java-sdk/commit/b390d5f0b0945948cd6b87e6486725d095d5ac8a))
+* **deps:** update github/codeql-action digest to 43cffee ([#1304](https://github.com/open-feature/java-sdk/issues/1304)) ([6874de6](https://github.com/open-feature/java-sdk/commit/6874de64ce589e853f5523019bfa9e1d60840baf))
+* **deps:** update github/codeql-action digest to 54b1c84 ([#1307](https://github.com/open-feature/java-sdk/issues/1307)) ([6f36434](https://github.com/open-feature/java-sdk/commit/6f36434c520dcef27deb04e04941693dc15acb2f))
+* **deps:** update github/codeql-action digest to 5f4f998 ([#1305](https://github.com/open-feature/java-sdk/issues/1305)) ([7916d76](https://github.com/open-feature/java-sdk/commit/7916d76635c5ab59dafe6d72058aad9cfcf05f4b))
+* **deps:** update github/codeql-action digest to 6063925 ([#1320](https://github.com/open-feature/java-sdk/issues/1320)) ([538140d](https://github.com/open-feature/java-sdk/commit/538140dfe713a421623b179e69b399f82200fe61))
+* **deps:** update github/codeql-action digest to 7e3036b ([#1300](https://github.com/open-feature/java-sdk/issues/1300)) ([3491956](https://github.com/open-feature/java-sdk/commit/34919561b73faa0cca489ad480e93cca9a854167))
+* **deps:** update github/codeql-action digest to 87fc816 ([#1277](https://github.com/open-feature/java-sdk/issues/1277)) ([c2a82db](https://github.com/open-feature/java-sdk/commit/c2a82dbdbafa134fae4b0c9aef88cf589e09aefa))
+* **deps:** update github/codeql-action digest to 93da9f2 ([#1283](https://github.com/open-feature/java-sdk/issues/1283)) ([45b3995](https://github.com/open-feature/java-sdk/commit/45b3995bdad9f1b05abb01455a9c8f57028cfde5))
+* **deps:** update github/codeql-action digest to affec20 ([#1323](https://github.com/open-feature/java-sdk/issues/1323)) ([8f3ced5](https://github.com/open-feature/java-sdk/commit/8f3ced590764760244cc81ac10c939ca62504dfe))
+* **deps:** update github/codeql-action digest to b44b19f ([#1297](https://github.com/open-feature/java-sdk/issues/1297)) ([305e032](https://github.com/open-feature/java-sdk/commit/305e0329e78116fe697240e420879ac85012d698))
+* **deps:** update github/codeql-action digest to d90e07f ([#1294](https://github.com/open-feature/java-sdk/issues/1294)) ([5671184](https://github.com/open-feature/java-sdk/commit/5671184e7f76f979d631c18bb2ebfb15dccfb207))
+* **deps:** update github/codeql-action digest to db7177a ([#1279](https://github.com/open-feature/java-sdk/issues/1279)) ([b997946](https://github.com/open-feature/java-sdk/commit/b997946db1c7663b7ebb775ad45cdb2b0aaeb291))
+* **deps:** update github/codeql-action digest to e7c0c9d ([#1302](https://github.com/open-feature/java-sdk/issues/1302)) ([78adc77](https://github.com/open-feature/java-sdk/commit/78adc77c23da6116e1f58b3a45dc283c3c58837b))
+* **deps:** update github/codeql-action digest to e9987ad ([#1308](https://github.com/open-feature/java-sdk/issues/1308)) ([99d8185](https://github.com/open-feature/java-sdk/commit/99d818572a3407ca6b25f6e91f69ef3e83bdc657))
+* **deps:** update github/codeql-action digest to f89b8a7 ([#1295](https://github.com/open-feature/java-sdk/issues/1295)) ([122e82f](https://github.com/open-feature/java-sdk/commit/122e82f8431fb116ae3b147f7e2245d7f90b1c77))
+
## [1.14.0](https://github.com/open-feature/java-sdk/compare/v1.13.0...v1.14.0) (2025-01-10)
diff --git a/CODEOWNERS b/CODEOWNERS
index e75c1d5f1..342eb8df1 100644
--- a/CODEOWNERS
+++ b/CODEOWNERS
@@ -3,4 +3,4 @@
#
# Managed by Peribolos: https://github.com/open-feature/community/blob/main/config/open-feature/sdk-java/workgroup.yaml
#
-* @open-feature/sdk-java-maintainers
+* @open-feature/sdk-java-maintainers @open-feature/maintainers
diff --git a/LICENSE b/LICENSE
index 261eeb9e9..96b3dc8fc 100644
--- a/LICENSE
+++ b/LICENSE
@@ -186,7 +186,7 @@
same "printed page" as the copyright notice for easier
identification within third-party archives.
- Copyright [yyyy] [name of copyright owner]
+ Copyright OpenFeature Maintainers
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
diff --git a/README.md b/README.md
index cbb9d9f13..70b131e9a 100644
--- a/README.md
+++ b/README.md
@@ -18,8 +18,8 @@
-
-
+
+
@@ -46,7 +46,7 @@
### Requirements
-- Java 8+ (compiler target is 1.8)
+- Java 11+ (compiler target is 11)
Note that this library is intended to be used in server-side contexts and has not been evaluated for use on mobile devices.
@@ -59,7 +59,7 @@ Note that this library is intended to be used in server-side contexts and has no
dev.openfeaturesdk
- 1.14.0
+ 1.18.2
```
@@ -84,7 +84,7 @@ If you would like snapshot builds, this is the relevant repository information:
```groovy
dependencies {
- implementation 'dev.openfeature:sdk:1.14.0'
+ implementation 'dev.openfeature:sdk:1.18.2'
}
```
@@ -104,7 +104,12 @@ public void example(){
// configure a provider
OpenFeatureAPI api = OpenFeatureAPI.getInstance();
- api.setProviderAndWait(new InMemoryProvider(myFlags));
+ try {
+ api.setProviderAndWait(new InMemoryProvider(myFlags));
+ } catch (Exception e) {
+ // handle initialization failure
+ e.printStackTrace();
+ }
// create a client
Client client = api.getClient();
@@ -149,7 +154,12 @@ To register a provider in a blocking manner to ensure it is ready before further
```java
OpenFeatureAPI api = OpenFeatureAPI.getInstance();
- api.setProviderAndWait(new MyProvider());
+ try {
+ api.setProviderAndWait(new MyProvider());
+ } catch (Exception e) {
+ // handle initialization failure
+ e.printStackTrace();
+ }
```
#### Asynchronous
diff --git a/mvnw b/mvnw
index 19529ddf8..bd8896bf2 100644
--- a/mvnw
+++ b/mvnw
@@ -19,7 +19,7 @@
# ----------------------------------------------------------------------------
# ----------------------------------------------------------------------------
-# Apache Maven Wrapper startup batch script, version 3.3.2
+# Apache Maven Wrapper startup batch script, version 3.3.4
#
# Optional ENV vars
# -----------------
@@ -105,14 +105,17 @@ trim() {
printf "%s" "${1}" | tr -d '[:space:]'
}
+scriptDir="$(dirname "$0")"
+scriptName="$(basename "$0")"
+
# parse distributionUrl and optional distributionSha256Sum, requires .mvn/wrapper/maven-wrapper.properties
while IFS="=" read -r key value; do
case "${key-}" in
distributionUrl) distributionUrl=$(trim "${value-}") ;;
distributionSha256Sum) distributionSha256Sum=$(trim "${value-}") ;;
esac
-done <"${0%/*}/.mvn/wrapper/maven-wrapper.properties"
-[ -n "${distributionUrl-}" ] || die "cannot read distributionUrl property in ${0%/*}/.mvn/wrapper/maven-wrapper.properties"
+done <"$scriptDir/.mvn/wrapper/maven-wrapper.properties"
+[ -n "${distributionUrl-}" ] || die "cannot read distributionUrl property in $scriptDir/.mvn/wrapper/maven-wrapper.properties"
case "${distributionUrl##*/}" in
maven-mvnd-*bin.*)
@@ -130,7 +133,7 @@ maven-mvnd-*bin.*)
distributionUrl="${distributionUrl%-bin.*}-$distributionPlatform.zip"
;;
maven-mvnd-*) MVN_CMD=mvnd.sh _MVNW_REPO_PATTERN=/maven/mvnd/ ;;
-*) MVN_CMD="mvn${0##*/mvnw}" _MVNW_REPO_PATTERN=/org/apache/maven/ ;;
+*) MVN_CMD="mvn${scriptName#mvnw}" _MVNW_REPO_PATTERN=/org/apache/maven/ ;;
esac
# apply MVNW_REPOURL and calculate MAVEN_HOME
@@ -227,7 +230,7 @@ if [ -n "${distributionSha256Sum-}" ]; then
echo "Please disable validation by removing 'distributionSha256Sum' from your maven-wrapper.properties." >&2
exit 1
elif command -v sha256sum >/dev/null; then
- if echo "$distributionSha256Sum $TMP_DOWNLOAD_DIR/$distributionUrlName" | sha256sum -c >/dev/null 2>&1; then
+ if echo "$distributionSha256Sum $TMP_DOWNLOAD_DIR/$distributionUrlName" | sha256sum -c - >/dev/null 2>&1; then
distributionSha256Result=true
fi
elif command -v shasum >/dev/null; then
@@ -252,8 +255,41 @@ if command -v unzip >/dev/null; then
else
tar xzf${__MVNW_QUIET_TAR:+"$__MVNW_QUIET_TAR"} "$TMP_DOWNLOAD_DIR/$distributionUrlName" -C "$TMP_DOWNLOAD_DIR" || die "failed to untar"
fi
-printf %s\\n "$distributionUrl" >"$TMP_DOWNLOAD_DIR/$distributionUrlNameMain/mvnw.url"
-mv -- "$TMP_DOWNLOAD_DIR/$distributionUrlNameMain" "$MAVEN_HOME" || [ -d "$MAVEN_HOME" ] || die "fail to move MAVEN_HOME"
+
+# Find the actual extracted directory name (handles snapshots where filename != directory name)
+actualDistributionDir=""
+
+# First try the expected directory name (for regular distributions)
+if [ -d "$TMP_DOWNLOAD_DIR/$distributionUrlNameMain" ]; then
+ if [ -f "$TMP_DOWNLOAD_DIR/$distributionUrlNameMain/bin/$MVN_CMD" ]; then
+ actualDistributionDir="$distributionUrlNameMain"
+ fi
+fi
+
+# If not found, search for any directory with the Maven executable (for snapshots)
+if [ -z "$actualDistributionDir" ]; then
+ # enable globbing to iterate over items
+ set +f
+ for dir in "$TMP_DOWNLOAD_DIR"/*; do
+ if [ -d "$dir" ]; then
+ if [ -f "$dir/bin/$MVN_CMD" ]; then
+ actualDistributionDir="$(basename "$dir")"
+ break
+ fi
+ fi
+ done
+ set -f
+fi
+
+if [ -z "$actualDistributionDir" ]; then
+ verbose "Contents of $TMP_DOWNLOAD_DIR:"
+ verbose "$(ls -la "$TMP_DOWNLOAD_DIR")"
+ die "Could not find Maven distribution directory in extracted archive"
+fi
+
+verbose "Found extracted Maven distribution directory: $actualDistributionDir"
+printf %s\\n "$distributionUrl" >"$TMP_DOWNLOAD_DIR/$actualDistributionDir/mvnw.url"
+mv -- "$TMP_DOWNLOAD_DIR/$actualDistributionDir" "$MAVEN_HOME" || [ -d "$MAVEN_HOME" ] || die "fail to move MAVEN_HOME"
clean || :
exec_maven "$@"
diff --git a/mvnw.cmd b/mvnw.cmd
index 249bdf382..5761d9489 100644
--- a/mvnw.cmd
+++ b/mvnw.cmd
@@ -1,149 +1,189 @@
-<# : batch portion
-@REM ----------------------------------------------------------------------------
-@REM Licensed to the Apache Software Foundation (ASF) under one
-@REM or more contributor license agreements. See the NOTICE file
-@REM distributed with this work for additional information
-@REM regarding copyright ownership. The ASF licenses this file
-@REM to you under the Apache License, Version 2.0 (the
-@REM "License"); you may not use this file except in compliance
-@REM with the License. You may obtain a copy of the License at
-@REM
-@REM http://www.apache.org/licenses/LICENSE-2.0
-@REM
-@REM Unless required by applicable law or agreed to in writing,
-@REM software distributed under the License is distributed on an
-@REM "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-@REM KIND, either express or implied. See the License for the
-@REM specific language governing permissions and limitations
-@REM under the License.
-@REM ----------------------------------------------------------------------------
-
-@REM ----------------------------------------------------------------------------
-@REM Apache Maven Wrapper startup batch script, version 3.3.2
-@REM
-@REM Optional ENV vars
-@REM MVNW_REPOURL - repo url base for downloading maven distribution
-@REM MVNW_USERNAME/MVNW_PASSWORD - user and password for downloading maven
-@REM MVNW_VERBOSE - true: enable verbose log; others: silence the output
-@REM ----------------------------------------------------------------------------
-
-@IF "%__MVNW_ARG0_NAME__%"=="" (SET __MVNW_ARG0_NAME__=%~nx0)
-@SET __MVNW_CMD__=
-@SET __MVNW_ERROR__=
-@SET __MVNW_PSMODULEP_SAVE=%PSModulePath%
-@SET PSModulePath=
-@FOR /F "usebackq tokens=1* delims==" %%A IN (`powershell -noprofile "& {$scriptDir='%~dp0'; $script='%__MVNW_ARG0_NAME__%'; icm -ScriptBlock ([Scriptblock]::Create((Get-Content -Raw '%~f0'))) -NoNewScope}"`) DO @(
- IF "%%A"=="MVN_CMD" (set __MVNW_CMD__=%%B) ELSE IF "%%B"=="" (echo %%A) ELSE (echo %%A=%%B)
-)
-@SET PSModulePath=%__MVNW_PSMODULEP_SAVE%
-@SET __MVNW_PSMODULEP_SAVE=
-@SET __MVNW_ARG0_NAME__=
-@SET MVNW_USERNAME=
-@SET MVNW_PASSWORD=
-@IF NOT "%__MVNW_CMD__%"=="" (%__MVNW_CMD__% %*)
-@echo Cannot start maven from wrapper >&2 && exit /b 1
-@GOTO :EOF
-: end batch / begin powershell #>
-
-$ErrorActionPreference = "Stop"
-if ($env:MVNW_VERBOSE -eq "true") {
- $VerbosePreference = "Continue"
-}
-
-# calculate distributionUrl, requires .mvn/wrapper/maven-wrapper.properties
-$distributionUrl = (Get-Content -Raw "$scriptDir/.mvn/wrapper/maven-wrapper.properties" | ConvertFrom-StringData).distributionUrl
-if (!$distributionUrl) {
- Write-Error "cannot read distributionUrl property in $scriptDir/.mvn/wrapper/maven-wrapper.properties"
-}
-
-switch -wildcard -casesensitive ( $($distributionUrl -replace '^.*/','') ) {
- "maven-mvnd-*" {
- $USE_MVND = $true
- $distributionUrl = $distributionUrl -replace '-bin\.[^.]*$',"-windows-amd64.zip"
- $MVN_CMD = "mvnd.cmd"
- break
- }
- default {
- $USE_MVND = $false
- $MVN_CMD = $script -replace '^mvnw','mvn'
- break
- }
-}
-
-# apply MVNW_REPOURL and calculate MAVEN_HOME
-# maven home pattern: ~/.m2/wrapper/dists/{apache-maven-,maven-mvnd--}/
-if ($env:MVNW_REPOURL) {
- $MVNW_REPO_PATTERN = if ($USE_MVND) { "/org/apache/maven/" } else { "/maven/mvnd/" }
- $distributionUrl = "$env:MVNW_REPOURL$MVNW_REPO_PATTERN$($distributionUrl -replace '^.*'+$MVNW_REPO_PATTERN,'')"
-}
-$distributionUrlName = $distributionUrl -replace '^.*/',''
-$distributionUrlNameMain = $distributionUrlName -replace '\.[^.]*$','' -replace '-bin$',''
-$MAVEN_HOME_PARENT = "$HOME/.m2/wrapper/dists/$distributionUrlNameMain"
-if ($env:MAVEN_USER_HOME) {
- $MAVEN_HOME_PARENT = "$env:MAVEN_USER_HOME/wrapper/dists/$distributionUrlNameMain"
-}
-$MAVEN_HOME_NAME = ([System.Security.Cryptography.MD5]::Create().ComputeHash([byte[]][char[]]$distributionUrl) | ForEach-Object {$_.ToString("x2")}) -join ''
-$MAVEN_HOME = "$MAVEN_HOME_PARENT/$MAVEN_HOME_NAME"
-
-if (Test-Path -Path "$MAVEN_HOME" -PathType Container) {
- Write-Verbose "found existing MAVEN_HOME at $MAVEN_HOME"
- Write-Output "MVN_CMD=$MAVEN_HOME/bin/$MVN_CMD"
- exit $?
-}
-
-if (! $distributionUrlNameMain -or ($distributionUrlName -eq $distributionUrlNameMain)) {
- Write-Error "distributionUrl is not valid, must end with *-bin.zip, but found $distributionUrl"
-}
-
-# prepare tmp dir
-$TMP_DOWNLOAD_DIR_HOLDER = New-TemporaryFile
-$TMP_DOWNLOAD_DIR = New-Item -Itemtype Directory -Path "$TMP_DOWNLOAD_DIR_HOLDER.dir"
-$TMP_DOWNLOAD_DIR_HOLDER.Delete() | Out-Null
-trap {
- if ($TMP_DOWNLOAD_DIR.Exists) {
- try { Remove-Item $TMP_DOWNLOAD_DIR -Recurse -Force | Out-Null }
- catch { Write-Warning "Cannot remove $TMP_DOWNLOAD_DIR" }
- }
-}
-
-New-Item -Itemtype Directory -Path "$MAVEN_HOME_PARENT" -Force | Out-Null
-
-# Download and Install Apache Maven
-Write-Verbose "Couldn't find MAVEN_HOME, downloading and installing it ..."
-Write-Verbose "Downloading from: $distributionUrl"
-Write-Verbose "Downloading to: $TMP_DOWNLOAD_DIR/$distributionUrlName"
-
-$webclient = New-Object System.Net.WebClient
-if ($env:MVNW_USERNAME -and $env:MVNW_PASSWORD) {
- $webclient.Credentials = New-Object System.Net.NetworkCredential($env:MVNW_USERNAME, $env:MVNW_PASSWORD)
-}
-[Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12
-$webclient.DownloadFile($distributionUrl, "$TMP_DOWNLOAD_DIR/$distributionUrlName") | Out-Null
-
-# If specified, validate the SHA-256 sum of the Maven distribution zip file
-$distributionSha256Sum = (Get-Content -Raw "$scriptDir/.mvn/wrapper/maven-wrapper.properties" | ConvertFrom-StringData).distributionSha256Sum
-if ($distributionSha256Sum) {
- if ($USE_MVND) {
- Write-Error "Checksum validation is not supported for maven-mvnd. `nPlease disable validation by removing 'distributionSha256Sum' from your maven-wrapper.properties."
- }
- Import-Module $PSHOME\Modules\Microsoft.PowerShell.Utility -Function Get-FileHash
- if ((Get-FileHash "$TMP_DOWNLOAD_DIR/$distributionUrlName" -Algorithm SHA256).Hash.ToLower() -ne $distributionSha256Sum) {
- Write-Error "Error: Failed to validate Maven distribution SHA-256, your Maven distribution might be compromised. If you updated your Maven version, you need to update the specified distributionSha256Sum property."
- }
-}
-
-# unzip and move
-Expand-Archive "$TMP_DOWNLOAD_DIR/$distributionUrlName" -DestinationPath "$TMP_DOWNLOAD_DIR" | Out-Null
-Rename-Item -Path "$TMP_DOWNLOAD_DIR/$distributionUrlNameMain" -NewName $MAVEN_HOME_NAME | Out-Null
-try {
- Move-Item -Path "$TMP_DOWNLOAD_DIR/$MAVEN_HOME_NAME" -Destination $MAVEN_HOME_PARENT | Out-Null
-} catch {
- if (! (Test-Path -Path "$MAVEN_HOME" -PathType Container)) {
- Write-Error "fail to move MAVEN_HOME"
- }
-} finally {
- try { Remove-Item $TMP_DOWNLOAD_DIR -Recurse -Force | Out-Null }
- catch { Write-Warning "Cannot remove $TMP_DOWNLOAD_DIR" }
-}
-
-Write-Output "MVN_CMD=$MAVEN_HOME/bin/$MVN_CMD"
+<# : batch portion
+@REM ----------------------------------------------------------------------------
+@REM Licensed to the Apache Software Foundation (ASF) under one
+@REM or more contributor license agreements. See the NOTICE file
+@REM distributed with this work for additional information
+@REM regarding copyright ownership. The ASF licenses this file
+@REM to you under the Apache License, Version 2.0 (the
+@REM "License"); you may not use this file except in compliance
+@REM with the License. You may obtain a copy of the License at
+@REM
+@REM http://www.apache.org/licenses/LICENSE-2.0
+@REM
+@REM Unless required by applicable law or agreed to in writing,
+@REM software distributed under the License is distributed on an
+@REM "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+@REM KIND, either express or implied. See the License for the
+@REM specific language governing permissions and limitations
+@REM under the License.
+@REM ----------------------------------------------------------------------------
+
+@REM ----------------------------------------------------------------------------
+@REM Apache Maven Wrapper startup batch script, version 3.3.4
+@REM
+@REM Optional ENV vars
+@REM MVNW_REPOURL - repo url base for downloading maven distribution
+@REM MVNW_USERNAME/MVNW_PASSWORD - user and password for downloading maven
+@REM MVNW_VERBOSE - true: enable verbose log; others: silence the output
+@REM ----------------------------------------------------------------------------
+
+@IF "%__MVNW_ARG0_NAME__%"=="" (SET __MVNW_ARG0_NAME__=%~nx0)
+@SET __MVNW_CMD__=
+@SET __MVNW_ERROR__=
+@SET __MVNW_PSMODULEP_SAVE=%PSModulePath%
+@SET PSModulePath=
+@FOR /F "usebackq tokens=1* delims==" %%A IN (`powershell -noprofile "& {$scriptDir='%~dp0'; $script='%__MVNW_ARG0_NAME__%'; icm -ScriptBlock ([Scriptblock]::Create((Get-Content -Raw '%~f0'))) -NoNewScope}"`) DO @(
+ IF "%%A"=="MVN_CMD" (set __MVNW_CMD__=%%B) ELSE IF "%%B"=="" (echo %%A) ELSE (echo %%A=%%B)
+)
+@SET PSModulePath=%__MVNW_PSMODULEP_SAVE%
+@SET __MVNW_PSMODULEP_SAVE=
+@SET __MVNW_ARG0_NAME__=
+@SET MVNW_USERNAME=
+@SET MVNW_PASSWORD=
+@IF NOT "%__MVNW_CMD__%"=="" ("%__MVNW_CMD__%" %*)
+@echo Cannot start maven from wrapper >&2 && exit /b 1
+@GOTO :EOF
+: end batch / begin powershell #>
+
+$ErrorActionPreference = "Stop"
+if ($env:MVNW_VERBOSE -eq "true") {
+ $VerbosePreference = "Continue"
+}
+
+# calculate distributionUrl, requires .mvn/wrapper/maven-wrapper.properties
+$distributionUrl = (Get-Content -Raw "$scriptDir/.mvn/wrapper/maven-wrapper.properties" | ConvertFrom-StringData).distributionUrl
+if (!$distributionUrl) {
+ Write-Error "cannot read distributionUrl property in $scriptDir/.mvn/wrapper/maven-wrapper.properties"
+}
+
+switch -wildcard -casesensitive ( $($distributionUrl -replace '^.*/','') ) {
+ "maven-mvnd-*" {
+ $USE_MVND = $true
+ $distributionUrl = $distributionUrl -replace '-bin\.[^.]*$',"-windows-amd64.zip"
+ $MVN_CMD = "mvnd.cmd"
+ break
+ }
+ default {
+ $USE_MVND = $false
+ $MVN_CMD = $script -replace '^mvnw','mvn'
+ break
+ }
+}
+
+# apply MVNW_REPOURL and calculate MAVEN_HOME
+# maven home pattern: ~/.m2/wrapper/dists/{apache-maven-,maven-mvnd--}/
+if ($env:MVNW_REPOURL) {
+ $MVNW_REPO_PATTERN = if ($USE_MVND -eq $False) { "/org/apache/maven/" } else { "/maven/mvnd/" }
+ $distributionUrl = "$env:MVNW_REPOURL$MVNW_REPO_PATTERN$($distributionUrl -replace "^.*$MVNW_REPO_PATTERN",'')"
+}
+$distributionUrlName = $distributionUrl -replace '^.*/',''
+$distributionUrlNameMain = $distributionUrlName -replace '\.[^.]*$','' -replace '-bin$',''
+
+$MAVEN_M2_PATH = "$HOME/.m2"
+if ($env:MAVEN_USER_HOME) {
+ $MAVEN_M2_PATH = "$env:MAVEN_USER_HOME"
+}
+
+if (-not (Test-Path -Path $MAVEN_M2_PATH)) {
+ New-Item -Path $MAVEN_M2_PATH -ItemType Directory | Out-Null
+}
+
+$MAVEN_WRAPPER_DISTS = $null
+if ((Get-Item $MAVEN_M2_PATH).Target[0] -eq $null) {
+ $MAVEN_WRAPPER_DISTS = "$MAVEN_M2_PATH/wrapper/dists"
+} else {
+ $MAVEN_WRAPPER_DISTS = (Get-Item $MAVEN_M2_PATH).Target[0] + "/wrapper/dists"
+}
+
+$MAVEN_HOME_PARENT = "$MAVEN_WRAPPER_DISTS/$distributionUrlNameMain"
+$MAVEN_HOME_NAME = ([System.Security.Cryptography.SHA256]::Create().ComputeHash([byte[]][char[]]$distributionUrl) | ForEach-Object {$_.ToString("x2")}) -join ''
+$MAVEN_HOME = "$MAVEN_HOME_PARENT/$MAVEN_HOME_NAME"
+
+if (Test-Path -Path "$MAVEN_HOME" -PathType Container) {
+ Write-Verbose "found existing MAVEN_HOME at $MAVEN_HOME"
+ Write-Output "MVN_CMD=$MAVEN_HOME/bin/$MVN_CMD"
+ exit $?
+}
+
+if (! $distributionUrlNameMain -or ($distributionUrlName -eq $distributionUrlNameMain)) {
+ Write-Error "distributionUrl is not valid, must end with *-bin.zip, but found $distributionUrl"
+}
+
+# prepare tmp dir
+$TMP_DOWNLOAD_DIR_HOLDER = New-TemporaryFile
+$TMP_DOWNLOAD_DIR = New-Item -Itemtype Directory -Path "$TMP_DOWNLOAD_DIR_HOLDER.dir"
+$TMP_DOWNLOAD_DIR_HOLDER.Delete() | Out-Null
+trap {
+ if ($TMP_DOWNLOAD_DIR.Exists) {
+ try { Remove-Item $TMP_DOWNLOAD_DIR -Recurse -Force | Out-Null }
+ catch { Write-Warning "Cannot remove $TMP_DOWNLOAD_DIR" }
+ }
+}
+
+New-Item -Itemtype Directory -Path "$MAVEN_HOME_PARENT" -Force | Out-Null
+
+# Download and Install Apache Maven
+Write-Verbose "Couldn't find MAVEN_HOME, downloading and installing it ..."
+Write-Verbose "Downloading from: $distributionUrl"
+Write-Verbose "Downloading to: $TMP_DOWNLOAD_DIR/$distributionUrlName"
+
+$webclient = New-Object System.Net.WebClient
+if ($env:MVNW_USERNAME -and $env:MVNW_PASSWORD) {
+ $webclient.Credentials = New-Object System.Net.NetworkCredential($env:MVNW_USERNAME, $env:MVNW_PASSWORD)
+}
+[Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12
+$webclient.DownloadFile($distributionUrl, "$TMP_DOWNLOAD_DIR/$distributionUrlName") | Out-Null
+
+# If specified, validate the SHA-256 sum of the Maven distribution zip file
+$distributionSha256Sum = (Get-Content -Raw "$scriptDir/.mvn/wrapper/maven-wrapper.properties" | ConvertFrom-StringData).distributionSha256Sum
+if ($distributionSha256Sum) {
+ if ($USE_MVND) {
+ Write-Error "Checksum validation is not supported for maven-mvnd. `nPlease disable validation by removing 'distributionSha256Sum' from your maven-wrapper.properties."
+ }
+ Import-Module $PSHOME\Modules\Microsoft.PowerShell.Utility -Function Get-FileHash
+ if ((Get-FileHash "$TMP_DOWNLOAD_DIR/$distributionUrlName" -Algorithm SHA256).Hash.ToLower() -ne $distributionSha256Sum) {
+ Write-Error "Error: Failed to validate Maven distribution SHA-256, your Maven distribution might be compromised. If you updated your Maven version, you need to update the specified distributionSha256Sum property."
+ }
+}
+
+# unzip and move
+Expand-Archive "$TMP_DOWNLOAD_DIR/$distributionUrlName" -DestinationPath "$TMP_DOWNLOAD_DIR" | Out-Null
+
+# Find the actual extracted directory name (handles snapshots where filename != directory name)
+$actualDistributionDir = ""
+
+# First try the expected directory name (for regular distributions)
+$expectedPath = Join-Path "$TMP_DOWNLOAD_DIR" "$distributionUrlNameMain"
+$expectedMvnPath = Join-Path "$expectedPath" "bin/$MVN_CMD"
+if ((Test-Path -Path $expectedPath -PathType Container) -and (Test-Path -Path $expectedMvnPath -PathType Leaf)) {
+ $actualDistributionDir = $distributionUrlNameMain
+}
+
+# If not found, search for any directory with the Maven executable (for snapshots)
+if (!$actualDistributionDir) {
+ Get-ChildItem -Path "$TMP_DOWNLOAD_DIR" -Directory | ForEach-Object {
+ $testPath = Join-Path $_.FullName "bin/$MVN_CMD"
+ if (Test-Path -Path $testPath -PathType Leaf) {
+ $actualDistributionDir = $_.Name
+ }
+ }
+}
+
+if (!$actualDistributionDir) {
+ Write-Error "Could not find Maven distribution directory in extracted archive"
+}
+
+Write-Verbose "Found extracted Maven distribution directory: $actualDistributionDir"
+Rename-Item -Path "$TMP_DOWNLOAD_DIR/$actualDistributionDir" -NewName $MAVEN_HOME_NAME | Out-Null
+try {
+ Move-Item -Path "$TMP_DOWNLOAD_DIR/$MAVEN_HOME_NAME" -Destination $MAVEN_HOME_PARENT | Out-Null
+} catch {
+ if (! (Test-Path -Path "$MAVEN_HOME" -PathType Container)) {
+ Write-Error "fail to move MAVEN_HOME"
+ }
+} finally {
+ try { Remove-Item $TMP_DOWNLOAD_DIR -Recurse -Force | Out-Null }
+ catch { Write-Warning "Cannot remove $TMP_DOWNLOAD_DIR" }
+}
+
+Write-Output "MVN_CMD=$MAVEN_HOME/bin/$MVN_CMD"
diff --git a/pom.xml b/pom.xml
index e75dd506a..07e78eb42 100644
--- a/pom.xml
+++ b/pom.xml
@@ -5,16 +5,23 @@
dev.openfeaturesdk
- 1.14.0
+ 1.18.2
+ [17,)UTF-8
- 1.8
+ 11${maven.compiler.source}
- 5.11.4
+ 5.20.0
+ 1.2.22**/e2e/*.java${project.groupId}.${project.artifactId}
+ false
+
+ 11
+ ${settings.localRepository}/org/mockito/mockito-core/${org.mockito.version}/mockito-core-${org.mockito.version}.jar
+ -javaagent:${org.mockito.jar}OpenFeature Java SDK
@@ -48,7 +55,7 @@
org.projectlomboklombok
- 1.18.36
+ 1.18.42provided
@@ -56,63 +63,65 @@
com.github.spotbugsspotbugs
- 4.8.6
+ 4.9.8providedorg.slf4jslf4j-api
- 2.0.16
+ 2.0.17
+
+ com.tngtech.archunit
+ archunit-junit5
+ 1.4.1
+ test
+
+
org.mockitomockito-core
- 4.11.0
+ ${org.mockito.version}testorg.assertjassertj-core
- 3.27.3
+ 3.27.6testorg.junit.jupiterjunit-jupiter
- ${junit.jupiter.version}testorg.junit.jupiterjunit-jupiter-engine
- ${junit.jupiter.version}testorg.junit.jupiterjunit-jupiter-api
- ${junit.jupiter.version}testorg.junit.jupiterjunit-jupiter-params
- ${junit.jupiter.version}testorg.junit.platformjunit-platform-suite
- 1.11.4test
@@ -128,6 +137,12 @@
test
+
+ io.cucumber
+ cucumber-picocontainer
+ test
+
+
org.simplify4uslf4j2-mock
@@ -138,14 +153,14 @@
com.google.guavaguava
- 33.4.0-jre
+ 33.5.0-jretestorg.awaitilityawaitility
- 4.2.2
+ 4.3.0test
@@ -156,6 +171,38 @@
test
+
+ com.fasterxml.jackson.core
+ jackson-core
+ test
+
+
+
+ com.fasterxml.jackson.core
+ jackson-annotations
+ test
+
+
+
+ com.fasterxml.jackson.core
+ jackson-databind
+ test
+
+
+
+ dev.cel
+ cel
+ 0.11.1
+ test
+
+
+
+ com.vmlens
+ api
+ ${com.vmlens.version}
+ test
+
+
@@ -167,22 +214,30 @@
net.bytebuddybyte-buddy
- 1.17.0
+ 1.18.1testnet.bytebuddybyte-buddy-agent
- 1.17.0
+ 1.18.1test
+
+ com.fasterxml.jackson
+ jackson-bom
+ 2.20.1
+ pom
+ import
+
+
io.cucumbercucumber-bom
- 7.21.0
+ 7.31.0pomimport
@@ -190,16 +245,27 @@
org.junitjunit-bom
- 5.11.4
+ 6.0.1pomimport
-
+
+ org.apache.maven.plugins
+ maven-toolchains-plugin
+ 3.2.0
+
+
+
+ select-jdk-toolchain
+
+
+
+ org.cyclonedxcyclonedx-maven-plugin
@@ -226,47 +292,21 @@
-
- maven-dependency-plugin
- 3.8.1
-
-
- verify
-
- analyze
-
-
-
-
- true
-
- com.github.spotbugs:*
- org.junit*
- org.simplify4u:slf4j2-mock*
-
-
- com.google.guava*
- io.cucumber*
- org.junit*
- com.google.code.findbugs*
- com.github.spotbugs*
- org.simplify4u:slf4j-mock-common:*
-
-
-
-
maven-compiler-plugin
- 3.13.0
+ 3.14.1org.apache.maven.pluginsmaven-surefire-plugin
- 3.5.2
+ 3.5.4
${surefireArgLine}
+ ${org.mockito.agent.argline}
+ --add-opens java.base/java.util=ALL-UNNAMED
+ --add-opens java.base/java.lang=ALL-UNNAMED
@@ -278,78 +318,20 @@
org.apache.maven.pluginsmaven-failsafe-plugin
- 3.5.2
+ 3.5.4
${surefireArgLine}
+ ${org.mockito.agent.argline}
-
- org.jacoco
- jacoco-maven-plugin
- 0.8.12
-
-
-
- prepare-agent
-
- prepare-agent
-
-
-
- ${project.build.directory}/coverage-reports/jacoco-ut.exec
- surefireArgLine
-
-
-
-
- report
- verify
-
- report
-
-
-
- ${project.build.directory}/coverage-reports/jacoco-ut.exec
- ${project.reporting.outputDirectory}/jacoco-ut
-
-
-
-
- jacoco-check
-
- check
-
-
- ${project.build.directory}/coverage-reports/jacoco-ut.exec
-
- dev/openfeature/sdk/exceptions/**
-
-
-
-
- PACKAGE
-
-
- LINE
- COVEREDRATIO
- 0.80
-
-
-
-
-
-
-
-
- org.apache.maven.pluginsmaven-jar-plugin
- 3.4.2
+ 3.5.0
@@ -358,156 +340,234 @@
-
-
- org.apache.maven.plugins
- maven-pmd-plugin
- 3.26.0
-
-
- run-pmd
- verify
-
- check
-
-
-
-
-
-
- com.github.spotbugs
- spotbugs-maven-plugin
- 4.8.6.6
-
- spotbugs-exclusions.xml
-
-
- com.h3xstream.findsecbugs
- findsecbugs-plugin
- 1.13.0
-
-
-
-
-
-
- com.github.spotbugs
- spotbugs
- 4.8.6
-
-
-
-
- run-spotbugs
- verify
-
- check
-
-
-
-
-
-
- org.apache.maven.plugins
- maven-checkstyle-plugin
- 3.6.0
-
- checkstyle.xml
- UTF-8
- true
- true
- false
-
-
-
- com.puppycrawl.tools
- checkstyle
- 9.3
-
-
-
-
- validate
- validate
-
- check
-
-
-
-
-
- com.diffplug.spotless
- spotless-maven-plugin
- 2.30.0
-
-
-
-
-
-
-
-
- .gitattributes
- .gitignore
-
-
-
-
-
- true
- 4
-
-
-
-
-
-
-
-
- true
- 4
-
-
-
-
-
-
-
-
-
-
-
- check
-
-
-
-
-
- deploy
+ codequalitytrue
-
-
- org.sonatype.plugins
- nexus-staging-maven-plugin
- 1.7.0
- true
+ com.vmlens
+ vmlens-maven-plugin
+ ${com.vmlens.version}
+
+
+ test
+
+ test
+
+
+
+ **/*CT.java
+
+ true
+ ${org.mockito.agent.argline}
+
+
+
+
+
+ maven-dependency-plugin
+ 3.9.0
+
+
+ verify
+
+ analyze
+
+
+
- ossrh
- https://s01.oss.sonatype.org/
- true
+ true
+
+ com.github.spotbugs:*
+ org.junit*
+ com.tngtech.archunit*
+ org.simplify4u:slf4j2-mock*
+
+
+ com.google.guava*
+ io.cucumber*
+ org.junit*
+ com.tngtech.archunit*
+ com.google.code.findbugs*
+ com.github.spotbugs*
+ org.simplify4u:slf4j-mock-common:*
+
-
+
+
+ org.jacoco
+ jacoco-maven-plugin
+ 0.8.14
+
+
+
+ prepare-agent
+
+ prepare-agent
+
+
+
+ ${project.build.directory}/coverage-reports/jacoco-ut.exec
+ surefireArgLine
+
+
+
+
+ report
+ verify
+
+ report
+
+
+
+ ${project.build.directory}/coverage-reports/jacoco-ut.exec
+ ${project.reporting.outputDirectory}/jacoco-ut
+
+
+
+
+ jacoco-check
+
+ check
+
+
+ ${project.build.directory}/coverage-reports/jacoco-ut.exec
+
+ dev/openfeature/sdk/exceptions/**
+
+
+
+
+ PACKAGE
+
+
+ LINE
+ COVEREDRATIO
+ 0.70
+
+
+
+
+
+
+
+
+
+
+ com.github.spotbugs
+ spotbugs-maven-plugin
+ 4.9.8.1
+
+ spotbugs-exclusions.xml
+
+
+ com.h3xstream.findsecbugs
+ findsecbugs-plugin
+ 1.14.0
+
+
+
+
+
+
+ com.github.spotbugs
+ spotbugs
+ 4.9.8
+
+
+
+
+ run-spotbugs
+ verify
+
+ check
+
+
+
+
+
+
+ org.apache.maven.plugins
+ maven-checkstyle-plugin
+ 3.6.0
+
+ checkstyle.xml
+ true
+ true
+ false
+
+
+
+ com.puppycrawl.tools
+ checkstyle
+ 12.1.2
+
+
+
+
+ validate
+ validate
+
+ check
+
+
+
+
+
+ com.diffplug.spotless
+ spotless-maven-plugin
+ 3.1.0
+
+
+
+
+
+
+
+
+ .gitattributes
+ .gitignore
+
+
+
+
+
+ true
+ 4
+
+
+
+
+
+
+
+
+ true
+ 4
+
+
+
+
+
+
+
+
+
+
+
+ check
+
+
+
+
@@ -527,7 +587,7 @@
org.apache.maven.pluginsmaven-javadoc-plugin
- 3.11.2
+ 3.12.0trueall,-missing
@@ -543,12 +603,35 @@
+
+
+
+
+ deploy
+
+ true
+
+
+
+
+
+
+ org.sonatype.central
+ central-publishing-maven-plugin
+ 0.9.0
+ true
+
+ central
+ true
+
+
+
org.apache.maven.pluginsmaven-gpg-plugin
- 3.2.7
+ 3.2.8sign-artifacts
@@ -589,7 +672,7 @@
org.codehaus.mojoexec-maven-plugin
- 3.5.0
+ 3.6.2update-test-harness-submodule
@@ -608,19 +691,76 @@
+
+
+
+
+
+
+
+
+ java11
+
+
+
+ [11,)
+ true
+
+
+
+
+
+ org.apache.maven.plugins
+ maven-toolchains-plugin
+ 3.2.0
+
+
+
+ select-jdk-toolchain
+
+
+
+
+
+ org.apache.maven.plugins
+ maven-surefire-plugin
+ 3.5.4
+
+
+ ${surefireArgLine}
+
+
+
+ ${testExclusions}
+
+
+ ${skip.tests}
+
+
+
+ org.apache.maven.plugins
+ maven-failsafe-plugin
+ 3.5.4
+
+
+ ${org.mockito.agent.argline}
+ ${surefireArgLine}
+
+
+
+
+ org.apache.maven.plugins
+ maven-compiler-plugin
+ 3.14.1
+
- copy-evaluation-gherkin-tests
- validate
+ default-testCompile
+ test-compile
- exec
+ testCompile
-
- cp
-
- spec/specification/assets/gherkin/evaluation.feature
- src/test/resources/features/
-
+ true
@@ -632,8 +772,8 @@
- ossrh
- https://s01.oss.sonatype.org/content/repositories/snapshots
+ central
+ https://central.sonatype.com/repository/maven-snapshots/
diff --git a/release-please-config.json b/release-please-config.json
index ad00d89a5..bc4fa6b53 100644
--- a/release-please-config.json
+++ b/release-please-config.json
@@ -1,5 +1,6 @@
{
- "bootstrap-sha": "c701a6c4ebbe1170a25ca7636a31508b9628831c",
+ "bootstrap-sha": "d7b591c9f910afad303d6d814f65c7f9dab33b89",
+ "signoff": "OpenFeature Bot <109696520+openfeaturebot@users.noreply.github.com>",
"packages": {
".": {
"package-name": "dev.openfeature.sdk",
diff --git a/release/m2-settings.xml b/release/m2-settings.xml
index 9b7a585a3..517375160 100644
--- a/release/m2-settings.xml
+++ b/release/m2-settings.xml
@@ -5,5 +5,10 @@
${env.OSSRH_USERNAME}${env.OSSRH_PASSWORD}
+
+ central
+ ${env.CENTRAL_USERNAME}
+ ${env.CENTRAL_PASSWORD}
+
diff --git a/spec b/spec
index d4a9a9109..e33a15e92 160000
--- a/spec
+++ b/spec
@@ -1 +1 @@
-Subproject commit d4a9a910946eded57cf82d6fd4921785a5e64c2b
+Subproject commit e33a15e92bd0e45f0de087e7e55ee7e87f952c29
diff --git a/spotbugs-exclusions.xml b/spotbugs-exclusions.xml
index 66032ad08..b841bbad4 100644
--- a/spotbugs-exclusions.xml
+++ b/spotbugs-exclusions.xml
@@ -49,7 +49,6 @@
-
@@ -58,4 +57,4 @@
-
\ No newline at end of file
+
diff --git a/src/main/java/dev/openfeature/sdk/AbstractStructure.java b/src/main/java/dev/openfeature/sdk/AbstractStructure.java
index 6c652114c..7962705c3 100644
--- a/src/main/java/dev/openfeature/sdk/AbstractStructure.java
+++ b/src/main/java/dev/openfeature/sdk/AbstractStructure.java
@@ -3,15 +3,17 @@
import java.util.Collections;
import java.util.HashMap;
import java.util.Map;
+import lombok.EqualsAndHashCode;
@SuppressWarnings({"PMD.BeanMembersShouldSerialize", "checkstyle:MissingJavadocType"})
+@EqualsAndHashCode
abstract class AbstractStructure implements Structure {
protected final Map attributes;
@Override
public boolean isEmpty() {
- return attributes == null || attributes.size() == 0;
+ return attributes == null || attributes.isEmpty();
}
AbstractStructure() {
diff --git a/src/main/java/dev/openfeature/sdk/Awaitable.java b/src/main/java/dev/openfeature/sdk/Awaitable.java
new file mode 100644
index 000000000..7d5f477dc
--- /dev/null
+++ b/src/main/java/dev/openfeature/sdk/Awaitable.java
@@ -0,0 +1,44 @@
+package dev.openfeature.sdk;
+
+/**
+ * A class to help with synchronization by allowing the optional awaiting of the associated action.
+ */
+public class Awaitable {
+
+ /**
+ * An already-completed Awaitable. Awaiting this will return immediately.
+ */
+ public static final Awaitable FINISHED = new Awaitable(true);
+
+ private boolean isDone = false;
+
+ public Awaitable() {}
+
+ private Awaitable(boolean isDone) {
+ this.isDone = isDone;
+ }
+
+ /**
+ * Lets the calling thread wait until some other thread calls {@link Awaitable#wakeup()}. If
+ * {@link Awaitable#wakeup()} has been called before the current thread invokes this method, it will return
+ * immediately.
+ */
+ @SuppressWarnings("java:S2142")
+ public synchronized void await() {
+ while (!isDone) {
+ try {
+ this.wait();
+ } catch (InterruptedException ignored) {
+ // ignored, do not propagate the interrupted state
+ }
+ }
+ }
+
+ /**
+ * Wakes up all threads that have called {@link Awaitable#await()} and lets them proceed.
+ */
+ public synchronized void wakeup() {
+ isDone = true;
+ this.notifyAll();
+ }
+}
diff --git a/src/main/java/dev/openfeature/sdk/DefaultHookData.java b/src/main/java/dev/openfeature/sdk/DefaultHookData.java
new file mode 100644
index 000000000..d0efe49d0
--- /dev/null
+++ b/src/main/java/dev/openfeature/sdk/DefaultHookData.java
@@ -0,0 +1,39 @@
+package dev.openfeature.sdk;
+
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * Default implementation of HookData.
+ */
+public class DefaultHookData implements HookData {
+ private Map data;
+
+ @Override
+ public void set(String key, Object value) {
+ if (data == null) {
+ data = new HashMap<>();
+ }
+ data.put(key, value);
+ }
+
+ @Override
+ public Object get(String key) {
+ if (data == null) {
+ return null;
+ }
+ return data.get(key);
+ }
+
+ @Override
+ public T get(String key, Class type) {
+ Object value = get(key);
+ if (value == null) {
+ return null;
+ }
+ if (!type.isInstance(value)) {
+ throw new ClassCastException("Value for key '" + key + "' is not of type " + type.getName());
+ }
+ return type.cast(value);
+ }
+}
diff --git a/src/main/java/dev/openfeature/sdk/EvaluationEvent.java b/src/main/java/dev/openfeature/sdk/EvaluationEvent.java
new file mode 100644
index 000000000..f92e24d5a
--- /dev/null
+++ b/src/main/java/dev/openfeature/sdk/EvaluationEvent.java
@@ -0,0 +1,24 @@
+package dev.openfeature.sdk;
+
+import java.util.HashMap;
+import java.util.Map;
+import lombok.Builder;
+import lombok.Getter;
+import lombok.Singular;
+
+/**
+ * Represents an evaluation event.
+ */
+@Builder
+@Getter
+public class EvaluationEvent {
+
+ private String name;
+
+ @Singular("attribute")
+ private Map attributes;
+
+ public Map getAttributes() {
+ return new HashMap<>(attributes);
+ }
+}
diff --git a/src/main/java/dev/openfeature/sdk/EventDetails.java b/src/main/java/dev/openfeature/sdk/EventDetails.java
index e32e61013..c75b046e0 100644
--- a/src/main/java/dev/openfeature/sdk/EventDetails.java
+++ b/src/main/java/dev/openfeature/sdk/EventDetails.java
@@ -1,11 +1,13 @@
package dev.openfeature.sdk;
import lombok.Data;
+import lombok.EqualsAndHashCode;
import lombok.experimental.SuperBuilder;
/**
* The details of a particular event.
*/
+@EqualsAndHashCode(callSuper = true)
@Data
@SuperBuilder(toBuilder = true)
public class EventDetails extends ProviderEventDetails {
diff --git a/src/main/java/dev/openfeature/sdk/EventProvider.java b/src/main/java/dev/openfeature/sdk/EventProvider.java
index e9cdae55b..4ccac184e 100644
--- a/src/main/java/dev/openfeature/sdk/EventProvider.java
+++ b/src/main/java/dev/openfeature/sdk/EventProvider.java
@@ -1,6 +1,11 @@
package dev.openfeature.sdk;
+import dev.openfeature.sdk.internal.ConfigurableThreadFactory;
import dev.openfeature.sdk.internal.TriConsumer;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+import java.util.concurrent.TimeUnit;
+import lombok.extern.slf4j.Slf4j;
/**
* Abstract EventProvider. Providers must extend this class to support events.
@@ -14,8 +19,11 @@
*
* @see FeatureProvider
*/
+@Slf4j
public abstract class EventProvider implements FeatureProvider {
private EventProviderListener eventProviderListener;
+ private final ExecutorService emitterExecutor =
+ Executors.newCachedThreadPool(new ConfigurableThreadFactory("openfeature-event-emitter-thread"));
void setEventProviderListener(EventProviderListener eventProviderListener) {
this.eventProviderListener = eventProviderListener;
@@ -46,19 +54,56 @@ void detach() {
this.onEmit = null;
}
+ /**
+ * Stop the event emitter executor and block until either termination has completed
+ * or timeout period has elapsed.
+ */
+ @Override
+ public void shutdown() {
+ emitterExecutor.shutdown();
+ try {
+ if (!emitterExecutor.awaitTermination(EventSupport.SHUTDOWN_TIMEOUT_SECONDS, TimeUnit.SECONDS)) {
+ log.warn("Emitter executor did not terminate before the timeout period had elapsed");
+ emitterExecutor.shutdownNow();
+ }
+ } catch (InterruptedException e) {
+ emitterExecutor.shutdownNow();
+ Thread.currentThread().interrupt();
+ }
+ }
+
/**
* Emit the specified {@link ProviderEvent}.
*
* @param event The event type
* @param details The details of the event
*/
- public void emit(ProviderEvent event, ProviderEventDetails details) {
- if (eventProviderListener != null) {
- eventProviderListener.onEmit(event, details);
- }
- if (this.onEmit != null) {
- this.onEmit.accept(this, event, details);
+ public Awaitable emit(final ProviderEvent event, final ProviderEventDetails details) {
+ final var localEventProviderListener = this.eventProviderListener;
+ final var localOnEmit = this.onEmit;
+
+ if (localEventProviderListener == null && localOnEmit == null) {
+ return Awaitable.FINISHED;
}
+
+ final var awaitable = new Awaitable();
+
+ // These calls need to be executed on a different thread to prevent deadlocks when the provider initialization
+ // relies on a ready event to be emitted
+ emitterExecutor.submit(() -> {
+ try (var ignored = OpenFeatureAPI.lock.readLockAutoCloseable()) {
+ if (localEventProviderListener != null) {
+ localEventProviderListener.onEmit(event, details);
+ }
+ if (localOnEmit != null) {
+ localOnEmit.accept(this, event, details);
+ }
+ } finally {
+ awaitable.wakeup();
+ }
+ });
+
+ return awaitable;
}
/**
@@ -67,8 +112,8 @@ public void emit(ProviderEvent event, ProviderEventDetails details) {
*
* @param details The details of the event
*/
- public void emitProviderReady(ProviderEventDetails details) {
- emit(ProviderEvent.PROVIDER_READY, details);
+ public Awaitable emitProviderReady(ProviderEventDetails details) {
+ return emit(ProviderEvent.PROVIDER_READY, details);
}
/**
@@ -78,8 +123,8 @@ public void emitProviderReady(ProviderEventDetails details) {
*
* @param details The details of the event
*/
- public void emitProviderConfigurationChanged(ProviderEventDetails details) {
- emit(ProviderEvent.PROVIDER_CONFIGURATION_CHANGED, details);
+ public Awaitable emitProviderConfigurationChanged(ProviderEventDetails details) {
+ return emit(ProviderEvent.PROVIDER_CONFIGURATION_CHANGED, details);
}
/**
@@ -88,8 +133,8 @@ public void emitProviderConfigurationChanged(ProviderEventDetails details) {
*
* @param details The details of the event
*/
- public void emitProviderStale(ProviderEventDetails details) {
- emit(ProviderEvent.PROVIDER_STALE, details);
+ public Awaitable emitProviderStale(ProviderEventDetails details) {
+ return emit(ProviderEvent.PROVIDER_STALE, details);
}
/**
@@ -98,7 +143,7 @@ public void emitProviderStale(ProviderEventDetails details) {
*
* @param details The details of the event
*/
- public void emitProviderError(ProviderEventDetails details) {
- emit(ProviderEvent.PROVIDER_ERROR, details);
+ public Awaitable emitProviderError(ProviderEventDetails details) {
+ return emit(ProviderEvent.PROVIDER_ERROR, details);
}
}
diff --git a/src/main/java/dev/openfeature/sdk/EventSupport.java b/src/main/java/dev/openfeature/sdk/EventSupport.java
index d3af45991..0b446c6b2 100644
--- a/src/main/java/dev/openfeature/sdk/EventSupport.java
+++ b/src/main/java/dev/openfeature/sdk/EventSupport.java
@@ -1,12 +1,13 @@
package dev.openfeature.sdk;
-import java.util.ArrayList;
-import java.util.List;
+import dev.openfeature.sdk.internal.ConfigurableThreadFactory;
+import java.util.Collection;
import java.util.Map;
import java.util.Optional;
import java.util.Set;
import java.util.UUID;
import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.ConcurrentLinkedQueue;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.TimeUnit;
@@ -19,17 +20,15 @@
@Slf4j
class EventSupport {
+ public static final int SHUTDOWN_TIMEOUT_SECONDS = 3;
+
// we use a v4 uuid as a "placeholder" for anonymous clients, since
// ConcurrentHashMap doesn't support nulls
- private static final String defaultClientUuid = UUID.randomUUID().toString();
- private static final int SHUTDOWN_TIMEOUT_SECONDS = 3;
+ private static final String DEFAULT_CLIENT_UUID = UUID.randomUUID().toString();
private final Map handlerStores = new ConcurrentHashMap<>();
private final HandlerStore globalHandlerStore = new HandlerStore();
- private final ExecutorService taskExecutor = Executors.newCachedThreadPool(runnable -> {
- final Thread thread = new Thread(runnable);
- thread.setDaemon(true);
- return thread;
- });
+ private final ExecutorService taskExecutor =
+ Executors.newCachedThreadPool(new ConfigurableThreadFactory("openfeature-event-handler-thread"));
/**
* Run all the event handlers associated with this domain.
@@ -40,11 +39,10 @@ class EventSupport {
* @param eventDetails the event details
*/
public void runClientHandlers(String domain, ProviderEvent event, EventDetails eventDetails) {
- domain = Optional.ofNullable(domain).orElse(defaultClientUuid);
+ domain = Optional.ofNullable(domain).orElse(DEFAULT_CLIENT_UUID);
// run handlers if they exist
Optional.ofNullable(handlerStores.get(domain))
- .filter(store -> Optional.of(store).isPresent())
.map(store -> store.handlerMap.get(event))
.ifPresent(handlers -> handlers.forEach(handler -> runHandler(handler, eventDetails)));
}
@@ -69,7 +67,7 @@ public void runGlobalHandlers(ProviderEvent event, EventDetails eventDetails) {
* @param handler the handler function to run
*/
public void addClientHandler(String domain, ProviderEvent event, Consumer handler) {
- final String name = Optional.ofNullable(domain).orElse(defaultClientUuid);
+ final String name = Optional.ofNullable(domain).orElse(DEFAULT_CLIENT_UUID);
// lazily create and cache a HandlerStore if it doesn't exist
HandlerStore store = Optional.ofNullable(this.handlerStores.get(name)).orElseGet(() -> {
@@ -89,7 +87,7 @@ public void addClientHandler(String domain, ProviderEvent event, Consumer handler) {
- domain = Optional.ofNullable(domain).orElse(defaultClientUuid);
+ domain = Optional.ofNullable(domain).orElse(DEFAULT_CLIENT_UUID);
this.handlerStores.get(domain).removeHandler(event, handler);
}
@@ -160,14 +158,14 @@ public void shutdown() {
// instantiated when a handler is added to that client.
static class HandlerStore {
- private final Map>> handlerMap;
+ private final Map>> handlerMap;
HandlerStore() {
handlerMap = new ConcurrentHashMap<>();
- handlerMap.put(ProviderEvent.PROVIDER_READY, new ArrayList<>());
- handlerMap.put(ProviderEvent.PROVIDER_CONFIGURATION_CHANGED, new ArrayList<>());
- handlerMap.put(ProviderEvent.PROVIDER_ERROR, new ArrayList<>());
- handlerMap.put(ProviderEvent.PROVIDER_STALE, new ArrayList<>());
+ handlerMap.put(ProviderEvent.PROVIDER_READY, new ConcurrentLinkedQueue<>());
+ handlerMap.put(ProviderEvent.PROVIDER_CONFIGURATION_CHANGED, new ConcurrentLinkedQueue<>());
+ handlerMap.put(ProviderEvent.PROVIDER_ERROR, new ConcurrentLinkedQueue<>());
+ handlerMap.put(ProviderEvent.PROVIDER_STALE, new ConcurrentLinkedQueue<>());
}
void addHandler(ProviderEvent event, Consumer handler) {
diff --git a/src/main/java/dev/openfeature/sdk/FeatureProvider.java b/src/main/java/dev/openfeature/sdk/FeatureProvider.java
index 4c630cb80..22819ef10 100644
--- a/src/main/java/dev/openfeature/sdk/FeatureProvider.java
+++ b/src/main/java/dev/openfeature/sdk/FeatureProvider.java
@@ -30,6 +30,7 @@ default List getProviderHooks() {
* can overwrite this method,
* if they have special initialization needed prior being called for flag
* evaluation.
+ *
*
* It is ok if the method is expensive as it is executed in the background. All
* runtime exceptions will be
@@ -45,6 +46,7 @@ default void initialize(EvaluationContext evaluationContext) throws Exception {
* flags, or the SDK is shut down.
* Providers can overwrite this method, if they have special shutdown actions
* needed.
+ *
*
* It is ok if the method is expensive as it is executed in the background. All
* runtime exceptions will be
diff --git a/src/main/java/dev/openfeature/sdk/FeatureProviderStateManager.java b/src/main/java/dev/openfeature/sdk/FeatureProviderStateManager.java
index 2c39ece6b..5fd70221b 100644
--- a/src/main/java/dev/openfeature/sdk/FeatureProviderStateManager.java
+++ b/src/main/java/dev/openfeature/sdk/FeatureProviderStateManager.java
@@ -2,14 +2,14 @@
import dev.openfeature.sdk.exceptions.OpenFeatureError;
import java.util.concurrent.atomic.AtomicBoolean;
-import lombok.Getter;
+import java.util.concurrent.atomic.AtomicReference;
+import lombok.extern.slf4j.Slf4j;
+@Slf4j
class FeatureProviderStateManager implements EventProviderListener {
private final FeatureProvider delegate;
private final AtomicBoolean isInitialized = new AtomicBoolean();
-
- @Getter
- private ProviderState state = ProviderState.NOT_READY;
+ private final AtomicReference state = new AtomicReference<>(ProviderState.NOT_READY);
public FeatureProviderStateManager(FeatureProvider delegate) {
this.delegate = delegate;
@@ -24,17 +24,17 @@ public void initialize(EvaluationContext evaluationContext) throws Exception {
}
try {
delegate.initialize(evaluationContext);
- state = ProviderState.READY;
+ setState(ProviderState.READY);
} catch (OpenFeatureError openFeatureError) {
if (ErrorCode.PROVIDER_FATAL.equals(openFeatureError.getErrorCode())) {
- state = ProviderState.FATAL;
+ setState(ProviderState.FATAL);
} else {
- state = ProviderState.ERROR;
+ setState(ProviderState.ERROR);
}
isInitialized.set(false);
throw openFeatureError;
} catch (Exception e) {
- state = ProviderState.ERROR;
+ setState(ProviderState.ERROR);
isInitialized.set(false);
throw e;
}
@@ -42,7 +42,7 @@ public void initialize(EvaluationContext evaluationContext) throws Exception {
public void shutdown() {
delegate.shutdown();
- state = ProviderState.NOT_READY;
+ setState(ProviderState.NOT_READY);
isInitialized.set(false);
}
@@ -50,17 +50,34 @@ public void shutdown() {
public void onEmit(ProviderEvent event, ProviderEventDetails details) {
if (ProviderEvent.PROVIDER_ERROR.equals(event)) {
if (details != null && details.getErrorCode() == ErrorCode.PROVIDER_FATAL) {
- state = ProviderState.FATAL;
+ setState(ProviderState.FATAL);
} else {
- state = ProviderState.ERROR;
+ setState(ProviderState.ERROR);
}
} else if (ProviderEvent.PROVIDER_STALE.equals(event)) {
- state = ProviderState.STALE;
+ setState(ProviderState.STALE);
} else if (ProviderEvent.PROVIDER_READY.equals(event)) {
- state = ProviderState.READY;
+ setState(ProviderState.READY);
+ }
+ }
+
+ private void setState(ProviderState state) {
+ ProviderState oldState = this.state.getAndSet(state);
+ if (oldState != state) {
+ String providerName;
+ if (delegate.getMetadata() == null || delegate.getMetadata().getName() == null) {
+ providerName = "unknown";
+ } else {
+ providerName = delegate.getMetadata().getName();
+ }
+ log.info("Provider {} transitioned from state {} to state {}", providerName, oldState, state);
}
}
+ public ProviderState getState() {
+ return state.get();
+ }
+
FeatureProvider getProvider() {
return delegate;
}
diff --git a/src/main/java/dev/openfeature/sdk/HookContext.java b/src/main/java/dev/openfeature/sdk/HookContext.java
index e14eeb643..8d4d2e13a 100644
--- a/src/main/java/dev/openfeature/sdk/HookContext.java
+++ b/src/main/java/dev/openfeature/sdk/HookContext.java
@@ -1,32 +1,56 @@
package dev.openfeature.sdk;
-import lombok.Builder;
+import dev.openfeature.sdk.internal.ExcludeFromGeneratedCoverageReport;
+import edu.umd.cs.findbugs.annotations.SuppressFBWarnings;
+import java.util.Objects;
+import lombok.EqualsAndHashCode;
import lombok.NonNull;
-import lombok.Value;
-import lombok.With;
+import lombok.ToString;
/**
* A data class to hold immutable context that {@link Hook} instances use.
*
* @param the type for the flag being evaluated
*/
-@Value
-@Builder
-@With
-public class HookContext {
- @NonNull String flagKey;
+@EqualsAndHashCode
+@ToString
+public final class HookContext {
+ private final SharedHookContext sharedContext;
+ private EvaluationContext ctx;
+ private final HookData hookData;
- @NonNull FlagValueType type;
-
- @NonNull T defaultValue;
-
- @NonNull EvaluationContext ctx;
+ HookContext(@NonNull SharedHookContext sharedContext, EvaluationContext evaluationContext, HookData hookData) {
+ this.sharedContext = sharedContext;
+ ctx = evaluationContext;
+ this.hookData = hookData;
+ }
- ClientMetadata clientMetadata;
- Metadata providerMetadata;
+ /**
+ * Obsolete constructor.
+ * This constructor is retained for binary compatibility but is no longer part of the public API.
+ *
+ * @param flagKey feature flag key
+ * @param type flag value type
+ * @param clientMetadata info on which client is calling
+ * @param providerMetadata info on the provider
+ * @param ctx Evaluation Context for the request
+ * @param defaultValue Fallback value
+ * @deprecated HookContext is initialized by the SDK and passed to hooks. Users should not create new instances.
+ */
+ @Deprecated
+ HookContext(
+ @NonNull String flagKey,
+ @NonNull FlagValueType type,
+ @NonNull T defaultValue,
+ @NonNull EvaluationContext ctx,
+ ClientMetadata clientMetadata,
+ Metadata providerMetadata,
+ HookData hookData) {
+ this(new SharedHookContext<>(flagKey, type, clientMetadata, providerMetadata, defaultValue), ctx, hookData);
+ }
/**
- * Builds a {@link HookContext} instances from request data.
+ * Builds {@link HookContext} instances from request data.
*
* @param key feature flag key
* @param type flag value type
@@ -36,7 +60,9 @@ public class HookContext {
* @param defaultValue Fallback value
* @param type that the flag is evaluating against
* @return resulting context for hook
+ * @deprecated HookContext is initialized by the SDK and passed to hooks. Users should not create new instances.
*/
+ @Deprecated
public static HookContext from(
String key,
FlagValueType type,
@@ -51,6 +77,286 @@ public static HookContext from(
.providerMetadata(providerMetadata)
.ctx(ctx)
.defaultValue(defaultValue)
+ .hookData(null)
.build();
}
+
+ /**
+ * Creates a new builder for {@link HookContext}.
+ *
+ * @param the type for the flag being evaluated
+ * @return a new builder
+ * @deprecated HookContext is initialized by the SDK and passed to hooks. Users should not create new instances.
+ */
+ @Deprecated
+ public static HookContextBuilder builder() {
+ return new HookContextBuilder();
+ }
+
+ public @NonNull String getFlagKey() {
+ return sharedContext.getFlagKey();
+ }
+
+ public @NonNull FlagValueType getType() {
+ return sharedContext.getType();
+ }
+
+ public @NonNull T getDefaultValue() {
+ return sharedContext.getDefaultValue();
+ }
+
+ public @NonNull EvaluationContext getCtx() {
+ return this.ctx;
+ }
+
+ public ClientMetadata getClientMetadata() {
+ return sharedContext.getClientMetadata();
+ }
+
+ public Metadata getProviderMetadata() {
+ return sharedContext.getProviderMetadata();
+ }
+
+ @SuppressFBWarnings(value = "EI_EXPOSE_REP", justification = "Intentional exposure of hookData")
+ public HookData getHookData() {
+ return this.hookData;
+ }
+
+ void setCtx(@NonNull EvaluationContext ctx) {
+ this.ctx = ctx;
+ }
+
+ /**
+ * Returns a new HookContext with the provided flagKey if it is different from the current one.
+ *
+ * @param flagKey new flag key
+ * @return new HookContext with updated flagKey or the same instance if unchanged
+ * @deprecated HookContext is initialized by the SDK and passed to hooks. Users should not create new instances.
+ */
+ @ExcludeFromGeneratedCoverageReport
+ @Deprecated
+ public HookContext withFlagKey(@NonNull String flagKey) {
+ return Objects.equals(this.getFlagKey(), flagKey)
+ ? this
+ : new HookContext(
+ flagKey,
+ this.getType(),
+ this.getDefaultValue(),
+ this.getCtx(),
+ this.getClientMetadata(),
+ this.getProviderMetadata(),
+ this.hookData);
+ }
+
+ /**
+ * Returns a new HookContext with the provided type if it is different from the current one.
+ *
+ * @param type new flag value type
+ * @return new HookContext with updated type or the same instance if unchanged
+ * @deprecated HookContext is initialized by the SDK and passed to hooks. Users should not create new instances.
+ */
+ @ExcludeFromGeneratedCoverageReport
+ @Deprecated
+ public HookContext withType(@NonNull FlagValueType type) {
+ return this.getType() == type
+ ? this
+ : new HookContext(
+ this.getFlagKey(),
+ type,
+ this.getDefaultValue(),
+ this.getCtx(),
+ this.getClientMetadata(),
+ this.getProviderMetadata(),
+ this.hookData);
+ }
+
+ /**
+ * Returns a new HookContext with the provided defaultValue if it is different from the current one.
+ *
+ * @param defaultValue new default value
+ * @return new HookContext with updated defaultValue or the same instance if unchanged
+ * @deprecated HookContext is initialized by the SDK and passed to hooks. Users should not create new instances.
+ */
+ @ExcludeFromGeneratedCoverageReport
+ @Deprecated
+ public HookContext withDefaultValue(@NonNull T defaultValue) {
+ return this.getDefaultValue() == defaultValue
+ ? this
+ : new HookContext(
+ this.getFlagKey(),
+ this.getType(),
+ defaultValue,
+ this.getCtx(),
+ this.getClientMetadata(),
+ this.getProviderMetadata(),
+ this.hookData);
+ }
+
+ /**
+ * Returns a new HookContext with the provided ctx if it is different from the current one.
+ *
+ * @param ctx new evaluation context
+ * @return new HookContext with updated ctx or the same instance if unchanged
+ * @deprecated HookContext is initialized by the SDK and passed to hooks. Users should not create new instances.
+ */
+ @ExcludeFromGeneratedCoverageReport
+ @Deprecated
+ public HookContext withCtx(@NonNull EvaluationContext ctx) {
+ return this.ctx == ctx
+ ? this
+ : new HookContext(
+ this.getFlagKey(),
+ this.getType(),
+ this.getDefaultValue(),
+ ctx,
+ this.getClientMetadata(),
+ this.getProviderMetadata(),
+ this.hookData);
+ }
+
+ /**
+ * Returns a new HookContext with the provided clientMetadata if it is different from the current one.
+ *
+ * @param clientMetadata new client metadata
+ * @return new HookContext with updated clientMetadata or the same instance if unchanged
+ * @deprecated HookContext is initialized by the SDK and passed to hooks. Users should not create new instances.
+ */
+ @ExcludeFromGeneratedCoverageReport
+ @Deprecated
+ public HookContext withClientMetadata(ClientMetadata clientMetadata) {
+ return this.getClientMetadata() == clientMetadata
+ ? this
+ : new HookContext(
+ this.getFlagKey(),
+ this.getType(),
+ this.getDefaultValue(),
+ this.getCtx(),
+ clientMetadata,
+ this.getProviderMetadata(),
+ this.hookData);
+ }
+
+ /**
+ * Returns a new HookContext with the provided providerMetadata if it is different from the current one.
+ *
+ * @param providerMetadata new provider metadata
+ * @return new HookContext with updated providerMetadata or the same instance if unchanged
+ * @deprecated HookContext is initialized by the SDK and passed to hooks. Users should not create new instances.
+ */
+ @ExcludeFromGeneratedCoverageReport
+ @Deprecated
+ public HookContext withProviderMetadata(Metadata providerMetadata) {
+ return this.getProviderMetadata() == providerMetadata
+ ? this
+ : new HookContext(
+ this.getFlagKey(),
+ this.getType(),
+ this.getDefaultValue(),
+ this.getCtx(),
+ this.getClientMetadata(),
+ providerMetadata,
+ this.hookData);
+ }
+
+ /**
+ * Returns a new HookContext with the provided hookData if it is different from the current one.
+ *
+ * @param hookData new hook data
+ * @return new HookContext with updated hookData or the same instance if unchanged
+ * @deprecated HookContext is initialized by the SDK and passed to hooks. Users should not create new instances.
+ */
+ @ExcludeFromGeneratedCoverageReport
+ @Deprecated
+ public HookContext withHookData(HookData hookData) {
+ return this.hookData == hookData
+ ? this
+ : new HookContext(
+ this.getFlagKey(),
+ this.getType(),
+ this.getDefaultValue(),
+ this.getCtx(),
+ this.getClientMetadata(),
+ this.getProviderMetadata(),
+ hookData);
+ }
+
+ /**
+ * Builder for HookContext.
+ *
+ * @param The flag type.
+ * @deprecated HookContext is initialized by the SDK and passed to hooks. Users should not create new instances.
+ */
+ @Deprecated
+ @ToString
+ public static class HookContextBuilder {
+ private String flagKey;
+ private FlagValueType type;
+ private T defaultValue;
+ private EvaluationContext ctx;
+ private ClientMetadata clientMetadata;
+ private Metadata providerMetadata;
+ private HookData hookData;
+
+ HookContextBuilder() {}
+
+ @ExcludeFromGeneratedCoverageReport
+ public HookContextBuilder flagKey(@NonNull String flagKey) {
+ this.flagKey = flagKey;
+ return this;
+ }
+
+ @ExcludeFromGeneratedCoverageReport
+ public HookContextBuilder type(@NonNull FlagValueType type) {
+ this.type = type;
+ return this;
+ }
+
+ @ExcludeFromGeneratedCoverageReport
+ public HookContextBuilder defaultValue(@NonNull T defaultValue) {
+ this.defaultValue = defaultValue;
+ return this;
+ }
+
+ @ExcludeFromGeneratedCoverageReport
+ public HookContextBuilder ctx(@NonNull EvaluationContext ctx) {
+ this.ctx = ctx;
+ return this;
+ }
+
+ @ExcludeFromGeneratedCoverageReport
+ public HookContextBuilder clientMetadata(ClientMetadata clientMetadata) {
+ this.clientMetadata = clientMetadata;
+ return this;
+ }
+
+ @ExcludeFromGeneratedCoverageReport
+ public HookContextBuilder providerMetadata(Metadata providerMetadata) {
+ this.providerMetadata = providerMetadata;
+ return this;
+ }
+
+ @SuppressFBWarnings(value = "EI_EXPOSE_REP2", justification = "Intentional exposure of hookData")
+ @ExcludeFromGeneratedCoverageReport
+ public HookContextBuilder hookData(HookData hookData) {
+ this.hookData = hookData;
+ return this;
+ }
+
+ /**
+ * Builds the HookContext instance.
+ *
+ * @return a new HookContext
+ */
+ @ExcludeFromGeneratedCoverageReport
+ public HookContext build() {
+ return new HookContext(
+ this.flagKey,
+ this.type,
+ this.defaultValue,
+ this.ctx,
+ this.clientMetadata,
+ this.providerMetadata,
+ this.hookData);
+ }
+ }
}
diff --git a/src/main/java/dev/openfeature/sdk/HookData.java b/src/main/java/dev/openfeature/sdk/HookData.java
new file mode 100644
index 000000000..bd2c5dba9
--- /dev/null
+++ b/src/main/java/dev/openfeature/sdk/HookData.java
@@ -0,0 +1,35 @@
+package dev.openfeature.sdk;
+
+/**
+ * Hook data provides a way for hooks to maintain state across their execution stages.
+ * Each hook instance gets its own isolated data store that persists only for the duration
+ * of a single flag evaluation.
+ */
+public interface HookData {
+ /**
+ * Sets a value for the given key.
+ *
+ * @param key the key to store the value under
+ * @param value the value to store
+ */
+ void set(String key, Object value);
+
+ /**
+ * Gets the value for the given key.
+ *
+ * @param key the key to retrieve the value for
+ * @return the value, or null if not found
+ */
+ Object get(String key);
+
+ /**
+ * Gets the value for the given key, cast to the specified type.
+ *
+ * @param the type to cast to
+ * @param key the key to retrieve the value for
+ * @param type the class to cast to
+ * @return the value cast to the specified type, or null if not found
+ * @throws ClassCastException if the value cannot be cast to the specified type
+ */
+ T get(String key, Class type);
+}
diff --git a/src/main/java/dev/openfeature/sdk/HookSupport.java b/src/main/java/dev/openfeature/sdk/HookSupport.java
index 73518ee8e..c7a7630da 100644
--- a/src/main/java/dev/openfeature/sdk/HookSupport.java
+++ b/src/main/java/dev/openfeature/sdk/HookSupport.java
@@ -3,99 +3,124 @@
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
-import java.util.Map;
import java.util.Optional;
-import java.util.function.Consumer;
-import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
+/**
+ * Helper class to run hooks. Initialize {@link HookSupportData} by calling setHooks, setHookContexts
+ * & updateEvaluationContext in this exact order.
+ */
@Slf4j
-@RequiredArgsConstructor
-@SuppressWarnings({"unchecked", "rawtypes"})
class HookSupport {
- public EvaluationContext beforeHooks(
- FlagValueType flagValueType, HookContext hookCtx, List hooks, Map hints) {
- return callBeforeHooks(flagValueType, hookCtx, hooks, hints);
+ /**
+ * Sets the {@link Hook}-{@link HookContext}-{@link Pair} list in the given data object with {@link HookContext}
+ * set to null. Filters hooks by supported {@link FlagValueType}.
+ *
+ * @param hookSupportData the data object to modify
+ * @param hooks the hooks to set
+ * @param type the flag value type to filter unsupported hooks
+ */
+ public void setHooks(HookSupportData hookSupportData, List hooks, FlagValueType type) {
+ List> hookContextPairs = new ArrayList<>();
+ for (Hook hook : hooks) {
+ if (hook.supportsFlagValueType(type)) {
+ hookContextPairs.add(Pair.of(hook, null));
+ }
+ }
+ hookSupportData.hooks = hookContextPairs;
}
- public void afterHooks(
- FlagValueType flagValueType,
- HookContext hookContext,
- FlagEvaluationDetails details,
- List hooks,
- Map hints) {
- executeHooksUnchecked(flagValueType, hooks, hook -> hook.after(hookContext, details, hints));
+ /**
+ * Creates & sets a {@link HookContext} for every {@link Hook}-{@link HookContext}-{@link Pair}
+ * in the given data object with a new {@link HookData} instance.
+ *
+ * @param hookSupportData the data object to modify
+ * @param sharedContext the shared context from which the new {@link HookContext} is created
+ */
+ public void setHookContexts(HookSupportData hookSupportData, SharedHookContext sharedContext) {
+ for (int i = 0; i < hookSupportData.hooks.size(); i++) {
+ Pair hookContextPair = hookSupportData.hooks.get(i);
+ HookContext curHookContext = sharedContext.hookContextFor(null, new DefaultHookData());
+ hookContextPair.setValue(curHookContext);
+ }
}
- public void afterAllHooks(
- FlagValueType flagValueType,
- HookContext hookCtx,
- FlagEvaluationDetails details,
- List hooks,
- Map hints) {
- executeHooks(flagValueType, hooks, "finally", hook -> hook.finallyAfter(hookCtx, details, hints));
+ /**
+ * Updates the evaluation context in the given data object's eval context and each hooks eval context.
+ *
+ * @param hookSupportData the data object to modify
+ * @param evaluationContext the new context to set
+ */
+ public void updateEvaluationContext(HookSupportData hookSupportData, EvaluationContext evaluationContext) {
+ hookSupportData.evaluationContext = evaluationContext;
+ if (hookSupportData.hooks != null) {
+ for (Pair hookContextPair : hookSupportData.hooks) {
+ var curHookContext = hookContextPair.getValue();
+ if (curHookContext != null) {
+ curHookContext.setCtx(evaluationContext);
+ }
+ }
+ }
}
- public void errorHooks(
- FlagValueType flagValueType,
- HookContext hookCtx,
- Exception e,
- List hooks,
- Map hints) {
- executeHooks(flagValueType, hooks, "error", hook -> hook.error(hookCtx, e, hints));
- }
+ public void executeBeforeHooks(HookSupportData data) {
+ // These traverse backwards from normal.
+ List> reversedHooks = new ArrayList<>(data.getHooks());
+ Collections.reverse(reversedHooks);
- private void executeHooks(
- FlagValueType flagValueType, List hooks, String hookMethod, Consumer> hookCode) {
- if (hooks != null) {
- for (Hook hook : hooks) {
- if (hook.supportsFlagValueType(flagValueType)) {
- executeChecked(hook, hookCode, hookMethod);
- }
+ for (Pair hookContextPair : reversedHooks) {
+ var hook = hookContextPair.getKey();
+ var hookContext = hookContextPair.getValue();
+
+ Optional returnedEvalContext = Optional.ofNullable(
+ hook.before(hookContext, data.getHints()))
+ .orElse(Optional.empty());
+ if (returnedEvalContext.isPresent()) {
+ // update shared evaluation context for all hooks
+ updateEvaluationContext(data, data.getEvaluationContext().merge(returnedEvalContext.get()));
}
}
}
- // before, error, and finally hooks shouldn't throw
- private void executeChecked(Hook hook, Consumer> hookCode, String hookMethod) {
- try {
- hookCode.accept(hook);
- } catch (Exception exception) {
- log.error(
- "Unhandled exception when running {} hook {} (only 'after' hooks should throw)",
- hookMethod,
- hook.getClass(),
- exception);
+ public void executeErrorHooks(HookSupportData data, Exception error) {
+ for (Pair hookContextPair : data.getHooks()) {
+ var hook = hookContextPair.getKey();
+ var hookContext = hookContextPair.getValue();
+ try {
+ hook.error(hookContext, error, data.getHints());
+ } catch (Exception e) {
+ log.error(
+ "Unhandled exception when running {} hook {} (only 'after' hooks should throw)",
+ "error",
+ hook.getClass(),
+ e);
+ }
}
}
// after hooks can throw in order to do validation
- private void executeHooksUnchecked(FlagValueType flagValueType, List hooks, Consumer> hookCode) {
- if (hooks != null) {
- for (Hook hook : hooks) {
- if (hook.supportsFlagValueType(flagValueType)) {
- hookCode.accept(hook);
- }
- }
+ public void executeAfterHooks(HookSupportData data, FlagEvaluationDetails details) {
+ for (Pair hookContextPair : data.getHooks()) {
+ var hook = hookContextPair.getKey();
+ var hookContext = hookContextPair.getValue();
+ hook.after(hookContext, details, data.getHints());
}
}
- private EvaluationContext callBeforeHooks(
- FlagValueType flagValueType, HookContext hookCtx, List hooks, Map hints) {
- // These traverse backwards from normal.
- List reversedHooks = new ArrayList<>(hooks);
- Collections.reverse(reversedHooks);
- EvaluationContext context = hookCtx.getCtx();
- for (Hook hook : reversedHooks) {
- if (hook.supportsFlagValueType(flagValueType)) {
- Optional optional =
- Optional.ofNullable(hook.before(hookCtx, hints)).orElse(Optional.empty());
- if (optional.isPresent()) {
- context = context.merge(optional.get());
- }
+ public void executeAfterAllHooks(HookSupportData data, FlagEvaluationDetails details) {
+ for (Pair hookContextPair : data.getHooks()) {
+ var hook = hookContextPair.getKey();
+ var hookContext = hookContextPair.getValue();
+ try {
+ hook.finallyAfter(hookContext, details, data.getHints());
+ } catch (Exception e) {
+ log.error(
+ "Unhandled exception when running {} hook {} (only 'after' hooks should throw)",
+ "finally",
+ hook.getClass(),
+ e);
}
}
- return context;
}
}
diff --git a/src/main/java/dev/openfeature/sdk/HookSupportData.java b/src/main/java/dev/openfeature/sdk/HookSupportData.java
new file mode 100644
index 000000000..2d3346ba1
--- /dev/null
+++ b/src/main/java/dev/openfeature/sdk/HookSupportData.java
@@ -0,0 +1,18 @@
+package dev.openfeature.sdk;
+
+import java.util.List;
+import java.util.Map;
+import lombok.Getter;
+
+/**
+ * Encapsulates data for hook execution per flag evaluation.
+ */
+@Getter
+class HookSupportData {
+
+ List> hooks;
+ EvaluationContext evaluationContext;
+ Map hints;
+
+ HookSupportData() {}
+}
diff --git a/src/main/java/dev/openfeature/sdk/ImmutableContext.java b/src/main/java/dev/openfeature/sdk/ImmutableContext.java
index 23a452e08..e4916dfca 100644
--- a/src/main/java/dev/openfeature/sdk/ImmutableContext.java
+++ b/src/main/java/dev/openfeature/sdk/ImmutableContext.java
@@ -4,6 +4,7 @@
import java.util.HashMap;
import java.util.Map;
import java.util.function.Function;
+import lombok.EqualsAndHashCode;
import lombok.ToString;
import lombok.experimental.Delegate;
@@ -15,9 +16,12 @@
* not be modified after instantiation.
*/
@ToString
+@EqualsAndHashCode
@SuppressWarnings("PMD.BeanMembersShouldSerialize")
public final class ImmutableContext implements EvaluationContext {
+ public static final ImmutableContext EMPTY = new ImmutableContext();
+
@Delegate(excludes = DelegateExclusions.class)
private final ImmutableStructure structure;
diff --git a/src/main/java/dev/openfeature/sdk/ImmutableMetadata.java b/src/main/java/dev/openfeature/sdk/ImmutableMetadata.java
index c2b6f5838..945e0ea17 100644
--- a/src/main/java/dev/openfeature/sdk/ImmutableMetadata.java
+++ b/src/main/java/dev/openfeature/sdk/ImmutableMetadata.java
@@ -1,5 +1,6 @@
package dev.openfeature.sdk;
+import java.util.Collections;
import java.util.HashMap;
import java.util.Map;
import lombok.EqualsAndHashCode;
@@ -12,6 +13,8 @@
@Slf4j
@EqualsAndHashCode
public class ImmutableMetadata {
+ public static final ImmutableMetadata EMPTY = new ImmutableMetadata(Collections.emptyMap());
+
private final Map metadata;
private ImmutableMetadata(Map metadata) {
@@ -97,6 +100,18 @@ public T getValue(final String key, final Class type) {
}
}
+ public Map asUnmodifiableMap() {
+ return Collections.unmodifiableMap(metadata);
+ }
+
+ public boolean isEmpty() {
+ return metadata.isEmpty();
+ }
+
+ public boolean isNotEmpty() {
+ return !metadata.isEmpty();
+ }
+
/**
* Obtain a builder for {@link ImmutableMetadata}.
*/
diff --git a/src/main/java/dev/openfeature/sdk/ImmutableStructure.java b/src/main/java/dev/openfeature/sdk/ImmutableStructure.java
index c47a49eb3..849359424 100644
--- a/src/main/java/dev/openfeature/sdk/ImmutableStructure.java
+++ b/src/main/java/dev/openfeature/sdk/ImmutableStructure.java
@@ -18,7 +18,7 @@
* not be modified after instantiation. All references are clones.
*/
@ToString
-@EqualsAndHashCode
+@EqualsAndHashCode(callSuper = true)
@SuppressWarnings({"PMD.BeanMembersShouldSerialize", "checkstyle:MissingJavadocType"})
public final class ImmutableStructure extends AbstractStructure {
@@ -38,7 +38,7 @@ public ImmutableStructure(Map attributes) {
super(copyAttributes(attributes, null));
}
- protected ImmutableStructure(String targetingKey, Map attributes) {
+ ImmutableStructure(String targetingKey, Map attributes) {
super(copyAttributes(attributes, targetingKey));
}
@@ -70,12 +70,14 @@ private static Map copyAttributes(Map in) {
private static Map copyAttributes(Map in, String targetingKey) {
Map copy = new HashMap<>();
- for (Entry entry : in.entrySet()) {
- copy.put(
- entry.getKey(),
- Optional.ofNullable(entry.getValue())
- .map((Value val) -> val.clone())
- .orElse(null));
+ if (in != null) {
+ for (Entry entry : in.entrySet()) {
+ copy.put(
+ entry.getKey(),
+ Optional.ofNullable(entry.getValue())
+ .map((Value val) -> val.clone())
+ .orElse(null));
+ }
}
if (targetingKey != null) {
copy.put(EvaluationContext.TARGETING_KEY, new Value(targetingKey));
diff --git a/src/main/java/dev/openfeature/sdk/MutableStructure.java b/src/main/java/dev/openfeature/sdk/MutableStructure.java
index a06e2f2d3..f3158456d 100644
--- a/src/main/java/dev/openfeature/sdk/MutableStructure.java
+++ b/src/main/java/dev/openfeature/sdk/MutableStructure.java
@@ -15,8 +15,8 @@
* be modified after instantiation.
*/
@ToString
-@EqualsAndHashCode
@SuppressWarnings({"PMD.BeanMembersShouldSerialize", "checkstyle:MissingJavadocType"})
+@EqualsAndHashCode(callSuper = true)
public class MutableStructure extends AbstractStructure {
public MutableStructure() {
diff --git a/src/main/java/dev/openfeature/sdk/ObjectHook.java b/src/main/java/dev/openfeature/sdk/ObjectHook.java
new file mode 100644
index 000000000..ad3af6444
--- /dev/null
+++ b/src/main/java/dev/openfeature/sdk/ObjectHook.java
@@ -0,0 +1,15 @@
+package dev.openfeature.sdk;
+
+/**
+ * An extension point which can run around flag resolution. They are intended to be used as a way to add custom logic
+ * to the lifecycle of flag evaluation.
+ *
+ * @see Hook
+ */
+public interface ObjectHook extends Hook