From 79113bcce6ee303318289730f784dc687269705f Mon Sep 17 00:00:00 2001 From: Fahad Heylaal Date: Sat, 29 Aug 2026 19:05:11 +0200 Subject: [PATCH] chore: upgrade to Ruby SDK v3 --- .github/workflows/checks.yml | 3 ++ Gemfile | 2 +- Gemfile.lock | 4 +-- README.md | 42 ++++++++++++++++++++++------ Rakefile | 28 +++++++++---------- app.rb | 53 +++++++++++++++++++++++++++--------- 6 files changed, 94 insertions(+), 38 deletions(-) mode change 100644 => 100755 app.rb diff --git a/.github/workflows/checks.yml b/.github/workflows/checks.yml index c47a6ce..8397183 100644 --- a/.github/workflows/checks.yml +++ b/.github/workflows/checks.yml @@ -32,5 +32,8 @@ jobs: - name: Check syntax run: bundle exec ruby -c app.rb + - name: Lint + run: bundle exec rubocop --cache false + - name: Run application run: bundle exec ruby app.rb diff --git a/Gemfile b/Gemfile index 0083d64..c7ae34a 100644 --- a/Gemfile +++ b/Gemfile @@ -3,8 +3,8 @@ source 'https://rubygems.org' ruby '>= 3.0.0' # Add your gems here +gem 'featurevisor', '~> 3.0' gem 'rake', '~> 13.0' -gem 'featurevisor', '~> 2.0' group :development do gem 'rubocop', '~> 1.50' diff --git a/Gemfile.lock b/Gemfile.lock index d2b71dd..4a1d738 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -3,7 +3,7 @@ GEM specs: ast (2.4.3) benchmark (0.5.0) - featurevisor (2.0.0) + featurevisor (3.0.0) benchmark (>= 0, < 1) json (2.21.1) language_server-protocol (3.17.0.6) @@ -41,7 +41,7 @@ PLATFORMS ruby DEPENDENCIES - featurevisor (~> 2.0) + featurevisor (~> 3.0) rake (~> 13.0) rubocop (~> 1.50) diff --git a/README.md b/README.md index cc5f751..26db29d 100644 --- a/README.md +++ b/README.md @@ -1,25 +1,51 @@ # featurevisor-example-ruby -Example Ruby application that demonstrates how to use Featurevisor [Ruby SDK](https://github.com/featurevisor/featurevisor-ruby). +A small Ruby application showing how to use the [Featurevisor Ruby SDK](https://github.com/featurevisor/featurevisor-ruby). Learn more about Featurevisor [here](https://featurevisor.com). -## Installation +It fetches a production datafile, creates a Featurevisor instance with customer context, then evaluates a flag, a variation, feature variables, and global variables. -Clone the repository, and run: +## Installation +```sh +bundle install ``` -$ bundle install + +## Run the example + +```sh +bundle exec ruby app.rb ``` -## Usage +The application evaluates `commerce_platform`, `checkout_experience`, `max_items`, `payment_methods`, `serviceEndpoints`, and `supportContact` from this datafile: + +```text +https://featurevisor-example-cloudflare.pages.dev/production/featurevisor-sdk-v3.json +``` -Run the server locally, running: +Expected output: +```text +Commerce platform enabled: true +Checkout variation: express +Maximum checkout items: 25 +Payment methods: ["card", "wallet"] +Service endpoint: https://api.eu.example.com (timeout: 1200 ms, retries: 4) +Support contact: support-nl@example.com ``` -$ rake run + +Change the context in `app.rb` to see how Featurevisor selects different rules, variations, and global variable overrides. + +## Checks + +```sh +bundle exec rubocop +bundle exec ruby app.rb ``` ## Featurevisor project -Uses this Featurevisor project to fetch the configuration from: https://github.com/featurevisor/featurevisor-example-cloudflare +The datafile is generated by the [Featurevisor Cloudflare example](https://github.com/featurevisor/featurevisor-example-cloudflare). + +Learn more in the [Featurevisor Ruby SDK documentation](https://featurevisor.com/docs/sdks/ruby/). diff --git a/Rakefile b/Rakefile index 4fec54c..77c2e4e 100644 --- a/Rakefile +++ b/Rakefile @@ -4,33 +4,33 @@ require 'rake' task default: [:run] # Run the Hello World program -desc "Run the Hello World program with Featurevisor" +desc 'Run the Hello World program with Featurevisor' task :run do - puts "Running Ruby Hello World program with Featurevisor..." + puts 'Running Ruby Hello World program with Featurevisor...' puts - system("ruby app.rb") + system('ruby app.rb') end # Clean temporary files -desc "Clean temporary files" +desc 'Clean temporary files' task :clean do - puts "Cleaning temporary files..." - FileList["*.log", "*.tmp", "*.temp"].each do |file| - File.delete(file) if File.exist?(file) + puts 'Cleaning temporary files...' + FileList['*.log', '*.tmp', '*.temp'].each do |file| + FileUtils.rm_f(file) end - puts "Cleanup complete!" + puts 'Cleanup complete!' end # Install dependencies -desc "Install gem dependencies" +desc 'Install gem dependencies' task :install do - puts "Installing gem dependencies..." - system("bundle install") + puts 'Installing gem dependencies...' + system('bundle install') end # Run RuboCop -desc "Run RuboCop for code style checking" +desc 'Run RuboCop for code style checking' task :lint do - puts "Running RuboCop..." - system("bundle exec rubocop") + puts 'Running RuboCop...' + system('bundle exec rubocop') end diff --git a/app.rb b/app.rb old mode 100644 new mode 100755 index 3b90075..1adbd12 --- a/app.rb +++ b/app.rb @@ -1,23 +1,50 @@ #!/usr/bin/env ruby require 'featurevisor' -require 'net/http' require 'json' +require 'net/http' + +DATAFILE_URL = 'https://featurevisor-example-cloudflare.pages.dev/production/featurevisor-sdk-v3.json'.freeze + +uri = URI(DATAFILE_URL) +response = Net::HTTP.start( + uri.host, + uri.port, + use_ssl: uri.scheme == 'https', + open_timeout: 10, + read_timeout: 10 +) { |http| http.get(uri.request_uri, { 'Accept' => 'application/json' }) } -## -# Fetch datafile -# -datafile_url = "https://featurevisor-example-cloudflare.pages.dev/production/featurevisor-tag-all.json" -response = Net::HTTP.get(URI(datafile_url)) -datafile_content = JSON.parse(response, symbolize_names: true) +unless response.is_a?(Net::HTTPSuccess) + raise "Datafile request failed with HTTP #{response.code}" +end -# Create Featurevisor instance f = Featurevisor.create_featurevisor( - datafile: datafile_content, + datafile: JSON.parse(response.body, symbolize_names: true), + log_level: 'error', + context: { + userId: 'customer-123', + country: 'nl', + locale: 'nl-NL', + accountPlan: 'pro' + } ) -# Get the feature flag value -feature_flag_value = f.is_enabled("my_feature") +begin + commerce_enabled = f.is_enabled('commerce_platform') + checkout_variation = f.get_variation('checkout_experience') + max_items = f.get_variable_integer('checkout_experience', 'max_items') + payment_methods = f.get_variable_array('checkout_experience', 'payment_methods') + endpoints = f.get_variable_object('serviceEndpoints') + support_contact = f.get_variable_string('supportContact') -# Print results to terminal -puts "Feature flag 'my_feature' is enabled: #{feature_flag_value}" + puts "Commerce platform enabled: #{commerce_enabled}" + puts "Checkout variation: #{checkout_variation || 'unavailable'}" + puts "Maximum checkout items: #{max_items || 'unavailable'}" + puts "Payment methods: #{payment_methods || []}" + puts "Service endpoint: #{endpoints[:baseUrl]} " \ + "(timeout: #{endpoints[:timeoutMs]} ms, retries: #{endpoints[:retries]})" + puts "Support contact: #{support_contact || 'unavailable'}" +ensure + f.close +end