Browse Source

Merge branch 'TechEmpower:master' into master

Huang ziquan 7 months ago
parent
commit
76a58d8e19

+ 1 - 0
frameworks/PHP/reactphp/benchmark_config.json

@@ -1,5 +1,6 @@
 {
   "framework": "reactphp",
+  "maintainers": ["WyriHaximus"],
   "tests": [{
     "default": {
       "json_url": "/json",

+ 1 - 1
frameworks/Ruby/rack/rack-iodine.dockerfile

@@ -19,4 +19,4 @@ COPY . .
 
 EXPOSE 8080
 
-CMD bundle exec iodine -p 8080
+CMD bundle exec iodine -p 8080 -w $(ruby config/auto_tune.rb | grep -Eo '[0-9]+' | head -n 1)

+ 7 - 0
frameworks/Ruby/rage-sequel/Gemfile

@@ -0,0 +1,7 @@
+source "https://rubygems.org"
+
+gem "rage-rb", "~> 1.10"
+
+gem "pg", "~> 1.0"
+gem 'sequel', '~> 5.0'
+gem 'sequel_pg', '~> 1.6', platforms: :ruby, require: false

+ 37 - 0
frameworks/Ruby/rage-sequel/Gemfile.lock

@@ -0,0 +1,37 @@
+GEM
+  remote: https://rubygems.org/
+  specs:
+    bigdecimal (3.1.9)
+    pg (1.5.9)
+    rack (2.2.10)
+    rack-test (2.2.0)
+      rack (>= 1.3)
+    rage-iodine (4.0.0)
+    rage-rb (1.11.0)
+      rack (~> 2.0)
+      rack-test (~> 2.1)
+      rage-iodine (~> 4.0)
+      rake (>= 12.0)
+      thor (~> 1.0)
+      zeitwerk (~> 2.6)
+    rake (13.2.1)
+    sequel (5.88.0)
+      bigdecimal
+    sequel_pg (1.17.1)
+      pg (>= 0.18.0, != 1.2.0)
+      sequel (>= 4.38.0)
+    thor (1.3.2)
+    zeitwerk (2.7.1)
+
+PLATFORMS
+  ruby
+  x86_64-darwin-20
+
+DEPENDENCIES
+  pg (~> 1.0)
+  rage-rb (~> 1.10)
+  sequel (~> 5.0)
+  sequel_pg (~> 1.6)
+
+BUNDLED WITH
+   2.5.6

+ 47 - 0
frameworks/Ruby/rage-sequel/README.md

@@ -0,0 +1,47 @@
+# Rage Benchmarking Test
+
+Rage is a fast web framework compatible with Rails. It uses an event-driven architecture and implements a lightweight, cooperative concurrency model based on Ruby Fibers.
+
+https://github.com/rage-rb/rage
+
+### Test Type Implementation Source Code
+
+* [JSON](app/controllers/benchmarks_controller.rb)
+* [PLAINTEXT](app/controllers/benchmarks_controller.rb)
+* [DB](app/controllers/benchmarks_controller.rb)
+* [QUERY](app/controllers/benchmarks_controller.rb)
+* [UPDATE](app/controllers/benchmarks_controller.rb)
+* [FORTUNES](app/controllers/benchmarks_controller.rb)
+
+## Important Libraries
+
+The tests were run with:
+
+* [Sequel](https://rubygems.org/gems/sequel)
+* [PG](https://rubygems.org/gems/pg)
+
+## Test URLs
+
+### JSON
+
+http://localhost:8080/json
+
+### PLAINTEXT
+
+http://localhost:8080/plaintext
+
+### DB
+
+http://localhost:8080/db
+
+### QUERY
+
+http://localhost:8080/queries?queries=
+
+### UPDATE
+
+http://localhost:8080/updates?queries=
+
+### FORTUNES
+
+http://localhost:8080/fortunes

+ 1 - 0
frameworks/Ruby/rage-sequel/Rakefile

@@ -0,0 +1 @@
+require_relative "config/application"

+ 2 - 0
frameworks/Ruby/rage-sequel/app/controllers/application_controller.rb

@@ -0,0 +1,2 @@
+class ApplicationController < RageController::API
+end

+ 71 - 0
frameworks/Ruby/rage-sequel/app/controllers/benchmarks_controller.rb

@@ -0,0 +1,71 @@
+# frozen_string_literal: true
+
+class BenchmarksController < ApplicationController
+  ALL_DB_IDS = (1..10_000).to_a
+  FORTUNES_TEMPLATE = ERB.new(Rage.root.join("app/views/fortunes.html.erb").read)
+
+  before_action do
+    headers["server"] = "rage"
+  end
+
+  def db
+    render json: World.with_pk(random_id).values
+  end
+
+  def queries
+    worlds = DB.synchronize do
+      requested_ids.map do |id|
+        World.with_pk(id)
+      end
+    end
+
+    render json: worlds.map!(&:values)
+  end
+
+  def fortunes
+    records = Fortune.all
+
+    records << Fortune.new(id: 0, message: "Additional fortune added at request time.")
+    records.sort_by!(&:message)
+
+    render plain: FORTUNES_TEMPLATE.result(binding)
+    headers["content-type"] = "text/html; charset=utf-8"
+  end
+
+  def updates
+    worlds = nil
+
+    DB.synchronize do
+      worlds = requested_ids.map do |id|
+        world = World.with_pk(id)
+        new_value = random_id
+        new_value = random_id while new_value == world.randomnumber
+        world.randomnumber = new_value
+
+        world
+      end
+
+      World.batch_update(worlds)
+    end
+
+    render json: worlds.map!(&:values)
+  end
+
+  private
+
+  def requested_ids
+    num = params[:queries].to_i
+
+    if num > 500
+      num = 500
+    elsif num < 1
+      num = 1
+    end
+
+    ALL_DB_IDS.sample(num)
+  end
+
+  def random_id
+    Random.rand(9_999) + 1
+  end
+end

+ 12 - 0
frameworks/Ruby/rage-sequel/app/views/fortunes.html.erb

@@ -0,0 +1,12 @@
+<!DOCTYPE html>
+<html>
+  <head><title>Fortunes</title></head>
+  <body>
+    <table>
+    <tr><th>id</th><th>message</th></tr>
+    <% records.each do |record| %>
+      <tr><td><%= record.id %></td><td><%= CGI.escape_html(record.message) %></td></tr>
+    <% end %>
+    </table>
+  </body>
+</html>

+ 28 - 0
frameworks/Ruby/rage-sequel/benchmark_config.json

@@ -0,0 +1,28 @@
+{
+  "framework": "rage-sequel",
+  "tests": [
+    {
+      "default": {
+        "db_url": "/db",
+        "query_url": "/queries?queries=",
+        "fortune_url": "/fortunes",
+        "update_url": "/updates?queries=",
+        "port": 8080,
+        "approach": "Realistic",
+        "classification": "Micro",
+        "database": "postgres",
+        "framework": "Rage",
+        "language": "Ruby",
+        "flavor": "None",
+        "orm": "Full",
+        "platform": "Rack",
+        "webserver": "Rage-Iodine",
+        "os": "Linux",
+        "database_os": "Linux",
+        "display_name": "Rage-Sequel",
+        "notes": "",
+        "versus": "None"
+      }
+    }
+  ]
+}

+ 3 - 0
frameworks/Ruby/rage-sequel/config.ru

@@ -0,0 +1,3 @@
+require_relative "config/application"
+
+run Rage.application

+ 14 - 0
frameworks/Ruby/rage-sequel/config/application.rb

@@ -0,0 +1,14 @@
+require "bundler/setup"
+require "rage"
+Bundler.require(*Rage.groups)
+
+require "rage/all"
+
+Rage.configure do
+  # use this to add settings that are constant across all environments
+end
+
+require "erb"
+require "cgi"
+
+require "rage/setup"

+ 4 - 0
frameworks/Ruby/rage-sequel/config/environments/development.rb

@@ -0,0 +1,4 @@
+Rage.configure do
+  config.server.workers_count = -1
+  config.logger = Rage::Logger.new(STDOUT)
+end

+ 3 - 0
frameworks/Ruby/rage-sequel/config/environments/production.rb

@@ -0,0 +1,3 @@
+Rage.configure do
+  config.logger = nil
+end

+ 41 - 0
frameworks/Ruby/rage-sequel/config/initializers/sequel.rb

@@ -0,0 +1,41 @@
+# frozen_string_literal: true
+
+SEQUEL_NO_ASSOCIATIONS = true
+Sequel.extension :fiber_concurrency
+
+# Determine thread pool size and timeout
+opts = {
+  max_connections: 512,
+  pool_timeout: 10
+}
+
+DB = Sequel.connect \
+  '%{adapter}://%{host}/%{database}?user=%{user}&password=%{password}' % {
+    :adapter=>'postgres',
+    :host=>'tfb-database',
+    :database=>'hello_world',
+    :user=>'benchmarkdbuser',
+    :password=>'benchmarkdbpass'
+  }, opts
+
+# Define ORM models
+class World < Sequel::Model(:World)
+  def self.batch_update(worlds)
+    ids = []
+    sql = String.new("UPDATE world SET randomnumber = CASE id ")
+    worlds.each do |world|
+      sql << "when #{world.id} then #{world.randomnumber} "
+      ids << world.id
+    end
+    sql << "ELSE randomnumber END WHERE id IN ( #{ids.join(',')})"
+    DB.run(sql)
+  end
+end
+
+class Fortune < Sequel::Model(:Fortune)
+  # Allow setting id to zero (0) per benchmark requirements
+  unrestrict_primary_key
+end
+
+[World, Fortune].each(&:freeze)
+DB.freeze

+ 8 - 0
frameworks/Ruby/rage-sequel/config/routes.rb

@@ -0,0 +1,8 @@
+Rage.routes.draw do
+  root to: ->(env) { [200, {}, "It works!"] }
+
+  get "db", to: "benchmarks#db"
+  get "queries", to: "benchmarks#queries"
+  get "fortunes", to: "benchmarks#fortunes"
+  get "updates", to: "benchmarks#updates"
+end

+ 0 - 0
frameworks/Ruby/rage-sequel/lib/.keep


+ 13 - 0
frameworks/Ruby/rage-sequel/rage-sequel.dockerfile

@@ -0,0 +1,13 @@
+FROM ruby:3.4
+
+EXPOSE 8080
+WORKDIR /rage-sequel
+
+COPY Gemfile*  /rage-sequel/
+RUN bundle install --jobs=8
+COPY . /rage-sequel
+
+ENV RUBY_YJIT_ENABLE=1
+ENV BUNDLE_FORCE_RUBY_PLATFORM=true
+
+CMD bundle exec rage s -b 0.0.0.0 -p 8080 -e production

+ 1 - 1
frameworks/Ruby/roda-sequel/roda-sequel-postgres-iodine-mri.dockerfile

@@ -18,4 +18,4 @@ ENV DBTYPE=postgresql
 
 EXPOSE 8080
 
-CMD bundle exec iodine -p 8080
+CMD bundle exec iodine -p 8080 -w $(ruby config/auto_tune.rb | grep -Eo '[0-9]+' | head -n 1)