Skip to content

Commit f52291b

Browse files
committed
split gems
1 parent 15c24d1 commit f52291b

17 files changed

Lines changed: 432 additions & 82 deletions

‎.github/workflows/checks.yml‎

Lines changed: 52 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -3,50 +3,75 @@ name: Checks
33
on:
44
push:
55
branches:
6-
- "**"
6+
- main
77
pull_request:
8-
types:
9-
- opened
10-
- synchronize # when a PR is updated
11-
- reopened # when a PR is reopened
12-
- ready_for_review # when a PR is ready for review
13-
- review_requested # when a PR is requested for review
8+
9+
permissions:
10+
contents: read
11+
12+
concurrency:
13+
group: checks-${{ github.workflow }}-${{ github.ref }}
14+
cancel-in-progress: true
1415

1516
jobs:
16-
ci:
17+
base-sdk:
18+
name: Base SDK on Ruby ${{ matrix.ruby-version }}
1719
runs-on: ubuntu-latest
20+
timeout-minutes: 15
21+
strategy:
22+
fail-fast: false
23+
matrix:
24+
ruby-version: ["3.0", "3.4"]
25+
env:
26+
BUNDLE_GEMFILE: gemfiles/base.gemfile
1827

1928
steps:
20-
- name: Check out
21-
uses: actions/checkout@v4
29+
- name: Check out repository
30+
uses: actions/checkout@v6
2231

23-
- name: Set up Ruby ${{ matrix.ruby-version }}
32+
- name: Set up Ruby
2433
uses: ruby/setup-ruby@v1
2534
with:
35+
ruby-version: ${{ matrix.ruby-version }}
2636
bundler-cache: true
2737

28-
- name: Install
29-
run: |
30-
make install
38+
- name: Test base SDK without OpenFeature dependencies
39+
run: bundle exec rspec spec/ --exclude-pattern spec/openfeature_provider_spec.rb
3140

32-
- name: Build
33-
run: |
34-
make build
41+
full:
42+
name: Full SDK and provider
43+
runs-on: ubuntu-latest
44+
timeout-minutes: 20
3545

36-
- name: Test
37-
run: |
38-
make test
46+
steps:
47+
- name: Check out repository
48+
uses: actions/checkout@v6
49+
50+
- name: Set up Ruby
51+
uses: ruby/setup-ruby@v1
52+
with:
53+
ruby-version: "3.4"
54+
bundler-cache: true
55+
56+
- name: Test both packages
57+
run: make test
58+
59+
- name: Build and verify both gem artifacts
60+
run: make build
3961

40-
- uses: actions/setup-node@v4
62+
- name: Set up Node.js
63+
uses: actions/setup-node@v7
4164
with:
42-
node-version-file: ".nvmrc"
65+
node-version-file: .nvmrc
4366

44-
- name: Setup Featurevisor example-1 project
67+
- name: Set up Featurevisor example-1 project
4568
run: |
4669
mkdir example-1
47-
(cd example-1 && npx @featurevisor/cli@2.x init --example=1)
48-
(cd example-1 && npm install)
49-
(cd example-1 && npx featurevisor test)
70+
cd example-1
71+
npx --yes @featurevisor/cli@3 init --example=1
72+
npm install
73+
npx featurevisor build
74+
npx featurevisor test --onlyFailures
5075
5176
- name: Run Featurevisor project tests against Ruby SDK
52-
run: ./bin/featurevisor test --projectDirectoryPath=./example-1
77+
run: bundle exec ruby bin/featurevisor test --projectDirectoryPath=example-1 --onlyFailures

‎.github/workflows/publish.yml‎

Lines changed: 34 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -5,32 +5,51 @@ on:
55
tags:
66
- "v*.*.*"
77

8+
permissions:
9+
contents: read
10+
11+
concurrency:
12+
group: publish-${{ github.ref }}
13+
cancel-in-progress: false
14+
815
jobs:
916
publish:
1017
runs-on: ubuntu-latest
18+
timeout-minutes: 15
1119

1220
steps:
13-
- name: Check out
14-
uses: actions/checkout@v4
21+
- name: Check out repository
22+
uses: actions/checkout@v6
1523

1624
- name: Set up Ruby
1725
uses: ruby/setup-ruby@v1
1826
with:
27+
ruby-version: "3.4"
1928
bundler-cache: true
2029

21-
- name: Configure RubyGems credentials
22-
run: |
23-
mkdir -p ~/.gem
24-
echo ":rubygems_api_key: $RUBYGEMS_API_KEY" > ~/.gem/credentials
25-
chmod 0600 ~/.gem/credentials
26-
env:
27-
RUBYGEMS_API_KEY: ${{ secrets.RUBYGEMS_API_KEY }}
30+
- name: Test both packages
31+
run: make test
2832

29-
- name: Build
30-
run: |
31-
make build
32-
ls -l *.gem
33+
- name: Build and verify both gem artifacts
34+
run: make build
3335

34-
- name: Push to RubyGems
36+
- name: Verify tag matches package version
37+
id: version
38+
shell: bash
3539
run: |
36-
gem push *.gem
40+
version="$(bundle exec ruby -Ilib -rfeaturevisor/version -e 'print Featurevisor::VERSION')"
41+
if [ "$GITHUB_REF_NAME" != "v$version" ]; then
42+
echo "Tag $GITHUB_REF_NAME does not match gem version $version" >&2
43+
exit 1
44+
fi
45+
echo "version=$version" >> "$GITHUB_OUTPUT"
46+
47+
- name: Publish Featurevisor SDK
48+
env:
49+
GEM_HOST_API_KEY: ${{ secrets.RUBYGEMS_API_KEY }}
50+
run: gem push "featurevisor-${{ steps.version.outputs.version }}.gem"
51+
52+
- name: Publish Featurevisor OpenFeature provider
53+
env:
54+
GEM_HOST_API_KEY: ${{ secrets.RUBYGEMS_API_KEY }}
55+
run: gem push "featurevisor-openfeature-${{ steps.version.outputs.version }}.gem"

‎.nvmrc‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
20
1+
24

‎Gemfile‎

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,6 @@
11
source "https://rubygems.org"
22

3-
# Specify your gem's dependencies in featurevisor.gemspec
4-
gemspec
3+
gemspec name: "featurevisor"
4+
5+
# Needed only when developing and testing the separately packaged provider.
6+
gem "openfeature-sdk", "~> 0.6.5"

‎Gemfile.lock‎

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
PATH
22
remote: .
33
specs:
4-
featurevisor (1.0.0)
5-
benchmark
4+
featurevisor (1.1.0)
5+
benchmark (>= 0, < 1)
66

77
GEM
88
remote: https://rubygems.org/

‎Makefile‎

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,20 @@
1-
.PHONY: install build test test-example-1 setup-monorepo update-monorepo
1+
.PHONY: install build verify-artifacts test test-base test-example-1 setup-monorepo update-monorepo
22

33
install:
44
bundle install
55

66
build:
7-
gem build featurevisor.gemspec
7+
bundle exec rake build
8+
9+
verify-artifacts:
10+
bundle exec ruby scripts/verify_gems.rb
811

912
test:
1013
bundle exec rspec spec/
1114

15+
test-base:
16+
BUNDLE_GEMFILE=gemfiles/base.gemfile bundle exec rspec spec/ --exclude-pattern spec/openfeature_provider_spec.rb
17+
1218
test-example-1:
1319
bundle exec rspec spec/
1420
bundle exec ruby bin/featurevisor test --projectDirectoryPath=../featurevisor/examples/example-1 --onlyFailures

‎README.md‎

Lines changed: 36 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -779,7 +779,7 @@ All three commands accept repeatable `--target=<target>` options. `test` builds
779779

780780
```bash
781781
$ cd /absolute/path/to/featurevisor-ruby
782-
$ bundle exec ruby bin/featurevisor test --projectDirectoryPath=/Users/fahad/Projects/featurevisor/featurevisor/examples/example-1 --onlyFailures
782+
$ bundle exec ruby bin/featurevisor test --projectDirectoryPath=../featurevisor/examples/example-1 --onlyFailures
783783
$ make test-example-1
784784
```
785785

@@ -814,13 +814,18 @@ $ bundle exec featurevisor assess-distribution \
814814

815815
## OpenFeature
816816

817-
Install the official OpenFeature SDK next to Featurevisor:
817+
The OpenFeature provider is published as a separate gem. This keeps OpenFeature code and dependencies out of applications that only use the Featurevisor SDK.
818+
819+
The provider currently requires Ruby 3.4 or newer because that is the minimum version supported by the official OpenFeature Ruby SDK.
820+
821+
Install the provider:
818822

819823
```ruby
820-
gem "featurevisor"
821-
gem "openfeature-sdk", "~> 0.6.5"
824+
gem "featurevisor-openfeature", "~> 1.1"
822825
```
823826

827+
It installs the matching `featurevisor` gem and the official `openfeature-sdk` dependency. The provider and base SDK deliberately share the same version, and the provider requires that exact Featurevisor version.
828+
824829
```ruby
825830
require "featurevisor/openfeature_provider"
826831

@@ -844,6 +849,17 @@ Use `checkout` for a flag, `checkout:variation` for its variation, and `checkout
844849

845850
OpenFeature's targeting key maps to `userId` by default. `targeting_key_field`, `key_separator`, and `variation_key` can customize the mapping.
846851

852+
You can pass any Featurevisor initialization options directly to the provider. These options are used to create the Featurevisor instance owned by the provider:
853+
854+
```ruby
855+
provider = Featurevisor::OpenFeatureProvider.new(
856+
datafile: datafile_content,
857+
targeting_key_field: "accountId",
858+
key_separator: "/",
859+
variation_key: "$variation",
860+
)
861+
```
862+
847863
You can also reuse an existing Featurevisor instance:
848864

849865
```ruby
@@ -861,24 +877,35 @@ See the [OpenFeature provider guide](https://featurevisor.com/docs/sdks/openfeat
861877

862878
### Setting up
863879

864-
After checking out the repo, run `bin/setup` to install dependencies. Then, run `rake spec` to run the tests. You can also run `bin/console` for an interactive prompt that will allow you to experiment.
880+
After checking out the repository, run `make install` to install dependencies.
865881

866882
### Running tests
867883

868884
```bash
869885
$ bundle exec rspec
886+
$ make test-base
887+
$ make test-example-1
888+
```
889+
890+
Build and verify both gems with:
891+
892+
```bash
893+
$ make build
870894
```
871895

872-
To install this gem onto your local machine, run `bundle exec rake install`. To release a new version, update the version number in `version.rb`, and then run `bundle exec rake release`, which will create a git tag for the version, push git commits and tags, and push the `.gem` file to [rubygems.org](https://rubygems.org).
896+
The build produces `featurevisor-VERSION.gem` and `featurevisor-openfeature-VERSION.gem`. The artifact verifier confirms that OpenFeature code and dependencies are absent from the base gem and present only in the provider gem.
873897

874898
### Releasing
875899

876-
- Update version in `lib/featurevisor/version.rb`
900+
- Update the shared version in `lib/featurevisor/version.rb`
877901
- Run `bundle install`
878902
- Push commit to `main` branch
879903
- Wait for CI to complete
880-
- Tag the release with the version number
881-
- This will trigger a new release to [RubyGems](https://rubygems.org/gems/featurevisor)
904+
- Tag the release with the same version number, for example `v1.1.0`
905+
- The workflow verifies that the tag matches the shared version
906+
- The workflow publishes `featurevisor` first, followed by `featurevisor-openfeature`
907+
908+
The gems are separate RubyGems packages built from the same repository. Publishing the base gem first ensures the provider's exact Featurevisor dependency is available when the provider is published. If the second push fails, rerun or retry the provider publication without republishing the existing base version.
882909

883910
## License
884911

‎Rakefile‎

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,17 +1,22 @@
11
require "rspec/core/rake_task"
2+
require "fileutils"
3+
require_relative "lib/featurevisor/version"
24

35
RSpec::Core::RakeTask.new(:spec)
46

57
task default: :spec
68

7-
desc "Build the gem"
9+
desc "Build and verify both gems"
810
task :build do
9-
system "gem build featurevisor.gemspec"
11+
sh "gem build featurevisor.gemspec"
12+
sh "gem build featurevisor-openfeature.gemspec"
13+
sh "ruby scripts/verify_gems.rb"
1014
end
1115

1216
desc "Install the gem locally"
1317
task :install => :build do
14-
system "gem install featurevisor-*.gem"
18+
sh "gem install featurevisor-#{Featurevisor::VERSION}.gem"
19+
sh "gem install featurevisor-openfeature-#{Featurevisor::VERSION}.gem"
1520
end
1621

1722
desc "Clean up built gems"

‎featurevisor-openfeature.gemspec‎

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
require_relative "lib/featurevisor/version"
2+
3+
Gem::Specification.new do |spec|
4+
spec.name = "featurevisor-openfeature"
5+
spec.version = Featurevisor::VERSION
6+
spec.authors = ["Fahad Heylaal"]
7+
spec.summary = "OpenFeature provider for Featurevisor"
8+
spec.description = "OpenFeature provider backed by the Featurevisor Ruby SDK"
9+
spec.homepage = "https://featurevisor.com/docs/sdks/openfeature/"
10+
spec.license = "MIT"
11+
spec.required_ruby_version = ">= 3.4.0"
12+
13+
spec.metadata = {
14+
"source_code_uri" => "https://github.com/featurevisor/featurevisor-ruby",
15+
"documentation_uri" => "https://featurevisor.com/docs/sdks/ruby/#openfeature",
16+
"bug_tracker_uri" => "https://github.com/featurevisor/featurevisor-ruby/issues",
17+
"allowed_push_host" => "https://rubygems.org",
18+
"rubygems_mfa_required" => "true"
19+
}
20+
21+
spec.files = %w[
22+
lib/featurevisor-openfeature.rb
23+
lib/featurevisor/openfeature_provider.rb
24+
README.md
25+
LICENSE
26+
]
27+
spec.require_paths = ["lib"]
28+
29+
spec.add_dependency "featurevisor", "= #{Featurevisor::VERSION}"
30+
spec.add_dependency "openfeature-sdk", "~> 0.6.5"
31+
end

‎featurevisor.gemspec‎

Lines changed: 12 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -10,13 +10,22 @@ Gem::Specification.new do |spec|
1010
spec.license = "MIT"
1111
spec.required_ruby_version = ">= 3.0.0"
1212

13-
spec.files = Dir.glob("lib/**/*") + Dir.glob("bin/**/*") + %w[README.md LICENSE]
13+
spec.metadata = {
14+
"source_code_uri" => "https://github.com/featurevisor/featurevisor-ruby",
15+
"documentation_uri" => "https://featurevisor.com/docs/sdks/ruby/",
16+
"bug_tracker_uri" => "https://github.com/featurevisor/featurevisor-ruby/issues",
17+
"allowed_push_host" => "https://rubygems.org",
18+
"rubygems_mfa_required" => "true"
19+
}
20+
21+
spec.files = (Dir.glob("lib/**/*") + Dir.glob("bin/**/*") + %w[README.md LICENSE]).reject do |file|
22+
file == "lib/featurevisor/openfeature_provider.rb" || file == "lib/featurevisor-openfeature.rb"
23+
end
1424
spec.bindir = "bin"
1525
spec.executables = ["featurevisor"]
1626
spec.require_paths = ["lib"]
1727

18-
spec.add_dependency "benchmark", ">= 0"
28+
spec.add_dependency "benchmark", ">= 0", "< 1"
1929
spec.add_development_dependency "rspec", "~> 3.12"
2030
spec.add_development_dependency "rake", "~> 13.0"
21-
spec.add_development_dependency "openfeature-sdk", "~> 0.6.5"
2231
end

0 commit comments

Comments
 (0)