From 28c9077f05d1e4746cc08d543947fb43bcbcfed0 Mon Sep 17 00:00:00 2001 From: Uladzislau Tarsunou Date: Mon, 16 Nov 2020 22:01:58 -0600 Subject: [PATCH] v0.1.0.pre.3 --- .gitattributes | 53 +- .gitignore | 3 - CHANGELOG.md | 23 +- Dockerfile | 2 +- History.txt | 7 + README.md | 117 ++- Rakefile | 176 ++--- bin/audit/all_but_performance | 21 - bin/audit/full | 11 - bin/audit/quick | 9 - bin/console/docker | 4 - bin/console/{minimal => ruby} | 0 bin/console/ruuuby_debugging | 28 - bin/{zsh => }/docker/clean.zsh | 0 .../compose/dev/build.zsh} | 0 .../compose/dev/down.zsh} | 2 +- .../compose/dev/rebuild_and_restart.zsh} | 0 bin/docker/compose/dev/run.zsh | 12 + .../compose/dev/tty_rebuild_and_restart.zsh} | 0 .../compose/dev/tty_run.zsh} | 0 .../compose/test/build.zsh} | 0 .../compose/test/down.zsh} | 2 +- .../compose/test/run.zsh} | 2 +- bin/zsh/docker/compose/dev_run.zsh | 9 - bin/zsh/get_local_ip.zsh | 4 - docker-compose.dev.yml | 53 +- docker-compose.prod.yml | 49 +- docker-compose.test.yml | 69 +- ext/ruby_class_mods/c3_macro_utilities.h | 9 - ext/ruby_class_mods/ruby_class_mods.c | 7 +- help/architecture_notes.md | 142 ---- help/db_notes.md | 149 ---- help/extensions/c/c_extension.md | 111 --- help/extensions/c/gcc.md | 47 -- help/extensions/c/open_cl.md | 19 - help/extensions/c/open_mp.md | 8 - help/extensions/java/jruby.md | 32 - help/math/automatic_differentiation.md | 54 -- help/math/diagrams.md | 15 - help/math/math.md | 235 ------ help/math/units.md | 42 -- help/python.md | 4 - help/ruby.md | 93 --- help/ruuuby.md | 151 ---- lib/ruuuby/class/enumerable/hsh.rb | 13 +- lib/ruuuby/class/io/file.rb | 1 - lib/ruuuby/class/obj.rb | 26 - lib/ruuuby/configs.rb | 13 - lib/ruuuby/db/db_connection.rb | 35 +- lib/ruuuby/db/migrations/migration_ext.rb | 28 +- .../{01_ruuuby_gem.sql => 00_ruuuby_gem.sql} | 13 +- .../db/migrations/rollback/00_utils.sql | 16 - .../{01_ruuuby_gem.sql => 00_ruuuby_gem.sql} | 73 +- lib/ruuuby/db/migrations/rollout/00_utils.sql | 72 -- lib/ruuuby/db/migrations/ruuuby_gem.rb | 59 +- lib/ruuuby/db/migrations/ruuuby_resource.rb | 59 -- .../{01_ruuuby_gem.sql => 00_ruuuby_gem.sql} | 18 + lib/ruuuby/db/migrations/seed/00_utils.sql | 14 - .../db/model_attributes/application_record.rb | 2 + .../db/seeds/ruuuby_feature_behaviors.rb | 10 - lib/ruuuby/db/seeds/ruuuby_features.rb | 5 +- .../math/algebra/tropical/context_matrix.rb | 144 ++-- .../math/algebra/tropical/context_numeric.rb | 128 ++-- .../math/complex_analysis/complex_analysis.rb | 13 - lib/ruuuby/math/expr/equation.rb | 20 - lib/ruuuby/math/expr/expression.rb | 36 - lib/ruuuby/math/expr/math_func.rb | 62 -- lib/ruuuby/math/expr/seq/arithmetic.rb | 19 - lib/ruuuby/math/expr/seq/geometric.rb | 18 - lib/ruuuby/math/expr/seq/recursive.rb | 19 - lib/ruuuby/math/expr/{seq => }/sequence.rb | 1 - lib/ruuuby/math/geometry/shape/circle.rb | 30 - .../math/geometry/shape/plane_figure.rb | 32 - .../math/geometry/shape/quadrilateral.rb | 59 -- lib/ruuuby/math/geometry/shape/shape.rb | 31 - lib/ruuuby/math/geometry/shape/sphere.rb | 20 - lib/ruuuby/math/geometry/shape/triangle.rb | 152 ---- .../math/number_theory/number_theory.rb | 690 +++++++++--------- .../attribute/includable/connectable.rb | 2 +- lib/ruuuby/module/gem.rb | 30 + lib/ruuuby/module/kernel.rb | 8 +- lib/ruuuby/protocol/http_request.rb | 9 +- lib/ruuuby/protocol/unix_socket.rb | 20 - lib/ruuuby/ruuuby/api/docker/api_docker.rb | 4 +- .../conditional/discrete/service_nginx.rb | 2 +- .../conditional/docker_service_set_dev.rb | 28 +- .../ruuuby/api/docker/docker_container.rb | 1 + lib/ruuuby/ruuuby/api/git/api_git.rb | 569 +++++++-------- lib/ruuuby/ruuuby/engine/f22/b05.rb | 29 + lib/ruuuby/ruuuby/engine/ruuuby_engine.rb | 2 +- lib/ruuuby/ruuuby/ruuuby_api.rb | 26 +- lib/ruuuby/ruuuby/ruuuby_orm.rb | 3 +- lib/ruuuby/version.rb | 9 +- ruuuby.gemspec | 20 +- .../dev_configs/mac/spec/locale/f43_spec.rb | 19 + .../dev_configs/mac/spec/locale/f44_spec.rb | 13 + .../dev_configs/mac/spec/locale/f45_spec.rb | 13 + .../dev_configs/mac/spec/locale/f46_spec.rb | 34 + .../dev_configs/mac/spec/locale/f47_spec.rb | 16 + .../mac/spec/locale/f92_b00_spec.rb | 17 + .../dev_configs/mac/spec/locale/f98_spec.rb | 24 + .../locale/locale_full_verification_spec.rb | 40 + services/message_bot/models/entity_channel.rb | 22 + services/message_bot/models/entity_user.rb | 22 + services/nginx/Dockerfile | 1 + .../default.nginx} | 0 .../nginx/includes/proxy_pass/pgadmin.nginx | 6 + .../nginx/includes/proxy_pass/rabbitmq.nginx | 4 + services/nginx/includes/unsorted/cors.nginx | 13 +- services/nginx/ruuuby.dev.nginx | 75 +- services/nginx/ruuuby.prod.nginx | 59 +- services/nginx/ruuuby.test.nginx | 80 +- services/pgadmin/Dockerfile | 5 + services/rabbitmq/Dockerfile | 2 + services/rabbitmq/{ => dev}/definitions.json | 0 services/rabbitmq/{ => dev}/rabbitmq.config | 0 services/rabbitmq/prod/definitions.json | 59 ++ services/rabbitmq/prod/rabbitmq.config | 20 + services/rabbitmq/test/definitions.json | 59 ++ services/rabbitmq/test/rabbitmq.config | 20 + services/ruuuby/Dockerfile | 27 + services/ruuuby_db/Dockerfile | 10 + services/ruuuby_db/bin/db | 9 +- services/ruuuby_db/init.sql | 145 ++++ services/ruuuby_db/spec/dev/migration_spec.rb | 1 + services/ruuuby_db/spec/migration_spec.rb | 114 +++ .../ruuuby_db/spec/test/migration_spec.rb | 1 + services/web_assets/package.json | 2 +- .../models/application_record/data_spec.rb | 59 -- .../app/models/application_record/orm_spec.rb | 61 -- spec/app/models/ruuuby_features/orm_spec.rb | 7 - spec/app/models/ruuuby_releases/data_spec.rb | 7 - .../ruuuby_releases/integration_spec.rb | 17 - spec/class/enumerable/hsh_spec.rb | 60 ++ spec/class/enumerable/set_spec.rb | 2 - spec/class/str_spec.rb | 5 + spec/db/db_spec.rb | 31 - spec/db/seed_data_spec.rb | 6 - spec/feature/f11/f11_b00_spec.rb | 25 - spec/feature/f11/f11_b01_spec.rb | 16 - spec/feature/f11/f11_b02_spec.rb | 320 -------- spec/feature/f11/f11_db_orm_spec.rb | 27 - spec/feature/f11/f11_spec.rb | 489 ------------- spec/feature/f15/readme_spec.rb | 3 + spec/feature/f30/f30_b00_spec.rb | 15 - spec/feature/f30/f30_b02_spec.rb | 4 - spec/feature/f30/f30_b03_spec.rb | 13 - spec/feature/f30/f30_b04_spec.rb | 3 - spec/feature/f34/f34_b00_spec.rb | 13 - spec/feature/f34/f34_b01_spec.rb | 13 - spec/feature/f34/f34_b02_spec.rb | 63 -- spec/feature/f34/f34_b03_spec.rb | 13 - spec/feature/f34/f34_b04_spec.rb | 13 - spec/feature/f34/f34_db_orm_spec.rb | 39 - spec/feature/f34/f34_spec.rb | 87 --- spec/feature/f37/f37_b00_spec.rb | 12 + .../{helper_db.rb => db/autoload_me.rb} | 9 + spec/helpers/helper_math.rb | 57 -- spec/helpers/helper_ruuuby.rb | 53 +- spec/helpers/integration/autoload_me.rb | 3 + spec/helpers/load_benchmark.rb | 3 - spec/helpers/locale/autoload_me.rb | 15 + .../autoload_me.rb} | 2 + spec/locale/ag_gem_configs_spec.rb | 13 - spec/locale/locale_full_verification_spec.rb | 88 --- spec/locale/ruby_locale_spec.rb | 3 - spec/spec_helper.rb | 36 +- spec/system/javascript_docker_service_spec.rb | 2 +- spec/system/nginx_docker_service_spec.rb | 2 +- spec/system/pgadmin_docker_service_spec.rb | 13 +- spec/system/postgres_docker_service_spec.rb | 14 +- 171 files changed, 2251 insertions(+), 4884 deletions(-) delete mode 100755 bin/audit/all_but_performance delete mode 100755 bin/audit/full delete mode 100755 bin/audit/quick rename bin/console/{minimal => ruby} (100%) delete mode 100755 bin/console/ruuuby_debugging rename bin/{zsh => }/docker/clean.zsh (100%) rename bin/{zsh/docker/compose/dev_build.zsh => docker/compose/dev/build.zsh} (100%) rename bin/{zsh/docker/compose/test_down.zsh => docker/compose/dev/down.zsh} (61%) rename bin/{zsh/docker/compose/dev_rebuild_and_restart.zsh => docker/compose/dev/rebuild_and_restart.zsh} (100%) create mode 100755 bin/docker/compose/dev/run.zsh rename bin/{zsh/docker/compose/dev_tty_rebuild_and_restart.zsh => docker/compose/dev/tty_rebuild_and_restart.zsh} (100%) rename bin/{zsh/docker/compose/dev_tty_run.zsh => docker/compose/dev/tty_run.zsh} (100%) rename bin/{zsh/docker/compose/test_build.zsh => docker/compose/test/build.zsh} (100%) rename bin/{zsh/docker/compose/test_run.zsh => docker/compose/test/down.zsh} (61%) rename bin/{zsh/docker/compose/dev_down.zsh => docker/compose/test/run.zsh} (63%) delete mode 100755 bin/zsh/docker/compose/dev_run.zsh delete mode 100644 bin/zsh/get_local_ip.zsh delete mode 100644 help/architecture_notes.md delete mode 100644 help/db_notes.md delete mode 100644 help/extensions/c/c_extension.md delete mode 100644 help/extensions/c/gcc.md delete mode 100644 help/extensions/c/open_cl.md delete mode 100644 help/extensions/c/open_mp.md delete mode 100644 help/extensions/java/jruby.md delete mode 100644 help/math/automatic_differentiation.md delete mode 100644 help/math/diagrams.md delete mode 100644 help/math/math.md delete mode 100644 help/math/units.md delete mode 100644 help/python.md delete mode 100644 help/ruby.md delete mode 100644 help/ruuuby.md rename lib/ruuuby/db/migrations/rollback/{01_ruuuby_gem.sql => 00_ruuuby_gem.sql} (71%) delete mode 100644 lib/ruuuby/db/migrations/rollback/00_utils.sql rename lib/ruuuby/db/migrations/rollout/{01_ruuuby_gem.sql => 00_ruuuby_gem.sql} (64%) delete mode 100644 lib/ruuuby/db/migrations/rollout/00_utils.sql delete mode 100644 lib/ruuuby/db/migrations/ruuuby_resource.rb rename lib/ruuuby/db/migrations/seed/{01_ruuuby_gem.sql => 00_ruuuby_gem.sql} (90%) delete mode 100644 lib/ruuuby/db/migrations/seed/00_utils.sql delete mode 100644 lib/ruuuby/math/complex_analysis/complex_analysis.rb delete mode 100644 lib/ruuuby/math/expr/equation.rb delete mode 100644 lib/ruuuby/math/expr/expression.rb delete mode 100644 lib/ruuuby/math/expr/math_func.rb delete mode 100644 lib/ruuuby/math/expr/seq/arithmetic.rb delete mode 100644 lib/ruuuby/math/expr/seq/geometric.rb delete mode 100644 lib/ruuuby/math/expr/seq/recursive.rb rename lib/ruuuby/math/expr/{seq => }/sequence.rb (99%) delete mode 100644 lib/ruuuby/math/geometry/shape/circle.rb delete mode 100644 lib/ruuuby/math/geometry/shape/plane_figure.rb delete mode 100644 lib/ruuuby/math/geometry/shape/quadrilateral.rb delete mode 100644 lib/ruuuby/math/geometry/shape/shape.rb delete mode 100644 lib/ruuuby/math/geometry/shape/sphere.rb delete mode 100644 lib/ruuuby/math/geometry/shape/triangle.rb create mode 100644 services/dev_configs/mac/spec/locale/f43_spec.rb create mode 100644 services/dev_configs/mac/spec/locale/f44_spec.rb create mode 100644 services/dev_configs/mac/spec/locale/f45_spec.rb create mode 100644 services/dev_configs/mac/spec/locale/f46_spec.rb create mode 100644 services/dev_configs/mac/spec/locale/f47_spec.rb create mode 100644 services/dev_configs/mac/spec/locale/f92_b00_spec.rb create mode 100644 services/dev_configs/mac/spec/locale/f98_spec.rb create mode 100644 services/dev_configs/mac/spec/locale/locale_full_verification_spec.rb create mode 100644 services/message_bot/models/entity_channel.rb create mode 100644 services/message_bot/models/entity_user.rb rename services/nginx/includes/{unsorted/proxy_pass.nginx => proxy_pass/default.nginx} (100%) create mode 100644 services/nginx/includes/proxy_pass/pgadmin.nginx create mode 100644 services/nginx/includes/proxy_pass/rabbitmq.nginx create mode 100644 services/pgadmin/Dockerfile rename services/rabbitmq/{ => dev}/definitions.json (100%) rename services/rabbitmq/{ => dev}/rabbitmq.config (100%) create mode 100644 services/rabbitmq/prod/definitions.json create mode 100644 services/rabbitmq/prod/rabbitmq.config create mode 100644 services/rabbitmq/test/definitions.json create mode 100644 services/rabbitmq/test/rabbitmq.config create mode 100644 services/ruuuby_db/Dockerfile create mode 100644 services/ruuuby_db/init.sql create mode 100644 services/ruuuby_db/spec/dev/migration_spec.rb create mode 100644 services/ruuuby_db/spec/migration_spec.rb create mode 100644 services/ruuuby_db/spec/test/migration_spec.rb delete mode 100644 spec/app/models/application_record/data_spec.rb delete mode 100644 spec/app/models/application_record/orm_spec.rb delete mode 100644 spec/app/models/ruuuby_releases/integration_spec.rb delete mode 100644 spec/db/db_spec.rb delete mode 100644 spec/feature/f11/f11_b00_spec.rb delete mode 100644 spec/feature/f11/f11_b01_spec.rb delete mode 100644 spec/feature/f11/f11_b02_spec.rb delete mode 100644 spec/feature/f11/f11_db_orm_spec.rb delete mode 100644 spec/feature/f11/f11_spec.rb delete mode 100644 spec/feature/f30/f30_b00_spec.rb delete mode 100644 spec/feature/f30/f30_b03_spec.rb delete mode 100644 spec/feature/f34/f34_b00_spec.rb delete mode 100644 spec/feature/f34/f34_b01_spec.rb delete mode 100644 spec/feature/f34/f34_b02_spec.rb delete mode 100644 spec/feature/f34/f34_b03_spec.rb delete mode 100644 spec/feature/f34/f34_b04_spec.rb delete mode 100644 spec/feature/f34/f34_db_orm_spec.rb delete mode 100644 spec/feature/f34/f34_spec.rb rename spec/helpers/{helper_db.rb => db/autoload_me.rb} (97%) delete mode 100644 spec/helpers/helper_math.rb create mode 100644 spec/helpers/integration/autoload_me.rb delete mode 100644 spec/helpers/load_benchmark.rb create mode 100644 spec/helpers/locale/autoload_me.rb rename spec/helpers/{helper_performance.rb => performance/autoload_me.rb} (99%) diff --git a/.gitattributes b/.gitattributes index c220919..fc53af4 100644 --- a/.gitattributes +++ b/.gitattributes @@ -99,18 +99,20 @@ # \/_/ \/____/\/__/\/_/\/__,_ / \/__/\/_/\/___/ \/__/\/____/\//\/_/ \/__/ # ---------------------------------------------------------------------------------------------------------------------- -*.txt diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol -*.text diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol -*.log diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol -*.csv diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol -*.yml diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol -*.yaml diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol -*.nginx diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol -*.sh diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol -*.sql diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol -*.scpt diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol -*.cjs diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol -*.mjs diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol +*.txt diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol +*.text diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol +*.ruby-version diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol +*.log diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol +*.csv diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol +*.yml diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol +*.yaml diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol +*.nginx diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol +*.sh diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol +*.zsh diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol +*.sql diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol +*.scpt diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol +*.cjs diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol +*.mjs diff=text text=text eol=lf whitespace=blank-at-eof,blank-at-eol # 0x3) ----------------------------------------------------------------------------------------------------------------- # __ __ @@ -288,10 +290,29 @@ # \_/__/ # # @see https://github.com/github/linguist/issues/3666 +# @see https://github.com/github/linguist/blob/master/lib/linguist/languages.yml # ---------------------------------------------------------------------------------------------------------------------- -*.sql linguist-detectable=true -*.sql linguist-language=sql +*.sql linguist-detectable=true +*.sql linguist-language=SQL -*.c linguist-language=c -*.h linguist-language=c +*.c linguist-language=C +*.h linguist-language=C + +*.sh linguist-language=Shell +*.zsh linguist-language=Shell + +*.rb linguist-language=Ruby +*.gemspec linguist-language=Ruby +Rakefile linguist-language=Ruby +Gemfile linguist-language=Ruby + +Dockerfile linguist-language=Dockerfile +docker-compose.yml linguist-language=Dockerfile +docker-compose.dev.yml linguist-language=Dockerfile +docker-compose.test.yml linguist-language=Dockerfile +docker-compose.prod.yml linguist-language=Dockerfile + +LICENSE.txt linguist-documentation=false +History.txt linguist-documentation=false +CHANGELOG.md linguist-documentation=false diff --git a/.gitignore b/.gitignore index 6768443..026a1ad 100644 --- a/.gitignore +++ b/.gitignore @@ -28,9 +28,6 @@ vendor/ services/ruuuby/f93/ services/temp/ -# preference based config checks or anything un-related to Ruuuby -spec/dev_settings/ - # Gemfile.lock diff --git a/CHANGELOG.md b/CHANGELOG.md index 316a1ad..5127bbd 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,8 +1,10 @@ ---- -#### ⚠️: documentation & testing synchronization targeted {0.1.0} +# `v0.1.0.pre.3` ---- + * add gem{`open3`} + * continue `DB` migrations + * iterative improvement for custom builds, lazy-loading, and separation between `dev`/`test`/`prod` environments + * apply clean ups, any removed core functionality to return closer to version{`0.1.0`} # `v0.1.0.pre.2` @@ -507,8 +509,6 @@ | `TOPLEVEL_BINDING` | `θ°`, `θʳ`, `θᵍ`, `θ𝞽` | `f27` | | `ThetaAngle` | `real`, `repr`, `as_radian`, `as_degree`, `as_gon`, `as_turn`, `radians?`, `degrees?`, `gons?`, `turns?`, `-@`, `+@`, `coerce`, `~`, `!`, `+`, `-`, `*`, `%`,`==`, `/`, `<=>`, `angle?`, `normal?`, `normalize!`, `golden_with?`, `explementary_with?`, `supplementary_with?`, `complementary_with?`, | `f27` | -* remove the following methods/aliases: - | from | methods/aliases removed | | ---------- | ----------------------- | | `Kernel` | `∠ᶜ`, `∠°` | @@ -555,9 +555,9 @@ | `GitCommit` | `get_latest`, `query_get_newest_within_version` | `f15` | | `RuuubyRelease` | `on_before_save` | `f15` | -| (c)lass or (m)odule | methods/aliases *removed* | +| from | methods/aliases *removed* | | ------------------- | --------------------- | -| (c) `Symbol` | `power?`, `pow_to_i` | +| `Symbol` | `power?`, `pow_to_i` | --- @@ -620,11 +620,6 @@ | `lib/ruuuby/ruuuby/ruuuby_orm.rb` | `Ruuuby::MetaData::RuuubyORM` | | `f15` | | `lib/ruuuby/ruuuby/routine_cli.rb` | `Ruuuby::Routine::CommandCLI` | | `f15` | -| path removed | notes | -| ---: | --- | -| `app/models/db_schema.rb` | seemed like a bad location | -| `conditionals/ide_helper.rb` | moved to `lib/ruuuby/ide_helper.rb`, gets excluded by `ruuuby.gemspec` | - | class | method(s) added | feature(s) | | --- | --- | --- | | `String` | `char?`, | `f06` | @@ -680,10 +675,6 @@ | --- | --- | --- | | `Object` | (freeze) `❄`, `❄?` | `f10` | -| path removed | notes | -| ---: | --- | -| `conditionals/ruuuby_configs.rb` | configs not needed during runtime should be dynamically handled, not with conditionally loaded files (created explicitly for such need) | - --- # `v0.0.25` diff --git a/Dockerfile b/Dockerfile index 0a6e5c2..0defacf 100644 --- a/Dockerfile +++ b/Dockerfile @@ -32,7 +32,7 @@ ENV LC_CTYPE en_US.UTF-8 ENV LC_MESSAGES en_US.UTF-8 #ENV BUILD_CORE_LIBS bash bash-completion git wget curl vim build-base readline readline-dev openssl-dev zlib-dev -ENV BUILD_CORE_LIBS git wget curl vim build-base readline readline-dev openssl-dev zlib-dev +ENV BUILD_CORE_LIBS git wget curl vim build-base readline readline-dev openssl-dev zlib-dev gmp-dev ENV SERVICE_OS="alpine" ENV SERVICE_OS_VERSION="TODO:" diff --git a/History.txt b/History.txt index 666e76e..58026c5 100644 --- a/History.txt +++ b/History.txt @@ -1,4 +1,11 @@ += `v0.1.0.pre.3` / 2020-11-16 + +* add gem{`open3`} +* continue `DB` migrations +* iterative improvement for custom builds, lazy-loading, and separation between `dev`/`test`/`prod` environments +* apply clean ups, any removed core functionality to return closer to version{`0.1.0`} + = `v0.1.0.pre.2` / 2020-11-06 * modify `.gitattributes` to track `.sql` files diff --git a/README.md b/README.md index bc06ff7..264c19a 100644 --- a/README.md +++ b/README.md @@ -1,17 +1,14 @@ # Ruuuby [![Gem Version](https://badge.fury.io/rb/ruuuby.svg)](https://badge.fury.io/rb/ruuuby) -> flavored modifications & extensions for increased quality of Ruby coding life - | for resource | reference | | ------------------: | :---------------------------------------------------------- | -| latest: `Gemfile` | `gem 'ruuuby', '~> 0.1.0.pre.2'` | -| stable: `Gemfile` | `gem 'ruuuby', '~> 0.0.49` | -| ruby scripts | `require 'ruuuby'` | -| gem url | https://rubygems.org/gems/ruuuby | -| changelog | https://github.com/utarsuno/ruuuby/blob/master/CHANGELOG.md
`note: style of changelog will be adapted to the` [`[History.txt format]`](https://guides.rubygems.org/releasing-rubygems/) | +| latest version | [`0.1.0.pre.3`](https://rubygems.org/gems/ruuuby/versions/0.1.0.pre.3-x86_64-darwin-19) | +| stable version | [`0.0.49`](https://rubygems.org/gems/ruuuby/versions/0.0.49-x86_64-darwin-18) | +| changelog | [`CHANGELOG.md`](https://github.com/utarsuno/ruuuby/blob/master/CHANGELOG.md) with in progress migration to [`[History.txt format]`](https://guides.rubygems.org/releasing-rubygems/) | | `JIT` testing | `RUBYOPT="--jit --jit-warnings --jit-wait --jit-max-cache=1337 --jit-verbose=2 --jit-debug -w" ./bin/console/ruuuby` | -| common
non-ascii | `∅`,`∃`,`∄`,`∋`,`∌`,`∈`,`∉`,`ⓣ`,`Ⓣ`,`≈`,`∞`,`π`,`℮`,`𝚽`
`η̂`,`μ`,`∴`,`𝔠`,`𝔦`,`𝔣`,`Λ`,`λ`,`∫`,`⨍`,`𝑓`,`∀`,`τ`,`x̃`,`𝚡`,`𝛿`,`σ`,`⌋`,`⌈`
`𝔹`,`ℂ`,`ℕ`,`𝕎`,`ℤ`,`ℚ`,`𝔸ᵣ`,`ℂ`,`𝕋`,`𝕀`,`ℝ`,`𝕌`,`𝕊`,`🅱`
`±`,`Ω`,`γ`,`Ψ`,`ρ`,`δ`,`Ⴔ`,`⨁`,`⨂`,`∖`,`≡`,`√`,`∛`,`↩`,`‣`,`⟶`,`↘`,`⬇`,`⬆`
`𝞽`,`θ`,`°`,`ʳ`,`ᵍ`,`⦜`,`○`,`ₑ`,`₀`,`₁`,`₂`,`₃`,`ₓ`,`ᵢ`,`ᵀ`,`▣`
`⁻ⁿ`,`⁰`,`¹`,`²`,`³`,`⁴`,`⁵`,`⁶`,`⁷`,`⁸`,`⁹`
`¼`,`½`,`¾`,`⅓`,`⅕`,`⅕`,`⅖`,`⅗`,`⅘`,`⅙`,`⅐`,`⅛`,`⅜`,`⅝`,`⅞`,`⅑`,`⅒`
`📁`,`🗄️`,`💾`,`🕒`,`🎲`,`📊`,`🧟`,`💻`,`📱`,`🌐`,`❄️`,`💎`,`⚠️`,`🔑`,`✏️`,`📖`,`🏠`
`✅`,`♻️`,`🍺`,`🛡`,`📅`,`🛑`,`❌`,`❓`,`🆔`,`🧬`
`🐇`,`🐋`,`🐍`,`🐫`,`🙈` | +| common
non-ascii | `∅`,`∃`,`∄`,`∋`,`∌`,`∈`,`∉`,`ⓣ`,`Ⓣ`,`≈`,`∞`,`π`,`℮`,`𝚽`
`η̂`,`μ`,`∴`,`𝔠`,`𝔦`,`𝔣`,`Λ`,`λ`,`∫`,`⨍`,`𝑓`,`∀`,`τ`,`x̃`,`𝚡`,`𝛿`,`σ`,`⌋`,`⌈`
`𝔹`,`ℂ`,`ℕ`,`𝕎`,`ℤ`,`ℚ`,`𝔸ᵣ`,`ℂ`,`𝕋`,`𝕀`,`ℝ`,`𝕌`,`𝕊`,`🅱`
`±`,`Ω`,`γ`,`Ψ`,`ρ`,`δ`,`Ⴔ`,`⨁`,`⨂`,`∖`,`≡`,`√`,`∛`,`↩`,`‣`,`⟶`,`↘`,`⬇`,`⬆`
`𝞽`,`θ`,`°`,`ʳ`,`ᵍ`,`⦜`,`○`,`ₑ`,`₀`,`₁`,`₂`,`₃`,`ₓ`,`ᵢ`,`ᵀ`,`▣`
`⁻ⁿ`,`⁰`,`¹`,`²`,`³`,`⁴`,`⁵`,`⁶`,`⁷`,`⁸`,`⁹`,`●`,`◆`,`▲,`▬,`▰`
`¼`,`½`,`¾`,`⅓`,`⅕`,`⅕`,`⅖`,`⅗`,`⅘`,`⅙`,`⅐`,`⅛`,`⅜`,`⅝`,`⅞`,`⅑`,`⅒`
`📁`,`🗄️`,`💾`,`🕒`,`🎲`,`📊`,`🧟`,`💻`,`📱`,`🌐`,`❄️`,`💎`,`⚠️`,`🔑`,`✏️`,`📖`,`🏠`
`✅`,`♻️`,`🍺`,`🛡`,`📅`,`🛑`,`❌`,`❓`,`🆔`,`🧬`
`🐇`,`🐋`,`🐍`,`🐫`,`🙈` | | download source for utilized version of Ruby | [Ruby3.0.0-preview1](https://www.ruby-lang.org/en/news/2020/09/25/ruby-3-0-0-preview1-released/) | +| summary & purpose | in migration until version{`0.1.0`} | ### Examples @@ -21,25 +18,25 @@ # |__/ |___ \/ \__/ | | |___ | | | |___ .__/ # run node.js tests on live container{A}, transfer results as file to live container{B} -qa_results = 🐋['service_js'].cmd!(%w(npm test --check-leaks)).join.as_utf8 -🐋['service_nginx'].📁✏️('/v/js_qa_results.txt', qa_results) +qa_results = 🐋['service_js_dev'].cmd!(%w(npm test --check-leaks)).join.as_utf8 +🐋['service_nginx_dev'].📁✏️('/example/file/path', qa_results) # send chat message, triggering execution of background QA tests which involve randomness # ‣ allowing relatively ∞ time for tests to complete, as needed # ‣ jobs can be scheduled from mobile-phone! 📱 # # AMQP & REST: Ruuuby ⟶ Discord ⟶ JavaScript ⟶ RabbitMQ ⟶ Ruuuby ⟶ Discord -$discord.msg('!cmd: RUUUBY_F01="b00"; bundle exec rake rspec_rng') - -# ‣ check if today's average temperature in Chicago is below freezing -# ‣ check if specified file does not already exists -# ‣ if both checks pass, create file w/ results from local command ran (updating brew) -path_to_log_file = "brew_update_#{📅.today.to_s}.txt" -chicago_weather = 🌐.get_json!('https://www.metaweather.com/api/location/2379574/') -if chicago_weather['consolidated_weather'].first['the_temp'] < 0 - 💻("brew update > #{path_to_log_file}") unless 📁.∃?(path_to_log_file) +$discord.msg('!cmd: bundle exec rake qa:rng') + +# ‣ A) is the specified path an empty file or not exist? +# ‣ B) is today's average temperature in Chicago below freezing? +# ‣ if yes to (A) and (B), save results of brew update command to file at path specified +path_file = "brew_update_#{📅.today.to_s}.txt" +unless 📁.∃?(path_file) || 📁.∅?(path_file) + chicago_data = 🌐.get_json!('https://www.metaweather.com/api/location/2379574/') + avg_temp_celsius = chicago_data['consolidated_weather'].first['the_temp'] + 💻("brew update > #{path_file}") if avg_temp_celsius < 0 end - ``` ```ruby @@ -47,14 +44,12 @@ end # |__ |__ /\ | | | |__) |__ | \ | / _` |__ /__` | # | |___ /~~\ | \__/ | \ |___ |__/ | \__> |___ .__/ | -# | ✔ | ✔ | ✔ | ✔ | ✔ | ✔ | ✔ | +# | ✔ | ✔ | ✔ | ✔ | ✔ | 𝚽 == 1 + (𝚽^⁻¹) 𝚽 == 2 * sin(θ°(54)) -𝚽 == (θ°(360) - Ⴔ) / Ⴔ π == 5 * acos(𝚽 / 2) +θ°(360) == θʳ(π/2) * 4 √(√(-1337.0^⁴)) == 1337 -θ°(360) == θʳ(π/2) * 4 -θ𝞽(0.75) == 𝞽 - θᵍ(100) # | ✔ | ✔ | ✘ | ✘ | ✔ | 'b'.∈? 'abc' @@ -64,9 +59,8 @@ end [1337, 'xyz'].∋? 1337 # | ✔ | ✘ | -elements_a = [1, 'a', 2, nil, [], 2] -elements_b = [nil, 2, 2, 'a', 1, []] -[elements_a.≈≈(elements_b), elements_a == elements_b] +[1, 'a', 2, nil, [], 2].≈≈ [nil, 2, 2, 'a', 1, []] +[1, 'a', 2, nil, [], 2] == [nil, 2, 2, 'a', 1, []] # | ✔ | ✔ | ✔ | ✔ | ['snake_case'.🐍?, 'AHHH_CAPITALS'.🐍⬆?, 'UpperCaseCamel'.🐫?, 'lowerCaseCamel'.🐫⬇?] @@ -100,6 +94,7 @@ data = {haaallo: 'wooorld', ye: 'ee'} | `finite_machine` | [`0.14.0`](https://rubygems.org/gems/finite_machine/versions/0.14.0) | ✅, ✅ | always required | | `bunny` | [`2.17.0`](https://rubygems.org/gems/bunny/versions/2.17.0) | ✅, ❌ | toggleable feature | | `docker-api` | [`2.0.0`](https://rubygems.org/gems/docker-api/versions/2.0.0) | ✅, ❌ | toggleable feature | +| `open3` | [`0.1.0`](https://rubygems.org/gems/open3/versions/0.1.0) | ✅, ❌ | toggleable feature | | `pg` | [`1.2.3`](https://rubygems.org/gems/pg/versions/1.2.3) | ✅, ❌ | toggleable feature | | `activerecord` | [`6.1.0.rc1`](https://rubygems.org/gems/activerecord/versions/6.1.0.rc1) | ✅, ❌ | toggleable feature | | `rdoc` | [`6.2.1`](https://rubygems.org/gems/rdoc/versions/6.2.1) | ✅, ❌ | development utility | @@ -118,10 +113,9 @@ data = {haaallo: 'wooorld', ye: 'ee'} | base context | sub context | applies to | example of added functions | | ------------ | ----------- | -----------| --------------------------- | | `ThetaAngle` | `ContextStr` | `String` | `ʳ?`,`ᵍ?`,`ʳ`,`ᵍ` | -| `ThetaAngle` | -`ContextRuuuby`
-`ContextParamCheck` | `Object` | `θ°`,`θʳ`,`θᵍ`,`θ𝞽`
`θ?`, `🛑θ❓` | +| `ThetaAngle` | -`ContextRuuuby`
-`ContextParamCheck` | `Object` | -`θ°`,`θʳ`,`θᵍ`,`θ𝞽`
-`θ?`,`🛑θ❓` | | `Math::Algebra::Tropical` | `ContextNumeric` | `Numeric` | `⨁`, `⨂` | | `Math::Algebra::Tropical` | `ContextMatrix` | `Matrix` | `⨁`, `⨁!`, `⨂`, `⨂ⁿ` | -| `Math::NumberTheory` | `ℤ³` | `Integer` | `≡` | | `Heuristics` | `ContextParsingCommandOutput` | -`String`
-`Array` | `clean` | ### Example Math Modules Modification: @@ -129,8 +123,6 @@ data = {haaallo: 'wooorld', ye: 'ee'} | module(s) | sub-module | func(s) added | | ------: | :----: | :---------------- | | `Math` | `Ratio` | `golden?`, `super_golden?` | -| `Trig` | | `cot²`, `cos²`, `sin²`, `tan²`, `sec²`, `csc²` | -| `Trig` | `ℕ³` | `pythagorean?` | | `NumberTheory` | | `semiprime?` | | `NumberTheory` | `ℕ¹` | `prime_factors`, `divisors`, `proper_divisors`, `aliquot_sum`, `perfect?`, `almost_perfect?`, `abundant?`, `abundance`, `abundancy_index`, `deficient?`, `deficiency`, `composite?` | | `NumberTheory` | `𝕎¹` | `nᵗʰ_euler_totient`, `nᵗʰ_cototient`, `digit_sum`, `digital_root`, `additive_persistence` | @@ -148,9 +140,9 @@ data = {haaallo: 'wooorld', ye: 'ee'} | base-context | sub-context | sample functionality | | -------------: | :----------: | :------ | -| `Trigonometry` | class: `ThetaAngle` | | -| `Statistics` | class: `TimeSeriesData` | | -| `NumberTheory::𝕎¹` | singleton-objs of class: `Math::Expr::Sequence` | | +| `Trigonometry` | class: `ThetaAngle` | `°?`,`°`,`ʳ?`,`ʳ`,`∅?`,`⦜?`,`○?`,`η̂?`,`η̂!` | +| `Statistics` | class: `TimeSeriesData` | `μ`,`x̃`,`σ`,`σ²`,`ρ`,`mse`,`mape`,`λ`,`Λ`,`η̂?`,`η̂!`
`mem_size`,`free_memory`,`Q₁`,`Q₂`,`Q₃`,`IQR`,`outliers_lower`,`outliers_upper` | +| `NumberTheory::𝕎¹` | singleton-objs of class: `Math::Expr::Sequence` | `seq_pronic`,`seq_fibonacci`,`seq_lucas`,`seq_square`,`seq_triangle`,`seq_hexagonal` | | `Forex` | class: `CurrencyMatrix` | | | `GraphTheory` | class: `PseudoGraph` | | @@ -159,17 +151,12 @@ data = {haaallo: 'wooorld', ye: 'ee'} | class(es) | func(s) added | | ---------------------: | :---------------------------------- | | `File`, `Dir`, `ENV`, `NilClass`, `Vector` | `∅?` | -| `File`, `Dir` | `∃?` | | `Module` | `∃⨍_alias?`, `∃⨍?` | | `File` | `replace_expr_with`, `replace_expr_with!`, `insert_line_before_expr` | | `Object` | `Ⓣ`, `ary?`, `bool?`, `hsh?`, `int?`, `flt?`, `num?`, `str?`, `chr?`, `sym?`, `matrix?`, `vec?`
`🛑bool❓`, `🛑int❓`, `🛑flt❓`, `🛑num❓`, `🛑ary❓`, `🛑str❓`, `🛑sym❓` | | `String` | `♻️⟵`, `♻️⟶`, `♻️⟶∞`,`∋?`, `∌?`, `∈?`, `∉?`
`⬇?`⟶`downcase?`, `⬆?`⟶`upcase?`, `⬇!`⟶`downcase!`, `⬆!`⟶`upcase!`
`🐫?`, `🐫⬇?`, `to_🐫``🐍⬆?`, `🐍?`, `to_🐍`
`digit?`, `to_num`, `to_num?`, `palindrome?`
`as_utf8`, `iso8601?`, `to_iso8601`, `as_iso8601` | -| `Array`, `String` | `η̂!` | -| `Array` | `⨁`⟶`disjunctive_union`, `∖`, `end_with?`, `start_with?` | | `Enumerable` | `∌?`, `∀τ²∈λ𝑓₍ᵢ،ᵢ₊₁₎` | -| `Array`, `String` | `>>` | -| `String`, `Array` | `ensure_start!`, `ensure_ending!` | -| `Float` | `≈≈`, `∞ℂ?` | +| `Array`, `String` | `>>`, `η̂!`, `ensure_start!`, `ensure_ending!` | | `Matrix` | `∀ₓ↘`, `∀ₓᵢ↘`, `↘_to_a`, `∀ₓᵢⱼ` | ### Example Aliases: @@ -180,14 +167,11 @@ data = {haaallo: 'wooorld', ye: 'ee'} | `Object` | `object_id`, `class`, `freeze`, `frozen?` | `🆔`, `ⓣ`, `❄️`, `❄️?` | | `Module` | `private`, `protected`, `const_defined?`, `private_method_defined?`, `protected_method_defined?` | `🙈`, `🛡️`, `∃const?`, `∃🙈⨍`, `∃🛡️⨍?` | | `String`, `Symbol` | `upcase`, `downcase` | `⬆`, `⬇` | -| `Array` | `tally`, `↩∀` | `📊`, `reverse_each`| | `Array`, `Hash`, `Set` | `each` | `∀` | -| `Array`, `String` | `reverse`, `reverse!` | `↩`, `↩!` | | `Enumerable` | `map`, `each_with_index` | `⨍`, `∀ₓᵢ` | | `Hash` | `key?` | `∃🔑?` | | `NilClass`, `Hash`, `Array`, `String`, `Set` | `empty?` | `∅?`| | `String`, `Array`, `Set`, `Hash`, `Proc` | `length` (`arity` for `Proc`) * | `𝔠` | -| `Matrix` | `square?`, `tranpose`, `row_count`, `column_count` | `▣?`, `ᵀ`, `num_rows`, `num_cols` | --- @@ -199,31 +183,22 @@ data = {haaallo: 'wooorld', ye: 'ee'} ### Code Base Statistics: -> tests marked with a ~~strikethrough~~ will not exist/work before version{`0.1.0`} - -| category | attribute | value(s) | # of | -| ----------: | :---------------------: | ---------------: | :---- | -| `QA` | `unit` | `1274` | tests (core functionality) | -| `QA` | `integration` | `22` | tests (state & functionality of grouped units) | -| `QA` | `performance (runtime)` | ~~142 : 85~~ | ~~tests{`non_numeric`,`numeric`}~~ | -| `QA` | `DB` | ~~291~~ | ~~tests (combined categories of `DB`, `ORM`, & `Service`)~~ | -| `QA` | `rng` | `2` | tests (involving statistics/randomness, ex: verifying a geometric distribution) | -| `QA` | `system` | `7` | tests (`integration` scaled to `micro-services` & w/ randomness involved to help encounter niche error-states) | -| `CI` | `audit` | `124` | tests (anything non-functionality based) | -| `CI` | `locale` | `66`:`32` | tests on local setup & configs{`core`:`excessive_checks`} | -| `tech-debt` | `coverage` | `31` | tests (tracking missing functionality) | -| `structure` | `features` | `1`:`32`:`9`:`6` | features{`stable`:`wip`:`⚠️`:`todo`} | -| `coverage` | `LOCs` | `???` | `wip` | -| `coverage` | `runtime` | `???` | `wip` | -| `coverage` | `documentation` | `???` | `wip` | - ---- - ->#### Contributing ->###### Bug reports and pull requests are welcome on GitHub at https://github.com/utarsuno/ruuuby. This project is intended to be a safe, welcoming space for collaboration, and contributors are expected to adhere to the [code of conduct](https://github.com/utarsuno/ruuuby/blob/master/CODE_OF_CONDUCT.md). -> ->#### License ->###### The gem is available as open source under the terms of the [MIT License](https://opensource.org/licenses/MIT). -> ->#### Code of Conduct ->###### Everyone interacting in the Ruuuby project's codebases, issue trackers, chat rooms and mailing lists is expected to follow the [code of conduct](https://github.com/utarsuno/ruuuby/blob/master/CODE_OF_CONDUCT.md). +| categories | attribute | value(s) | stable before version{`0.1.0`} | # of | +| -----------------: | :----------------------: | ----------: | :-----: | :---- | +| `QA` | `unit` | `1202` | ✅ | tests (core functionality) | +| `QA` | `integration` | `20` | ✅ | tests (state & functionality of grouped units) | +| `QA`,`performance` | `benchmarks-runtime` | | ❌ | | +| `QA`,`performance` | `benchmarks-memory` | | ❌ | | +| `QA` | `rng` | `2` | ✅ | tests (involving statistics/randomness, ex: verifying a geometric distribution)) | +| `QA`,`DB` | `system` | `7` | ✅ | tests (`integration` scaled to `micro-services` & w/ randomness involved to help encounter niche error-states) | +| `QA`,`DB` | `engine` | | ❌ | | +| `QA`,`DB` | `ORM` | | ❌ | | +| `QA`,`DB` | `services` | | ❌ | | +| `QA`,`CICD`,`DB` | `domain` | | ❌ | | +| `CICD` | `audit` | `83` | ✅ | tests (anything non-functionality based) | +| `CICD` | `locale` | `66` | ✅ | tests (verifying `Ruuuby` needed build configs) | +| `CICD` | `preferences` | `20` | ❌ | tests (verifying preferred `OS & development configs & values`) | +| `structure` | `tech-debt` | `8` | ✅ | tests (tracking missing functionality) | +| `structure` | `features` | | ❌ | | +| `coverage` | `code-documentation` | `? %` | ❌ | | +| `coverage` | `code-coverage-tested` | `? %` | ❌ | | diff --git a/Rakefile b/Rakefile index 97b04d3..b0bf957 100644 --- a/Rakefile +++ b/Rakefile @@ -8,67 +8,71 @@ require 'rdoc/rdoc' require 'rake' -namespace :dev_settings do - - f92 = ENV['RUUUBY_F92'] - - task :disable_db_dev do - raise ::RuntimeError.new("| ENV[RUUUBY_F92] w/ value{#{f92.to_s}} indicates it should not be disabled |") if (f92 != nil && (f92.include?('b01') || f92.include?('b02'))) - `bundle config unset with` - `bundle config unset without` - `bundle config set with 'development'` - `bundle config set without 'db'` - end - - task :enable_db_dev do - raise ::RuntimeError.new("| ENV[RUUUBY_F92] w/ value{#{f92.to_s}} does not have the required feature behavior needed |") if (f92.class == ::String && !(f92.include?('b01') || f92.include?('b02'))) - `bundle config unset with` - `bundle config unset without` - `bundle config set with 'db' 'development'` - #`bundle config set without 'prod'` - end - -end - namespace :qa do task :unit do - #ENV['RUBYOPT'] = '-W:no-deprecated -W:no-experimental' #ENV['RUUUBY_F01'] = 'b00' + ENV['RUUUBY_PERFORMANCE_LIMIT'] = 'on' + ENV['RUUUBY_AUTOLOAD_DB'] = 'off' ::Rake::Task['rspec_unit'].invoke end task :functionality do - #ENV['RUBYOPT'] = '-W:no-deprecated -W:no-experimental' #ENV['RUUUBY_F01'] = 'b00' + ENV['RUUUBY_PERFORMANCE_LIMIT'] = 'on' ::Rake::Task['rspec_audit'].execute ::Rake::Task['rspec_locale'].execute ::Rake::Task['rspec_tech_debt'].execute - ::Rake::Task['rspec_integration'].execute ::Rake::Task['qa:unit'].invoke + + ::Rake::Task['qa:integration'].invoke + end + + task :integration do + ENV['RUBYOPT'] = '-W:no-deprecated -W:no-experimental' + ENV['RUUUBY_F01'] = 'b00' + ENV['RUUUBY_PERFORMANCE_LIMIT'] = 'on' + ENV['RUUUBY_AUTOLOAD_DB'] = 'off' + ENV['RUUUBY_RSPEC_INTEGRATION'] = 'on' + ::Rake::Task['rspec_integration'].execute end task :db do - ENV['RUBYOPT'] = '-W:no-deprecated -W:no-experimental' - ENV['RUUUBY_F01'] = 'b00' - ::Rake::Task['rspec_db'].execute + ENV['RUBYOPT'] = '-W:no-deprecated -W:no-experimental' + ENV['RUUUBY_F01'] = 'b00' + ENV['RUUUBY_PERFORMANCE_LIMIT'] = 'on' + ENV['RUUUBY_F92'] = 'b01|b02' + ENV['RUUUBY_RSPEC_INTEGRATION'] = 'off' + ENV['RUUUBY_AUTOLOAD_DB'] = 'on' + ::Rake::Task['rspec_db'].invoke + end + + task :rng do + ENV['RUBYOPT'] = '-W:no-deprecated -W:no-experimental' + ENV['RUUUBY_F01'] = 'b00' + ENV['RUUUBY_PERFORMANCE_LIMIT'] = 'on' + ::Rake::Task['rspec_rng'].execute end task :audit do - ENV['RUBYOPT'] = '-W:no-deprecated -W:no-experimental' - ENV['RUUUBY_F01'] = 'b00' + ENV['RUBYOPT'] = '-W:no-deprecated -W:no-experimental' + ENV['RUUUBY_F01'] = 'b00' + ENV['RUUUBY_PERFORMANCE_LIMIT'] = 'on' ::Rake::Task['rspec_audit'].execute end task :locale do - ENV['RUBYOPT'] = '-W:no-deprecated -W:no-experimental' - ENV['RUUUBY_F01'] = 'b00' + ENV['RUBYOPT'] = '-W:no-deprecated -W:no-experimental' + ENV['RUUUBY_F01'] = 'b00' + ENV['RUUUBY_PERFORMANCE_LIMIT'] = 'on' ::Rake::Task['rspec_locale'].execute end task :locale_full do - ENV['RUBYOPT'] = '-W:no-deprecated -W:no-experimental' - ENV['RUUUBY_F01'] = 'b00' + ENV['RUBYOPT'] = '-W:no-deprecated -W:no-experimental' + ENV['RUUUBY_F01'] = 'b00' + ENV['RUUUBY_F43'] = 'b00' + ENV['RUUUBY_PERFORMANCE_LIMIT'] = 'on' ::Rake::Task['rspec_locale_full'].execute end @@ -115,35 +119,58 @@ end # ______________________________________________________________________________________________________________________ module CategoriesQA - ALL_SINGULAR_CATEGORIES = %w(audit db performance locale tech_debt unit integration system service rng) - PATH_BASE = ::File.dirname(__FILE__) + RSPEC_TAG_NAMES = %w(audit db db_new performance locale preferences tech_debt unit integration system service rng) + PATH_BASE = ::File.dirname(__FILE__) module Preload - DB_PARTIAL = %w(/db/db) - DB_FULL = %w(/db/db /db/seed) - LIB_BENCHMARK = %w(/spec/helpers/load_benchmark) + DB_FULL = %w(/db/db /db/seed) +# DB_NEW = %w(/services/ruuuby_db/spec/migration_spec) + DB_NEW = %w( + /spec/helpers/db/autoload_me + /services/ruuuby_db/spec/migration_spec +) + INTEGRATION = %w(/spec/helpers/integration/autoload_me) + LIB_BENCHMARK = %w(/spec/helpers/performance/autoload_me) + LOCALE_BASE = %w(/spec/helpers/locale/autoload_me) + LOCALE_FULL = LOCALE_BASE + %w( + /services/dev_configs/mac/spec/locale/f43_spec + /services/dev_configs/mac/spec/locale/f44_spec + /services/dev_configs/mac/spec/locale/f45_spec + /services/dev_configs/mac/spec/locale/f46_spec + /services/dev_configs/mac/spec/locale/f47_spec + /services/dev_configs/mac/spec/locale/f92_b00_spec + /services/dev_configs/mac/spec/locale/f98_spec + /services/dev_configs/mac/spec/locale/locale_full_verification_spec +) end end # https://rubydoc.info/github/rspec/rspec-core/RSpec/Core/Configuration -def add_task_rspec(task_name, sub_category, with_warnings, singular_category_test, exclude_other_categories, exclude_patterns='', files_to_require=[]) - official_task_name = "#{task_name}" - official_task_name += "_#{sub_category}" unless sub_category.empty? +# @param [String] task_name +# @param [String] exclude_patterns +# @param [Array] files_to_require +def add_task_rspec(task_name, exclude_patterns='', files_to_require=[]) + rspec_task = RSpec::Core::RakeTask.new("rspec_#{task_name}".to_sym) local_opts = ['--format progress', '--color', '--require spec_helper'] - #local_opts = ['--color', '--require spec_helper'] - local_opts << '--warnings' if with_warnings - if singular_category_test && task_name != 'unit' - local_opts << "--tag @#{task_name}" - end - if exclude_other_categories - CategoriesQA::ALL_SINGULAR_CATEGORIES.each do |c| - local_opts << "--tag ~@#{c}" if c != task_name + + if task_name == 'all' + local_opts << '--warnings' + rspec_task.verbose = true + else + rspec_task.verbose = false + CategoriesQA::RSPEC_TAG_NAMES.each do |tag| + local_opts << "--tag ~@#{tag}" if tag != task_name + end + local_opts << "--tag @#{task_name}" unless task_name == 'unit' + case task_name + when 'rng' + local_opts << '--out rspec_rng.txt' + else end end - rspec_task = RSpec::Core::RakeTask.new("rspec_#{official_task_name}".to_sym) - rspec_task.verbose = with_warnings rspec_task.rspec_opts = local_opts.join(' ') + unless files_to_require.empty? files_to_require.each do |relative_path| rspec_task.rspec_opts << " --require #{CategoriesQA::PATH_BASE}#{relative_path}.rb" @@ -152,40 +179,23 @@ def add_task_rspec(task_name, sub_category, with_warnings, singular_category_tes unless exclude_patterns.empty? rspec_task.rspec_opts << " --exclude-pattern \"#{exclude_patterns}\"" end - - - if task_name == 'rng' - rspec_task.rspec_opts << ' --out rspec_rng.txt' - else - #rspec_task.rspec_opts << ' --format progress' - end - - #puts "task{#{official_task_name}}, rspec_opts{#{rspec_task.rspec_opts.to_s}}" end -add_task_rspec('unit', '',false, true, true) -add_task_rspec('audit', '', false, true, true) -add_task_rspec('db', '', false, true, true, '', CategoriesQA::Preload::DB_FULL) +add_task_rspec('db', '', CategoriesQA::Preload::DB_FULL) +add_task_rspec('db_new', '', CategoriesQA::Preload::DB_NEW) +add_task_rspec('performance', '', CategoriesQA::Preload::LIB_BENCHMARK) -add_task_rspec('rng', '', false, true, true) +add_task_rspec('unit') +add_task_rspec('audit') +add_task_rspec('rng') +add_task_rspec('locale', '**/*_full_verification_spec.rb', CategoriesQA::Preload::LOCALE_BASE) +add_task_rspec('preferences', '', CategoriesQA::Preload::LOCALE_FULL) +add_task_rspec('tech_debt') +add_task_rspec('integration', '', CategoriesQA::Preload::INTEGRATION) +add_task_rspec('system', '', %w(/spec/helpers/db/autoload_me)) +add_task_rspec('service') -# TODO: use better solution for loading benchmark (use existing rake task settings) -add_task_rspec('performance', '', false, true, true, '', CategoriesQA::Preload::LIB_BENCHMARK) -add_task_rspec('performance', 'no_nums', false, true, true, '**/int_spec.rb,**/float_spec.rb,**/complex_spec.rb,**/rational_spec.rb', CategoriesQA::Preload::LIB_BENCHMARK) - -add_task_rspec('locale', '', false, true, true, '**/*_full_verification_spec.rb') -add_task_rspec('locale', 'full', false, true, true, '') -add_task_rspec('tech_debt', '', false, true, true) -add_task_rspec('integration', '', false, true, true) -add_task_rspec('system', '', false, true, true) -add_task_rspec('service', '', false, true, true) -add_task_rspec('all', '', true, false, false, '**/*_service_spec.rb', CategoriesQA::Preload::DB_FULL) - -# ______________________________________________________________________________________________________________________ -# __ ___ __ __ ___ -# | \ /\ | /\ |__) /\ /__` |__ -# |__/ /~~\ | /~~\ |__) /~~\ .__/ |___ -# ______________________________________________________________________________________________________________________ +#add_task_rspec('all', '**/*_service_spec.rb', CategoriesQA::Preload::DB_FULL) # ______________________________________________________________________________________________________________________ # __ __ __ ___ ___ ___ __ @@ -207,3 +217,5 @@ RDoc::Task.new do |rdoc| end #task :default => :rspec + +task :default => :'qa:unit' diff --git a/bin/audit/all_but_performance b/bin/audit/all_but_performance deleted file mode 100755 index 19a3454..0000000 --- a/bin/audit/all_but_performance +++ /dev/null @@ -1,21 +0,0 @@ -#!/usr/bin/env bash -# encoding: UTF-8 - -export RUBYOPT='-W:no-deprecated -W:no-experimental' -#export RUUUBY_F01="b00|b04{debug}" -export RUUUBY_F01="b01|b03|b04{debug}" - - -set -euo pipefail -IFS=$'\n\t' -set -vx - -bundle exec rake compile:ruby_class_mods -bundle exec rake rspec_audit -bundle exec rake rspec_locale -#bundle exec rake rspec_db -bundle exec rake rspec_tech_debt -bundle exec rake rspec_integration -bundle exec rake rspec_unit - -#bundle exec rake rspec_system diff --git a/bin/audit/full b/bin/audit/full deleted file mode 100755 index 2edc43c..0000000 --- a/bin/audit/full +++ /dev/null @@ -1,11 +0,0 @@ -#!/usr/bin/env bash -# encoding: UTF-8 - -set -euo pipefail -IFS=$'\n\t' -set -vx - -bundle exec rake compile:ruby_class_mods -bundle exec rake rdoc -bundle exec rake rspec_all -bundle exec rake build diff --git a/bin/audit/quick b/bin/audit/quick deleted file mode 100755 index c3ff58b..0000000 --- a/bin/audit/quick +++ /dev/null @@ -1,9 +0,0 @@ -#!/usr/bin/env bash -# encoding: UTF-8 - -set -euo pipefail -IFS=$'\n\t' -set -vx - -bundle exec rake compile:ruby_class_mods -bundle exec rake rspec_unit diff --git a/bin/console/docker b/bin/console/docker index e03e50e..3738eb4 100755 --- a/bin/console/docker +++ b/bin/console/docker @@ -8,10 +8,6 @@ require 'ruuuby' $ruuuby = 💎 $docker = 🐋 -#using ::Math::Algebra::Tropical::ContextNumeric -#using ::Math::Algebra::Tropical::ContextMatrix -#using ::ThetaAngle::ContextRuuuby -#using ::ThetaAngle::ContextParamCheck using ::String::ContextF24 using ::Ruuuby::Heuristics::ContextParsingCommandOutput diff --git a/bin/console/minimal b/bin/console/ruby similarity index 100% rename from bin/console/minimal rename to bin/console/ruby diff --git a/bin/console/ruuuby_debugging b/bin/console/ruuuby_debugging deleted file mode 100755 index 5432fd5..0000000 --- a/bin/console/ruuuby_debugging +++ /dev/null @@ -1,28 +0,0 @@ -#!/usr/bin/env ruby -# encoding: UTF-8 - -RUBYOPT='-W:no-deprecated -W:no-experimental' -ENV['RUUUBY_F01']="b01|b03|b04{debug}" -require 'bundler/setup' -require 'ruuuby' - -$ruuuby = 💎 -using ::String::ContextF24 -using ::Ruuuby::Heuristics::ContextParsingCommandOutput - -class TempDiscord - - def initialize - @temp_url = ENV['TEMP_URL'] - end - - def msg(the_msg) - 🌐.post_json(@temp_url, {username: "B O T", avatar_url: "", content: the_msg}) - end - -end - -$discord = TempDiscord.new - -require 'irb' -IRB.start(__FILE__) diff --git a/bin/zsh/docker/clean.zsh b/bin/docker/clean.zsh similarity index 100% rename from bin/zsh/docker/clean.zsh rename to bin/docker/clean.zsh diff --git a/bin/zsh/docker/compose/dev_build.zsh b/bin/docker/compose/dev/build.zsh similarity index 100% rename from bin/zsh/docker/compose/dev_build.zsh rename to bin/docker/compose/dev/build.zsh diff --git a/bin/zsh/docker/compose/test_down.zsh b/bin/docker/compose/dev/down.zsh similarity index 61% rename from bin/zsh/docker/compose/test_down.zsh rename to bin/docker/compose/dev/down.zsh index 87e49e7..f6e0474 100755 --- a/bin/zsh/docker/compose/test_down.zsh +++ b/bin/docker/compose/dev/down.zsh @@ -1,6 +1,6 @@ #!/bin/zsh -docker-compose -f ./docker-compose.test.yml down +docker-compose -f ./docker-compose.dev.yml down --remove-orphans exit_code=$? if [[ $exit_code -ne 0 ]]; then echo "error{${exit_code}}" diff --git a/bin/zsh/docker/compose/dev_rebuild_and_restart.zsh b/bin/docker/compose/dev/rebuild_and_restart.zsh similarity index 100% rename from bin/zsh/docker/compose/dev_rebuild_and_restart.zsh rename to bin/docker/compose/dev/rebuild_and_restart.zsh diff --git a/bin/docker/compose/dev/run.zsh b/bin/docker/compose/dev/run.zsh new file mode 100755 index 0000000..571de00 --- /dev/null +++ b/bin/docker/compose/dev/run.zsh @@ -0,0 +1,12 @@ +#!/bin/zsh + +#docker-compose -f ./docker-compose.dev.yml up -d 2>/dev/null + +docker-compose -f ./docker-compose.dev.yml up -d + +exit_code=$? +if [[ $exit_code -ne 0 ]]; then + echo "error{${exit_code}}" +else + echo "ok" +fi diff --git a/bin/zsh/docker/compose/dev_tty_rebuild_and_restart.zsh b/bin/docker/compose/dev/tty_rebuild_and_restart.zsh similarity index 100% rename from bin/zsh/docker/compose/dev_tty_rebuild_and_restart.zsh rename to bin/docker/compose/dev/tty_rebuild_and_restart.zsh diff --git a/bin/zsh/docker/compose/dev_tty_run.zsh b/bin/docker/compose/dev/tty_run.zsh similarity index 100% rename from bin/zsh/docker/compose/dev_tty_run.zsh rename to bin/docker/compose/dev/tty_run.zsh diff --git a/bin/zsh/docker/compose/test_build.zsh b/bin/docker/compose/test/build.zsh similarity index 100% rename from bin/zsh/docker/compose/test_build.zsh rename to bin/docker/compose/test/build.zsh diff --git a/bin/zsh/docker/compose/test_run.zsh b/bin/docker/compose/test/down.zsh similarity index 61% rename from bin/zsh/docker/compose/test_run.zsh rename to bin/docker/compose/test/down.zsh index 87e49e7..0d77624 100755 --- a/bin/zsh/docker/compose/test_run.zsh +++ b/bin/docker/compose/test/down.zsh @@ -1,6 +1,6 @@ #!/bin/zsh -docker-compose -f ./docker-compose.test.yml down +docker-compose -f ./docker-compose.test.yml down --remove-orphans exit_code=$? if [[ $exit_code -ne 0 ]]; then echo "error{${exit_code}}" diff --git a/bin/zsh/docker/compose/dev_down.zsh b/bin/docker/compose/test/run.zsh similarity index 63% rename from bin/zsh/docker/compose/dev_down.zsh rename to bin/docker/compose/test/run.zsh index 5d6b32b..7dc7964 100755 --- a/bin/zsh/docker/compose/dev_down.zsh +++ b/bin/docker/compose/test/run.zsh @@ -1,6 +1,6 @@ #!/bin/zsh -docker-compose -f ./docker-compose.dev.yml down +docker-compose -f ./docker-compose.test.yml up -d 2>/dev/null exit_code=$? if [[ $exit_code -ne 0 ]]; then echo "error{${exit_code}}" diff --git a/bin/zsh/docker/compose/dev_run.zsh b/bin/zsh/docker/compose/dev_run.zsh deleted file mode 100755 index 6dd3599..0000000 --- a/bin/zsh/docker/compose/dev_run.zsh +++ /dev/null @@ -1,9 +0,0 @@ -#!/bin/zsh - -docker-compose -f ./docker-compose.dev.yml up -d 2>/dev/null -exit_code=$? -if [[ $exit_code -ne 0 ]]; then - echo "error{${exit_code}}" -else - echo "ok" -fi diff --git a/bin/zsh/get_local_ip.zsh b/bin/zsh/get_local_ip.zsh deleted file mode 100644 index ba046d4..0000000 --- a/bin/zsh/get_local_ip.zsh +++ /dev/null @@ -1,4 +0,0 @@ -#!/bin/zsh - -# @see https://www.linuxtrainingacademy.com/determine-public-ip-address-command-line-curl/ -echo "$(ifconfig | sed -En 's/127.0.0.1//;s/.*inet (addr:)?(([0-9]*\.){3}[0-9]*).*/\2/p')" diff --git a/docker-compose.dev.yml b/docker-compose.dev.yml index 54e9add..82b7d9c 100644 --- a/docker-compose.dev.yml +++ b/docker-compose.dev.yml @@ -5,7 +5,8 @@ services: # TODO: ruuuby server - service_nginx: + service_nginx_dev: + container_name: "service_nginx_dev" build: context: ./services/nginx dockerfile: ./Dockerfile @@ -19,19 +20,18 @@ services: - 1337:1337 - 8080:8080 - 15672:15672 - - 80:80 + - 13337:13337 depends_on: - - service_postgres - - service_pgadmin - - service_js - - service_rabbitmq + - service_postgresql_dev + - service_pgadmin_dev + - service_js_dev + - service_rabbitmq_dev - #image: 'rabbitmq:3-management' - service_rabbitmq: + service_rabbitmq_dev: + container_name: "service_rabbitmq_dev" build: context: ./services/rabbitmq dockerfile: ./Dockerfile - #target: build_env_dev environment: RABBIT_ERLANG_COOKIE: 'secret string' RABBIT_NODENAME: 'service_rabbitmq' @@ -39,10 +39,11 @@ services: - 5672:5672 volumes: - 'vol_rabbitmq_dev:/data' - - './services/rabbitmq/rabbitmq.config:/etc/rabbitmq/rabbitmq.config' - - './services/rabbitmq/definitions.json:/etc/rabbitmq/definitions.json' + - './services/rabbitmq/dev/rabbitmq.config:/etc/rabbitmq/rabbitmq.config' + - './services/rabbitmq/dev/definitions.json:/etc/rabbitmq/definitions.json' - service_js: + service_js_dev: + container_name: "service_js_dev" build: context: ./services/web_assets dockerfile: ./Dockerfile @@ -53,38 +54,40 @@ services: SERVICE_PORT: '8080' SERVICE_HOST: 'http://localhost' - service_postgres: - image: 'amd64/postgres:13-alpine' + service_postgresql_dev: + container_name: "service_postgresql_dev" + build: + context: ./services/ruuuby_db + dockerfile: ./Dockerfile command: postgres -c 'max_connections=10' restart: always tty: false environment: - SERVICE_NAME: 'service_postgres' - BUILD_ENV: 'dev' SERVICE_ENV: 'dev' - SERVICE_OS: 'alpine' - SERVICE_OS_VERSION: '3.12.0' - POSTGRES_DB: 'mydb' POSTGRES_USER: 'myuser' POSTGRES_PASSWORD: 'mypassword' + POSTGRES_DB: 'env_dev' ports: - 5432:5432 volumes: - 'vol_db_dev/:/var/lib/postgresql/data/' + - './services/ruuuby_db/init.sql:/docker-entrypoint-initdb.d/init.sql' - service_pgadmin: - image: 'dpage/pgadmin4' + service_pgadmin_dev: + container_name: "service_pgadmin_dev" + build: + context: ./services/pgadmin + dockerfile: ./Dockerfile tty: false environment: - SERVICE_NAME: 'service_pgadmin' BUILD_ENV: 'dev' SERVICE_ENV: 'dev' - SERVICE_OS: 'alpine' - SERVICE_OS_VERSION: '3.9.4' PGADMIN_DEFAULT_EMAIL: 'pgadmin4@pgadmin.org' PGADMIN_DEFAULT_PASSWORD: 'admin' - PGADMIN_ADMIN_PORT: '1337' + PGADMIN_ADMIN_PORT: '13337' PGADMIN_LISTEN_ADDRESS: '0.0.0.0' + PGADMIN_LISTEN_PORT: '13337' + GUNICORN_THREADS: '15' volumes: - 'vol_pgadmin_dev/:/var/lib/pgadmin/' diff --git a/docker-compose.prod.yml b/docker-compose.prod.yml index cf41a0e..734c993 100644 --- a/docker-compose.prod.yml +++ b/docker-compose.prod.yml @@ -1,4 +1,3 @@ -# {'Compose file format': '3.8', 'Docker Engine release': '19.03.13'}; utilized API-Version: `1.40` version: '3.8' services: @@ -14,12 +13,12 @@ services: volumes: - 'vol_nginx_prod:/v' ports: - - 80:80 - - 443:443 - - 1337:1337 - - 8080:8080 + - 1339:1339 + - 8082:8082 + - 15674:15674 + - 13339:13339 depends_on: - - service_postgres + - service_postgresql - service_pgadmin - service_js - service_rabbitmq @@ -28,52 +27,58 @@ services: build: context: ./services/rabbitmq dockerfile: ./Dockerfile - #target: build_env_prod environment: RABBIT_ERLANG_COOKIE: 'secret string' RABBIT_NODENAME: 'service_rabbitmq' ports: - - 5672:5672 + - 5674:5674 volumes: - 'vol_rabbitmq_prod:/data' - - './services/rabbitmq/rabbitmq.config:/etc/rabbitmq/rabbitmq.config' - - './services/rabbitmq/definitions.json:/etc/rabbitmq/definitions.json' + - './services/rabbitmq/prod/rabbitmq.config:/etc/rabbitmq/rabbitmq.config' + - './services/rabbitmq/prod/definitions.json:/etc/rabbitmq/definitions.json' service_js: build: context: ./services/web_assets dockerfile: ./Dockerfile target: build_env_prod + tty: false + environment: + SERVICE_ENV: 'prod' + SERVICE_PORT: '8082' + SERVICE_HOST: 'http://localhost' - service_postgres: - image: 'amd64/postgres:13-alpine' + service_postgresql: + container_name: "service_postgresql" + build: + context: ./services/ruuuby_db + dockerfile: ./Dockerfile + command: postgres -c 'max_connections=10' restart: always tty: false environment: - SERVICE_NAME: 'service_postgres' - BUILD_ENV: 'prod' SERVICE_ENV: 'prod' - SERVICE_OS: 'alpine' - SERVICE_OS_VERSION: '3.12.0' - POSTGRES_DB: 'mydb' + POSTGRES_DB: 'env_prod' POSTGRES_USER: 'myuser' POSTGRES_PASSWORD: 'mypassword' volumes: - "vol_dv_prod/:/var/lib/postgresql/data/" service_pgadmin: - image: 'dpage/pgadmin4' + container_name: "service_pgadmin" + build: + context: ./services/pgadmin + dockerfile: ./Dockerfile tty: false environment: - SERVICE_NAME: 'service_pgadmin' BUILD_ENV: 'prod' SERVICE_ENV: 'prod' - SERVICE_OS: 'alpine' - SERVICE_OS_VERSION: '3.9.4' PGADMIN_DEFAULT_EMAIL: 'pgadmin4@pgadmin.org' PGADMIN_DEFAULT_PASSWORD: 'admin' - PGADMIN_ADMIN_PORT: '1337' + PGADMIN_ADMIN_PORT: '13339' PGADMIN_LISTEN_ADDRESS: '0.0.0.0' + PGADMIN_LISTEN_PORT: '13339' + GUNICORN_THREADS: '30' volumes: - 'vol_pgadmin_prod/:/var/lib/pgadmin/' diff --git a/docker-compose.test.yml b/docker-compose.test.yml index 17163e6..31a93de 100644 --- a/docker-compose.test.yml +++ b/docker-compose.test.yml @@ -1,11 +1,9 @@ -# {'Compose file format': '3.8', 'Docker Engine release': '19.03.13'}; utilized API-Version: `1.40` version: '3.8' services: - # TODO: ruuuby server - - service_nginx: + service_nginx_test: + container_name: "service_nginx_test" build: context: ./services/nginx dockerfile: ./Dockerfile @@ -16,18 +14,18 @@ services: volumes: - 'vol_nginx_test:/v' ports: - - 1337:1337 - - 8080:8080 - - 15672:15672 - - 80:80 + - 1338:1338 + - 8081:8081 + - 15673:15673 + - 13338:13338 depends_on: - - service_postgres - - service_pgadmin - - service_js - - service_rabbitmq + - service_postgresql_test + - service_pgadmin_test + - service_js_test + - service_rabbitmq_test - #image: 'rabbitmq:3-management' - service_rabbitmq: + service_rabbitmq_test: + container_name: "service_rabbitmq_test" build: context: ./services/rabbitmq dockerfile: ./Dockerfile @@ -36,13 +34,14 @@ services: RABBIT_ERLANG_COOKIE: 'secret string' RABBIT_NODENAME: 'service_rabbitmq' ports: - - 5672:5672 + - 5673:5673 volumes: - 'vol_rabbitmq_test:/data' - - './services/rabbitmq/rabbitmq.config:/etc/rabbitmq/rabbitmq.config' - - './services/rabbitmq/definitions.json:/etc/rabbitmq/definitions.json' + - './services/rabbitmq/test/rabbitmq.config:/etc/rabbitmq/rabbitmq.config' + - './services/rabbitmq/test/definitions.json:/etc/rabbitmq/definitions.json' - service_js: + service_js_test: + container_name: "service_js_test" build: context: ./services/web_assets dockerfile: ./Dockerfile @@ -50,41 +49,43 @@ services: tty: false environment: SERVICE_ENV: 'test' - SERVICE_PORT: '8080' + SERVICE_PORT: '8081' SERVICE_HOST: 'http://localhost' - service_postgres: - image: 'amd64/postgres:13-alpine' + service_postgresql_test: + container_name: "service_postgresql_test" + build: + context: ./services/ruuuby_db + dockerfile: ./Dockerfile command: postgres -c 'max_connections=10' restart: always tty: false environment: - SERVICE_NAME: 'service_postgres' - BUILD_ENV: 'test' SERVICE_ENV: 'test' - SERVICE_OS: 'alpine' - SERVICE_OS_VERSION: '3.12.0' - POSTGRES_DB: 'env_test' POSTGRES_USER: 'myuser' POSTGRES_PASSWORD: 'mypassword' - ports: - - 5432:5432 + POSTGRES_DB: 'env_test' + # ports: + # - 5433:5433 volumes: - 'vol_db_test/:/var/lib/postgresql/data/' + - './services/ruuuby_db/init.sql:/docker-entrypoint-initdb.d/init.sql' - service_pgadmin: - image: 'dpage/pgadmin4' + service_pgadmin_test: + container_name: "service_pgadmin_test" + build: + context: ./services/pgadmin + dockerfile: ./Dockerfile tty: false environment: - SERVICE_NAME: 'service_pgadmin' BUILD_ENV: 'test' SERVICE_ENV: 'test' - SERVICE_OS: 'alpine' - SERVICE_OS_VERSION: '3.9.4' PGADMIN_DEFAULT_EMAIL: 'pgadmin4@pgadmin.org' PGADMIN_DEFAULT_PASSWORD: 'admin' - PGADMIN_ADMIN_PORT: '1337' + PGADMIN_ADMIN_PORT: '13338' PGADMIN_LISTEN_ADDRESS: '0.0.0.0' + PGADMIN_LISTEN_PORT: '13338' + GUNICORN_THREADS: '20' volumes: - 'vol_pgadmin_test/:/var/lib/pgadmin/' diff --git a/ext/ruby_class_mods/c3_macro_utilities.h b/ext/ruby_class_mods/c3_macro_utilities.h index 2a6c19d..2c913c1 100644 --- a/ext/ruby_class_mods/c3_macro_utilities.h +++ b/ext/ruby_class_mods/c3_macro_utilities.h @@ -75,11 +75,6 @@ ________________________________________________________________________________ ensure_loaded_math(space/discrete/symbolic_numbers_space)\ } -#define ensure_all_loaded_for_math_expressions(){\ - ensure_loaded_math(expr/seq/sequence)\ - ensure_loaded_math(expr/seq/recursive)\ -} - #define ensure_all_loaded_for_tropical_algebra(){\ ensure_loaded_math(algebra/tropical/tropical)\ ensure_loaded_math(algebra/tropical/context_numeric)\ @@ -87,10 +82,6 @@ ________________________________________________________________________________ } #define ensure_all_loaded_for_geometry(){\ - ensure_loaded_math(geometry/shape/shape)\ - ensure_loaded_math(geometry/shape/plane_figure)\ - ensure_loaded_math(geometry/shape/quadrilateral)\ - ensure_loaded_math(geometry/shape/circle)\ ensure_loaded_math(geometry/theta_angle)\ ensure_loaded_math(geometry/trig)\ } diff --git a/ext/ruby_class_mods/ruby_class_mods.c b/ext/ruby_class_mods/ruby_class_mods.c index dea258e..d926f74 100644 --- a/ext/ruby_class_mods/ruby_class_mods.c +++ b/ext/ruby_class_mods/ruby_class_mods.c @@ -351,10 +351,6 @@ static void startup_step4_load_needed_ruuuby_files(void) { ensure_loaded_enumerable(ary) ensure_loaded_enumerable(hsh) // must be after{ary} - // TODO: REMOVE FROM RUNTIME, ONLY NEEDED FOR TESTING CODE - ensure_loaded_module(gem) - ensure_loaded_module(bundler) - ensure_all_loaded_for_nums() ensure_loaded_enumerable(set) @@ -375,7 +371,7 @@ static void startup_step4_load_needed_ruuuby_files(void) { ensure_all_loaded_for_math_space() - ensure_all_loaded_for_math_expressions() + ensure_loaded_math(expr/sequence) #ifdef RUUUBY_F06_B08 ensure_loaded_nums(matrix) #endif @@ -419,7 +415,6 @@ static void startup_step4_load_needed_ruuuby_files(void) { #ifdef RUUUBY_F22_B07 ensure_loaded_ruuuby(ruuuby/engine/f22/b07) #endif - ensure_loaded_math(geometry/shape/triangle) #ifdef RUUUBY_F43 ensure_loaded_ruuuby(ruuuby/api/f43_api_iconv) diff --git a/help/architecture_notes.md b/help/architecture_notes.md deleted file mode 100644 index 06efd97..0000000 --- a/help/architecture_notes.md +++ /dev/null @@ -1,142 +0,0 @@ - -### ⚠️, file added early, wip - -| term | definition | notes | -| ---------------------- | --------------- | ----------- | -| `web stack` | the set of technologies composing a live web solution | typically composed of `operating system, database, web server, and scripting languages` | -| `LAMP stack` | `Linux`, `Apache`, `MySQL`, and `PHP`/`Perl`/`Python` | longer history thus more support, many reliable `CMS` engines | -| `LEMP stack` | `Linux`, `NGINX`, `MySQL`, and `PHP`/`Perl`/`Python` | | -| `LAPP stack` | `Linux`, `Apache`, `PostgreSQL`, and `PHP`/`Perl`/`Python` | | -| `LLMP stack` | `Linux`, `Lighttpd`, `MySQL`, and `PHP`/`Perl`/`Python` | | -| `MERN stack` | `MongoDB`, `ExpressJS`, `ReactJS`, `NodeJS` | allows single language{`JS`} for both front-end and back-end | -| `MEAN stack` | `MongoDB`, `ExpressJS`, `AngularJS`, `NodeJS` | same as above note | - -| term | definition | notes and/or source | -| -------------------------------------------------- | --------------- | ------------------- | -| `Disaster Recovery` (`DR`) | "set of policies, tools and procedures to enable the recovery or continuation of vital technology infrastructure and systems following a natural or human-induced disaster" | 0x3 | -| `Business Continuity Planning` (`BCP`) | "the process of creating systems of prevention and recovery to deal with potential threats to a company" | 0x4 | -| `IT Service Continuity` (`ITSC`) | "subset of business continuity planning and encompasses IT disaster recovery planning and wider IT resilience planning" | 0x3 | -| `Recovery Time Objective` (`RTO`) | "the targeted duration of time and a service level within which a business process must be restored after a disaster (or disruption) in order to avoid unacceptable consequences associated with a break in business continuity" | 0x3 | -| `Recovery Time Actual` (`RTA`) | "the critical metric for business continuity and disaster recovery" | 0x3 | -| `Recovery Point Objective` (`RPO`) | "the maximum targeted period in which data (`transacations`) might be lost from an IT service due to a major incident" | 0x3 | -| `Recovery Consistency Objective` (`RCO`) | "when more than one system crashes, recovery plans much balance the need for data consistency with other objectives, such as `RTO` and `RPO`"; `RCO = 1 - {(number of inconsistent entities) / (number of entities)} | 0x4 | -| `Business Continuity` | "the intended outcome of proper execution of Business continuity planning and Disaster recovery. It is the payoff for cost-effective buying of spare machines and servers, performing backups and bringing them off-site, assigning responsibility, performing drills, educating employees and being vigilant" | 0x4 | -| `work area recovery sites` (`WAR sites`) | relocation zone following a disaster | 0x5 | -| `cold sites` | "On occurring of an incident and if the operations can do with a little down time, alternative facilities are brought to and set up in the cold site to resume operations. A cold site is the least expensive type of backup site for an organization to operate. It does include backed up copies of data and information from the original location of the organization, nor does it include hardware already set up" | 0x5 | -| `warm sites` | "a compromise between `hot` and `cold`. These sites will have hardware and connectivity already established, though on a smaller scale than the original production site or even a hot site" | 0x5 | -| `hot sites` | "a duplicate of the original site of the organization, with full computer systems as well as near-complete backups of user data. Real time synchronization between the two sites may be used to completely mirror the data environment of the original site using wide area network links and specialized software" | 0x5 | -| `alternative sites` | "a site where people and the equipment that they need to work is relocated for a period of time until the normal production environment, whether reconstituted or replaced, is available" | 0x5 | -| `off-site data protection` (`vaulting`) | "the strategy of sending critical data out of the main location (off the main site) as part of a disaster recovery plan" | 0x6 | -| `business impact analysis` (`BIA`) | "differentiates critical (urgent) and non-critical (non-urgent) organization functions/activities. A function may be considered critical if dictated by law" | 0x4 | -| `maximum tolerable period of disruption` (`MTPoD`) | | 0x4 | -| `maximum tolerable downtime` (`MTD`) | | 0x4 | -| `maximum tolerable outage` (`MTO`) | | 0x4 | -| `maximum allowable outage` (`MAO`) | | 0x4 | -| `RPC framework` | the general "set of tools that enable the programmer to call a piece of code in a remote process, be it on a different machine or just another process on the same machine" | 0x8 | - -TODO: document relating data acts - * Federal Information Security Management Act of 2002 - * Health Insurance Portability and Accountability Act - * GAO Federal Information System Controls Audit Manual (FISCAM) - -| term | definition | notes | -| ---------------------- | --------------- | ----------- | -| `Node.js` | a "JavaScript runtime built on Chrome's V8 JavaScript engine" | | - -| dev type | key terms | more narrow terms | -| ----------- | --------- | --------- | -| front-end | `CSS`, `JS`, `SPA` (Single Page Application) | `LESS`, `SASS`, `GULP`, `Angular2`, `React`, `TypeScript` | -| back-end | `Python`, `NodeJS`, `PHP`, `GO` | `Django`, `ExpressJS`, `Design`, `Caching`, `Middleware` | -| database | `MySQL`, `SQLite`, `PostgreSQL`, `MongoDB` | `SQL`, `Clusters`, `Joins`, `Sharding` | -| dev-ops | `CI`, `CD`, `AWS` | `Nginx`, `Ansible`, `Lambda`, `SQS` | -| mobile apps | `hybrid apps`, `iOS`, `Andriod` | `React Native`, `Iconic` | - -### Docker Notes - -0x1) helped w/ switch from `ash` to `zsh` - - https://stackoverflow.com/questions/339483/how-can-i-remove-the-first-line-of-a-text-file-using-bash-sed-script - - https://unix.stackexchange.com/questions/99350/how-to-insert-text-before-the-first-line-of-a-file - -0x2) creating a multi-stage build - - https://docs.docker.com/develop/develop-images/multistage-build/ - -#### DevOps Notes - -TODO: * https://wiki.alpinelinux.org/wiki/Comparison_with_other_distros -TODO: `puppet`, `chef`, `ansible`, and the other hybrids out there -TODO: https://medium.com/@bhargavshah2011/hello-world-on-kubernetes-cluster-6bec6f4b1bfd - - > re-phrase these, don't just copy paste - -https://www.upguard.com/blog/ansible-vs-chef -" * DevOps tools tend to fall into two categories: - 1. Orchestration: deals with provisioning servers and other infrastructure including databases across clusters while handling over responsibility for managing the software running on the instances to configuration management tools - 2. Configuration management: focus on managing the software on infrastructure nodes, including installation and upgrades on servers already in existence -" - -### Ansible - -| term | definition | source | -| ---- | --------- | ------ | -| ansible server | machine w/ Ansible which runs all tasks and playbooks | 0x1 | -| module | one or multiple commands to execute on client-side | 0x1 | -| task | "section that consists of a single procedure to be completed" | 0x1 | -| role | "a way of organizing tasks and related files to be later called in a playbook | 0x1 | -| fact | "information fetched from the client system from the global variables with the gather-facts operation" | 0x1 | -| inventory | "file containing data about the ansible client servers" | 0x1 | -| play | "execution of a playbook" | 0x1 | -| handler | "task which is called only if a notifier is present" | 0x1 | -| notifier | "section attributed to a task which calls a handler if the output is changed" | 0x1 | -| tag | "name set to a task which can be used later on to issue just that specific task or group of tasks" | 0x1 | - -### RPA (Robotic Process Automation) Notes - -> any quotes are taken from resource{`0x0`} - - * term coined in the 1950s - * `robotic`: "entities that mimic human actions" - * `process`: "sequence of steps that lead to meaningful activity" - * `automation`: "any process that is done by a robot without human intervention" - * `RPA (Robotic Process Automation`: "mimicking human actions to perform a sequence of steps, leading to a meaningful activity, without any human intervention" - -### TODOs - -* https://www.howtogeek.com/117435/htg-explains-the-linux-directory-structure-explained/ -* https://quality-one.com/fmea -* https://en.wikipedia.org/wiki/Failure_mode_and_effects_analysis -* https://www.geeksforgeeks.org/introduction-to-net-framework/ -* TODO: https://blog.scottlogic.com/2020/01/13/selenium-vs-puppeteer.html -* TODO: https://github.com/puppeteer/puppeteer/blob/main/docs/api.md#puppeteer-vs-puppeteer-core -* https://github.com/puppeteer/puppeteer -* https://blog.bitsrc.io/top-javascript-testing-frameworks-in-demand-for-2019-90c76e7777e9 -* https://www.lambdatest.com/blog/top-javascript-automation-testing-framework/ -* https://www.chaijs.com/ -* https://try-puppeteer.appspot.com/ - -#### resources - -| reference_id | url | -| ------------ | ----- | -| | https://www.suffescom.com/blog/lamp-vs-mern-introduction-and-web-stack-comparison/ | -| | https://www.chapter247.com/blog/choosing-the-right-stack-for-your-next-web-project-fullstack-vs-mean-stack-vs-mern-stack/ | -| | https://medium.com/better-programming/mean-stack-vs-mern-stack-whats-the-difference-d29bad43243d | -| | https://www.upguard.com/blog/salt-vs-chef | -| 0x0) | https://www.edureka.co/blog/what-is-robotic-process-automation/ | -| 0x1) | https://www.guru99.com/ansible-tutorial.html | -| 0x2) | https://www.intervision.com/rpo-rto-pto-draas-disaster-recovery-explained | -| 0x3) | https://en.wikipedia.org/wiki/Disaster_recovery | -| 0x4) | https://en.wikipedia.org/wiki/Business_continuity_planning | -| 0x5) | https://en.wikipedia.org/wiki/Backup_site | -| 0x6) | https://en.wikipedia.org/wiki/Off-site_data_protection | -| 0x7) | https://en.wikipedia.org/wiki/Failure_mode_and_effects_analysis | -| 0x8) | https://stackoverflow.com/questions/20653240/what-is-rpc-framework-and-apache-thrift# | - -### TODOs (short descriptions)) - -| term | definition | notes and/or source | -| -------------------------------------------------- | ----- | --- | -| `SDET` | | | -| `Inversion of Control` (`IoC`) | | | -| `Aspect Oriented Programming` (`AOP`) | | | -| `Model View Controller` (`MVC`) | | | -| `Data Access Object` (`DAO`) | | | diff --git a/help/db_notes.md b/help/db_notes.md deleted file mode 100644 index e2e2728..0000000 --- a/help/db_notes.md +++ /dev/null @@ -1,149 +0,0 @@ - -### ⚠️, file added early, wip - -| term | definition | note | -| ------------------------ | --------- | ----- | -| `database` | container for storing organized data, usually a set of files | the layer between the `raw data` and the `DBMS` | -| `table` | structured list of data w/ each heaving a specific data type | must be unique, composing of: database name combined w/ table name, some implementations include the db owner as a starting identifier as well | -| `DBMS` | the software responsible for creating and manipulating the database | -| `schema` | information describing the metadata of the database and tables (layout, properties, etc) | -| `column` | single table field | the level of `granularity` is an important design decision, w/ `atomicity` often preferred | -| `field` | synonymous to `column` but also `calculated fields` which is just a logical grouping of information units composed of multiple `atomic fields` | -| `row` | record in table | | -| `data types` | - | careful on datatype naming conventions, many `DBMS` implementations can utilize the same datatype name but have different rules applied | -| `primary key` | one or more columns whose value(s) can be used to uniquely identify every single creatable row in the table | critical for avoiding lots of operational expensive for operations such as `updating` and `deleting` | -| `transactional database` | a `DBMS` offering `ACID properties` for set of operation within a `begin-commit` scope | -| `wildcards` | "special characters used to match parts of a value" | -| `predicates` | "when is an operator not an operator? When it is a `predicate`. Technically, `LIKE` is a predicate, not an operator. The end result is the same, just be aware of this term" | -| `aggregate functions` | "functions that operate on a set of rows to calculate and return a single value" | -| `subqueries` | queries that are embedded into other queries | in an `SQL statement`, the `inner-most subqueries` are always calculated first traversing outward | - -| useful resource | url | -| --------------- | --- | -| `COLLATE` | https://stackoverflow.com/questions/37984264/purpose-of-collate-in-postgres | -| `COLLATE` | https://dba.stackexchange.com/questions/94887/what-is-the-impact-of-lc-ctype-on-a-postgresql-database | - -#### `ACID properties`: - -| term | definition | -| ------------- | --------- | -| `Atomicity` | `indivisible` such that the operation(s) either all occurs or not at all | -| `Consistency` | ensurance that a transaction only moves the `DB` from exactly one `state` to another | -| `Isolation` | ensurance that `concurrent transacations` performed `iteratively` both result in same ending `DB state` | -| `Durability` | ensurance that a transaction gets committed, even w/ a system failure | - - * `database transaction`: - * single `unit-of-work` that applies a change to a Database w/ the guarantee of recoverability in the case of any sudden system failure - * provides `isolation` between the `DB` and various `DBMS` to prevent erroneous states - - * primary key conditions: - * "no two rows can have the same primary key value" - * "every row must have a primary key value" (non-NULL) - * "Values in primary key columns should never be modified or updated" - * "should not be re-used" (a deleted row should not have it's primary key assigned for a newly created row) - - * SQL: Structured Query Language - * `Standard SQL` is governed by the `ANSI standards committee` (and thus called `ANSI SQL`) - * `DBMS` specific keywords will be very `vendor` specific - * multiple statements are separated w/ the character{`;`} - -## Query Tips & Notes - - * `SQL` processes the operator `AND` before the operator `OR` - * reminder: use parenthesis to ensure needed groupings of operations - * use the `IN` operator instead of longer concatenations of `OR` statements - * unlike other operators, the `NOT` keyword can be used before the column to filter on, not just after it - -### General Performance Tips - -| scenario | resolution | -| ----------------------------------------------------------------------- | --------------------------------------------------------------------------------- | -| generally `search operators` will perform better than using `wildcards` | if `query readability/complexity` is not significantly impacted, avoid `wildcards` | - -### Example Queries - -> tested with `postgresql` - -| scenario | query | -| --------------------- | ------------------- | -| get current timestamp | `SELECT Now();` | -| get current version | `SELECT version();` | -| document later | `COPY public.the_table(the_column_a, the_column_b) FROM '/tmp/data.csv' DELIMITER ',' CSV HEADER;` | - -#### Math Functions Available - -> note, many of the following functions will ignore NULL values all-together - - * `ABS()` - * `COS()` - * `EXP()` - * `PI()` - * `SIN()` - * `SQRT()` - * `TAN()` - * `AVG()` - * `COUNT()` - * `MAX()` - * `MIN()` - * `SUM()` - -## Wildcards (in context on search strings) - - | wildcard | meaning | notes | - | -------- | ------------------------------------------------------------------------------------ | ----------------------------------------------------------------------- | - | `&` | "match any number of occurrences of any character" | not even the search string of just{`%`} will match against a `NULL row` | - | `_` | match any single character | | - | `[]` | at position of brackets, match any character provided by the set within the brackets | this wildcard can be negated, ex: `SELECT name FROM names WHERE name LIKE '[^AB]%'`; # this query will return all names longer than one character, that do not start w/ `A` or `B` | - -## `GROUP BY` - - * "if you have nested groups in your `GROUP BY` clause, data is summarized at the last specified group. In other words, all the columns specified are evaluated together when grouping is established (so you won't get data back for each individual column level" - * "every column listed in `GROUP BY` must be a retrieved column or a valid expression (but not an aggregate function)" - * must be after any `WHERE` and before any `ORDER BY` - * "`WHERE` filters before data is grouped, and `HAVING` filters after data is grouped" - * lots of variability by `DBMS` - -### Reserved Words - -> specific DBMS flavors will have their own variation of the following list, regardless, for general compatibility sake it's better to avoid naming anything that same as the following keywords - - * ABORT, ABSOLUTE, ACTION, ADD, AFTER, ALL, ALLOCATE, ALTER, ANALYZE, AND, ANY, ARE, AS, ASC, ASCENDING, ASSERTION, AT, AUTHORIZATION, AUTO, AUTO-INCREMENT, AUTOINC, AVG - * BACKUP, BEFORE, BEGIN, BETWEEN, BIGINT, BINARY, BIT, BLOB, BOOLEAN, BOTH, BREAK, BROWSE, BULK, BY, BYTES - * CACHE, CALL, CASCADE, CASCADED, CASE, CAST, CATALOG, CHANGE, CHAR, CHARACTER, CHARACTER_LENGTH, CHECK, CHECKPOINT, CLOSE, CLUSTER, CLUSTERED, COALESCE, COLLATE, COLUMN, COLUMNS, COMMENT, COMMIT, COMMITTED, COMPUTE, COMPUTED, CONDITIONAL, CONFIRM, CONNECT, CONNECTION, CONSTRAINT, CONSTRAINTS, CONTAINING, CONTAINS, CONTAINSTABLE, CONTINUE, CONTROLROW, CONVERT, COPY, COUNT, CREATE, CROSS, CSTRING, CUBE, CURRENT, CURRENT_DATE, CURRENT_TIME, CURRENT_TIMESTAMP, CURRENT_USER, CURSOR - * DATABASE, DATABASES, DATE, DATETIME, DAY, DBCC, DEALLOCATE, DEBUG, DEC, DECIMAL, DECLARE, DEFAULT, DELETE, DENT, DESC, DESCENDING, DESCRIBE, DISCONNECT, DISK, DISTINCT, DISTRIBUTED, DIV, DO, DOMAIN, DOUBLE, DROP, DUMMY, DUMP - * ELSE, ELSEIF, ENCLOSED, END, ERRLVL, ERROREXIT, ESCAPE, ESCAPED, EXCEPT, EXCEPTION, EXEC, EXECUTE, EXISTS, EXIT, EXPLAIN, EXTEND, EXTERNAL, EXTRACT - * FALSE, FETCH, FIELD, FIELDS, FFILE, FILLFACTOR, FILTER< FLOAT, FLOPPY, FOR, FORCE, FOREIGN, FOUND, FREETEXT, FREETEXTTABLE, FROM, FULL, FUNCTION - * GENERATOR, GET, GLOBAL, GO, GOTO, GRANT, GROUP - * HAVING, HOLDLOCK, HOUR - * IDENTITY, IF, IN, INACTIVE, INDEX, INDICATOR, INFILE, INNER, INOUT, INPUT, INSENSITIVE, INSERT, INT, INTEGER, INTERSECT, INTERVAL, INTO, IS, ISOLATION - * JOIN - * KEY, KILL - * LANGUAGE, LAST LEADING, LEFT, LENGTH, LEVEL, LIKE, LIMIT, LINENO, LINES, LISTEN, LOAD, LOCAL, LOCK, LOGFILE, LONG, LOWER - * MANUAL, MATCH, MAX, MERGE, MESSAGE, MIN, MINUTE, MIRROREXIT, MODULE, MONEY, MONTH, MOVE - * NAMES, NATIONAL, NATURAL, NCHAR, NEXT, NEW, NO, NOCHECK, NONCLUSTERED, NONE, NOT, NULL, NULLIF, NUMERIC - * OF, OFF, OFFSET, OFFSETS, ON, ONCE, ONLY, OPEN, OPTION, OR, ORDER, OUTER, OUTPUT, OVER, OVERFLOW, OVERLAPS - * PAD, PAGE, PAGES, PARAMETER, PARTIAL, PASSWORD< PERCENT, PERM, PERMANENT, PIPE, PLAN, POSITION, PRECISION, PREPARE, PRIMARY, PRINT, PRIOR, PRIVILEGES, PROC, PROCEDURE, PROCESSEXIT, PROTECTED, PUBLIC, PURGE - * RAISEERROR, READ, READTEXT, REAL, REFERENCES, REGEXP, RELATIVE, RENAME, REPEAT, REPLACE, REPLICATION, REQUIRE, RESERV, RESERVING, RESET, RESTORE, RESTRICT, RETAIN, RETURN, RETURNS, REVOKE, RIGHT, ROLLBACK, ROLLUP, ROWCOUNT, RULE - * SAVE, SAVEPOINT, SCHEMA, SECOND, SECTION, SEGMENT, SELECT, SENSITIVE, SEPARATOR, SEQUENCE, SESSION_USER, SET, SETUSER, SHADOW, SHARED< SHOW, SHUTDOWN, SINGULAR, SIZE, SMALLINT, SNAPSHOT, SOME, SORT, SPACE, SQL, SQLCODE, SQLERROR, STABILITY, STARTING, STARTS, STATISTICS, SUBSTRING, SUM, SUSPEND - * TABLE, TABLES, TAPE, TEMP, TEMPORARY, TEXT, TEXTSIZE, THEN, TIME, TIMESTAMP, TO, TOP, TRAILING, TRAN, TRANSACTION, TRANSLATE, TRIGGER, TRIM, TRUE, TRUNCATE - * UNCOMMITTED, UNION, UNIQUE, UNTIL, UPDATE, UPDATETEXT, UPPER, USAGE, USE, USER, USING - * VALUE, VALUES, VARCHAR, VARIABLE, VARYING, VERBOSE, VIEW, VOLUME - * WAIT, WAITFOR, WHEN, WHERE, WHILE, WITH, WORK, WRITE, WRITETEXT - * XOR - * YEAR - * ZONE - -### misc notes to organize - - * number of decimals displayed w/ numbers is `DBMS` specific - * Databases are optimized to perform filtering quickly and efficiently, shifting too much of this work onto the client application will cause serious long-term scaling issues - * generally the operators `!=` and `<>` can be easily interchanged, but this is still `DBMS` specific - -# TODOs (short description) - -| term | definition | note | -| ------------------------ | --------- | ----- | -| all the normalization forms!!!!!! | -| `DDL``Database Definition Language` | -| `DML``Data Manipulation Language` | -| `DCL``Data Control Language` | diff --git a/help/extensions/c/c_extension.md b/help/extensions/c/c_extension.md deleted file mode 100644 index d2d8649..0000000 --- a/help/extensions/c/c_extension.md +++ /dev/null @@ -1,111 +0,0 @@ - -// TODO: look into: https://developer.apple.com/library/archive/documentation/Cocoa/Conceptual/RubyPythonCocoa/Articles/GenerateFrameworkMetadata.html#/ - -## Notes - - * 🆔 of any positive FIXNUM: `(2 * value) + 1` - * 🆔 of any negative FIXNUM: `(2 * value) - 1` - * the c-type `ID` is equivalent to `unsigned long` - -### extension code guidelines - -| guideline | -| --- | -| if including `include/ruby/ruby.h`, don't use the `..._PTR` macros (ex: `RARRAY_PTR`, instead use function `rb_ary_aref`) | -| avoid `rb_eval_string` when possible, it's quite slow `ಠ╭╮ಠ` (relative to most alternatives) | -| use `ALLOC_N` over `malloc`; ex: `(double *) malloc(sizeof(double) * n) == ALLOC_N(double, n)` | - -| resources | -| --- | -| https://docs.ruby-lang.org/en/2.7.0/extension_rdoc.html#label-Ruby+Language+Core | -| https://www.ruby-forum.com/t/rb-gc-register-address-or-rb-gc-mark/219828/13 | -| https://bugs.ruby-lang.org/issues/15626 | -| https://ruby-doc.com/docs/ProgrammingRuby/html/ext_ruby.html | -| https://bugs.ruby-lang.org/projects/ruby-master/wiki/RGenGC | -| https://github.com/ruby/ruby/blob/v2_7_0/gc.c#L258 | - -## Ruby Methods - -``` - -# TODO: finish documenting this (look for option to create stackless-func-call) -table from: -https://we4tech.wordpress.com/2013/05/09/different-type-methods-in-ruby/ -``` - -| flag | use-case | -| --- | --- | -| VM_METHOD_TYPE_ISEQ | for "any ruby method which is referenced from source code" | -| VM_METHOD_TYPE_CFUNC | "method which is created on behalf of native C function | -| VM_METHOD_TYPE_ATTRSET | methods "declaring attribute setter using 'attr_writer'" | -| VM_METHOD_TYPE_IVAR | methods "declaring attribute getter using 'attr_reader'" | -| VM_METHOD_TYPE_BMETHOD | methods "declaring method using 'define_method' and passing proc for method body" | -| VM_METHOD_TYPE_ZSUPER | methods "explicitly declaring method scope (private, public, or protected) from the class hierarchy, ruby will redeclare method in the child class and mark that one with this flag" | -| VM_METHOD_TYPE_UNDEF | methods "undef using (undef_method or undef) will be marked with this flag (still method exists but won't respond to) | -| VM_METHOD_TYPE_NOTIMPLEMENTED | "if not implemented c function (which actually refers to rb_f_notimplement function)" | -| VM_METHOD_TYPE_OPTIMIZED | "this flag is used for separating few sets of methods from rest; so that VM can handle them better and optimized way", ex: Kernel#send, Proc#call, etc | -| VM_METHOD_TYPE_MISSING | "When method_missing is declared and - -### Warnings -``` -// see: https://croisant.net/ruby-c-extension-cheat-sheet/ -rb_warn -rb_warning (only print warning if $VERBOSE is true) -``` - -### MacOS C Support - -// TODO: look into: https://github.com/jrom/rubyosa - -``` - -// to fix missing header: sys/statfs.h - -brew cask install osxfuse -// (kinda, header still missing but adding the following 2 works) -#include -#include - -* http://macappstore.org/osxfuse/ -* https://developer.apple.com/library/archive/documentation/System/Conceptual/ManPages_iPhoneOS/man2/statfs.2.html - -``` - -### Source Code Snippets - -``` -//rb_enc_set_default_external(rb_enc_from_encoding(rb_utf8_encoding())); -//rb_enc_set_default_internal(rb_enc_from_encoding(rb_utf8_encoding())); - -/* locale insensitive functions */ - -static inline int rb_isascii(int c){ return '\0' <= c && c <= '\x7f'; } -static inline int rb_isupper(int c){ return 'A' <= c && c <= 'Z'; } -static inline int rb_islower(int c){ return 'a' <= c && c <= 'z'; } -static inline int rb_isalpha(int c){ return rb_isupper(c) || rb_islower(c); } -static inline int rb_isdigit(int c){ return '0' <= c && c <= '9'; } -static inline int rb_isalnum(int c){ return rb_isalpha(c) || rb_isdigit(c); } -static inline int rb_isxdigit(int c){ return rb_isdigit(c) || ('A' <= c && c <= 'F') || ('a' <= c && c <= 'f'); } -static inline int rb_isblank(int c){ return c == ' ' || c == '\t'; } -static inline int rb_isspace(int c){ return c == ' ' || ('\t' <= c && c <= '\r'); } -static inline int rb_iscntrl(int c){ return ('\0' <= c && c < ' ') || c == '\x7f'; } -static inline int rb_isprint(int c){ return ' ' <= c && c <= '\x7e'; } -static inline int rb_ispunct(int c){ return !rb_isalnum(c); } -static inline int rb_isgraph(int c){ return '!' <= c && c <= '\x7e'; } -static inline int rb_tolower(int c) { return rb_isupper(c) ? (c|0x20) : c; } -static inline int rb_toupper(int c) { return rb_islower(c) ? (c&0x5f) : c; } - -``` - -### Misc - - * https://stackoverflow.com/questions/10192903/time-in-milliseconds-in-c - -``` - -export LC_ALL=en_US.UTF-8 -export LANG=en_US.UTF-8 - -# verifiying: following cmd should output {UTF-8} -locale charmap -``` diff --git a/help/extensions/c/gcc.md b/help/extensions/c/gcc.md deleted file mode 100644 index fb0299d..0000000 --- a/help/extensions/c/gcc.md +++ /dev/null @@ -1,47 +0,0 @@ - -### GCC flags - -* https://gcc.gnu.org/onlinedocs/gcc/Invoking-GCC.html#Invoking-GCC -* https://stackoverflow.com/questions/7880812/complete-list-of-clang-flags -* https://docs.freebsd.org/info/gcc/gcc.info.Preprocessor_Options.html - ---- - -| gcc-flag case | result | -| ---: | :--- | -| `-fpic` vs `-fPIC` | `-fPIC` for `x86-64` | - ---- - -`fix later w/ a build-process w/ Docker and such` - -``` -# Wnested-externs -# Wabi -# faggressive-loop-optimizations -# fira-loop-pressure -# fearly-inlining -# fvariable-expansion-in-unroller - -# "The compiler failed to generate an executable file. (RuntimeError) You have to install development tools first." -#$CFLAGS << ' -Wformat-overflow' -#$CFLAGS << ' -Wformat-truncation' -#$LDFLAGS << ' --gc-sections' -``` - -### GCC Build - - * https://www.gnu.org/software/gcc/mirrors.html - - -### misc - - * https://stackoverflow.com/questions/14737104/what-is-the-default-c-std-standard-version-for-the-current-gcc-especially-on-u - * https://developers.redhat.com/blog/2018/03/21/compiler-and-linker-flags-gcc/ - * https://stackoverflow.com/questions/10192903/time-in-milliseconds-in-c - * https://stackoverflow.com/questions/9450394/how-to-install-gcc-piece-by-piece-with-gmp-mpfr-mpc-elf-without-shared-libra - -``` -find /usr /opt -name "mpfr.h" - -``` diff --git a/help/extensions/c/open_cl.md b/help/extensions/c/open_cl.md deleted file mode 100644 index 6145e3a..0000000 --- a/help/extensions/c/open_cl.md +++ /dev/null @@ -1,19 +0,0 @@ - -## Resources: - - * https://www.khronos.org/registry/OpenCL/ - * http://www.aronaldg.org/webfiles/compecon/src/opencl/doc/OpenCL_Mac_OS_X.pdf - * https://support.apple.com/en-us/HT202823 - -### TODOs: - - * https://developer.apple.com/library/archive/samplecode/OpenCL_Hello_World_Example/Introduction/Intro.html#/ - * https://software.intel.com/content/www/us/en/develop/articles/opencl-drivers.html - * https://developer.apple.com/library/archive/documentation/Performance/Conceptual/OpenCL_MacProgGuide/XCodeHelloWorld/XCodeHelloWorld.html - -#### Misc Notes: - -| flag_type | flag_value | -| ---: | :--- | -| `ld` | `-L/System/Library/Frameworks/OpenCL.framework` | -| `ld` | `-framework OpenCL'` | diff --git a/help/extensions/c/open_mp.md b/help/extensions/c/open_mp.md deleted file mode 100644 index 1707e86..0000000 --- a/help/extensions/c/open_mp.md +++ /dev/null @@ -1,8 +0,0 @@ - -## Resources - - * https://www.mathworks.com/help/coder/ug/install-openmp-library-on-macos-platform.html - * https://releases.llvm.org/ - * https://clang.llvm.org/docs/OpenMPSupport.html - * https://iscinumpy.gitlab.io/post/omp-on-high-sierra/ - * https://en.wikipedia.org/wiki/OpenMP diff --git a/help/extensions/java/jruby.md b/help/extensions/java/jruby.md deleted file mode 100644 index 566bb7d..0000000 --- a/help/extensions/java/jruby.md +++ /dev/null @@ -1,32 +0,0 @@ - -## Extensions Notes - -#### public abstract class DynamicMethod extends java.lang.Object -``` -DynamicMethod represents a method handle in JRuby, to provide both entry points into AST and bytecode interpreters, but also to provide handles to JIT-compiled and hand-implemented Java methods. -All methods invokable from Ruby code are referenced by method handles, either directly or through delegation or callback mechanisms. -``` - -### Java Notes - -| for | reference | -| ---- | ------- | -| `Java` versions | https://en.wikipedia.org/wiki/Java_version_history | - -| term | def/notes | reference | -| ---- | ----- | -------- | -| `JDK` | Java Development Kit | https://en.wikipedia.org/wiki/Java_(software_platform) | -| `JRE` | Java Runtime Environment | ^ | -| `JVM` | Java Virtual Machine | ^ | - -| 3rd party compilers/interpreters | definition | reference | -| -------- | -------- | ------ | -| `BeanShell` | "lightweight scripting language for Java" | https://en.wikipedia.org/wiki/Java_(software_platform) | -| `Ceylon` | "an object-oriented, strongly statically typed programming language with an emphasis on immutability" | ^ | -| `Clojure` | "a modern, dynamic, and functional dialect of the List programming language on the Java platform" | ^ | -| `Gosu` | "a general-purpose Java Virtual Machine-based programming language released under the Apache License 2.0" | ^ | -| `Groovy` | "a fully Java interoperable, Java-syntax-compatible, static and dynamic language with features from `Python`, `Ruby`, `Perl`, and `Smalltalk`" | ^ | -| `JRuby` | "a Ruby interpreter" | ^ | -| `Jython` | "a Python interpreter" | ^ | -| `Kotlin` | "an industrial programming language for `JVM` with full Java interoperability" | ^ | -| `Scala` | "a multi-paradigm programming language with non-Jave compatible syntax designed as a 'better Java'" | ^ | diff --git a/help/math/automatic_differentiation.md b/help/math/automatic_differentiation.md deleted file mode 100644 index 049cc49..0000000 --- a/help/math/automatic_differentiation.md +++ /dev/null @@ -1,54 +0,0 @@ - - -# Automatic Differentiation - - * abstractions that enable you to write a function and efficiently apply the chain rule to it - * `Automatic Differentiation` is not: - * `Symbolic differentitation`: automatic manipulation of mathematical expressions to get derivatives - * `Numeric differentiation`: approximating derivatives by finite differences - - -#### Resources - -| resource | link | -| --- | --- | -| paper: `The Simple Essense of Automatic Differentation` | http://conal.net/papers/essence-of-ad/essence-of-ad-icfp.pdf | -| Conal Elliott | https://www.youtube.com/watch?v=ne99laPUxN4 | -| `PDF slides` of above resource | https://www.microsoft.com/en-us/research/uploads/prod/2018/07/The-Simple-Essence-of-Automatic-Differentiation-slides.pdf | - - -#### What's a derivative? - -`a` and `b` are vector spaces that share a common underlying field - -* `D :: (a → b) → (a → (a ⊸ b))` -* `lim(ε→0) of` - * `0 = ∥⨍(a+E)-(⨍a + D⨍aε)∥ / ∥ε∥` - -#### Composition - -Sequential: - * `(∘) :: (b → c) → (a → b) → (a → c)` - * `(g → ⨍)a = g(⨍a)` - * `chain rule`: `D(g ∘ ⨍)a = Dg(⨍a) ∘ D⨍a` - -Parallel: - * `( ▵ )::(a → c) → (a → d) → (a → cXd)` -- 'c cross-product d' - * `(⨍ ▵ g)a = (⨍a, ga)` - * `D(⨍ ▵ g)a = D⨍a ▵ Dga` - -#### Compositionality - * notice with the `chain rule`(`D(g∘⨍)a = Dg(⨍a)∘D⨍a`), this is `non-compositional` - * fixed by combining regular result with derivative: - * `ˆD :: (a → b) → (a → (bX(a ⊸ b)) )` - * `specification`: `ˆD⨍ = ⨍ ▵ D⨍` - - -### Theorem 1 (Compose/"Chain" rule) - - -# TODO-USE: symbol(∥) -# ∥-5∥ == 5 - - - diff --git a/help/math/diagrams.md b/help/math/diagrams.md deleted file mode 100644 index f4e66d0..0000000 --- a/help/math/diagrams.md +++ /dev/null @@ -1,15 +0,0 @@ - -### Diagrams - -| category | id | for | link | -| --- |--- | --- | --- | -| function | 0x0 | `sigmoid function` | https://upload.wikimedia.org/wikipedia/commons/6/6f/Gjl-t%28x%29.svg | -| vocab | 0x25 | `Riemann sphere` | https://kids.kiddle.co/images/thumb/0/03/RiemannKugel.jpg/642px-RiemannKugel.jpg | -| set theory | - | `Complex Number Set Diagram` | https://thinkzone.wlonk.com/Numbers/NumberSets.htm | -| units | - | `SI Units` | https://physics.nist.gov/cuu/pdf/sp811.pdf | - -### Bonus - -| ??? | link | -| --- | --- | -| ??? | https://upload.wikimedia.org/wikipedia/commons/1/14/E8Petrie.svg | diff --git a/help/math/math.md b/help/math/math.md deleted file mode 100644 index d23f9d5..0000000 --- a/help/math/math.md +++ /dev/null @@ -1,235 +0,0 @@ - -# Numbers - -| symbol | set | domain | description | -| ------ | ---------------- | ----------------------------------------- | ----------- | -| 𝔹 | boolean domain | {0, 1} | | -| ℕ | Natural Numbers | {0, 1, 2, 3...} | | -| ℤ | Integers | {..., -3, -2, -1, 0, 1, 2, 3...} | set of all whole numbers | -| ℂ | Complex Numbers | | | -| ℚ | Rational Numbers | `p/q` where `p` and `q` `∈ ℤ` and `q ≠ 0` | | -| ℝ | Real Numbers | | | -| 𝕌 | Universal | any `n` where `n ∉ {NaN, +∞, -∞}` | | - -### ℤ - - * single operation: `+` (`-` operation is just adding a negative integer) - * `x + y -> an integer` "closed under addition" - * `x / y -> not an integer` "not closed under division" - -### Group - - * set of elements `G` - * set of operations, ex: `+`, `*` - * closer under operation `x, y ∈ G -> x * y ∈ G` - * inverse `x⁻¹` exists for all `x` - * `x * x⁻¹ = e` - * identity: `y * e = e * y = y` - * associativity: `(a * b) * c = a * (b * c)` - * may not be `commutative` - * if `G` is `commutative`, it's called `Abelian`/`Commutative` group - * if `G` is not `commutative`, `noncommutative`/`non-abelian` group - -### Ring - - * set of elements where you can `+`, `-`, `*` - * may not have `division` - * adding two elements in a ring will give another element from the ring - * `*` may be `non-commutative` - * multiplication is `associative` - * `distributive property`: `a * (b + c) = a * b + a * c` - -# Vocab - -(lots to be re-organized/sorted/etc) - -### Vocab-Groupings - -| # | term | alt. name | definition | extra | -| ---- | --- | --- | --- | --- | -| 1x00 | `Category theory` | | * "formalizes `mathematical structure` and its concepts in terms of a `labeled directed graph` called a `category`, whose `nodes` are called `objects`, and whose `labelled directed edges` are called `arrows` (or `morphisms`)
* "The `language` of `Category Theory` has been used to formalize concepts of other high-level `abstractions` such as `sets`, `rings`, and `groups`"
* "Informally, category theory is a general theory of `functions`"| has 2 basic properties:
* the ability to `compose` the arrows `associatively`
* and the existence of an `identity` arrow for each `object` | - -### Vocab-Discrete - -| # Grouping | # | term | alt. name | definition | extra | -| ---- | --- | --- | --- | --- | --- | -| 1x00 | 0x00 | `category` | `abstract category` | "a collection of `'objects'` that are linked by `'arrows'` | | -| 1x00 | 0x01 | `functor` | | "a `map` between `categories` | TODO: add formal-definition(https://en.wikipedia.org/wiki/Functor) | - - -| # | term | alt. name | definition | extra | -| ---- | --- | --- | --- | --- | -| 0x00 | `additive identity` | | "Let `N` be a set that is closed under the operation of addition, denoted `+`. An `additive identity` for `N` is any element `e` such that for element `n` in `N`, `e + n = n = n + e`; example: `n + 0 = n = 0 + n`" | ex: the number `0`, "but additive identities occur in other mathematical structures where addition is defined, such as in `groups` and `rings`" | -| 0x01 | `identity function` | `identity relation`, `identity map`, `identity transformation` | "a function that always returns the same value that was used as its argument" | for `⨍` being identity, the equality `f(x) = x` holds for all `x` | -| 0x02 | `cardinal numbers` | `cardinals` | "a generalization of the natural numbers used to measure the `cardinality (size)` of sets" | "`cardinality` of a finite set is a `natural number`" | -| 0x03 | `transfinite numbers` | | "numbers that are 'infinite' in the sense that they are larger than all finite numbers, yet not necessarily `absolutely infinite`" | "include the `transfinite cardinals`, which are used to quantify the size of infinite sets, and the `transfinite ordinals`, which are used to provide an ordering of infinite sets" | -| 0x05 | `urelement` | `ur-element`, `atoms`, `individuals` | "an object that is not a `set`, but that may be an `element` of a set" | | -| 0x06 | `0⁰` | | "a mathematical expression with no agreed-upon value. The most common possibilities are `1` or leaving the expression undefined, with justifications existing for each, depending on context" | `Ruuuby` will evaluate as: `0⁰ == 1` | -| 0x09 | `Ordinary Differential Equation` | | a `differential equation` involving only ordinary derivatives with respect to a single independent variable | -| 0x11 | `Partial Differential Equation` | | a `differential equation` involving partial derivatives with respect to more than one independent variable | -| 0x12 | `Lagarias arithmetic derivative` | `number derivative` | D(p) = 1 for any `prime` p
D(pq) = D(q)p + pD(q) for any p, q ∈ ℕ | "a function defined for `integers`, based on `prime factorization`, by analogy with the `product rule` for the `derivative of a function` that is used in `mathematical analysis` | -| 0x15 | `compositionality` | | "In mathematics, semantics, and philosophy of language, the principle of compositionality is the principle that the meaning of a complex expression is determined by the meanings of its constituent expressions and the rules used to combine them. This principle is also called Frege's principle, because Gottlob Frege is widely credited for the first modern formulation of it." | | -| 0x16 | `metric space` | | "a set together with a metric on the set. The metric is a function that defines a concept of distance between any two members of the set, which are usually called `points`" | satisfies the following:
* distance from a point to itself is zero
* distance between two distinct points is positive
* distance from `A` to `B` is the same as the distance from `B` to `A`
distance from `A` to `B` (directly) is less than or equal to the distance from `A` to `B` via any third point `C` | -| 0x17 | `topology` | (from Greek τόπος, 'place', and λόγος, 'study') | "is concerned with the properties of a `geometric object` that are preserved under `continuous deformations`, such as `stretching`, `twisting`, `crumpling` and `bending`, but not `tearing` or `gluing` | | -| 0x18 | `morphism` | | "is a structure-preserving `map` from one `mathematical strcuture` to another one of the same type. The notion of morphism recurs in much of contemporary mathematics. In `set theory`, morphisms are `functions`; in `linear algebra`, `linear transformations`; in `group theory`, `group homomorphisms`; in `topology`, `continuous functions`, and so on" -| 0x20 | `image` | | "in mathematics, the `image` of a `function` is the set of all output values it may produce" | "More generally, evaluating a given function `f` at each element of a given `subset A` of its `domain` produces a `set` called the `'image of A under (or through) f'" | -| 0x21 | `inverse image` | `preimage` | "the `preimage` of a given subset `B` of the `codomain` of `f` is the set of all elements of the `domain` that map to the members of `B` | | -| 0x22 | `injective function` | `injection`, `one-to-one function` | "a `function` that `maps distinct elements` of its `domain` to `distinct elements` of its `codomain`" | "every element of the `function's codomain` is the `image` of at most one element of its `domain` | -| 0x23 | `bijective functions` | | "`functions` such that each element in the `codomain` is an `image` of exactly on element in the `domain` | | -| 0x24 | `Jacobian matrix` | | "In `vector calculus`, the `Jacobian matrix`, of a `vector-valued function` in several variables is the `matrix` of all its first-order `partial derivatives`" | | -| 0x25 | `Reimann sphere` | | "is a `model` of the `extended complex plane`, the `complex plane` plus a `point at infinity`" | "this `extended plane` represents the `extended complex numbers`, that is, the `complex numbers` plus a value `∞` for `infinity` | -| 0x26 | `ring` | | "one of the fundamental `algebraic structures` used in `abstract algebra`. In consists of a `set` equipped with two `binary operations` that generalize the `arithmetic operations` of `addition` and `multiplication`. Through this generalization, theorems from `arithmetic` are extended to non-numerical objects such as `polynomials`, `series`, `matrices`, and `functions` | "a `ring` is an `abelian group` with a second `binary operation` that is `associative`, is `distributive` over the `abelian group operation` and has an `identity element`" | -| 0x27 | `trigonometric functions` | `circular functions`, `angle functions`, `goniometric functions` | "are `real functions` which relate an angle of a `right-angled triangle` to ratios fo two side lengths" | | -| 0x28 | `Niven's Theorem` | | if `x/π` and `sin(x)` are both `rational`, then the `sine` takes values `0, ±1/2, and ±1` | | -| 0x29 | `measure zero` | | "a set of points capable of being enclosed in intervals whose total length is arbitrarily small" | | -| 0x30 | `first-order logic` | `predicate logic`, `quantificational logic`, `first-order predicate calculus` | "a collection of `formal systems` used in mathematics, philosophy, linguistics, and computer science" | | -| 0x31 | `even & odd functions` | | "functions which satisfy particular `symmetry` relations, with respect to taking `additive inverses`" | | -| 0x32 | `domain` | | "what can go into a function" | | -| 0x33 | `codomain` | | "what may possibly come out of a function" | | -| 0x34 | `range` | | "what actually comes out of a function" | | -| 0x35 | `principal value` | | "the `principal value` of a `multivalued function` are the values along one chosen `branch` of that function, so that it is `single-valued`" | ex: 4 has two roots (±2); the positive root(2) is the `principal root` and denoted as `√4` | - -| # | more | example | -| --- | --- | --- | -| 0x20, 0x21 | `f: X → Y` is a `function` from the `set X` to the `set Y` | -| 0x22 | `one-to-one function` is different than `one-to-one correspondence` (`bijective functions`)(0x23) | - -TODO formal def: `logistic distribution` -TODO formal def: `normal distrubtion` - -### Properties - -| # | term | definition | extra | -| --- | --- | --- | --- | -| 0x0 | `commutative property` | "a `binary operation` is `commutative` if changing the order of the `operands` does not change the result. It is a fundamental property of many `binary operations`, and many `mathematrical proofs` depend on it" | `law of commutativity`: `a + b = b + a`; `ab = ba`, for all `a, b ∈ R` | -| 0x1 | `distributive property` | "in `abstract algebra` and `formal logic`, the `distributive property` of `binary operations` generalizes the `distributive law` from `Boolean algebra` and `elementary algebra`. In `propositional logic`, `distribution` refers to two `valid rules of replacement`. The rules allow one to reformulate `conjunctions` and `disjunctions` with `logical proofs`" | | -| 0x2 | `reflexive property` | "for every real number `x`, `x = x`" | | -| 0x3 | `symmetric property` | "for all real numbers `x` and `y`, if `x = y`, then `y = x`" | | -| 0x4 | `transitive property` | "for all real numbers `x`, `y`, and `z`, if `x = y` and `y = z`, then `x = z`" | | -| 0x5 | `substitution property` | "if `x = y` and `y = z`, then `x = z` | | -| 0x6 | `associative property` | TODO: | - -### Functions - -| # | term | definition | -| --- | --- | --- | -| 0x0 | `Sigmoid function` | | -| 0x1 | `logistic function` | | -| 0x2 | `odd function` | "Let `f` be a real-valued function of a real variable. Then `f` is `odd` if the following equation holds for all `x` such that `x` and `-x` are in the domain of `f`:
`-f(x) = f(-x)`
or equivalently if the following equation holds for all such `x`:
`f(x) + f(-x) = 0`" | -| 0x3 | `even functions` | "Let `f` be a real-valued function of a real variable. Then `f` is `even` if the following equation holds for all `x such that x` and `-x` in the domain of `f`:
`f(x) = f(-x)`
or equivalently if the following equation holds for all such `x`: `f(x) - f(-x) = 0`" | -| 0x4 | `hyperbolic tangent function` | TODO: ADD DESCRIPTION!!! | -| 0x5 | `error function erf` | TODO: !!!!!!!!!!!!!!!!!!!!!!! | -| 0x6 | `multivalued function` | "similar to a function, but may associate several values to each input" ; "from a `domain X` to a `codomain Y` associates each `x` in `X` to one or more values `y` in `Y`" | -| 0x7 | `principal branch` | "a function which selects one `branch` (`'slice'`) of a `multi-valued function`" | - -### Properties of Exponents - - * `xᵃ⋅xᵇ = xᵃ⁺ᵇ` - * `xᵃ/xᵇ = xᵃ⁻ᵇ` - * `(xᵃ)ᵇ = xᵃᵇ` - * `(x⋅y)ᵃ = xᵃ⋅xᵇ` - * `(x/y)ᵃ = xᵃ/yᵃ` - * TODO: - * `(d/dx)x^ᵃ = ax^ᵃ⁻ᵇ, {ᵇ=1}` - -#### Examples of `even-functions`: - - * `x -> |x|` - * `x -> x^2` - * `x -> x^4` - * `costine cos` - * `hyperbolic cosine cosh` - -#### Examples of `odd-functions`: - - * (identity function) `x -> x` - * `x -> x^3` - * `sine sin` - * `hyperbolic sine sinh` - * (error function) `erf` - -### Properties of `even-functions` & `odd-functions` - -Uniqueness: - - * "If a function is both `even` and `odd`, it is equal to `0` everywhere it is defined" - * "If a function is `odd`, the `absolute value` of that function is an `even` function" - -Addition and Subtraction: - - * "The `sum` of two `even` functions is `even`" - * "The `sum` of two `odd` functions is `odd`" - * "The `difference` between two `odd` functions is `odd`" - * "The `difference` between two `even` functions if `even`" - * "The `sum` of an `even` and `odd` function is neither `even` nor `odd`, unless one of the functions is equal to `zero over the given domain`" - -Multiplication and Division: - - * "The `product` of two `even` functions is an `even` function" - * "The `product` of two `odd` functions is an `even` function" - * "The `product` of an `even` function and an `odd` function is an `odd` function" - * "The `quotient` of two `even` functions is an `even` function" - * "The `quotient` of two `odd` functions is an `even` function" - * "The `quotient` of an `even` function and an `odd` function is an `odd` function" - -Composition: - - * "The `composition` of two `even` functions is `even`" - * "The `composition` of two `odd` functions is `odd`" - * "The `composition` of an `even` function and an `odd` function is `even`" - * "The `composition` of any function with an `even` function is `even` (but not vice versa)" - -Even-odd Decomposition: - - * "Every function may be `uniquely decomposed` as the `sum` of an `even` and an `odd` function, which are called respectively the `event part` and the `odd part` of the function; if one defines" - * `fe(x) = (f(x) + f(-x)) / 2` - * `fo(x) = (f(x) - f(-x)) / 2` - * then `fe` is `even` and `fo` is `odd`, and: `f(x) = fe(x) + fo(x)` - - - -### TODO: Unit-Tests - * `additive identity` for each `Numeric` sub-class - -#### TODOs - -* https://en.wikipedia.org/wiki/Ring_(mathematics) -* https://en.wikipedia.org/wiki/Lie_algebra -* https://en.wikipedia.org/wiki/Riemann_sphere -* https://en.wikipedia.org/wiki/Jacobian_matrix_and_determinant -* https://en.wikipedia.org/wiki/Category_theory -* https://en.wikipedia.org/wiki/Image_(mathematics) -* https://en.wikipedia.org/wiki/Functor -* https://en.wikipedia.org/wiki/Category_(mathematics) -* https://en.wikipedia.org/wiki/Category_theory -* https://en.wikipedia.org/wiki/Topological_property -* https://en.wikipedia.org/wiki/Topological_space -* http://functions.wolfram.com/Constants/ComplexInfinity/introductions/Symbols/ShowAll.html -* https://en.wikipedia.org/wiki/Directed_infinity -* https://en.wikipedia.org/wiki/Argument_(complex_analysis) -* https://www.quora.com/What-is-the-value-of-one-to-the-power-infinity - -``` -phi-constant-digits: https://www2.cs.arizona.edu/icon/oddsends/phi.htm - -| 0x10 | `method of least squares` | | `TODO:` add notes with respect to `α` and `β` for minimizing `S` (`partial derivatives` to be zero) | - - * Jacobian matrix - * Lagarias arithmetic derivative - -ε -ℙ -𝕀 -ℍ (quaternions) -𝔼 (expected value) -∂ (partial derivative) - -* Transcendental number -* https://en.wikipedia.org/wiki/Transcendental_number - -``` - - - -Clock Arithmetic similair to Modular Arthimetic - diff --git a/help/math/units.md b/help/math/units.md deleted file mode 100644 index 2eabe46..0000000 --- a/help/math/units.md +++ /dev/null @@ -1,42 +0,0 @@ - -### `International System of Units` (*SI*) - -@see https://en.wikipedia.org/wiki/International_System_of_Units - -| symbol | name | quantity | -| --- | --- | --- | -| `s` | second | time | -| `m` | metre | length | -| `kg` | kilogram | mass | -| `A` | ampere | electric current | -| `K` | kelvin | thermodynamic temperature | -| `mol` | mole | amount of substance | -| `cd` | candela | luminous intensity | - ---- - -@see https://en.wikipedia.org/wiki/International_System_of_Units - -| prefix | symbol | base 10 | decimal | -| ----: | :----: | ------- | --------------------------- | -| yotta | Y | 10²⁴ | 1000000000000000000000000 | -| zetta | Z | 10²¹ | 1000000000000000000000 | -| exa | E | 10¹⁸ | 1000000000000000000 | -| peta | P | 10¹⁵ | 1000000000000000 | -| tera | T | 10¹² | 1000000000000 | -| giga | G | 10⁹ | 1000000000 | -| mega | M | 10⁶ | 1000000 | -| kilo | k | 10³ | 1000 | -| hecto | h | 10² | 100 | -| deca | da | 10¹ | 10 | -| | | 1 | 1 | -| deci | d | 10⁻¹ | 0.1 | -| hecto | h | 10⁻² | 0.001 | -| milli | m | 10⁻³ | 0.0001 | -| micro | μ | 10⁻⁶ | 0.0000001 | -| nano | n | 10⁻⁹ | 0.0000000001 | -| pico | p | 10⁻¹² | 0.0000000000001 | -| femto | f | 10⁻¹⁵ | 0.0000000000000001 | -| atto | a | 10⁻¹⁸ | 0.0000000000000000001 | -| zepto | z | 10⁻²¹ | 0.0000000000000000000001 | -| yocta | y | 10⁻²⁴ | 0.0000000000000000000000001 | diff --git a/help/python.md b/help/python.md deleted file mode 100644 index ec41f8d..0000000 --- a/help/python.md +++ /dev/null @@ -1,4 +0,0 @@ - -| for | reference | -| ---- | -------- | -| `Python` versions | https://en.wikipedia.org/wiki/History_of_Python | diff --git a/help/ruby.md b/help/ruby.md deleted file mode 100644 index 4e543b6..0000000 --- a/help/ruby.md +++ /dev/null @@ -1,93 +0,0 @@ - -### ENVs (TODO) - -``` -RUBYOPT="--jit" ---Jit-wait ---jit-verbose=n ---jit-min-calls=n ---jit-max-cache ---jit-save-temps -``` - -### Operator Precedence Table - -`table from: https://www.techotopia.com/index.php/Ruby_Operator_Precedence` - -| as method? | operator | description | -| --- | --- | --- | -| ✅ | `[]`, `[]=` | element reference, element set | -| ✅ | `**` | exponentiation (raise to power) | -| ✅ | `!`, `~`, `+`, `-` | not, complement, unary plus and minus (method names for last two are `+@` and `-@` | -| ✅ | `*`, `/`, `%` | multiply, divide, modulo | -| ✅ | `+`, `-` | addition and subtraction | -| ✅ | `>>`, `<<` | right, left bitwise shift | -| ✅ | `&` | bitwise `AND` | -| ✅ | `^`, pipe-divider-chars | bitwise exclusive `OR` and regular `OR` | -| ✅ | `<=`, `<`, `>`, `>=` | comparison operators | -| ✅ | `<=>`, `==`, `===`, `!=`, `=~`, `!~` | equality and pattern match operators (`!=` and `!~` may not be defined as methods) | -| ❌ | `&&` | logical `AND` | -| ❌ | 2 pip-divider-chars | logical `OR` | -| ❌ | `..`, `...` | range (inclusive and exclusive) | -| ❌ | `?` `:` | ternary if-then-else | -| ❌ | `=`, `%=`, `{`, `/=`, `-=`, `pipe-divider-char=`, `&=`, `>>=`, `<<=`, `*=`, `&&=`, `2-pipe-divider-chars=`, `**=` | assignment | -| ❌ | `defined?` | check if specified symbol defined | -| ❌ | `not` | logical negation | -| ❌ | `or`, `and` | logical composition | -| ❌ | `if`, `unless`, `while`, `until` | expression modifiers | -| ❌ | `begin/end` | block expression | - -### $GLOBALS - -`table from: https://www.techotopia.com/index.php/Ruby_Variable_Scope` - -| Variable Name | Variable Value | -| ------------- | -------------- | -| $@ | The location of latest error | -| $_ | The string last read by gets | -| $. | The line number last read by interpreter | -| $& | The string last matched by regexp | -| $~ | The last regexp match, as an array of subexpressions | -| $n | The nth subexpression in the last match (same as $~[n]) | -| $= | The case-insensitivity flag | -| $/ | The input record separator | -| $\ | The output record separator | -| $0 | The name of the ruby script file currently executing | -| $* | The command line arguments used to invoke the script | -| $$ | The Ruby interpreter's process ID | -| $? | The exit status of last executed child process | - -### Syntax Sugar - -`table from: https://simpleror.wordpress.com/2009/03/15/q-q-w-w-x-r-s/#x` - -| format | example | description | -| --- | --- | --- | -| %Q | %Q("hi") -> \"hi\" | alternative for "" | -| %q | | same as above but for single-quoted strings (no expression substitution or escape sequences) | -| %W | | for double-quoted array elements | -| %w | | same as above but for single-quoted strings | -| %x | | returns standard output of ran `cmd` | -| %r | | used to create `Regular Expressions` | -| %s | | used to created symbols (not subject to expression substitution or escape sequences) | - -### TODOs: - - * resolve the following - * http://davidmoulton.me/2013/04/01/resign-ruby-executable-in-osx.html - -``` - -codesign -v $(which ruby) - -"...code object is not signed at all" -``` - -```ruby - require 'benchmark' - puts Benchmark.measure { - 10_000.times do - ::Math::NumberTheory::ℤ².gcd(1233, 5556) - end - } -``` diff --git a/help/ruuuby.md b/help/ruuuby.md deleted file mode 100644 index a0e1b70..0000000 --- a/help/ruuuby.md +++ /dev/null @@ -1,151 +0,0 @@ - -### Ruuuby Glossary - -#### TODOs -``` - unicode: - * https://www.honeybadger.io/blog/ruby-unicode-normalization/ - * https://idiosyncratic-ruby.com/41-proper-unicoding.html - * https://rollout.io/blog/how-ruby-string-encoding-benefits-developers/ - - investigate before adding NGINX: - * https://www.speedshop.co/2018/03/28/nginx-unit-for-ruby.html - * https://unit.nginx.org/configuration/#configuration-ruby -``` - -#### TODO: document these sources - - * https://www.iterm2.com/documentation-scripting.html - * https://alvinalexander.com/apple/mac-voice-speech-recognition-software-commands-custom/ - * https://osxdaily.com/2016/08/19/run-applescript-command-line-macos-osascript/ - * https://support.apple.com/lt-lt/guide/terminal/trml1003/mac - -# misc, todo - - * https://developer.apple.com/documentation/applicationservices/apple_event_manager - * https://stackoverflow.com/questions/17980759/xcode-select-active-developer-directory-error - - ->#### Testing Tasks (OLD REFERENCE, for 0.0.49 or below) ->| preface | cmd | description of test contests | w/ warnings? ->| -----------------: | :-----------------: | :---------- | ----------: ->| `bundle exec rake` | `rspec_unit` | all core expected functionality from `Ruuuby` | ❌ | ->| `bundle exec rake` | `rspec_integration` | expected state & functionality from `Ruuuby` code areas w/ using more than one feature/component | ❌ | ->| `bundle exec rake` | `rspec_db` | anything relating to the `DB` or `ORM` | ❌ | ->| `bundle exec rake` | `rspec_audit` | extra-checks for expected code-structure; ensures passing `Ruuuby` functionality tests are not occurring from any artifacts | ❌ | ->| `bundle exec rake` | `rspec_performance` | defines acceptable runtime-performance benchmarks (`TODO: missing Big-O tests`) | ❌ | ->| `bundle exec rake` | `rspec_tech_debt` | tracks/confirms missing coverage; ∀ resolved-test-case will transfer to a new test-category, lowering the total count of `tech_debt` tests | ❌ | ->| `bundle exec rake` | `rspec_locale` | extra-checks for properly configured local coding environment (`TODO: need to formalize Ruby build process`) | ❌ | ->| `bundle exec rake` | `rspec_all` | run all existing tests | ✅ | - -#### Temporary/Pseudo Code - -```ruby - - def perform_big_o_constant(bla) - RSpec::Benchmark::Matchers::ben - exec_func_n_times = bench_range() - expect{ |n, i| } - end - -``` - -### TODOs - - * formalize this into re-usable procedures - -```ruby -require 'benchmark' -FIXNUM_MAX = (2**(0.size * 8 -2) -1) -MAX_SIZE = FIXNUM_MAX / 8192 -Random.rand(MAX_SIZE) - -data = [] -(100..99999).each do |i| - data << [Random.rand(i), Random.rand(i)] -end - -def slow_gcd(a, b) - a, b = b, a%b until b.zero? - a -end - -def other_gcd(a, b) - a.gcd(b) -end - -def fast_gcd(a, b) - ::Math::NumberTheory.fast_gcd(a, b) -end - -Benchmark.bmbm do |x| - x.report('slow_gcd') do - 50000.times do |i| - slow_gcd(data[i][0], data[i][1]) - end - end - x.report('other_gcd') do - 50000.times do |i| - data[i][0].gcd(data[i][1]) - end - end - x.report('fast_gcd') do - 50000.times do |i| - ::Math::NumberTheory.fast_gcd(data[i][0], data[i][1]) - #fast_gcd(data[i][0], data[i][1]) - end - end -end - -puts Benchmark.measure { - 10000.times do |i| - slow_gcd(data[i][0], data[i][1]) - end -} -puts Benchmark.measure { - 10000.times do |i| - fast_gcd(data[i][0], data[i][1]) - end -} - -require 'benchmark' -FIXNUM_MAX = (2**(0.size * 8 -2) -1) -MAX_SIZE = FIXNUM_MAX / 8192 -Random.rand(MAX_SIZE) -data = [] -(100..99999).each do |i| - data << [Random.rand(i), Random.rand(i)] -end -puts Benchmark.measure { - 10000.times do |i| - b = data[0, data.length-1] - end -} -puts Benchmark.measure { - 10000.times do |i| - b = data[0..data.length-2] - end -} -puts Benchmark.measure { - 10000.times do |i| - b = data[0...data.length-1] - end -} -puts Benchmark.measure { - 10000.times do |i| - b = data[0...-1] - end -} - -``` - -``` -Rehearsal -------------------------------------------- -slow_gcd 0.005331 0.000008 0.005339 ( 0.005330) -fast_gcd 0.002493 0.000003 0.002496 ( 0.002495) ------------------------------------ total: 0.007835sec - - user system total real -slow_gcd 0.005161 0.000026 0.005187 ( 0.005206) -fast_gcd 0.002382 0.000003 0.002385 ( 0.002382) -``` diff --git a/lib/ruuuby/class/enumerable/hsh.rb b/lib/ruuuby/class/enumerable/hsh.rb index 0b6d62f..dc3bbbd 100644 --- a/lib/ruuuby/class/enumerable/hsh.rb +++ b/lib/ruuuby/class/enumerable/hsh.rb @@ -31,8 +31,6 @@ def λ𝑓∀🔑:₍🔑∉₎!(*keys) self end - # TODO: MISSING TDD! - # # `does each provided key exist w/ the the same provided value?` # # @param [Array] keys_to_find @@ -40,19 +38,16 @@ def λ𝑓∀🔑:₍🔑∉₎!(*keys) # # @return [Boolean] def ∀🔑∃_value?(keys_to_find, expected_value) + 🛑ary❓('keys_to_find', keys_to_find) matched_keys = 0 - num_to_find = keys_to_find.length keys_to_find.∀ do |key| - if self.∃🔑?(key) - if self[key] == expected_value - matched_keys += 1 - return true if matched_keys == num_to_find - end + if self.∃🔑?(key) && self[key] == expected_value + matched_keys += 1 else return false end end - 🛑 ::RuntimeError.new("| c{Hash}-> m{∀🔑∃_value?} called w/ keys_to_find as{#{keys_to_find.to_s}} and expected_value as {#{expected_value.to_s}} which did not match the result length of{#{matched_keys.to_s}} |") + matched_keys == keys_to_find.length end end diff --git a/lib/ruuuby/class/io/file.rb b/lib/ruuuby/class/io/file.rb index 42cdfcd..40fbdd3 100644 --- a/lib/ruuuby/class/io/file.rb +++ b/lib/ruuuby/class/io/file.rb @@ -225,7 +225,6 @@ def self.read!(path, expected_sections) end # end: {YAML} module JSON - #attribute_lazy_loadable('json', true) # @see https://makandracards.com/makandra/15611-how-to-fix-unexpected-token-error-for-json-parse # @see https://www.jvt.me/posts/2019/11/22/minify-json-ruby/ diff --git a/lib/ruuuby/class/obj.rb b/lib/ruuuby/class/obj.rb index ab8f796..e2b2a24 100644 --- a/lib/ruuuby/class/obj.rb +++ b/lib/ruuuby/class/obj.rb @@ -298,32 +298,6 @@ def Ⓣ; self.class.to_s; end alias_method :❄️?, :frozen? # | ------------------------------------------------------------------------------------------------------------------ - # @param [String] version_expected - # - # @raise [ArgumentError] - def attribute_versionable(version_expected, &block) - 🛑str❓('version_expected', version_expected) - self.instance_variable_set("@version_expected", version_expected) - - self.define_singleton_method(:∃version?) do || - self.instance_variable_set("@version_current", block.call) if @version_current.nil? - if @version_current == @version_expected - return true - else - 🛑 ::RuntimeError.new("{#{@version_current.to_s}}[#{@version_current.Ⓣ}] != {#{@version_expected.to_s}}[#{@version_expected.Ⓣ}]") - end - end - - class << self - attr_reader :version_expected - - # @return [String] - def version_current; self.∃version? if @version_current.nil?; @version_current; end - end - - self - end - def attribute_lazy_loadable(library_to_load, debug=false) 🛑str❓('library_to_load', library_to_load) self.instance_variable_set("@lazy_loaded", false) diff --git a/lib/ruuuby/configs.rb b/lib/ruuuby/configs.rb index 902e14f..7a9a361 100644 --- a/lib/ruuuby/configs.rb +++ b/lib/ruuuby/configs.rb @@ -15,18 +15,6 @@ class << self #$git = 💎.engine.api_locale.api_git end - # TODO: create better solution than loading it here - module ::TTY - class Command - attribute_versionable('0.10.0'){::TTY::Command::VERSION} - - # @return [Boolean] - def self.healthy? - ::TTY::Command.record_separator == $/ && !::TTY::Command.windows? && ::TTY::Command.∃version? - end - end - end - # TODO: create better solution than loading it here module ::Kernel @@ -83,7 +71,6 @@ def 𝕚; ::Math::SetTheory::ImaginaryNumbers.instance; end } - END { 💎.engine.engine.stop } diff --git a/lib/ruuuby/db/db_connection.rb b/lib/ruuuby/db/db_connection.rb index f6896cd..4c6a178 100644 --- a/lib/ruuuby/db/db_connection.rb +++ b/lib/ruuuby/db/db_connection.rb @@ -2,11 +2,6 @@ # --------------------------------------------- ⚠️ --------------------------------------------- -# ---------------------------------------------------------------------------------------------------------------- -#def get_connection_schema; ::ActiveRecord::Schema.connection; end -#def get_connection_base; ::ActiveRecord::Base.connection; end -# ---------------------------------------------------------------------------------------------------------------- - module ::Ruuuby::MetaData class DBConnection @@ -27,10 +22,7 @@ def initialize(configs) end def obtain_connection - if 💎.engine.stats_ext['F92_B01'] && 💎.engine.stats_ext['F92_B02'] - @connection_pool = ::ActiveRecord::Base.establish_connection(@configs) - @connection = @connection_pool.connection - elsif 💎.engine.stats_ext['F92_B01'] + if 💎.engine.stats_ext['F92_B01'] || 💎.engine.stats_ext['F92_B02'] @connection_pool = ::ActiveRecord::Base.establish_connection(@configs) @connection = @connection_pool.connection elsif 💎.engine.stats_ext['F92_B02'] @@ -49,9 +41,6 @@ def ♻️_connection!; @connection.disconnect! unless @connection.nil?; end # @see https://api.rubyonrails.org/classes/ActiveRecord/ConnectionAdapters/PostgreSQLAdapter.html#method-c-create_unlogged_tables class DBConnectionPostgreSQL < ::Ruuuby::MetaData::DBConnection - # @type [String] - SQL_GET_ALL_TABLE_NAMES = "SELECT table_name FROM information_schema.tables WHERE table_type='BASE TABLE' AND table_schema='public';" - # @param [Hash, String] configs or yaml file path def initialize(configs) super(configs) @@ -63,26 +52,8 @@ def initialize(configs) def sql(sql) 🛑str❓('sql', sql) puts "executing sql{#{sql}}" - #@connection.exec(sql) - @connection.execute(sql) - end - - # @param [String] fields - # @param [String] table - # @param [String] conditional_where - # - # @raise [ArgumentError] - def sql_select_one(fields, table, conditional_where='') - 🛑str❓('fields', fields) - 🛑str❓('table', table) - 🛑str❓('conditional_where', conditional_where) - conditional_str = '' - unless conditional_where == '' - conditional_str = " WHERE #{conditional_where} " - end - query = "SELECT #{fields} FROM #{table}#{conditional_str}LIMIT 1;" - puts "executing sql{#{query}}" - @connection.exec(query).values.first[0] + #@connection.execute(sql) + @connection.exec_query(sql) end def _connected?; @connection != nil; end diff --git a/lib/ruuuby/db/migrations/migration_ext.rb b/lib/ruuuby/db/migrations/migration_ext.rb index 5c6b8e8..c549217 100644 --- a/lib/ruuuby/db/migrations/migration_ext.rb +++ b/lib/ruuuby/db/migrations/migration_ext.rb @@ -2,16 +2,16 @@ class RuuubyDBMigration < ActiveRecord::Migration[6.0] - # @return [String] + # @return [String] relative_ending def self.read_sql_file(relative_ending); ::File.read("#{💎.engine.path_base}lib/ruuuby/db/migrations/#{relative_ending}"); end - # @return [String] + # @return [String] relative_ending def self.read_sql_rollout_file(relative_ending); self.read_sql_file("rollout/#{relative_ending}"); end - # @return [String] + # @return [String] relative_ending def self.read_sql_rollback_file(relative_ending); self.read_sql_file("rollback/#{relative_ending}"); end - # @return [String] + # @return [String] relative_ending def self.read_sql_seed_file(relative_ending); self.read_sql_file("seed/#{relative_ending}"); end # @param [String] func_name @@ -30,11 +30,25 @@ def self.∃⨍_sql?(func_name) end end - # TODO: MIGRATE TO DB_ORM_MANAGER # @param [String] table_name # # @return [Boolean] - def self.∃table?(table_name); $orm.db_orm.connection.table_exists?(table_name); end - #def self.∃table?(table_name); $ruuuby.engine.orm.db_orm.connection.table_exists?(table_name); end + def ∃table?(table_name); table_exists?(table_name); end + + # @param [Symbol] table_name + # @param [Symbol] single_field + def ♻️index(table_name, single_field) + remove_index(table_name, single_field) if index_exists?(table_name, single_field) + end + + # @param [Symbol] table_name + # @param [Symbol] single_field + def ♻️index!(table_name, single_field); remove_index(table_name, single_field); end + + # @param [Symbol] table_name + def ♻️table(table_name); drop_table(table_name, if_exists: true); end + + # @param [Symbol] table_name + def ♻️table!(table_name); drop_table(table_name); end end diff --git a/lib/ruuuby/db/migrations/rollback/01_ruuuby_gem.sql b/lib/ruuuby/db/migrations/rollback/00_ruuuby_gem.sql similarity index 71% rename from lib/ruuuby/db/migrations/rollback/01_ruuuby_gem.sql rename to lib/ruuuby/db/migrations/rollback/00_ruuuby_gem.sql index 225f78f..19ac3f1 100644 --- a/lib/ruuuby/db/migrations/rollback/01_ruuuby_gem.sql +++ b/lib/ruuuby/db/migrations/rollback/00_ruuuby_gem.sql @@ -11,17 +11,16 @@ DROP PROCEDURE IF EXISTS ruuuby_gem_add_dev(text,text,text,text,text,text); DROP PROCEDURE IF EXISTS ruuuby_gem_add_prod(text,text,text,text,text,text); DROP PROCEDURE IF EXISTS ruuuby_gem_update(text,text,text); DROP PROCEDURE IF EXISTS ruuuby_gem_remove(text,text); -DROP PROCEDURE IF EXISTS ruuuby_release_add(text); -DROP PROCEDURE IF EXISTS ruuuby_feature_add(text,boolean,text); +DROP PROCEDURE IF EXISTS ruuuby_release_add(text,timestamp); +DROP PROCEDURE IF EXISTS ruuuby_feature_add(_uid TEXT, _is_optional BOOLEAN, _desc_self TEXT); DROP PROCEDURE IF EXISTS ruuuby_feature_behavior_add(text,text,text); DROP FUNCTION IF EXISTS ruuuby_release_gem_changelogs(text); -DROP FUNCTION IF EXISTS ruuuby_gem_get_id(text); +DROP FUNCTION IF EXISTS ruuuby_active_gems(); +DROP FUNCTION IF EXISTS ruuuby_gem_id(_name TEXT); DROP FUNCTION IF EXISTS ruuuby_gem_latest_changelog_id(text); DROP FUNCTION IF EXISTS ruuuby_gem_current_version(text); -DROP FUNCTION IF EXISTS ruuuby_release_get_id(text); -DROP FUNCTION IF EXISTS ruuuby_feature_get_id(text); - -DROP FUNCTION does_func_exist(text); +DROP FUNCTION IF EXISTS ruuuby_release_id(_release_version TEXT); +DROP FUNCTION IF EXISTS ruuuby_feature_id(_uid TEXT); COMMIT TRANSACTION; diff --git a/lib/ruuuby/db/migrations/rollback/00_utils.sql b/lib/ruuuby/db/migrations/rollback/00_utils.sql deleted file mode 100644 index 3e52135..0000000 --- a/lib/ruuuby/db/migrations/rollback/00_utils.sql +++ /dev/null @@ -1,16 +0,0 @@ - --- -------------------------------------------- ⚠️ -------------------------------------------- --- testing purposes --- -------------------------------------------- ⚠️ -------------------------------------------- - -BEGIN TRANSACTION; - ---DROP FUNCTION IF EXISTS does_func_exist(); - -DROP FUNCTION IF EXISTS get_user_funcs(); -DROP FUNCTION IF EXISTS get_ruuuby_resources(TEXT); -DROP FUNCTION IF EXISTS ruuuby_resource_add_meta_data(TEXT, TEXT); -DROP FUNCTION IF EXISTS get_ruuuby_resource_id(TEXT); -DROP FUNCTION IF EXISTS get_ruuuby_meta_data_data_id(TEXT); - -COMMIT TRANSACTION; diff --git a/lib/ruuuby/db/migrations/rollout/01_ruuuby_gem.sql b/lib/ruuuby/db/migrations/rollout/00_ruuuby_gem.sql similarity index 64% rename from lib/ruuuby/db/migrations/rollout/01_ruuuby_gem.sql rename to lib/ruuuby/db/migrations/rollout/00_ruuuby_gem.sql index 4d70262..147647b 100644 --- a/lib/ruuuby/db/migrations/rollout/01_ruuuby_gem.sql +++ b/lib/ruuuby/db/migrations/rollout/00_ruuuby_gem.sql @@ -5,12 +5,23 @@ BEGIN TRANSACTION; -CREATE OR REPLACE FUNCTION ruuuby_release_get_id(_version_ruuuby TEXT) RETURNS BIGINT AS $$ +-- __ ___ ___ __ ___ __ +-- |__) |__ | |__ /\ /__` |__ /__` +-- | \ |___ |___ |___ /~~\ .__/ |___ .__/ +CREATE OR REPLACE FUNCTION ruuuby_release_id(_release_version TEXT) RETURNS BIGINT AS $$ BEGIN - RETURN (SELECT id FROM ruuuby_releases WHERE version = _version_ruuuby); + RETURN (SELECT id FROM ruuuby_releases WHERE version = _release_version); END; $$ LANGUAGE plpgsql; -CREATE OR REPLACE FUNCTION ruuuby_feature_get_id(_uid TEXT) RETURNS BIGINT AS $$ +CREATE OR REPLACE PROCEDURE ruuuby_release_add(_version_ruuuby TEXT, _time_released TIMESTAMP DEFAULT NULL) LANGUAGE plpgsql AS $$ +BEGIN + INSERT INTO ruuuby_releases (version, changelogs, dt_released) VALUES (_version_ruuuby, NULL, _time_released); +END; $$; + +-- ___ ___ ___ __ ___ __ +-- |__ |__ /\ | | | |__) |__ /__` +-- | |___ /~~\ | \__/ | \ |___ .__/ +CREATE OR REPLACE FUNCTION ruuuby_feature_id(_uid TEXT) RETURNS BIGINT AS $$ BEGIN RETURN (SELECT id FROM ruuuby_features WHERE uid = _uid); END; $$ LANGUAGE plpgsql; @@ -20,24 +31,25 @@ BEGIN INSERT INTO ruuuby_features(uid, is_optional, desc_self) VALUES (_uid, _is_optional, _desc_self); END; $$; -CREATE OR REPLACE PROCEDURE ruuuby_release_add(_version_ruuuby TEXT) LANGUAGE plpgsql AS $$ -BEGIN - INSERT INTO ruuuby_releases (version) VALUES (_version_ruuuby); -END; $$; - +-- __ ___ __ __ __ +-- |__) |__ |__| /\ \ / | / \ |__) /__` +-- |__) |___ | | /~~\ \/ | \__/ | \ .__/ CREATE OR REPLACE PROCEDURE ruuuby_feature_behavior_add(_feature_uid TEXT, _behavior_uid TEXT, _desc_self TEXT) LANGUAGE plpgsql AS $$ BEGIN - INSERT INTO ruuuby_feature_behaviors (uid, desc_self, ruuuby_features_id) VALUES (_behavior_uid, _desc_self, (SELECT id FROM ruuuby_features WHERE uid = _feature_uid)); + INSERT INTO ruuuby_feature_behaviors (uid, desc_self, ruuuby_features_id) VALUES (_behavior_uid, _desc_self, (ruuuby_feature_id(_feature_uid))); END; $$; +-- __ ___ __ +-- / _` |__ |\/| /__` +-- \__> |___ | | .__/ CREATE OR REPLACE PROCEDURE ruuuby_gem_add(_version_ruuuby TEXT, _name TEXT, _version_current TEXT, _env_dev BOOLEAN DEFAULT TRUE, _env_prod BOOLEAN DEFAULT FALSE, _ref_source TEXT DEFAULT NULL, _ref_version TEXT DEFAULT NULL, _git_url TEXT DEFAULT NULL) LANGUAGE plpgsql AS $$ DECLARE gem_id BIGINT; val_gem_url TEXT := (SELECT 'https://rubygems.org/gems/' || _name AS result_url); - ruuuby_id CONSTANT BIGINT := (SELECT ruuuby_release_get_id(_version_ruuuby)); + ruuuby_id CONSTANT BIGINT := (SELECT ruuuby_release_id(_version_ruuuby)); BEGIN INSERT INTO ruuuby_gems (name, env_dev, env_prod, ref_source, ref_version, url_gem) VALUES (_name, _env_dev, _env_prod, _ref_source, _ref_version, val_gem_url); - SELECT ruuuby_gem_get_id(_name) INTO gem_id; + SELECT ruuuby_gem_id(_name) INTO gem_id; INSERT INTO ruuuby_gem_changelogs (version_current, is_version_latest, ruuuby_gem_id, ruuuby_releases_id) VALUES (_version_current, TRUE, gem_id, ruuuby_id); END; $$; @@ -58,8 +70,8 @@ END; $$; CREATE OR REPLACE PROCEDURE ruuuby_gem_update(_version_ruuuby text, _name text, _version_current text) LANGUAGE plpgsql AS $$ DECLARE - gem_id CONSTANT BIGINT := (SELECT ruuuby_gem_get_id(_name)); - ruuuby_id CONSTANT BIGINT := (SELECT ruuuby_release_get_id(_version_ruuuby)); + gem_id CONSTANT BIGINT := (SELECT ruuuby_gem_id(_name)); + ruuuby_id CONSTANT BIGINT := (SELECT ruuuby_release_id(_version_ruuuby)); BEGIN UPDATE ruuuby_gem_changelogs AS rgc SET is_version_latest = FALSE WHERE rgc.ruuuby_gem_id = gem_id; INSERT INTO ruuuby_gem_changelogs (version_current, is_version_latest, ruuuby_gem_id, ruuuby_releases_id) VALUES (_version_current, TRUE, gem_id, ruuuby_id); @@ -67,34 +79,33 @@ END; $$; CREATE OR REPLACE PROCEDURE ruuuby_gem_remove(_version_ruuuby text, _name text) LANGUAGE plpgsql AS $$ DECLARE - gem_id CONSTANT BIGINT := (SELECT ruuuby_gem_get_id(_name)); - ruuuby_id CONSTANT BIGINT := (SELECT ruuuby_release_get_id(_version_ruuuby)); + gem_id CONSTANT BIGINT := (SELECT ruuuby_gem_id(_name)); + ruuuby_id CONSTANT BIGINT := (SELECT ruuuby_release_id(_version_ruuuby)); BEGIN UPDATE ruuuby_gem_changelogs AS rgc SET is_version_latest = FALSE WHERE rgc.ruuuby_gem_id = gem_id; INSERT INTO ruuuby_gem_changelogs (version_current, is_version_latest, ruuuby_gem_id, ruuuby_releases_id) VALUES ('REMOVE', TRUE, gem_id, ruuuby_id); END; $$; -CREATE OR REPLACE FUNCTION ruuuby_gem_get_id(_name TEXT) RETURNS BIGINT AS $$ +CREATE OR REPLACE FUNCTION ruuuby_gem_id(_name TEXT) RETURNS BIGINT AS $$ BEGIN RETURN (SELECT id FROM ruuuby_gems WHERE name = _name LIMIT 1); END; $$ LANGUAGE plpgsql; CREATE OR REPLACE FUNCTION ruuuby_gem_latest_changelog_id(_name text) RETURNS BIGINT AS $$ BEGIN - -- TODO: shouldn't it be max(id) for ruuuby_gem_changelogs? - RETURN (SELECT id FROM ruuuby_gem_changelogs WHERE ruuuby_gem_id = (SELECT ruuuby_gem_get_id(_name)) ORDER BY id DESC LIMIT 1); + RETURN (SELECT MAX(id) FROM ruuuby_gem_changelogs WHERE ruuuby_gem_id = (SELECT ruuuby_gem_id(_name))); END; $$ LANGUAGE plpgsql; CREATE OR REPLACE FUNCTION ruuuby_gem_current_version(_name text) RETURNS TEXT AS $$ BEGIN - RETURN (SELECT version_current FROM ruuuby_gem_changelogs WHERE ruuuby_gem_id = (SELECT ruuuby_gem_get_id(_name)) ORDER BY id DESC LIMIT 1); + RETURN (SELECT version_current FROM ruuuby_gem_changelogs WHERE ruuuby_gem_id = (SELECT ruuuby_gem_id(_name)) ORDER BY id DESC LIMIT 1); END; $$ LANGUAGE plpgsql; CREATE OR REPLACE FUNCTION ruuuby_release_gem_changelogs (_release_version TEXT) RETURNS TABLE ( version_current CHARACTER VARYING, - version CHARACTER VARYING, - name CHARACTER VARYING + version CHARACTER VARYING, + name CHARACTER VARYING ) AS $$ BEGIN RETURN QUERY @@ -105,4 +116,24 @@ BEGIN ORDER BY rgc.id DESC; END; $$ LANGUAGE plpgsql; +CREATE OR REPLACE FUNCTION ruuuby_active_gems () + RETURNS TABLE ( + name CHARACTER VARYING, + version CHARACTER VARYING, + env_dev BOOLEAN, + env_prod BOOLEAN + ) AS $$ +BEGIN + RETURN QUERY + SELECT rg.name, q0.version_current AS version, rg.env_dev, rg.env_prod + FROM ( + SELECT * FROM ruuuby_gem_changelogs AS rgc + WHERE rgc.is_version_latest = TRUE + AND rgc.version_current != 'REMOVE' + ) AS q0 + LEFT JOIN ruuuby_gems AS rg + ON rg.id = q0.ruuuby_gem_id + ORDER BY rg.env_prod DESC, rg.env_dev DESC, rg.name ASC, q0.version_current; +END; $$ LANGUAGE plpgsql; + COMMIT TRANSACTION; diff --git a/lib/ruuuby/db/migrations/rollout/00_utils.sql b/lib/ruuuby/db/migrations/rollout/00_utils.sql deleted file mode 100644 index 757d2f5..0000000 --- a/lib/ruuuby/db/migrations/rollout/00_utils.sql +++ /dev/null @@ -1,72 +0,0 @@ - --- -------------------------------------------- ⚠️ -------------------------------------------- --- testing purposes --- -------------------------------------------- ⚠️ -------------------------------------------- - -BEGIN TRANSACTION; - --- TODO: https://libgit2.org/docs/guides/101-samples/ --- @see https://dataedo.com/kb/query/postgresql/list-user-defined-functions - - --- get_user_funcs -CREATE OR REPLACE FUNCTION does_func_exist (_func_name TEXT) RETURNS BOOLEAN AS $$ -BEGIN - RETURN (SELECT COUNT(*) FROM get_user_funcs() AS data_src - WHERE data_src.function_name = _func_name - LIMIT 1) > 0; -END; $$ LANGUAGE plpgsql; - -CREATE OR REPLACE FUNCTION get_user_funcs () - RETURNS TABLE ( - function_schema NAME, - function_name NAME, - function_language NAME, - definition TEXT, - function_arguments TEXT, - return_type NAME - ) AS $$ -BEGIN - RETURN QUERY - SELECT n.nspname AS function_schema, - p.proname AS function_name, - l.lanname AS function_language, - CASE WHEN l.lanname = 'internal' THEN p.prosrc - ELSE pg_get_functiondef(p.oid) - END AS definition, - pg_get_function_arguments(p.oid) AS function_arguments, - t.typname AS return_type - FROM pg_proc p - LEFT JOIN pg_namespace n ON p.pronamespace = n.oid - LEFT JOIN pg_language l ON p.prolang = l.oid - LEFT JOIN pg_type t ON t.oid = p.prorettype - WHERE n.nspname NOT IN ('pg_catalog', 'information_schema') - ORDER BY function_schema, function_name; -END; $$ LANGUAGE plpgsql; - -CREATE OR REPLACE FUNCTION get_tag_id(_meta_data_name TEXT) RETURNS BIGINT AS $$ -BEGIN - RETURN (SELECT id FROM ruuuby_tags WHERE name = _meta_data_name LIMIT 1); -END; $$ LANGUAGE plpgsql; - -CREATE OR REPLACE FUNCTION get_ruuuby_resource_id(_resource_name TEXT) RETURNS BIGINT AS $$ -BEGIN - RETURN (SELECT id FROM ruuuby_resources WHERE name = _resource_name LIMIT 1); -END; $$ LANGUAGE plpgsql; - -CREATE OR REPLACE PROCEDURE ruuuby_spawn_resource(_name TEXT, _tag TEXT, _content JSON, _extra_str_data TEXT DEFAULT NULL) LANGUAGE plpgsql AS $$ -BEGIN - IF get_tag_id(_tag) IS NULL THEN - INSERT INTO ruuuby_tags (name) VALUES (_tag); - END IF; - IF get_ruuuby_resource_id(_name) IS NULL THEN - INSERT INTO ruuuby_resources (name, content, extra_str_data) VALUES (_name, _content, _extra_str_data); - INSERT INTO ruuuby_resource_tags (ruuuby_resources_id, ruuuby_tags_id) VALUES (get_ruuuby_resource_id(_name), get_tag_id(_tag)); - ELSE - RAISE 'ruuuby resources already exists for provided name'; - END IF; -END; $$; - ---END; $$ LANGUAGE plpgsql; - -COMMIT TRANSACTION; diff --git a/lib/ruuuby/db/migrations/ruuuby_gem.rb b/lib/ruuuby/db/migrations/ruuuby_gem.rb index 69b29e9..048fef9 100644 --- a/lib/ruuuby/db/migrations/ruuuby_gem.rb +++ b/lib/ruuuby/db/migrations/ruuuby_gem.rb @@ -3,13 +3,13 @@ #class CreateRuuubyGem < ActiveRecord::Migration[6.0] class CreateRuuubyGem < RuuubyDBMigration - DB_FILE_NAME = '01_ruuuby_gem.sql' + DB_FILE_NAME = '00_ruuuby_gem.sql' # @return [Boolean] def self.up_verify - needed_funcs = %w(ruuuby_release_get_id ruuuby_feature_get_id ruuuby_feature_add ruuuby_release_add + needed_funcs = %w(ruuuby_release_id ruuuby_feature_id ruuuby_feature_add ruuuby_release_add ruuuby_feature_behavior_add ruuuby_gem_add ruuuby_gem_add_dev ruuuby_gem_add_prod ruuuby_gem_add_recommended -ruuuby_gem_update ruuuby_gem_remove ruuuby_gem_get_id ruuuby_gem_latest_changelog_id ruuuby_gem_current_version +ruuuby_gem_update ruuuby_gem_remove ruuuby_gem_id ruuuby_gem_latest_changelog_id ruuuby_gem_current_version ruuuby_release_gem_changelogs) needed_tables = %w(ruuuby_releases ruuuby_features ruuuby_feature_behaviors ruuuby_gems ruuuby_gem_changelogs) @@ -23,37 +23,46 @@ def self.up_verify def self.up create_table :ruuuby_releases do |t| - t.string :version, :null => false, :unique => true - t.json :changelogs, :null => true, :unique => false + t.string :version, :null => false + t.json :changelogs, :null => true + t.timestamp :dt_released, :null => true + + t.index :version, unique: true end + add_index :ruuuby_releases, :version, unique: true create_table :ruuuby_features do |t| t.string :uid, :null => false, :unique => true - t.boolean :is_optional, :null => false, :unique => false + t.boolean :is_optional, :null => false t.string :desc_self, :null => false, :unique => true end + add_index :ruuuby_features, :uid, unique: true create_table :ruuuby_feature_behaviors do |t| t.string :uid, :null => false, :unique => true t.string :desc_self, :null => false, :unique => true - + # TODO: t.boolean :is_optional, :null => false t.references :ruuuby_features, foreign_key: { references: :ruuuby_features } end + add_index :ruuuby_feature_behaviors, :uid, unique: true + + # TODO: ruuuby_feature_groups + # TODO: ruuuby_feature_behaviors_ptrs create_table :ruuuby_gems do |t| t.string :name, :null => false, :unique => true t.text :url_gem, :null => true, :unique => true t.text :url_git, :null => true, :unique => true - t.boolean :env_dev, :null => false, :unique => false - t.boolean :env_prod, :null => false, :unique => false - t.string :ref_source, :null => true, :unique => false - t.string :ref_version, :null => true, :unique => false + t.boolean :env_dev, :null => false + t.boolean :env_prod, :null => false + t.string :ref_source, :null => true + t.string :ref_version, :null => true #t.timestamps end create_table :ruuuby_gem_changelogs do |t| - t.string :version_current, :null => false, :unique => false - t.boolean :is_version_latest, :null => false, :unique => false + t.string :version_current, :null => false + t.boolean :is_version_latest, :null => false t.references :ruuuby_gem, foreign_key: { references: :ruuuby_gems } t.references :ruuuby_releases, foreign_key: { references: :ruuuby_releases } @@ -62,19 +71,23 @@ def self.up execute(self.read_sql_rollout_file(DB_FILE_NAME)) execute(self.read_sql_seed_file(DB_FILE_NAME)) - if $ruuuby.engine.stats_ext['RUUUBY_ENV'] == 'test' - self.up_verify - else - puts 'env is not{test} skipping verification' - end + #if $ruuuby.engine.stats_ext['RUUUBY_ENV'] == 'test' + # self.up_verify + #else + # puts 'env is not{test} skipping verification' + #end end def self.down - drop_table :ruuuby_gem_changelogs - drop_table :ruuuby_gems - drop_table :ruuuby_releases - drop_table :ruuuby_feature_behaviors - drop_table :ruuuby_features + ♻️index(:ruuuby_releases, :version) + ♻️index(:ruuuby_features, :uid) + ♻️index(:ruuuby_feature_behaviors, :uid) + + ♻️table!(:ruuuby_gem_changelogs) + ♻️table!(:ruuuby_gems) + ♻️table!(:ruuuby_releases) + ♻️table!(:ruuuby_feature_behaviors) + ♻️table!(:ruuuby_features) execute(self.read_sql_rollback_file(DB_FILE_NAME)) end diff --git a/lib/ruuuby/db/migrations/ruuuby_resource.rb b/lib/ruuuby/db/migrations/ruuuby_resource.rb deleted file mode 100644 index a0334e0..0000000 --- a/lib/ruuuby/db/migrations/ruuuby_resource.rb +++ /dev/null @@ -1,59 +0,0 @@ -# encoding: UTF-8 - -#class CreateRuuubyGem < ActiveRecord::Migration[6.0] -class CreateUtils < RuuubyDBMigration - - DB_FILE_NAME = '00_utils.sql' - - def self.up - - create_table :ruuuby_tags do |t| - t.string :name, :null => false, :unique => true - end - - create_table :ruuuby_resource_types do |t| - t.string :name, :null => false, :unique => true - end - - create_table :ruuuby_resources do |t| - t.string :name, :null => false, :unique => true - t.json :content, :null => false, :unique => false - t.string :extra_str_data, :null => true, :unique => false - t.json :meta_data, :null => true, :unique => false - - t.references :ruuuby_resource_types, foreign_key: { references: :ruuuby_resource_types } - end - - create_table :ruuuby_resource_tags do |t| - t.references :ruuuby_resources, foreign_key: { references: :ruuuby_resources } - t.references :ruuuby_tags, foreign_key: { references: :ruuuby_tags } - end - - execute(self.read_sql_rollout_file(DB_FILE_NAME)) - execute(self.read_sql_seed_file(DB_FILE_NAME)) - end - - def self.down - drop_table :ruuuby_resource_tags - drop_table :ruuuby_tags - drop_table :ruuuby_resources - drop_table :ruuuby_resource_types - - #ActiveRecord::StatementInvalid - - execute(self.read_sql_rollback_file(DB_FILE_NAME)) - end - -end - -#ActiveRecord::Base.connection.execute(sql) - -class ::RuuubyResources < ::ApplicationRecord - - # @param [String] gem_name - def self.[](name) - 🛑str❓('name', gem_name) - ::RuuubyResources.where('name = ?', [gem_name]).limit(1).first - end - -end diff --git a/lib/ruuuby/db/migrations/seed/01_ruuuby_gem.sql b/lib/ruuuby/db/migrations/seed/00_ruuuby_gem.sql similarity index 90% rename from lib/ruuuby/db/migrations/seed/01_ruuuby_gem.sql rename to lib/ruuuby/db/migrations/seed/00_ruuuby_gem.sql index 6c38e88..72df09f 100644 --- a/lib/ruuuby/db/migrations/seed/01_ruuuby_gem.sql +++ b/lib/ruuuby/db/migrations/seed/00_ruuuby_gem.sql @@ -66,6 +66,7 @@ CALL ruuuby_release_add('0.0.49'); CALL ruuuby_release_add('0.1.0.pre.0'); CALL ruuuby_release_add('0.1.0.pre.1'); CALL ruuuby_release_add('0.1.0.pre.2'); +CALL ruuuby_release_add('0.1.0.pre.3'); -- ___ __ -- /'___\ /\ \__ @@ -77,7 +78,14 @@ CALL ruuuby_release_add('0.1.0.pre.2'); CALL ruuuby_feature_add('f00', FALSE, '`η̂` to alias concept of `normalization` (offered in any applicable context)'); + +CALL ruuuby_feature_add('f40', TRUE, 'provide an `API` for `Docker` operations w/ a light layer over gem{`docker-api`}'); +CALL ruuuby_feature_add('f41', TRUE, 'provide an `API` for `Brew` operations'); +CALL ruuuby_feature_add('f42', TRUE, 'provide an `API` for `RabbitMQ` operations w/ a light layer over gem{`bunny`}'); CALL ruuuby_feature_add('f43', TRUE, 'provide an `API` for `Iconv`'); +CALL ruuuby_feature_add('f44', TRUE, 'provide an `API` for `ZSH`'); +CALL ruuuby_feature_add('f46', TRUE, 'provide an `API` for `Bundler`'); +CALL ruuuby_feature_add('f47', TRUE, 'provide an `API` for `Gem`'); CALL ruuuby_feature_add('f92', TRUE, 'enable building with specific DB support loaded'); CALL ruuuby_feature_add('f93', TRUE, 'offer help in managing custom scripts, functionality, and anything else needed for too niche of scenarios to consider adding as a feature or even a conditionally-loadable feature'); @@ -176,4 +184,14 @@ CALL ruuuby_gem_update('0.1.0.pre.1', 'rspec', '3.10.0'); CALL ruuuby_gem_update('0.1.0.pre.2', 'activerecord', '6.1.0.rc1'); +CALL ruuuby_gem_add_dev('0.1.0.pre.3', 'open3', '0.1.0'); + +-- --------------------------------------------------------------------------------------------------------------------- + +INSERT INTO ruuuby_tags (name) VALUES ('finance'); +INSERT INTO ruuuby_tags (name) VALUES ('dev-tool'); +INSERT INTO ruuuby_tags (name) VALUES ('dev-url'); + +INSERT INTO ruuuby_resource_types (name) VALUES ('URL'); + COMMIT TRANSACTION; diff --git a/lib/ruuuby/db/migrations/seed/00_utils.sql b/lib/ruuuby/db/migrations/seed/00_utils.sql deleted file mode 100644 index 5ae51bc..0000000 --- a/lib/ruuuby/db/migrations/seed/00_utils.sql +++ /dev/null @@ -1,14 +0,0 @@ - --- -------------------------------------------- ⚠️ -------------------------------------------- --- testing purposes --- -------------------------------------------- ⚠️ -------------------------------------------- - -BEGIN TRANSACTION; - -INSERT INTO ruuuby_tags (name) VALUES ('finance'); -INSERT INTO ruuuby_tags (name) VALUES ('dev-tool'); -INSERT INTO ruuuby_tags (name) VALUES ('dev-url'); - -INSERT INTO ruuuby_resource_types (name) VALUES ('URL'); - -COMMIT TRANSACTION; diff --git a/lib/ruuuby/db/model_attributes/application_record.rb b/lib/ruuuby/db/model_attributes/application_record.rb index e502b6d..7fa1ebf 100644 --- a/lib/ruuuby/db/model_attributes/application_record.rb +++ b/lib/ruuuby/db/model_attributes/application_record.rb @@ -17,6 +17,8 @@ class ::ApplicationRecord < ActiveRecord::Base alias_method :♻️, :destroy alias_method :♻️!, :destroy! + alias_method :💾, :save + alias_method :💾!, :save! # @return [Integer] def self.length; self.all.length; end diff --git a/lib/ruuuby/db/seeds/ruuuby_feature_behaviors.rb b/lib/ruuuby/db/seeds/ruuuby_feature_behaviors.rb index fa1f055..ae89bb0 100644 --- a/lib/ruuuby/db/seeds/ruuuby_feature_behaviors.rb +++ b/lib/ruuuby/db/seeds/ruuuby_feature_behaviors.rb @@ -149,16 +149,6 @@ ] ) -@f34.spawn_behaviors( - [ - 'offer basic abstractions to `Shape`', - 'offer basic abstractions to `Shape::PlaneFigure`', - 'offer basic abstractions to `Shape::Triangle`', - 'offer basic abstractions to `Shape::Quadrilateral`', - 'offer basic abstractions to `Shape::Circle`', - ] -) - @f35.spawn_behaviors( [ 'offer categorical abstractions w/ module{`Descriptive`}', diff --git a/lib/ruuuby/db/seeds/ruuuby_features.rb b/lib/ruuuby/db/seeds/ruuuby_features.rb index 60a1c7d..0e80543 100644 --- a/lib/ruuuby/db/seeds/ruuuby_features.rb +++ b/lib/ruuuby/db/seeds/ruuuby_features.rb @@ -33,12 +33,9 @@ @f31 = ::RuuubyFeature.spawn(31, 'provide an `API` for `GIT` operations w/ a light layer over gem{`rugged`}', 2, %w(ruuuby engine git api)) @f32 = ::RuuubyFeature.spawn(32, 'abstract `NumberTheory`; offering static math functions', 2, %w(math number-theory)) @f33 = ::RuuubyFeature.spawn(33, 'abstract `Combinatorics`; offering static math functions', 2, %w(math combinatorics)) -@f34 = ::RuuubyFeature.spawn(34, 'abstract `Geometry`; offering static math functions; esp. those for `Shapes`', 2, %w(math geometry)) + @f35 = ::RuuubyFeature.spawn(35, 'abstract `Statistics`; offering static math functions', 2, %w(math statistics stats)) @f36 = ::RuuubyFeature.spawn(36, 'add new class (`TimeSeriesData`) for easier operations involving multi-sample based stats', 2, %w(math stats time-series data)) @f37 = ::RuuubyFeature.spawn(37, 'abstract `GraphTheory`; offering static math functions and custom `Graph classes`', 2, %w(math graph-theory graphs)) @f38 = ::RuuubyFeature.spawn(38, 'abstract `Tropical Algebra`; offering static math functions and `Refinements` for specific classes', 2, %w(math tropical-algebra tropical algebra)) @f39 = ::RuuubyFeature.spawn(39, "offer a light wrapper over `Ruby's` default web-based-protocol requests", 2, %w(web http socket https websocket)) -@f40 = ::RuuubyFeature.spawn(40, 'provide an `API` for `Docker` operations w/ a light layer over gem{`docker-api`}', 2, %w(api docker)) -@f41 = ::RuuubyFeature.spawn(41, 'provide an `API` for `Brew` operations', 2, %w(api brew)) -@f42 = ::RuuubyFeature.spawn(42, 'provide an `API` for `RabbitMQ` operations w/ a light layer over gem{`bunny`}', 2, %w(api rabbitmq rabbit)) diff --git a/lib/ruuuby/math/algebra/tropical/context_matrix.rb b/lib/ruuuby/math/algebra/tropical/context_matrix.rb index 3688b42..87dc629 100644 --- a/lib/ruuuby/math/algebra/tropical/context_matrix.rb +++ b/lib/ruuuby/math/algebra/tropical/context_matrix.rb @@ -3,84 +3,80 @@ using ::Math::Algebra::Tropical::ContextNumeric using ::Matrix::ContextParamCheck -module ::Math - module Algebra - module Tropical - module ContextMatrix - refine ::Matrix do +module ::Math::Algebra::Tropical + module ContextMatrix + refine ::Matrix do - # @note source-code heavily mimicked from `Matrix's` func{`+`} - # - # @return [Matrix] m - def ⨁(m) - 🛑matrix❓('m', m) - 🛑 ::ExceptionForMatrix::ErrDimensionMismatch unless self.num_rows == m.num_rows && self.num_cols == m.num_cols - rows = ::Array.new(self.num_rows) {|i| - ::Array.new(self.num_cols) {|j| - self[i, j].⨁(m[i, j]) - } - } - self.new_matrix(rows, m.num_cols) - end + # @note source-code heavily mimicked from `Matrix's` func{`+`} + # + # @return [Matrix] m + def ⨁(m) + 🛑matrix❓('m', m) + 🛑 ::ExceptionForMatrix::ErrDimensionMismatch unless self.num_rows == m.num_rows && self.num_cols == m.num_cols + rows = ::Array.new(self.num_rows) { |i| + ::Array.new(self.num_cols) { |j| + self[i, j].⨁(m[i, j]) + } + } + self.new_matrix(rows, m.num_cols) + end - # @param [Matrix] m - # - # @raise [ArgumentError, ::ExceptionForMatrix::ErrDimensionMismatch] - # - # @return [Matrix] self - def ⨁!(m) - 🛑matrix❓('m', m) - 🛑 ::ExceptionForMatrix::ErrDimensionMismatch unless self.num_rows == m.num_rows && self.num_cols == m.num_cols - self.∀ₓᵢⱼ{|x,i,j| self[i,j] = x.⨁(m[i,j])} - end + # @param [Matrix] m + # + # @raise [ArgumentError, ::ExceptionForMatrix::ErrDimensionMismatch] + # + # @return [Matrix] self + def ⨁!(m) + 🛑matrix❓('m', m) + 🛑 ::ExceptionForMatrix::ErrDimensionMismatch unless self.num_rows == m.num_rows && self.num_cols == m.num_cols + self.∀ₓᵢⱼ { |x, i, j| self[i, j] = x.⨁(m[i, j]) } + end - # @param [Integer] n - # - # @raise [ArgumentError] - # - # @return [Matrix] - def ⨂ⁿ(n) - 🛑int❓('n', n) - 🛑 ::ArgumentError.new("| func{⨂ⁿ} expected arg(n) to have value >= 2, instead received value{#{n.to_s}} |") unless n >= 2 - i = 2 - result = self.⨂(self) - while i < n - prev = result - result = self.⨂(prev) - i += 1 - end - result - end + # @param [Integer] n + # + # @raise [ArgumentError] + # + # @return [Matrix] + def ⨂ⁿ(n) + 🛑int❓('n', n) + 🛑 ::ArgumentError.new("| func{⨂ⁿ} expected arg(n) to have value >= 2, instead received value{#{n.to_s}} |") unless n >= 2 + i = 2 + result = self.⨂(self) + while i < n + prev = result + result = self.⨂(prev) + i += 1 + end + result + end - # @note source-code heavily mimicked from `Matrix's` func{`*`} - # - # @param [Matrix, Numeric, Integer, Float] m - # - # @return [Matrix] m - def ⨂(m) - if m.num? - return m.⨂(self) + # @note source-code heavily mimicked from `Matrix's` func{`*`} + # + # @param [Matrix, Numeric, Integer, Float] m + # + # @return [Matrix] m + def ⨂(m) + if m.num? + return m.⨂(self) + end + 🛑matrix❓('m', m) + 🛑 ::ExceptionForMatrix::ErrDimensionMismatch if self.num_cols != m.num_rows + rows = ::Array.new(self.num_rows) { |i| + ::Array.new(m.num_cols) { |j| + chunks = [] + (0...self.num_cols).each do |c| + curr_val = self[i, c] + val_them = m[c, j] + chunks << curr_val.⨂(val_them) end - 🛑matrix❓('m', m) - 🛑 ::ExceptionForMatrix::ErrDimensionMismatch if self.num_cols != m.num_rows - rows = ::Array.new(self.num_rows) {|i| - ::Array.new(m.num_cols) {|j| - chunks = [] - (0...self.num_cols).each do |c| - curr_val = self[i, c] - val_them = m[c, j] - chunks << curr_val.⨂(val_them) - end - local_sums = [] - chunks.∀τ²∈λ𝑓₍ᵢ،ᵢ₊₁₎{|prev, curr| local_sums << prev.⨁(curr)} - local_sums.max - } - } - self.new_matrix(rows, m.num_cols) - end + local_sums = [] + chunks.∀τ²∈λ𝑓₍ᵢ،ᵢ₊₁₎ { |prev, curr| local_sums << prev.⨁(curr) } + local_sums.max + } + } + self.new_matrix(rows, m.num_cols) + end - end # end: {refine ::Matrix} - end # end: {ContextMatrix} - end # end: {Tropical} - end # end: {Algebra} + end # end: {refine ::Matrix} + end # end: {ContextMatrix} end # end: {Math} diff --git a/lib/ruuuby/math/algebra/tropical/context_numeric.rb b/lib/ruuuby/math/algebra/tropical/context_numeric.rb index cf5bc14..b47b928 100644 --- a/lib/ruuuby/math/algebra/tropical/context_numeric.rb +++ b/lib/ruuuby/math/algebra/tropical/context_numeric.rb @@ -1,73 +1,69 @@ # encoding: UTF-8 -module ::Math - module Algebra +# @see https://en.wikipedia.org/wiki/Tropical_geometry +# @see https://en.wikipedia.org/wiki/Tropical_semiring +# @see https://en.wikipedia.org/wiki/Algebraic_structure +# +# @note geometry aspects will not be primary focus in this module +# +# "the study of polynomials and their `geometric properties` when addition is replaced with minimization and multiplication is replaced with ordinary addition" +# +# ‣ standard multiplication{`*`} is transformed to{`⨂`}: `x ⨂ y = x + y` +# ‣ standard addition(`+`) is transformed to{`⨁`} w/ 2 versions: +# +# | name | definition | additive identity | +# | ------------------ | -------------------- | ----------------- | +# | `min-plus algebra` | `x ⨁ y = min{x, y}` | `∞` | +# | `max-plus algebra` | `x ⨁ y = max{x, y}` | `−∞` | +# +# ‣ "unit for ⨁ is +∞, and the unit for ⨂ is 0" +# ‣ `tropical addition` is `commutative`: `∀ a,b ∈ ℝ max(a, b) = max(b, a)` +# ‣ `tropical addition` is `associative`: `∀ a,b ∈ ℝ max(max(a, b), c) = max(max(a, c), b)` +# ‣ `tropical multiplication` is `commutative` and `associative ∈ ℝ` +# ‣ `tropical multiplication` is `distributive` +# ‣ `additive inverse` DNE as ∀ element does not necessarily have a matching element that when summed, equal the `additive identity` +# ‣ (as -∞ is < ∀ element other than -∞; thus, won't be returned from func{`max`}) +# +# ‣ "`eigenvalue-eigenvector` pair `λ` and `x` for a given matrix `A` satisfy the equation `Ax = λx` where `λ ∈ ℝ, A ∈ ℝⁿˣⁿ`, and `x ∈ ℝⁿ`" +# +# ‣ `normalized weight of a cycle` = `sum of edge weights` / `number of edges` +# +# ‣ `tropical algebra` is a `semi-ring` +# ‣ "given by `(ℝᴹᴬˣ,⨁,⨂) where ℝᴹᴬˣ = ℝ∪{−∞}`" +module ::Math::Algebra::Tropical - # @see https://en.wikipedia.org/wiki/Tropical_geometry - # @see https://en.wikipedia.org/wiki/Tropical_semiring - # @see https://en.wikipedia.org/wiki/Algebraic_structure - # - # @note geometry aspects will not be primary focus in this module - # - # "the study of polynomials and their `geometric properties` when addition is replaced with minimization and multiplication is replaced with ordinary addition" - # - # ‣ standard multiplication{`*`} is transformed to{`⨂`}: `x ⨂ y = x + y` - # ‣ standard addition(`+`) is transformed to{`⨁`} w/ 2 versions: - # - # | name | definition | additive identity | - # | ------------------ | -------------------- | ----------------- | - # | `min-plus algebra` | `x ⨁ y = min{x, y}` | `∞` | - # | `max-plus algebra` | `x ⨁ y = max{x, y}` | `−∞` | - # - # ‣ "unit for ⨁ is +∞, and the unit for ⨂ is 0" - # ‣ `tropical addition` is `commutative`: `∀ a,b ∈ ℝ max(a, b) = max(b, a)` - # ‣ `tropical addition` is `associative`: `∀ a,b ∈ ℝ max(max(a, b), c) = max(max(a, c), b)` - # ‣ `tropical multiplication` is `commutative` and `associative ∈ ℝ` - # ‣ `tropical multiplication` is `distributive` - # ‣ `additive inverse` DNE as ∀ element does not necessarily have a matching element that when summed, equal the `additive identity` - # ‣ (as -∞ is < ∀ element other than -∞; thus, won't be returned from func{`max`}) - # - # ‣ "`eigenvalue-eigenvector` pair `λ` and `x` for a given matrix `A` satisfy the equation `Ax = λx` where `λ ∈ ℝ, A ∈ ℝⁿˣⁿ`, and `x ∈ ℝⁿ`" - # - # ‣ `normalized weight of a cycle` = `sum of edge weights` / `number of edges` - # - # ‣ `tropical algebra` is a `semi-ring` - # ‣ "given by `(ℝᴹᴬˣ,⨁,⨂) where ℝᴹᴬˣ = ℝ∪{−∞}`" - module Tropical - module ContextNumeric - refine ::Numeric do + module ContextNumeric + refine ::Numeric do - # @param [Integer, Float] m - # - # @return [ArgumentError] - # - # @return [Integer, Float] - def ⨁(m) - 🛑num❓('m', m) - self >= m ? self : m - end + # @param [Integer, Float] m + # + # @return [ArgumentError] + # + # @return [Integer, Float] + def ⨁(m) + 🛑num❓('m', m) + self >= m ? self : m + end - # @param [Integer, Float, Numeric, Matrix] m - # - # @return [ArgumentError] - # - # @return [Integer, Float] - def ⨂(m) - if m.matrix? - rows = ::Array.new(m.num_rows) {|i| - ::Array.new(m.num_cols) {|j| - m[i, j] + self - } - } - ::Matrix[*rows] - else - 🛑num❓('m', m) - self + m - end - end + # @param [Integer, Float, Numeric, Matrix] m + # + # @return [ArgumentError] + # + # @return [Integer, Float] + def ⨂(m) + if m.matrix? + rows = ::Array.new(m.num_rows) {|i| + ::Array.new(m.num_cols) {|j| + m[i, j] + self + } + } + ::Matrix[*rows] + else + 🛑num❓('m', m) + self + m + end + end - end # end: {refine ::Numeric} - end # end: {module ContextNumeric} - end # end: {module Tropical} - end + end # end: {refine ::Numeric} + end # end: {module ContextNumeric} end diff --git a/lib/ruuuby/math/complex_analysis/complex_analysis.rb b/lib/ruuuby/math/complex_analysis/complex_analysis.rb deleted file mode 100644 index 7025f92..0000000 --- a/lib/ruuuby/math/complex_analysis/complex_analysis.rb +++ /dev/null @@ -1,13 +0,0 @@ -# encoding: UTF-8 - -# mathematics related code -module ::Math - - # @see https://en.wikipedia.org/wiki/Complex_plane - # - # "multiplication by a complex number of modulus{1} acts as a rotation" - module ComplexAnalysis - - end - -end diff --git a/lib/ruuuby/math/expr/equation.rb b/lib/ruuuby/math/expr/equation.rb deleted file mode 100644 index 6e53a0a..0000000 --- a/lib/ruuuby/math/expr/equation.rb +++ /dev/null @@ -1,20 +0,0 @@ -# encoding: UTF-8 - -# mathematics related code -module ::Math - - module Expr - - # a declaration that `LHS` = `RHS` - class Equation - - def initialize(*args) - @all_args = args - @context = nil - end - - end - - end - -end diff --git a/lib/ruuuby/math/expr/expression.rb b/lib/ruuuby/math/expr/expression.rb deleted file mode 100644 index 5d0028c..0000000 --- a/lib/ruuuby/math/expr/expression.rb +++ /dev/null @@ -1,36 +0,0 @@ -# encoding: UTF-8 - -# mathematics related code -module ::Math - - module Expr - # a singular 'mathematical object', in `Ruuuby` context, something that can be evaluated given content and a context - # - # @see https://en.wikipedia.org/wiki/Expression_(mathematics) - # @see https://en.wikipedia.org/wiki/Well-formed_formula - class AbstractExpression - - def initialize(*args) - @all_args = args - @context = nil - end - - end - - # terminology: - # - variables/indeterminates: "a symbol that is treated as a variable" - # - coefficients: "a multiplicative factor in some term of a polynomial, a series, or any expression" - # - monic polynomial: a polynomial w/ a coefficient of 1 for the highest order term - # - # - # involves only the following operations: - # - addition[+] - # - subtraction[-] - # - multiplication[*] - # - non-negative integer exponents of variables - class Polynomial < AbstractExpression - - end - end - -end diff --git a/lib/ruuuby/math/expr/math_func.rb b/lib/ruuuby/math/expr/math_func.rb deleted file mode 100644 index c2bc967..0000000 --- a/lib/ruuuby/math/expr/math_func.rb +++ /dev/null @@ -1,62 +0,0 @@ -# encoding: UTF-8 - -# mathematics related code -module ::Math - - module Expr - - # - a statement on some 'mathematical object(s)' - # - a mapping of some input to some output - # - # also refer to as `Formula` - class MathFunc - - def initialize(*args) - @all_args = args - @context = nil - end - - end - - end - -end - -# to be extended upon in future versions - -# -------------------------------------------- ⚠️ -------------------------------------------- - -=begin -# layer over existing class +Method+ for meta-data purposes (not for runtime) -class ::MathFunction < ::Method - - attr_reader :source_method - - def initialize(source_method, category) - @source_method = source_method - @category = category - end - - # a func, f, is periodic if there can exist a such that f(x + a) = f(x) for all x - def periodic? - - # @example - # - # cos(-x) = cos(x) - # sec(-x) = sec(x) - def even? - - # @example - # - # sin(-x) = -sin(x) - # csc(-x) = -csc(x) - # tan(-x) = -tan(x) - # cot(-x) = -cot(x) - def odd? - -end -=end - -# -------------------------------------------- ⚠️ -------------------------------------------- - -# TODO: https://mathworld.wolfram.com/DirichletFunction.html diff --git a/lib/ruuuby/math/expr/seq/arithmetic.rb b/lib/ruuuby/math/expr/seq/arithmetic.rb deleted file mode 100644 index 815dd60..0000000 --- a/lib/ruuuby/math/expr/seq/arithmetic.rb +++ /dev/null @@ -1,19 +0,0 @@ -# encoding: UTF-8 - -# mathematics related code -module ::Math - - module Expr - - # "the difference between one term and the next is a constant" - class ArithmeticSequence < Sequence - # TODO: add gauss formula here (work w/ any arithmetic series, not just {1, 2, 3...n}) - - def initialize(max_cache_index, input_type) - super(max_cache_index, input_type) - end - - end - - end -end diff --git a/lib/ruuuby/math/expr/seq/geometric.rb b/lib/ruuuby/math/expr/seq/geometric.rb deleted file mode 100644 index fe9477f..0000000 --- a/lib/ruuuby/math/expr/seq/geometric.rb +++ /dev/null @@ -1,18 +0,0 @@ -# encoding: UTF-8 - -# mathematics related code -module ::Math - - module Expr - - # "each term is found by multiplying the previous term by a constant" - class GeometricSequence < Sequence - - def initialize(max_cache_index, input_type) - super(max_cache_index, input_type) - end - - end - - end -end diff --git a/lib/ruuuby/math/expr/seq/recursive.rb b/lib/ruuuby/math/expr/seq/recursive.rb deleted file mode 100644 index b8ccc4e..0000000 --- a/lib/ruuuby/math/expr/seq/recursive.rb +++ /dev/null @@ -1,19 +0,0 @@ -# encoding: UTF-8 - -# mathematics related code -module ::Math - - module Expr - - # "each term is dependent on the values of the previous N terms" - class RecursiveSequence < Sequence - - def initialize(max_cache_index, input_type) - super(max_cache_index, input_type) - end - - end - - end - -end diff --git a/lib/ruuuby/math/expr/seq/sequence.rb b/lib/ruuuby/math/expr/sequence.rb similarity index 99% rename from lib/ruuuby/math/expr/seq/sequence.rb rename to lib/ruuuby/math/expr/sequence.rb index 02e741a..da22a48 100644 --- a/lib/ruuuby/math/expr/seq/sequence.rb +++ b/lib/ruuuby/math/expr/sequence.rb @@ -96,4 +96,3 @@ def populate_cache end end - diff --git a/lib/ruuuby/math/geometry/shape/circle.rb b/lib/ruuuby/math/geometry/shape/circle.rb deleted file mode 100644 index 28e3c49..0000000 --- a/lib/ruuuby/math/geometry/shape/circle.rb +++ /dev/null @@ -1,30 +0,0 @@ -# encoding: UTF-8 - -# -------------------------------------------- ⚠️ -------------------------------------------- - -# mathematics related code -module ::Math - - # geometry related code - module Geometry - - # ● - class Circle < PlaneFigure - - def initialize(radius) - @radius = radius - @num_sides = ::Float::INFINITY - super() - end - - undef_method :sum_of_interior_angles - - def sum_of_interior_angles; ::ThetaAngle.new_degree(360); end - - end - - end - -end - -# -------------------------------------------- ⚠️ -------------------------------------------- diff --git a/lib/ruuuby/math/geometry/shape/plane_figure.rb b/lib/ruuuby/math/geometry/shape/plane_figure.rb deleted file mode 100644 index d05b4e4..0000000 --- a/lib/ruuuby/math/geometry/shape/plane_figure.rb +++ /dev/null @@ -1,32 +0,0 @@ -# encoding: UTF-8 - -# -------------------------------------------- ⚠️ -------------------------------------------- - -# mathematics related code -module ::Math - - # geometry related code - module Geometry - - class PlaneFigure < Shape - - attr_reader :num_sides - - # volume - # diameter - # num_sides - # interior angles - - def initialize - super() - end - - # @return [ThetaAngle] - def sum_of_interior_angles; ::ThetaAngle.new_degree(180.0 * (@num_sides - 2)); end - - end - - end -end - -# -------------------------------------------- ⚠️ -------------------------------------------- diff --git a/lib/ruuuby/math/geometry/shape/quadrilateral.rb b/lib/ruuuby/math/geometry/shape/quadrilateral.rb deleted file mode 100644 index a83f224..0000000 --- a/lib/ruuuby/math/geometry/shape/quadrilateral.rb +++ /dev/null @@ -1,59 +0,0 @@ -# encoding: UTF-8 - -# -------------------------------------------- ⚠️ -------------------------------------------- - -# mathematics related code -module ::Math - - # geometry related code - module Geometry - - # has `4 edges` and `4 vertices` - class Quadrilateral < PlaneFigure - - def initialize - @num_sides = 4 - end - - # @return [Integer, Float] - def area; @length * @height; end - - end - - # ▬ - class Rectangle < Quadrilateral - - # @param [Integer, Float] length - # @param [Integer, Float] height - def initialize(length, height) - @length = length - @height = height - super() - end - - # @return [Array] - def interior_angles - if @angles.nil? - corner_angle = θ°(90) - @angles = [corner_angle, corner_angle, corner_angle, corner_angle] - end - @angles - end - - # TODO: def func{golden?} - end - - class Square < Rectangle - - # @param [Integer, Float] length - def initialize(length) - super(length, length) - end - - end - - end - -end - -# -------------------------------------------- ⚠️ -------------------------------------------- diff --git a/lib/ruuuby/math/geometry/shape/shape.rb b/lib/ruuuby/math/geometry/shape/shape.rb deleted file mode 100644 index 9f4028a..0000000 --- a/lib/ruuuby/math/geometry/shape/shape.rb +++ /dev/null @@ -1,31 +0,0 @@ -# encoding: UTF-8 - -# -------------------------------------------- ⚠️ -------------------------------------------- - -# mathematics related code -module ::Math - - # geometry related code - module Geometry - - # @see https://en.wikipedia.org/wiki/Shape - # - # comparable in the following ways: - # ‣ congruence - # ‣ similarity - # ‣ isotopy - # - # ● ◆ ▲ ▬ ▰ - # - # `solid-figure` - class Shape - - def initialize - end - - end - - end -end - -# -------------------------------------------- ⚠️ -------------------------------------------- diff --git a/lib/ruuuby/math/geometry/shape/sphere.rb b/lib/ruuuby/math/geometry/shape/sphere.rb deleted file mode 100644 index 0b92f54..0000000 --- a/lib/ruuuby/math/geometry/shape/sphere.rb +++ /dev/null @@ -1,20 +0,0 @@ -# encoding: UTF-8 - -# -------------------------------------------- ⚠️ -------------------------------------------- - -# mathematics related code -module ::Math - - # geometry related code - module Geometry - - class Sphere < ::Math::Geometry::Shape - end - - # TODO: unit-sphere: [0, 4π] - - end - -end - -# -------------------------------------------- ⚠️ -------------------------------------------- diff --git a/lib/ruuuby/math/geometry/shape/triangle.rb b/lib/ruuuby/math/geometry/shape/triangle.rb deleted file mode 100644 index 9ebef6f..0000000 --- a/lib/ruuuby/math/geometry/shape/triangle.rb +++ /dev/null @@ -1,152 +0,0 @@ -# encoding: UTF-8 - -# -------------------------------------------- ⚠️ -------------------------------------------- - -# mathematics related code -module ::Math - - # geometry related code - module Geometry - - # ▲ - class Triangle < PlaneFigure - - attr_accessor :angle_a, :angle_b, :angle_c - attr_reader :side_a, :side_b, :side_c - - # @return [Math::Geometry::Triangle] - def self.new_equilateral(side_length); ::Math::Geometry::Triangle.new(side_length, side_length, side_length); end - - def golden? - if self.isosceles? - if @side_a == @side_b - @side_a / @side_c == ::Float::RATIO_GOLDEN - else - @side_a / @side_b == ::Float::RATIO_GOLDEN - end - else - false - end - end - - # @return [Boolean] true, if this triangle has `3` sides equal in length - def equilateral?; @side_a == @side_b && @side_b == @side_c; end - - # @return [Boolean] true, if this triangle has `3` sides equal in length - def equiangular?; @angle_a == @angle_b && @angle_b == @angle_c; end - - # @return [Boolean] true, if this triangle has `2` sides equal in length - def isosceles?; !self.equilateral? && (@side_a == @side_b || @side_b == @side_c || @side_a == @side_c); end - - # @return [Boolean] true, if this triangle has no sides equal in length - def scalene?; @side_a != @side_b && @side_b != @side_c && @side_a != @side_c; end - - # @return [Boolean] ‣ if `a² + b² > c²`, then the triangle is `acute` - def acute? - a²_b² = (@side_a ** 2) + (@side_c ** 2) - c² = @side_c ** 2 - if a²_b² < c² - true - else - if @angle_a.° + @angle_b.° + @angle_c.° == 180.0 - return @angle_a.⦟? && @angle_b.⦟? && @angle_c.⦟? - else - return false - end - end - end - - # @return [Boolean] ‣ if `a² + b² < c²`, then the triangle is `obtuse` - def obtuse? - a²_b² = (@side_a ** 2) + (@side_b ** 2) - c² = @side_c ** 2 - if a²_b² > c² - true - else - if @angle_a.° + @angle_b.° + @angle_c.° == 180.0 - return @angle_a.⦦? || @angle_b.⦦? || @angle_c.⦦? - else - return false - end - end - end - - # @return [Boolean] ‣ if `a² + b² = c²`, then the triangle is `right` - def ◣? - a²_b² = (@side_a ** 2) + (@side_c ** 2) - c² = @side_c ** 2 - if a²_b² == c² - true - else - angle_a = @angle_a.° - angle_b = @angle_b.° - angle_c = @angle_c.° - if angle_a + angle_b + angle_c == 180.0 - return (angle_a == 90.0 || angle_b == 90.0 || angle_c == 90.0) - else - return false - end - end - end - - # `angle_A` is opposite of `side_a` - # `angle_B` is opposite of `side_b` - # `angle_C` is opposite of `side_c` - # - # law of sines: `a/sin(A)` = `b/sin(B)` = `c/sin(C)` - def initialize(side_a, side_b, side_c) - @side_a = side_a - @side_b = side_b - @side_c = side_c - @num_sides = 3 - if @side_a == @side_b && @side_a == @side_c - @longest_val = @side_a - @angle_a = ::ThetaAngle.new_degree(60) - @angle_b = ::ThetaAngle.new_degree(60) - @angle_c = ::ThetaAngle.new_degree(60) - else - @longest_val = [@side_a, @side_b, @side_c].max - @angle_a = ::ThetaAngle.new_radian(::Math.acos(( ((@side_b ** 2) + (@side_c ** 2) - (@side_a ** 2)) / (2.0 * @side_b * @side_c) ))) - @angle_b = ::ThetaAngle.new_radian(::Math.acos(( ((@side_c ** 2) + (@side_a ** 2) - (@side_b ** 2)) / (2.0 * @side_c * @side_a) ))) - #@angle_c = θʳ(::Math.acos(( ((@side_a ** 2) + (@side_b ** 2) + (@side_c ** 2)) / (2.0 * @side_a * @side_b) ))) - @angle_c = ::ThetaAngle.new_degree(180.0) - (@angle_a + @angle_b) - #@angle_c = θʳ(::Math.acos(((@side_a ** 2 + @side_b ** 2 + @side_c ** 2) / (2.0 * @side_a * @side_b)))) - end - super() - end - - def perimeter - if self.equilateral? - @longest_val * 3 - else - @side_a + @side_b + @side_c - end - end - - def height - if self.scalene? - # either - #@side_b * ::Math.asin(@angle_c) - @side_c * ::Math.sin(@angle_b) - end - end - - def area - if self.equiangular? - (::Math.sqrt(3.0) / 4.0) * (@side_a ** 2) - elsif self.scalene? - (@side_a + @side_b + @side_c) / 2.0 - else - 1337 - end - end - - end - - end -end - -# TODO: https://mathworld.wolfram.com/Cevian.html -# TODO: https://mathworld.wolfram.com/TriangleMedian.html - -# -------------------------------------------- ⚠️ -------------------------------------------- diff --git a/lib/ruuuby/math/number_theory/number_theory.rb b/lib/ruuuby/math/number_theory/number_theory.rb index 98d0ef4..1764394 100644 --- a/lib/ruuuby/math/number_theory/number_theory.rb +++ b/lib/ruuuby/math/number_theory/number_theory.rb @@ -23,396 +23,390 @@ def ≡(b: ∞, mod: ∞) using ::Math::NumberTheory::ℤ³ -# mathematics related code -module ::Math - - # @see: https://en.wikipedia.org/wiki/Number_theory +# @see: https://en.wikipedia.org/wiki/Number_theory +# +# vocab: +# - | `ordinal numbers` | "is one generalization of the concept of a natural number that is used to describe a way to arrange a (possibly infinite) collection of objects in order, one after another" | +# +# math related code that can be categorized under +NumberTheory+ +module ::Math::NumberTheory + + # ==extension funcs: + # - semiprime? # - # vocab: - # - | `ordinal numbers` | "is one generalization of the concept of a natural number that is used to describe a way to arrange a (possibly infinite) collection of objects in order, one after another" | - # - # math related code that can be categorized under +NumberTheory+ - module NumberTheory + # equations within +NumberTheory+ that only involve 1-input (which belongs to the `natural-numbers`) + module ℕ¹ + attribute_lazy_loadable('prime', false) + + # vocab: + # - prime number: a natural-number that can't be created from the multiplication of other natural-numbers + # - factors: the numbers multiplied together resulting in another number + # - prime factorization: process of finding the prime numbers which multiply to equal some original number + # + # "the decomposition of a `composite number` into a product of smaller integers" + # + # @example + # prime factors of 76 are: 2² x 19¹ + # a = 76.prime_factors + # a == [[2, 2], [19, 1]] + # + # @param [Integer] n + # + # @raise [ArgumentError] if n is not ∈ ℕ + # + # @return [Array] + def self.prime_factors(n) + 🛑num❓('n', n, :∈ℕ) + self.ensure_lazy_loaded + ::Prime.prime_division(n) + end - # ==extension funcs: - # - semiprime? - - # equations within +NumberTheory+ that only involve 1-input (which belongs to the `natural-numbers`) - # - # TODO: sum of proper divisors{https://oeis.org/A001065} - module ℕ¹ - - attribute_lazy_loadable('prime', false) - - # vocab: - # - prime number: a natural-number that can't be created from the multiplication of other natural-numbers - # - factors: the numbers multiplied together resulting in another number - # - prime factorization: process of finding the prime numbers which multiply to equal some original number - # - # "the decomposition of a `composite number` into a product of smaller integers" - # - # @example - # prime factors of 76 are: 2² x 19¹ - # a = 76.prime_factors - # a == [[2, 2], [19, 1]] - # - # @param [Integer] n - # - # @raise [ArgumentError] if n is not ∈ ℕ - # - # @return [Array] - def self.prime_factors(n) - 🛑num❓('n', n, :∈ℕ) - self.ensure_lazy_loaded - ::Prime.prime_division(n) - end + # @see http://rosettacode.org/wiki/Factors_of_an_integer#Using_the_prime_library + # + # @param [Integer] n + # + # @raise [ArgumentError] if n is not ∈ ℕ + # + # @return [Array] + def self.divisors(n) + 🛑num❓('n', n, :∈ℕ) + return [1] if 1 == n + self.ensure_lazy_loaded + primes, powers = ::Prime.prime_division(n).transpose + ranges = powers.map{|m| (0..m).to_a} + ranges[0].product(*ranges[1..-1]).map{|es| primes.zip(es).map{|p,e| p**e}.reduce :*}.sort + end - # @see http://rosettacode.org/wiki/Factors_of_an_integer#Using_the_prime_library - # - # @param [Integer] n - # - # @raise [ArgumentError] if n is not ∈ ℕ - # - # @return [Array] - def self.divisors(n) - 🛑num❓('n', n, :∈ℕ) - return [1] if 1 == n - self.ensure_lazy_loaded - primes, powers = ::Prime.prime_division(n).transpose - ranges = powers.map{|m| (0..m).to_a} - ranges[0].product(*ranges[1..-1]).map{|es| primes.zip(es).map{|p,e| p**e}.reduce :*}.sort + # @param [Integer] n + # + # @raise [ArgumentError] if n is not ∈ ℕ + # + # @return [Array] the same result as +divisors+ but without `n` itself + def self.proper_divisors(n) + 🛑num❓('n', n, :∈ℕ) + if n == 1 + return [] + elsif n < 4 + return [1] + else + result = ::Math::NumberTheory::ℕ¹.divisors(n) + result[0...-1] end + end - # @param [Integer] n - # - # @raise [ArgumentError] if n is not ∈ ℕ - # - # @return [Array] the same result as +divisors+ but without `n` itself - def self.proper_divisors(n) - 🛑num❓('n', n, :∈ℕ) - if n == 1 - return [] - elsif n < 4 - return [1] - else - result = ::Math::NumberTheory::ℕ¹.divisors(n) - result[0...-1] - end - end + # @see https://oeis.org/A001065 + # + # @param [Integer] n + # + # @raise [ArgumentError] if n is not ∈ ℕ + # + # @return [Integer, Numeric] + def self.aliquot_sum(n) + 🛑num❓('n', n, :∈ℕ) + ::Math::NumberTheory::ℕ¹.proper_divisors(n).sum + end - # @param [Integer] n - # - # @raise [ArgumentError] if n is not ∈ ℕ - # - # @return [Integer, Numeric] - def self.aliquot_sum(n) - 🛑num❓('n', n, :∈ℕ) - ::Math::NumberTheory::ℕ¹.proper_divisors(n).sum - end + # @param [Integer] n + # + # @raise [ArgumentError] if n is not ∈ ℕ + # + # @return [Boolean] + def self.perfect?(n); ::Math::NumberTheory::ℕ¹.aliquot_sum(n) == n; end - # @param [Integer] n - # - # @raise [ArgumentError] if n is not ∈ ℕ - # - # @return [Boolean] - def self.perfect?(n); ::Math::NumberTheory::ℕ¹.aliquot_sum(n) == n; end - - # @param [Integer] n - # - # @raise [ArgumentError] if n is not ∈ ℕ - # - # @return [Boolean] - def self.almost_perfect?(n); ::Math::NumberTheory::ℕ¹.divisors(n).sum == n * 2 - 1; end - - # @param [Integer] n - # - # @raise [ArgumentError] if n is not ∈ ℕ - # - # @return [Boolean] - def self.abundant?(n); ::Math::NumberTheory::ℕ¹.aliquot_sum(n) > n; end - - # @param [Integer] n - # - # @raise [ArgumentError] if n is not ∈ ℕ OR n is not +abundant+ - # - # @return [Integer, Numeric] - def self.abundance(n) - if ::Math::NumberTheory::ℕ¹.abundant?(n) - ::Math::NumberTheory::ℕ¹.aliquot_sum(n) - n - else - 🛑 ArgumentError.new("| m{NumberTheory::ℕ¹}-> m{abundance} received arg(n) w/ value{#{n.to_s}} which is not `abundant` |") - end + # @param [Integer] n + # + # @raise [ArgumentError] if n is not ∈ ℕ + # + # @return [Boolean] + def self.almost_perfect?(n); ::Math::NumberTheory::ℕ¹.divisors(n).sum == n * 2 - 1; end + + # @param [Integer] n + # + # @raise [ArgumentError] if n is not ∈ ℕ + # + # @return [Boolean] + def self.abundant?(n); ::Math::NumberTheory::ℕ¹.aliquot_sum(n) > n; end + + # @param [Integer] n + # + # @raise [ArgumentError] if n is not ∈ ℕ OR n is not +abundant+ + # + # @return [Integer, Numeric] + def self.abundance(n) + if ::Math::NumberTheory::ℕ¹.abundant?(n) + ::Math::NumberTheory::ℕ¹.aliquot_sum(n) - n + else + 🛑 ArgumentError.new("| m{NumberTheory::ℕ¹}-> m{abundance} received arg(n) w/ value{#{n.to_s}} which is not `abundant` |") end + end - # @param [Integer] n - # - # @raise [ArgumentError] if n is not ∈ ℕ OR n is not +abundant+ - # - # @return [Rational] - def self.abundancy_index(n) - if ::Math::NumberTheory::ℕ¹.abundant?(n) - Rational(::Math::NumberTheory::ℕ¹.aliquot_sum(n), n) - else - 🛑 ArgumentError.new("| m{NumberTheory::ℕ¹}-> m{abundancy_index} received arg(n) w/ value{#{n.to_s}} which is not `abundant` |") - end + # @param [Integer] n + # + # @raise [ArgumentError] if n is not ∈ ℕ OR n is not +abundant+ + # + # @return [Rational] + def self.abundancy_index(n) + if ::Math::NumberTheory::ℕ¹.abundant?(n) + Rational(::Math::NumberTheory::ℕ¹.aliquot_sum(n), n) + else + 🛑 ArgumentError.new("| m{NumberTheory::ℕ¹}-> m{abundancy_index} received arg(n) w/ value{#{n.to_s}} which is not `abundant` |") end + end - # @see https://oeis.org/A005100 - # - # @param [Integer] n - # - # @raise [ArgumentError] if n is not ∈ ℕ - # - # @return [Boolean] - def self.deficient?(n); ::Math::NumberTheory::ℕ¹.aliquot_sum(n) < n; end - - # @param [Integer] n - # - # @raise [ArgumentError] if n is not ∈ ℕ OR n is not +deficient+ - # - # @return [Integer, Numeric] - def self.deficiency(n) - if ::Math::NumberTheory::ℕ¹.deficient?(n) - n - ::Math::NumberTheory::ℕ¹.aliquot_sum(n) - else - 🛑 ArgumentError.new("| m{NumberTheory::ℕ¹}-> m{deficiency} received arg(n) w/ value{#{n.to_s}} which is not `deficient` |") - end + # @see https://oeis.org/A005100 + # + # @param [Integer] n + # + # @raise [ArgumentError] if n is not ∈ ℕ + # + # @return [Boolean] + def self.deficient?(n); ::Math::NumberTheory::ℕ¹.aliquot_sum(n) < n; end + + # @param [Integer] n + # + # @raise [ArgumentError] if n is not ∈ ℕ OR n is not +deficient+ + # + # @return [Integer, Numeric] + def self.deficiency(n) + if ::Math::NumberTheory::ℕ¹.deficient?(n) + n - ::Math::NumberTheory::ℕ¹.aliquot_sum(n) + else + 🛑 ArgumentError.new("| m{NumberTheory::ℕ¹}-> m{deficiency} received arg(n) w/ value{#{n.to_s}} which is not `deficient` |") end + end - # @param [Integer] n - # - # @raise [ArgumentError] if n is not ∈ ℕ OR n is not +deficient+ - # - # @return [Boolean] true, if +n+ is neither +prime+ nor +1+ - def self.composite?(n) - 🛑num❓('n', n, :∈ℕ) - if n < 4 - return false - else - self.ensure_lazy_loaded - return !::Prime.prime?(n) - end + # @param [Integer] n + # + # @raise [ArgumentError] if n is not ∈ ℕ OR n is not +deficient+ + # + # @return [Boolean] true, if +n+ is neither +prime+ nor +1+ + def self.composite?(n) + 🛑num❓('n', n, :∈ℕ) + if n < 4 + return false + else + self.ensure_lazy_loaded + return !::Prime.prime?(n) end + end - end # end: {ℕ¹} + end # end: {ℕ¹} - # equations within +NumberTheory+ that only involve 1-input which ∈ 𝕎 - module 𝕎¹ + # equations within +NumberTheory+ that only involve 1-input which ∈ 𝕎 + module 𝕎¹ - def self.nᵗʰ_euler_totient(n); ::Math::NumberTheory.nth_euler_totient(n); end + def self.nᵗʰ_euler_totient(n); ::Math::NumberTheory.nth_euler_totient(n); end - def self.nᵗʰ_cototient(n) - 🛑num❓('n', n, :∈𝕎) - n - ::Math::NumberTheory.nth_euler_totient(n) - end + def self.nᵗʰ_cototient(n) + 🛑num❓('n', n, :∈𝕎) + n - ::Math::NumberTheory.nth_euler_totient(n) + end - # @param [Integer] n - # - # @raise [ArgumentError] if n is not ∈ 𝕎 - # - # @return [Integer] summation of all digits, in base{10}, from `n` - def self.digit_sum(n) - 🛑num❓('n', n, :∈𝕎) - if n < 10 - return n - else - return n.digits.sum - end + # @param [Integer] n + # + # @raise [ArgumentError] if n is not ∈ 𝕎 + # + # @return [Integer] summation of all digits, in base{10}, from `n` + def self.digit_sum(n) + 🛑num❓('n', n, :∈𝕎) + if n < 10 + return n + else + return n.digits.sum end + end - # @param [Integer] n - # - # @raise [ArgumentError] if n is not ∈ 𝕎 - # - # @return [Integer] summation of all digits recursively until the summation is a single digit, in base{10}, from `n` - def self.digital_root(n) - 🛑num❓('n', n, :∈𝕎) - if n < 10 - return n - else - mod_9 = n.modulo(9) - return mod_9 == 0 ? 9 : mod_9 - end + # @param [Integer] n + # + # @raise [ArgumentError] if n is not ∈ 𝕎 + # + # @return [Integer] summation of all digits recursively until the summation is a single digit, in base{10}, from `n` + def self.digital_root(n) + 🛑num❓('n', n, :∈𝕎) + if n < 10 + return n + else + mod_9 = n.modulo(9) + return mod_9 == 0 ? 9 : mod_9 end + end - # @param [Integer] n - # - # @raise [ArgumentError] if n is not ∈ 𝕎 - # - # @return [Integer] the number of +digit_sum+ iterations that func{+digital_root+} would perform for value `n` - def self.additive_persistence(n) - 🛑num❓('n', n, :∈𝕎) - if n < 10 - return 0 - elsif n < 19 - return 1 - else - the_sum = n.digits.sum - iterations = 1 - while the_sum >= 10 - iterations += 1 - the_sum = the_sum.digits.sum - end - return iterations + # @param [Integer] n + # + # @raise [ArgumentError] if n is not ∈ 𝕎 + # + # @return [Integer] the number of +digit_sum+ iterations that func{+digital_root+} would perform for value `n` + def self.additive_persistence(n) + 🛑num❓('n', n, :∈𝕎) + if n < 10 + return 0 + elsif n < 19 + return 1 + else + the_sum = n.digits.sum + iterations = 1 + while the_sum >= 10 + iterations += 1 + the_sum = the_sum.digits.sum end + return iterations end + end - # -------------------------------------------------------------------------------------------- | *b03* | *f32* | - @seq_pronic = ::Math::Expr::Sequence.new(:∈𝕎) - @seq_pronic.define_singleton_method(:_∋?) do |n| - x = ::Math.sqrt(n).to_i - (x * (x + 1)) == n - end - @seq_pronic.define_singleton_method(:calculate_value_at){|n| n * (n + 1)} - # -------------------------------------------------------------------------------------------- | *b04* | *f32* | - @seq_square = ::Math::Expr::Sequence.new(:∈𝕎) - @seq_square.define_singleton_method(:_∋?) do |n| - # TODO: for when needed: there are many properties that can be checked for to avoid expensive operations (loops, math operations, overflow checks, etc) - square_root = ::Math.sqrt(n) - square_root - square_root.floor == 0 + # -------------------------------------------------------------------------------------------- | *b03* | *f32* | + @seq_pronic = ::Math::Expr::Sequence.new(:∈𝕎) + @seq_pronic.define_singleton_method(:_∋?) do |n| + x = ::Math.sqrt(n).to_i + (x * (x + 1)) == n + end + @seq_pronic.define_singleton_method(:calculate_value_at){|n| n * (n + 1)} + # -------------------------------------------------------------------------------------------- | *b04* | *f32* | + @seq_square = ::Math::Expr::Sequence.new(:∈𝕎) + @seq_square.define_singleton_method(:_∋?) do |n| + # TODO: for when needed: there are many properties that can be checked for to avoid expensive operations (loops, math operations, overflow checks, etc) + square_root = ::Math.sqrt(n) + square_root - square_root.floor == 0 + end + @seq_square.define_singleton_method(:calculate_value_at){|n| n * n} + # -------------------------------------------------------------------------------------------- | *b05* | *f32* | + @seq_fibonacci = ::Math::Expr::Sequence.new(:∈𝕎, [0, 1, 1, 2, 3]) + @seq_fibonacci.define_singleton_method(:_∋?){|n| ::Math::NumberTheory::𝕎¹.seq_square.∋?(5 * (n * n) + 4) || ::Math::NumberTheory::𝕎¹.seq_square.∋?(5 * (n * n) - 4)} + @seq_fibonacci.define_singleton_method(:calculate_value_at){|n| (((::Float::RATIO_GOLDEN ** n) / ::Math.sqrt(5.0)) + 0.5).floor} + @seq_fibonacci.define_singleton_method(:nᵗʰ_sum){|n| ::Math::NumberTheory::𝕎¹.seq_fibonacci[n + 2] - 1} + @seq_fibonacci.define_singleton_method(:nᵗʰ_squared_sum){|n| ::Math::NumberTheory::𝕎¹.seq_fibonacci[n] * ::Math::NumberTheory::𝕎¹.seq_fibonacci[n + 1]} + # -------------------------------------------------------------------------------------------- | *b06* | *f32* | + @seq_lucas = ::Math::Expr::Sequence.new(:∈𝕎, [2, 1, 3]) + @seq_lucas.define_singleton_method(:A∀ₓ) do |max_n| + 🛑 NotImplementedError.new('todo =)!') + end + @seq_lucas.define_singleton_method(:_∋?) do |n| + prev = 4 + if n < prev + return false + elsif n == prev + return true end - @seq_square.define_singleton_method(:calculate_value_at){|n| n * n} - # -------------------------------------------------------------------------------------------- | *b05* | *f32* | - @seq_fibonacci = ::Math::Expr::Sequence.new(:∈𝕎, [0, 1, 1, 2, 3]) - @seq_fibonacci.define_singleton_method(:_∋?){|n| ::Math::NumberTheory::𝕎¹.seq_square.∋?(5 * (n * n) + 4) || ::Math::NumberTheory::𝕎¹.seq_square.∋?(5 * (n * n) - 4)} - @seq_fibonacci.define_singleton_method(:calculate_value_at){|n| (((::Float::RATIO_GOLDEN ** n) / ::Math.sqrt(5.0)) + 0.5).floor} - @seq_fibonacci.define_singleton_method(:nᵗʰ_sum){|n| ::Math::NumberTheory::𝕎¹.seq_fibonacci[n + 2] - 1} - @seq_fibonacci.define_singleton_method(:nᵗʰ_squared_sum){|n| ::Math::NumberTheory::𝕎¹.seq_fibonacci[n] * ::Math::NumberTheory::𝕎¹.seq_fibonacci[n + 1]} - # -------------------------------------------------------------------------------------------- | *b06* | *f32* | - @seq_lucas = ::Math::Expr::Sequence.new(:∈𝕎, [2, 1, 3]) - @seq_lucas.define_singleton_method(:A∀ₓ) do |max_n| - 🛑 NotImplementedError.new('todo =)!') + curr = 7 + if n < curr + return false + elsif n == curr + return true end - @seq_lucas.define_singleton_method(:_∋?) do |n| - prev = 4 - if n < prev - return false - elsif n == prev + while curr < n + temp = curr + curr += prev + prev = temp + if curr == n return true - end - curr = 7 - if n < curr + elsif curr > n return false - elsif n == curr - return true end - while curr < n - temp = curr - curr += prev - prev = temp - if curr == n - return true - elsif curr > n - return false - end - end - end - @seq_lucas.define_singleton_method(:calculate_value_at){|n| ((::Float::RATIO_GOLDEN ** n) + (-0.618033988749895 ** n)).round} - # -------------------------------------------------------------------------------------------- | *b07* | *f32* | - @seq_triangle = ::Math::Expr::Sequence.new(:∈𝕎, [0, 1, 3]) - @seq_triangle.define_singleton_method(:_∋?) do |n| - x = n * 8 + 1 - x.odd? && ::Math::NumberTheory::𝕎¹.seq_square.∋?(x) - end - @seq_triangle.define_singleton_method(:calculate_value_at){|n| ::Math::Combinatorics::𝕎².choose(n: n + 1, k: 2)} - # -------------------------------------------------------------------------------------------- | *b08* | *f32* | - @seq_hexagonal = ::Math::Expr::Sequence.new(:∈𝕎, [0, 1, 6, 15]) - @seq_hexagonal.define_singleton_method(:calculate_value_at){|n| n * (2 * n - 1)} - @seq_hexagonal.define_singleton_method(:_∋?){|n| ::Math::NumberTheory::𝕎¹.seq_triangle.∋?(n)} - @seq_hexagonal.define_singleton_method(:A∀ₓ) do |max_n| - 🛑 NotImplementedError.new('todo =)!') - end - # -------------------------------------------------------------------------------------------------------------- - class << self; attr_reader :seq_pronic, :seq_fibonacci, :seq_lucas, :seq_square, :seq_triangle, :seq_hexagonal; end - end # end: {𝕎¹} - - # equations within +NumberTheory+ that involve 2-inputs (with both belonging to the `natural-numbers`) - module ℕ² - - # @see https://en.wikipedia.org/wiki/Coprime_integers - # - # also referred to as `relatively-prime` and `mutually-prime` - # - # @note if a number `d` divides `(m * n)` and is coprime w/ `n`, then `d` divides `m` - # - # @param [Integer] a - # @param [Integer] b - # - # @raise [ArgumentError] if a or b is not ∈ ℕ - # - # @return [Boolean] true, if `a` and `b` have a `greatest common divisor` of 1 - def self.coprime?(a, b); ::Math::NumberTheory::ℤ².gcd(a, b) == 1; end - - # @param [Integer] a - # @param [Integer] b - # - # @raise [ArgumentError] if a or b is not ∈ ℕ - # - # @return [Boolean] true, if `a` and `b` have equal values for their `abundancy_index` - def self.friendly?(a, b); ::Math::NumberTheory::ℕ¹.abundancy_index(a) == ::Math::NumberTheory::ℕ¹.abundancy_index(b); end - - end # end: {ℕ²} - - # equations within +NumberTheory+ that involve 2-inputs w/ ∀ input ∈ ℤ {functions w/ exceptions to this rule may exist} - module ℤ² - - # for more information: - # @see https://www.khanacademy.org/computing/computer-science/cryptography/modarithmetic/a/the-euclidean-algorithm - # @see http://www.codecodex.com/wiki/Euclidean_algorithm - # @see https://tutorialspoint.dev/algorithm/mathematical-algorithms/steins-algorithm-for-finding-gcd - # - # ‣ [associative law] | gcd(a,b,c) = gcd(a, gcd(b,c)) - # ‣ [ ] | `∀ a, gcd(a,0) = |a|` - # ‣ [ ] | `∀ a, gcd(a,a) = |a|` - # - # @param [Integer] a - # @param [Integer] b - # - # @raise [ArgumentError] if a or b is not ∈ ℤ - # - # @return [Integer] - def self.gcd(a, b) - 🛑nums❓([a, b], :∈ℤ) - a.to_i.gcd(b.to_i) end + end + @seq_lucas.define_singleton_method(:calculate_value_at){|n| ((::Float::RATIO_GOLDEN ** n) + (-0.618033988749895 ** n)).round} + # -------------------------------------------------------------------------------------------- | *b07* | *f32* | + @seq_triangle = ::Math::Expr::Sequence.new(:∈𝕎, [0, 1, 3]) + @seq_triangle.define_singleton_method(:_∋?) do |n| + x = n * 8 + 1 + x.odd? && ::Math::NumberTheory::𝕎¹.seq_square.∋?(x) + end + @seq_triangle.define_singleton_method(:calculate_value_at){|n| ::Math::Combinatorics::𝕎².choose(n: n + 1, k: 2)} + # -------------------------------------------------------------------------------------------- | *b08* | *f32* | + @seq_hexagonal = ::Math::Expr::Sequence.new(:∈𝕎, [0, 1, 6, 15]) + @seq_hexagonal.define_singleton_method(:calculate_value_at){|n| n * (2 * n - 1)} + @seq_hexagonal.define_singleton_method(:_∋?){|n| ::Math::NumberTheory::𝕎¹.seq_triangle.∋?(n)} + @seq_hexagonal.define_singleton_method(:A∀ₓ) do |max_n| + 🛑 NotImplementedError.new('todo =)!') + end + # -------------------------------------------------------------------------------------------------------------- + class << self; attr_reader :seq_pronic, :seq_fibonacci, :seq_lucas, :seq_square, :seq_triangle, :seq_hexagonal; end + end # end: {𝕎¹} - end # end: {ℤ²} + # equations within +NumberTheory+ that involve 2-inputs (with both belonging to the `natural-numbers`) + module ℕ² - # `::Math::NumberTheory::ℤ³` + # @see https://en.wikipedia.org/wiki/Coprime_integers # - # equations within +NumberTheory+ that involve 3-inputs w/ ∀ input ∈ ℤ {functions w/ exceptions to this rule may exist} - module ℤ³ + # also referred to as `relatively-prime` and `mutually-prime` + # + # @note if a number `d` divides `(m * n)` and is coprime w/ `n`, then `d` divides `m` + # + # @param [Integer] a + # @param [Integer] b + # + # @raise [ArgumentError] if a or b is not ∈ ℕ + # + # @return [Boolean] true, if `a` and `b` have a `greatest common divisor` of 1 + def self.coprime?(a, b); ::Math::NumberTheory::ℤ².gcd(a, b) == 1; end - # ‣ [reflexivity] | `a ≡ a (mod c)` - # ‣ [symmetry] | if `a ≡ b (mod c)` then `b ≡ a (mod c)` - # ‣ [transitivity] | if `a ≡ b (mod n)` and `b ≡ c (mod n)`, then `a ≡ c (mod n)` - # - # @param [Integer, Numeric] a - # @param [Integer, Numeric] b - # @param [Integer, Numeric] c (must not be 0) - # - # @raise [ArgumentError] if a or b is not ∈ ℤ or c is not ∈ ℤ - # - # @return [Boolean] true, if `a ≡ b (mod c)` - def self.congruent?(a, b, c) - 🛑num❓(:a, a, :∈ℤ) - a.to_i.≡(b: b, mod: c) - end + # @param [Integer] a + # @param [Integer] b + # + # @raise [ArgumentError] if a or b is not ∈ ℕ + # + # @return [Boolean] true, if `a` and `b` have equal values for their `abundancy_index` + def self.friendly?(a, b); ::Math::NumberTheory::ℕ¹.abundancy_index(a) == ::Math::NumberTheory::ℕ¹.abundancy_index(b); end - end # end: {ℤ³} + end # end: {ℕ²} - #module Symbolic - # TODO: Liouville's Constant (OEIS A012245) - # https://mathworld.wolfram.com/LiouvillesConstant.html. - # https://en.wikipedia.org/wiki/Liouville_number - # ^ (relevant as no Liouville number can be `rational`) - # ^ (all Liouville numbers are `transcendental`) - #end + # equations within +NumberTheory+ that involve 2-inputs w/ ∀ input ∈ ℤ {functions w/ exceptions to this rule may exist} + module ℤ² - end # end: {NumberTheory} + # for more information: + # @see https://www.khanacademy.org/computing/computer-science/cryptography/modarithmetic/a/the-euclidean-algorithm + # @see http://www.codecodex.com/wiki/Euclidean_algorithm + # @see https://tutorialspoint.dev/algorithm/mathematical-algorithms/steins-algorithm-for-finding-gcd + # + # ‣ [associative law] | gcd(a,b,c) = gcd(a, gcd(b,c)) + # ‣ [ ] | `∀ a, gcd(a,0) = |a|` + # ‣ [ ] | `∀ a, gcd(a,a) = |a|` + # + # @param [Integer] a + # @param [Integer] b + # + # @raise [ArgumentError] if a or b is not ∈ ℤ + # + # @return [Integer] + def self.gcd(a, b) + 🛑nums❓([a, b], :∈ℤ) + a.to_i.gcd(b.to_i) + end + + end # end: {ℤ²} + + # `::Math::NumberTheory::ℤ³` + # + # equations within +NumberTheory+ that involve 3-inputs w/ ∀ input ∈ ℤ {functions w/ exceptions to this rule may exist} + module ℤ³ + + # ‣ [reflexivity] | `a ≡ a (mod c)` + # ‣ [symmetry] | if `a ≡ b (mod c)` then `b ≡ a (mod c)` + # ‣ [transitivity] | if `a ≡ b (mod n)` and `b ≡ c (mod n)`, then `a ≡ c (mod n)` + # + # @param [Integer, Numeric] a + # @param [Integer, Numeric] b + # @param [Integer, Numeric] c (must not be 0) + # + # @raise [ArgumentError] if a or b is not ∈ ℤ or c is not ∈ ℤ + # + # @return [Boolean] true, if `a ≡ b (mod c)` + def self.congruent?(a, b, c) + 🛑num❓(:a, a, :∈ℤ) + a.to_i.≡(b: b, mod: c) + end + + end # end: {ℤ³} end +#module Symbolic +# TODO: Liouville's Constant (OEIS A012245) +# https://mathworld.wolfram.com/LiouvillesConstant.html. +# https://en.wikipedia.org/wiki/Liouville_number +# ^ (relevant as no Liouville number can be `rational`) +# ^ (all Liouville numbers are `transcendental`) +#end + # TODO: https://en.wikipedia.org/wiki/Diophantine_equation # w/ efficient algorithms diff --git a/lib/ruuuby/module/attribute/includable/connectable.rb b/lib/ruuuby/module/attribute/includable/connectable.rb index ee2f080..8f9e9e9 100644 --- a/lib/ruuuby/module/attribute/includable/connectable.rb +++ b/lib/ruuuby/module/attribute/includable/connectable.rb @@ -41,7 +41,7 @@ def disconnect! if self.connected? self._disconnect else - 🛑 ::RuntimeError.new("| {🐋}-> m{disconnect!} called when the docker-engine is not running |") + 🛑 ::RuntimeError.new("| {#{self.Ⓣ}}-> m{disconnect!} called when the docker-engine is not running |") end end diff --git a/lib/ruuuby/module/gem.rb b/lib/ruuuby/module/gem.rb index 9db368e..3ec8f86 100644 --- a/lib/ruuuby/module/gem.rb +++ b/lib/ruuuby/module/gem.rb @@ -1,5 +1,35 @@ # encoding: UTF-8 +class ::Object + + # @param [String] version_expected + # + # @raise [ArgumentError] + def attribute_versionable(version_expected, &block) + 🛑str❓('version_expected', version_expected) + self.instance_variable_set("@version_expected", version_expected) + + self.define_singleton_method(:∃version?) do || + self.instance_variable_set("@version_current", block.call) if @version_current.nil? + if @version_current == @version_expected + return true + else + 🛑 ::RuntimeError.new("{#{@version_current.to_s}}[#{@version_current.Ⓣ}] != {#{@version_expected.to_s}}[#{@version_expected.Ⓣ}]") + end + end + + class << self + attr_reader :version_expected + + # @return [String] + def version_current; self.∃version? if @version_current.nil?; @version_current; end + end + + self + end + +end + # | useful cmd/template | purpose | # | --------------------------- | --------------------------------------------------------------------- | # | `gem -v` | print current `RubyGems` version | diff --git a/lib/ruuuby/module/kernel.rb b/lib/ruuuby/module/kernel.rb index 8709a61..c8bedb6 100644 --- a/lib/ruuuby/module/kernel.rb +++ b/lib/ruuuby/module/kernel.rb @@ -18,14 +18,16 @@ def 🐋; ::Ruuuby::MetaData.engine.api_locale.api_docker; end # @return [Ruuuby::MetaData::BrewAPI] def 🍺; ::Ruuuby::MetaData.engine.api_locale.api_brew; end - # @param [String] cmd + # @param [String] cmd + # @param [Boolean] allow_errors # # @raise [ArgumentError] # # @return [Array, String] - def 💻(cmd) + def 💻(cmd, allow_errors=false) 🛑str❓('cmd', cmd) - ::Ruuuby::MetaData.engine.api.run_cmd!(cmd) + 🛑bool❓('allow_errors', allow_errors) + ::Ruuuby::MetaData.engine.api.run_cmd!(cmd, allow_errors) end # @return [Ruuuby::Protocols::RequestHTTP] diff --git a/lib/ruuuby/protocol/http_request.rb b/lib/ruuuby/protocol/http_request.rb index 48e928e..8662478 100644 --- a/lib/ruuuby/protocol/http_request.rb +++ b/lib/ruuuby/protocol/http_request.rb @@ -98,8 +98,15 @@ def self.execute_debugging(uri, params={}, headers=nil) # @param [URI] uri # @param [Hash] params # @param [Hash, NilClass] headers + # + # @return [Hash, NilClass] def self.execute_json(uri, params={}, headers={"content-type" => "application/json"}) - request, response = (self.execute_post_debugging(uri, params, headers)) + request, response = self.execute_post_debugging(uri, params, headers) + + if response.body.nil? || response.body.length == 0 + return nil + end + ::JSON.parse(response.body) end diff --git a/lib/ruuuby/protocol/unix_socket.rb b/lib/ruuuby/protocol/unix_socket.rb index 3ada2b1..a4705d5 100644 --- a/lib/ruuuby/protocol/unix_socket.rb +++ b/lib/ruuuby/protocol/unix_socket.rb @@ -16,23 +16,3 @@ class ::UNIXSocket < ::UNIXSocket.superclass # TODO: document WebRTC (compare with WebSockets) # > https://en.wikipedia.org/wiki/WebRTC # > https://webrtc.org/ - -# ---------------------------------------------------------------------------------------- -# ___ ___ __ __ __ ___ __ __ __ -# | |__ |\/| |__) | / \ / ` /\ | | / \ |\ | . / ` | | |__) | -# | |___ | | | |___ \__/ \__, /~~\ | | \__/ | \| . \__, \__/ | \ |___ -# -# ---------------------------------------------------------------------------------------- - -# @see https://www.cyberciti.biz/faq/download-a-file-with-curl-on-linux-unix-command-line/ -# -# @param [String] url_resource -# @param [String] optional_save_as_path -#def curl_get(url_resource, optional_save_as_path='') -# 🛑strs❓([url_resource, optional_save_as_path]) -# if optional_save_as_path.∅? -# self.run_cmd("curl -L -O #{url_resource}") -# else -# self.run_cmd("curl -L #{url_resource} --output #{optional_save_as_path}") -# end -#end diff --git a/lib/ruuuby/ruuuby/api/docker/api_docker.rb b/lib/ruuuby/ruuuby/api/docker/api_docker.rb index b06d2f7..89a1492 100644 --- a/lib/ruuuby/ruuuby/api/docker/api_docker.rb +++ b/lib/ruuuby/ruuuby/api/docker/api_docker.rb @@ -106,7 +106,9 @@ def find_🐋_by_id(container_id) end # @return [Array] an array of all the alive containers - def ∀🐋; ::Docker::Container.all(all: true); end + def ∀🐋 + ::Docker::Container.all(all: true) + end # @param [String] container_name # diff --git a/lib/ruuuby/ruuuby/api/docker/conditional/discrete/service_nginx.rb b/lib/ruuuby/ruuuby/api/docker/conditional/discrete/service_nginx.rb index e2df521..6417e95 100644 --- a/lib/ruuuby/ruuuby/api/docker/conditional/discrete/service_nginx.rb +++ b/lib/ruuuby/ruuuby/api/docker/conditional/discrete/service_nginx.rb @@ -14,4 +14,4 @@ def file_delete(path) self.container.cmd!(['rm', self.path_self(path)]) end -end \ No newline at end of file +end diff --git a/lib/ruuuby/ruuuby/api/docker/conditional/docker_service_set_dev.rb b/lib/ruuuby/ruuuby/api/docker/conditional/docker_service_set_dev.rb index c5d78b9..3294ea7 100644 --- a/lib/ruuuby/ruuuby/api/docker/conditional/docker_service_set_dev.rb +++ b/lib/ruuuby/ruuuby/api/docker/conditional/docker_service_set_dev.rb @@ -12,7 +12,7 @@ def initialize(host) super("#{💎.engine.path_base}docker-compose.dev.yml") @host = host - @pgadmin = @services['service_pgadmin'] + @pgadmin = @services['service_pgadmin_dev'] @path_assets = 'services/web_assets/' @path_intermediate = "#{@path_assets}intermediate/" @@ -27,7 +27,7 @@ def initialize(host) def nginx if @nginx == nil require_relative 'discrete/service_nginx' - @nginx = ::RuuubyServiceNGINX.new(@services['service_nginx']) + @nginx = ::RuuubyServiceNGINX.new(@services['service_nginx_dev']) end @nginx end @@ -35,15 +35,20 @@ def nginx def js if @js == nil require_relative 'discrete/service_js' - @js = RuuubyServiceJS.new(@services['service_js'], self.nginx) + @js = RuuubyServiceJS.new(@services['service_js_dev'], self.nginx) end @js end + def create_needed_networks + 🛑 ::ArgumentError.new("| c{DockerAPI}-> m{create_needed_network} was called when the network{ruuuby_network} already exists |") if ∃🌐?('ruuuby_network') + 💻('docker network create -d bridge --subnet 192.168.0.0/24 --gateway 192.168.0.1 ruuuby_network') + end + #def postgresql # if @postgresql == nil # require_relative 'discrete/service_postgresql' - # @postgresql = RuuubyServicePostgreSQL.new(@services['service_postgres']) + # @postgresql = RuuubyServicePostgreSQL.new(@services['service_postgresql']) # end # @postgresql #end @@ -79,18 +84,3 @@ def build_web_manifest(path_input=nil, path_minified=nil, transfer_to_nginx) end # -------------------------------------------- ⚠️ -------------------------------------------- - -module ::Ruuuby - module MetaData - - # `🐋` - class DockerAPI < ::Ruuuby::MetaData::EngineComponentAPICLI - - def create_needed_network - 🛑 ::ArgumentError.new("| c{DockerAPI}-> m{create_needed_network} was called when the network{ruuuby_network} already exists |") if ∃🌐?('ruuuby_network') - self._run_cmd('network create -d bridge --subnet 192.168.0.0/24 --gateway 192.168.0.1 ruuuby_network') - end - - end - end -end diff --git a/lib/ruuuby/ruuuby/api/docker/docker_container.rb b/lib/ruuuby/ruuuby/api/docker/docker_container.rb index 7c3030d..ea8277a 100644 --- a/lib/ruuuby/ruuuby/api/docker/docker_container.rb +++ b/lib/ruuuby/ruuuby/api/docker/docker_container.rb @@ -40,6 +40,7 @@ def env; self.env_vars['SERVICE_ENV']; end # @return [String] def os; self.env_vars['SERVICE_OS']; end + # TODO: install for dev/test, don't install for prod # @raise [RuntimeError] # # @return [Boolean] diff --git a/lib/ruuuby/ruuuby/api/git/api_git.rb b/lib/ruuuby/ruuuby/api/git/api_git.rb index 11ee21c..8391be1 100644 --- a/lib/ruuuby/ruuuby/api/git/api_git.rb +++ b/lib/ruuuby/ruuuby/api/git/api_git.rb @@ -3,319 +3,318 @@ # -------------------------------------------- ⚠️ -------------------------------------------- # `💎` -module ::Ruuuby - - # information and utilities that define and work w/ aspects of `Ruuuby` - module MetaData - - # helpful CLI commands: - # --------------------------------------------------------------------------------------------------------- - # | scenario | {reference) command/template | - # | -------------------------------------------------- | ------------------------------------------------ | - # | human readable view of staging | `git diff --cached --stat` | - # | human readable view of commits | `git log --pretty=format:"%H|%ad|%s" --date=iso` | - # | human readable view of current configs applied | `git config --list --show-origin --show-scope` | - # | for script: get num files w/ diffs | `git diff --cached --numstat | wc -l` | - # | alternative for `git status` | `git status --porcelain=v2 -b` | - # | clone only latest data, save time & network-data | `git clone --depth 1 ` | - # | check for any fixable text/file/syntax issues | `git diff --cached --check` | - # | check if file is tracked (not tracked if no output) | `git ls-files ` | - # --------------------------------------------------------------------------------------------------------- - # - # helpful resources - # -------------------------------------------------------------------------------------------------------------------------------------------- - # | scenario(s) | resource | reference_id | - # | ------------------------------ | ---------------------------------------------------------------------------------------- | ------------ | - # | list of relating git functions | https://github.com/libgit2/libgit2sharp/wiki/LibGit2Sharp-Hitchhiker's-Guide-to-Git | 0x0 | - # | base gem documentation | https://github.com/libgit2/rugged | 0x1 | - # | provides version list overview | https://en.wikipedia.org/wiki/Git | 0x2 | - # | tips n tricks | https://community.lsst.org/t/git-tips-and-tricks/3169/2 | 0x3 | - # | useful settings esp. w/ MacOS | https://gist.github.com/trey/2722934 | 0x4 | - # | (not utilized/tested yet) | https://gist.github.com/brandonsimpson/54d9e085c9fde5e6ad3a | 0x5 | - # | turning off status hints | https://stackoverflow.com/questions/55463863/how-to-turn-off-the-help-hints-in-git-output | 0x6 | - # | TODO: look into | https://github.com/so-fancy/diff-so-fancy | | - # | TODO: look into | https://git-scm.com/book/en/v2/Appendix-B%3A-Embedding-Git-in-your-Applications-Libgit2 | | - # | TODO: look into | https://git-scm.com/book/en/v2/Customizing-Git-Git-Hooks | | - # -------------------------------------------------------------------------------------------------------------------------------------------- - # - # terminology: - # - repository: - # ‣ git mainly operates on the `.git` directory, not the entire filesystem - # ‣ you can have a repo within a repo - # - # - commits: - # ‣ snapshot composed of contents of all files as is - # ‣ there is a custom space-efficient compression algorithm used by git (but otherwise this is cause of any size bloat from .git) - # ‣ composed of: commit_message, author, parents(commit(s) that this commit points-to/follows), name(SHA of the commit-obj) - # - # - branches: - # ‣ convention for a logical/linear trail of git-commits - # - # - tags: - # ‣ similair to branches but they are a fixed pointer of a specific commit - # - # - index/staging-area: - # ‣ convention for a 'holding area' for changes to the current working directory, only these changes to `index/staging` are what get applied to the next `git commit` (so regardless of the state of the current working directory) - # - # misc notes: - # ‣ any two `disparate` commits chosen will have a common ancestor that can be found by traversing down both commit's pointer chains until reaching the common ancestor node - # ‣ "git tree" mathematically is a DAG (`directed asyclic graph`), note: every `tree` is a DAG but vise-versa is not implied (@see https://dev.to/nichartley/whats-a-git-tree-5149) - # ‣ `origin/master` vs `origin master`: https://stackoverflow.com/questions/18137175/in-git-what-is-the-difference-between-origin-master-vs-origin-master - # - # `$git` - # - # `💎.engine.api_locale.api_git` - class GitAPI < ::Ruuuby::MetaData::EngineComponentAPICLI - attribute_lazy_loadable('rugged', true) - - def initialize(engine) - super(engine, 'git') - @repo = nil - @branch_names = nil - @release_tags = nil +module ::Ruuuby::MetaData + + # helpful CLI commands: + # --------------------------------------------------------------------------------------------------------- + # | scenario | {reference) command/template | + # | -------------------------------------------------- | ------------------------------------------------ | + # | human readable view of staging | `git diff --cached --stat` | + # | human readable view of commits | `git log --pretty=format:"%H|%ad|%s" --date=iso` | + # | human readable view of current configs applied | `git config --list --show-origin --show-scope` | + # | for script: get num files w/ diffs | `git diff --cached --numstat | wc -l` | + # | alternative for `git status` | `git status --porcelain=v2 -b` | + # | clone only latest data, save time & network-data | `git clone --depth 1 ` | + # | check for any fixable text/file/syntax issues | `git diff --cached --check` | + # | check if file is tracked (not tracked if no output) | `git ls-files ` | + # --------------------------------------------------------------------------------------------------------- + # + # helpful resources + # -------------------------------------------------------------------------------------------------------------------------------------------- + # | scenario(s) | resource | reference_id | + # | ------------------------------ | ---------------------------------------------------------------------------------------- | ------------ | + # | list of relating git functions | https://github.com/libgit2/libgit2sharp/wiki/LibGit2Sharp-Hitchhiker's-Guide-to-Git | 0x0 | + # | base gem documentation | https://github.com/libgit2/rugged | 0x1 | + # | provides version list overview | https://en.wikipedia.org/wiki/Git | 0x2 | + # | tips n tricks | https://community.lsst.org/t/git-tips-and-tricks/3169/2 | 0x3 | + # | useful settings esp. w/ MacOS | https://gist.github.com/trey/2722934 | 0x4 | + # | (not utilized/tested yet) | https://gist.github.com/brandonsimpson/54d9e085c9fde5e6ad3a | 0x5 | + # | turning off status hints | https://stackoverflow.com/questions/55463863/how-to-turn-off-the-help-hints-in-git-output | 0x6 | + # | using IDE for gitdiff | https://brian.pontarelli.com/2013/10/25/using-idea-for-git-merging-and-diffing/ | 0x7 | + # | TODO: look into | https://github.com/so-fancy/diff-so-fancy | | + # | TODO: look into | https://git-scm.com/book/en/v2/Customizing-Git-Git-Hooks | | + # | | | | + # | TODO: (libgit2) | https://libgit2.org/docs/guides/101-samples/ | | + # | TODO: (libgit2) | https://git-scm.com/book/en/v2/Appendix-B%3A-Embedding-Git-in-your-Applications-Libgit2 | | + # -------------------------------------------------------------------------------------------------------------------------------------------- + # + # terminology: + # - repository: + # ‣ git mainly operates on the `.git` directory, not the entire filesystem + # ‣ you can have a repo within a repo + # + # - commits: + # ‣ snapshot composed of contents of all files as is + # ‣ there is a custom space-efficient compression algorithm used by git (but otherwise this is cause of any size bloat from .git) + # ‣ composed of: commit_message, author, parents(commit(s) that this commit points-to/follows), name(SHA of the commit-obj) + # + # - branches: + # ‣ convention for a logical/linear trail of git-commits + # + # - tags: + # ‣ similair to branches but they are a fixed pointer of a specific commit + # + # - index/staging-area: + # ‣ convention for a 'holding area' for changes to the current working directory, only these changes to `index/staging` are what get applied to the next `git commit` (so regardless of the state of the current working directory) + # + # misc notes: + # ‣ any two `disparate` commits chosen will have a common ancestor that can be found by traversing down both commit's pointer chains until reaching the common ancestor node + # ‣ "git tree" mathematically is a DAG (`directed asyclic graph`), note: every `tree` is a DAG but vise-versa is not implied (@see https://dev.to/nichartley/whats-a-git-tree-5149) + # ‣ `origin/master` vs `origin master`: https://stackoverflow.com/questions/18137175/in-git-what-is-the-difference-between-origin-master-vs-origin-master + # + # `$git` + # + # `💎.engine.api_locale.api_git` + class GitAPI < ::Ruuuby::MetaData::EngineComponentAPICLI + attribute_lazy_loadable('rugged', true) + + def initialize(engine) + super(engine, 'git') + @repo = nil + @branch_names = nil + @release_tags = nil + end + + def repo + if @repo.nil? + self.class.ensure_lazy_loaded + require_relative 'conditional' + @repo = ::Rugged::Repository.new(@engine.path_base) end + @repo + end - def repo - if @repo.nil? - self.class.ensure_lazy_loaded - require_relative 'conditional' - @repo = ::Rugged::Repository.new(@engine.path_base) - end - @repo - end + # @return [Rugged::Commit] + def last_commit; self.repo.last_commit; end - # @return [Rugged::Commit] - def last_commit; self.repo.last_commit; end - - # @param [String] attribute_key - # @param [Hash] expected_key_val_pairs - # - # @raise [ArgumentError] - # - # @return [Boolean] - def ∃attribute?(attribute_key, expected_key_val_pairs) - 🛑str❓('attribute_key', attribute_key) - 🛑hsh❓('expected_key_val_pairs', expected_key_val_pairs) - result = self.repo.fetch_attributes(attribute_key) - if result.length == expected_key_val_pairs.length - expected_key_val_pairs.∀ do |key, value| - if result.∃🔑?(key) - if result[key] != value - return false - end - else + # @param [String] attribute_key + # @param [Hash] expected_key_val_pairs + # + # @raise [ArgumentError] + # + # @return [Boolean] + def ∃attribute?(attribute_key, expected_key_val_pairs) + 🛑str❓('attribute_key', attribute_key) + 🛑hsh❓('expected_key_val_pairs', expected_key_val_pairs) + result = self.repo.fetch_attributes(attribute_key) + if result.length == expected_key_val_pairs.length + expected_key_val_pairs.∀ do |key, value| + if result.∃🔑?(key) + if result[key] != value return false end + else + return false end - true - else - false end + true + else + false end + end - # @param [String] sha | the SHA to search for - # - # @raise [ArgumentError] if sha is not a +String+ - # - # @return [Boolean] true, if the SHA was found as an existing GIT Commit - def ∃commit?(sha) - 🛑str❓('sha', sha) - begin - self.repo.lookup(sha).ⓣ == ::Rugged::Commit - rescue ::Rugged::OdbError - return false + # @param [String] sha | the SHA to search for + # + # @raise [ArgumentError] if sha is not a +String+ + # + # @return [Boolean] true, if the SHA was found as an existing GIT Commit + def ∃commit?(sha) + 🛑str❓('sha', sha) + begin + self.repo.lookup(sha).ⓣ == ::Rugged::Commit + rescue ::Rugged::OdbError + return false + end + end + + def changes(subset=true) + deltas = [] + diffs = self.repo.index.diff + diffs.each_delta{|d| deltas << [d.size_delta, d.new_file[:path], d]} + deltas.sort!{|a, b| a[0] <=> b[0]} + deltas + end + + def changes_smallest + f = $git.changes.map{|n| [n[0].to_f.abs, n[1], n[2]]}.sort!{|a,b| a[0] <=> b[0]}[0][2] + path = f.new_file[:path] + puts "PATH:\n#{path}" + found_changes = self.run_cmd("--no-pager diff --unified=0 " + path) + end + + # $git.changes.map{|n| [n[0].to_f.abs, n[1], n[2]]}.sort!{|a,b| a[0] <=> b[0]} + + def changes_fixing_encoding + _changes = self.changes.map{|node| [node[0], node[1]]}.reject{|node| node[0].to_f.abs != 2.0} + + _changes.each do |size, path| + found_changes = self.run_cmd("--no-pager diff --unified=0 #{path}") + if found_changes[-1].include?('+# encoding: UTF-8') + puts "path{#{path}} can be auto-added (it only includes fix first line in file marking the encoding type of{UTF-8})" + self.run_cmd("--no-pager add #{path}") end end + end - def changes(subset=true) - deltas = [] - diffs = self.repo.index.diff - diffs.each_delta{|d| deltas << [d.size_delta, d.new_file[:path], d]} - deltas.sort!{|a, b| a[0] <=> b[0]} - deltas + # TODO: NEEDS TDD!!! + # + # @param [String] stop_sha + # + # @raise [RuntimeError] + # + # @return [Array] + def fetch_commits_until(stop_sha) + if self.∃commit?(stop_sha) + all_commits = [] + curr_commit = self.repo.last_commit + if curr_commit.oid == stop_sha + return [] + end + while curr_commit.oid != stop_sha + all_commits << [curr_commit.oid, curr_commit.to_s, curr_commit.message] + if curr_commit.parents.length != 1 + 🛑 RuntimeError.new("{fetch_commits_until} missing coverage, please see SHA{#{stop_sha}}") + else + curr_commit = curr_commit.parents[0] + end + end + all_commits + else + 🛑 RuntimeError.new("unable to find GitCommit w/ SHA-value{#{stop_sha}}") end + end - def changes_smallest - f = $git.changes.map{|n| [n[0].to_f.abs, n[1], n[2]]}.sort!{|a,b| a[0] <=> b[0]}[0][2] - path = f.new_file[:path] - puts "PATH:\n#{path}" - found_changes = self.run_cmd("--no-pager diff --unified=0 " + path) - end + # @return [Array] + def remote_release_current; self.release_tags[-1]; end - # $git.changes.map{|n| [n[0].to_f.abs, n[1], n[2]]}.sort!{|a,b| a[0] <=> b[0]} + # @return [Array] + def remote_release_previous; self.release_tags[-2]; end - def changes_fixing_encoding - _changes = self.changes.map{|node| [node[0], node[1]]}.reject{|node| node[0].to_f.abs != 2.0} + # _______________________________________________________________ + # __ __ ___ __ __ + # / ` / \ |\ | |__ | / _` /__` + # \__, \__/ | \| | | \__> .__/ + # _______________________________________________________________ - _changes.each do |size, path| - found_changes = self.run_cmd("--no-pager diff --unified=0 #{path}") - if found_changes[-1].include?('+# encoding: UTF-8') - puts "path{#{path}} can be auto-added (it only includes fix first line in file marking the encoding type of{UTF-8})" - self.run_cmd("--no-pager add #{path}") - end - end - end + # @example + # + # > to create the following config: + # + # [diff "image"] + # textconv=exif + # cachetextconv=true + # + # > run these commands: + # + # $git.configs.store('diff.image.textconv','exif') + # $git.configs.store('diff.image.cachetextconv','true') + # + # @return [Rugged::Config] + def configs; self.repo.config; end - # TODO: NEEDS TDD!!! - # - # @param [String] stop_sha - # - # @raise [RuntimeError] - # - # @return [Array] - def fetch_commits_until(stop_sha) - if self.∃commit?(stop_sha) - all_commits = [] - curr_commit = self.repo.last_commit - if curr_commit.oid == stop_sha - return [] - end - while curr_commit.oid != stop_sha - all_commits << [curr_commit.oid, curr_commit.to_s, curr_commit.message] - if curr_commit.parents.length != 1 - 🛑 RuntimeError.new("{fetch_commits_until} missing coverage, please see SHA{#{stop_sha}}") - else - curr_commit = curr_commit.parents[0] - end - end - all_commits - else - 🛑 RuntimeError.new("unable to find GitCommit w/ SHA-value{#{stop_sha}}") - end - end + # _______________________________________________________________ + # ___ ___ __ ___ __ __ + # |__| |__ /\ | | |__| / ` |__| |__ / ` |__/ /__` + # | | |___ /~~\ |___ | | | \__, | | |___ \__, | \ .__/ + # _______________________________________________________________ - # @return [Array] - def remote_release_current; self.release_tags[-1]; end - - # @return [Array] - def remote_release_previous; self.release_tags[-2]; end - - # _______________________________________________________________ - # __ __ ___ __ __ - # / ` / \ |\ | |__ | / _` /__` - # \__, \__/ | \| | | \__> .__/ - # _______________________________________________________________ - - # @example - # - # > to create the following config: - # - # [diff "image"] - # textconv=exif - # cachetextconv=true - # - # > run these commands: - # - # $git.configs.store('diff.image.textconv','exif') - # $git.configs.store('diff.image.cachetextconv','true') - # - # @return [Rugged::Config] - def configs; self.repo.config; end - - # _______________________________________________________________ - # ___ ___ __ ___ __ __ - # |__| |__ /\ | | |__| / ` |__| |__ / ` |__/ /__` - # | | |___ /~~\ |___ | | | \__, | | |___ \__, | \ .__/ - # _______________________________________________________________ - - # @param [Boolean] perform_full_check - # - # @raise [ArgumentError] - # - # @return [Boolean] - def healthy?(perform_full_check=false) - 🛑bool❓('perform_full_check', perform_full_check) - is_healthy = self.healthy_repo? - if perform_full_check - !(!is_healthy || self.∃fixable_syntax_errors? || self.∃index_conflicts?) && ::Rugged.libgit2_version == [1, 0, 1] - else - is_healthy - end + # @param [Boolean] perform_full_check + # + # @raise [ArgumentError] + # + # @return [Boolean] + def healthy?(perform_full_check=false) + 🛑bool❓('perform_full_check', perform_full_check) + is_healthy = self.healthy_repo? + if perform_full_check + !(!is_healthy || self.∃fixable_syntax_errors? || self.∃index_conflicts?) && ::Rugged.libgit2_version == [1, 0, 1] + else + is_healthy end + end - # @see https://github.com/desktop/desktop/issues/5057 - # - "usually the `UNBORN HEAD` error happens when you are attempting to publish a branch that has no commits" - # - # @see https://stackoverflow.com/questions/5540883/whats-the-practical-difference-between-a-bare-and-non-bare-repository - # - "a bare repository does not have a default remote origin repository" - # - # @see https://www.git-tower.com/learn/git/faq/detached-head-when-checkout-commit - # - "when a specific commit is checkout out instead of a branch : `detached head`" - # - # @return [Boolean] - def healthy_repo?; (!self.repo.bare?) && (!self.repo.empty?) && (!self.repo.head_unborn?) && (!self.repo.head_detached?) && (!self.repo.shallow?); end - - # `$git.∃index_conflicts?` - # - # @return [Boolean] - def ∃index_conflicts?; self.repo.index.conflicts?; end - - # `$git.∃fixable_syntax_errors?` - # - # @return [Boolean] - def ∃fixable_syntax_errors?; self.run_cmd('diff --check') == [] || self.run_cmd('diff --cached --check') == []; end - - # _______________________________________________________________ - # __ __ ___ __ ___ ___ __ __ - # / ` /\ / ` |__| |__ | \ |__ | |__ | | \ /__` - # \__, /~~\ \__, | | |___ |__/ | | |___ |___ |__/ .__/ - # _______________________________________________________________ - - # @param [Array] version - # - # @raise [ArgumentError] - def release_tag_for_version(version) - 🛑ary❓('version', version) - self.release_tags.each {|t| return t[2] if t[0] == version} - false - end + # @see https://github.com/desktop/desktop/issues/5057 + # - "usually the `UNBORN HEAD` error happens when you are attempting to publish a branch that has no commits" + # + # @see https://stackoverflow.com/questions/5540883/whats-the-practical-difference-between-a-bare-and-non-bare-repository + # - "a bare repository does not have a default remote origin repository" + # + # @see https://www.git-tower.com/learn/git/faq/detached-head-when-checkout-commit + # - "when a specific commit is checkout out instead of a branch : `detached head`" + # + # @return [Boolean] + def healthy_repo?; (!self.repo.bare?) && (!self.repo.empty?) && (!self.repo.head_unborn?) && (!self.repo.head_detached?) && (!self.repo.shallow?); end - # @param [*] version - def release_commit_for_version(version); self.release_tags.each {|t| return t[1] if t[0] == version}; false; end + # `$git.∃index_conflicts?` + # + # @return [Boolean] + def ∃index_conflicts?; self.repo.index.conflicts?; end - # @param [Array] version - # - # @return [Boolean] - def ∃tag_for_version?(version) - self.release_tag_for_version(version) != false - end + # `$git.∃fixable_syntax_errors?` + # + # @return [Boolean] + def ∃fixable_syntax_errors?; self.run_cmd('diff --check') == [] || self.run_cmd('diff --cached --check') == []; end - # @param [Array] version - def find_release_tag(version); self.release_tags.each {|t| return t[2] if t[0] == version}; false; end - - # @param [Array] version - def find_release_commit(version); self.release_tags.each {|t| return t[1] if t[0] == version}; false; end - - # @param [Array] version - # - # @raise [RuntimeError] - def find_release_tag!(version); 🛑 ::RuntimeError.new("| m{find_release_tag!} did not find version{#{version.to_s}} |") unless (!self.release_tag_for_version(version)); end - - # @raise [RuntimeError] - # - # @return [Array] - def release_tags - if @release_tags.∅? - @release_tags = [] - self.repo.references.each('refs/tags/*') do |ref| - ref_annotation = ref.target - 🛑 ::RuntimeError.new("unexpected Class{#{ref_annotation.Ⓣ}}-> m{release_tags}, 2nd-obj{#{ref_annotation.to_s}}") unless ref_annotation.ⓣ == ::Rugged::Tag::Annotation - ref_commit = ref_annotation.target - 🛑 ::RuntimeError.new("unexpected Class{#{ref_commit.Ⓣ}}-> m{release_tags}, 3ʳᵈ-obj{#{ref_commit.to_s}}") unless ref_commit.ⓣ == ::Rugged::Commit - #@release_tags << [ref.name.to_s.♻️⟶('v').split('.').map(&:to_i), ref_commit.oid] - @release_tags << [ref.name.to_s.♻️⟶('v').split('.').map(&:to_i), ref_commit, ref_annotation] - end - @release_tags.sort!{|a,b| a <=> b } - #@release_tags.sort!{|a,b| a <=> b }.reverse! + # _______________________________________________________________ + # __ __ ___ __ ___ ___ __ __ + # / ` /\ / ` |__| |__ | \ |__ | |__ | | \ /__` + # \__, /~~\ \__, | | |___ |__/ | | |___ |___ |__/ .__/ + # _______________________________________________________________ + + # @param [Array] version + # + # @raise [ArgumentError] + def release_tag_for_version(version) + 🛑ary❓('version', version) + self.release_tags.each {|t| return t[2] if t[0] == version} + false + end + + # @param [*] version + def release_commit_for_version(version); self.release_tags.each {|t| return t[1] if t[0] == version}; false; end + + # @param [Array] version + # + # @return [Boolean] + def ∃tag_for_version?(version) + self.release_tag_for_version(version) != false + end + + # @param [Array] version + def find_release_tag(version); self.release_tags.each {|t| return t[2] if t[0] == version}; false; end + + # @param [Array] version + def find_release_commit(version); self.release_tags.each {|t| return t[1] if t[0] == version}; false; end + + # @param [Array] version + # + # @raise [RuntimeError] + def find_release_tag!(version); 🛑 ::RuntimeError.new("| m{find_release_tag!} did not find version{#{version.to_s}} |") unless (!self.release_tag_for_version(version)); end + + # @raise [RuntimeError] + # + # @return [Array] + def release_tags + if @release_tags.∅? + @release_tags = [] + self.repo.references.each('refs/tags/*') do |ref| + ref_annotation = ref.target + 🛑 ::RuntimeError.new("unexpected Class{#{ref_annotation.Ⓣ}}-> m{release_tags}, 2nd-obj{#{ref_annotation.to_s}}") unless ref_annotation.ⓣ == ::Rugged::Tag::Annotation + ref_commit = ref_annotation.target + 🛑 ::RuntimeError.new("unexpected Class{#{ref_commit.Ⓣ}}-> m{release_tags}, 3ʳᵈ-obj{#{ref_commit.to_s}}") unless ref_commit.ⓣ == ::Rugged::Commit + #@release_tags << [ref.name.to_s.♻️⟶('v').split('.').map(&:to_i), ref_commit.oid] + @release_tags << [ref.name.to_s.♻️⟶('v').split('.').map(&:to_i), ref_commit, ref_annotation] end - @release_tags + @release_tags.sort!{|a,b| a <=> b } + #@release_tags.sort!{|a,b| a <=> b }.reverse! end + @release_tags + end - # @return [Array] - def branch_names; @branch_names = self.repo.branches.each_name.sort if @branch_names.∅?; @branch_names; end + # @return [Array] + def branch_names; @branch_names = self.repo.branches.each_name.sort if @branch_names.∅?; @branch_names; end - end # end: Class{GitAPI} - end # end: Module{MetaData} + end # end: Class{GitAPI} end # -------------------------------------------- ⚠️ -------------------------------------------- diff --git a/lib/ruuuby/ruuuby/engine/f22/b05.rb b/lib/ruuuby/ruuuby/engine/f22/b05.rb index 80b2d2d..aa64b43 100644 --- a/lib/ruuuby/ruuuby/engine/f22/b05.rb +++ b/lib/ruuuby/ruuuby/engine/f22/b05.rb @@ -17,6 +17,35 @@ class RuuubyEngine # `💎.engine.os` module F22B05 + # @return [Ruuuby::MetaData::RuuubyEngine::F22B05::IPv4] + def self.ipv4; self::IPv4; end + + # `💎.engine.os.ipv4` + module IPv4 + + # TODO: TDD + # + # @see https://stackoverflow.com/questions/14112955/how-to-get-my-machines-ip-address-from-ruby-without-leveraging-from-other-ip-ad/27454154 + # @see https://en.wikipedia.org/wiki/Localhost + def self.internal + results = ::Socket.ip_address_list.reject(&:ipv6?).reject {|s| s.inspect_sockaddr == '127.0.0.1'} + if results.length == 1 + return results[0].inspect_sockaddr + else + error_message = "| {💎.engine.os.ipv4}-> m{ipv4_internal} got results{#{results.to_s}}, currently only built to expect single IP back |" + 🛑 ::NotImplementedError.new(error_message) + end + end + + # TODO: TDD + # + # @see https://unix.stackexchange.com/questions/22615/how-can-i-get-my-external-ip-address-in-a-shell-script + # @see https://www.linuxtrainingacademy.com/determine-public-ip-address-command-line-curl/ + # @see https://stackoverflow.com/questions/13270042/get-public-remote-ip-address + # @see https://www.whatismyip.com/what-is-my-public-ip-address/ + def self.external; res, req = 🌐.get!('https://api.ipify.org'); res.body; end + end + # @param [String] def self.current_user; ::Etc.getlogin; end diff --git a/lib/ruuuby/ruuuby/engine/ruuuby_engine.rb b/lib/ruuuby/ruuuby/engine/ruuuby_engine.rb index 29b8089..b366abb 100644 --- a/lib/ruuuby/ruuuby/engine/ruuuby_engine.rb +++ b/lib/ruuuby/ruuuby/engine/ruuuby_engine.rb @@ -114,7 +114,7 @@ def stats # @return [::Ruuuby::MetaData::RuuubyORM] def orm if @orm.nil? - @orm = ::Ruuuby::MetaData::RuuubyORM.new(self, 'configs_local/db/test.yml') + @orm = ::Ruuuby::MetaData::RuuubyORM.new(self) end @orm end diff --git a/lib/ruuuby/ruuuby/ruuuby_api.rb b/lib/ruuuby/ruuuby/ruuuby_api.rb index f26380b..1afba2e 100644 --- a/lib/ruuuby/ruuuby/ruuuby_api.rb +++ b/lib/ruuuby/ruuuby/ruuuby_api.rb @@ -30,11 +30,6 @@ def run_cmd(cmd) [out, err] end - # @return [String, Array] parsed output - def run_cmd_custom(cmd) - self.get_tty.run!(cmd, {timeout: @default_timeout, pty: false}) - end - # @see http://www.tldp.org/LDP/abs/html/exitcodes.html # # | error code | description | @@ -49,16 +44,23 @@ def run_cmd_custom(cmd) # | 255\* | exit status out of range | # # TODO: useful cmd: ps -lww -p - def run_cmd!(cmd) + # + # @param [String] cmd + # @param [Boolean] allow_errors + def run_cmd!(cmd, allow_errors=false) out, err = self.get_tty.run(cmd, timeout: @default_timeout, pty: false) unless err.empty? - raise "cmd{#{cmd.to_s}} encountered error{#{err.to_s}}" - end - if cmd.str? || cmd.ary? - out.clean - else - out + if allow_errors + if out.empty? + return [nil, err.clean] + else + return [out.clean, err.clean] + end + else + raise "cmd{#{cmd.to_s}} encountered error{#{err.to_s}}" + end end + out.clean end # @param [String] cmd diff --git a/lib/ruuuby/ruuuby/ruuuby_orm.rb b/lib/ruuuby/ruuuby/ruuuby_orm.rb index cf92a7b..184cd0f 100644 --- a/lib/ruuuby/ruuuby/ruuuby_orm.rb +++ b/lib/ruuuby/ruuuby/ruuuby_orm.rb @@ -8,8 +8,9 @@ class RuuubyORM < ::Ruuuby::MetaData::EngineComponentAPI attr_reader :db_orm - def initialize(engine, path_relative) + def initialize(engine) super(engine) + path_relative = engine.stats_ext['RUUUBY_CONFIGS'] if engine.stats_ext['F92_B02'] == true @db_orm = ::Ruuuby::MetaData::DBConnectionPostgreSQL.new("#{engine.path_base}#{path_relative}") @db_orm.obtain_connection diff --git a/lib/ruuuby/version.rb b/lib/ruuuby/version.rb index b2cccd4..e822767 100644 --- a/lib/ruuuby/version.rb +++ b/lib/ruuuby/version.rb @@ -2,9 +2,12 @@ # +Ruuuby+ module ::Ruuuby - # @type [String] the version of *Ruuuby* reflected in this source code - VERSION = '0.1.0.pre.2'.freeze + # @type [String] the version of Gem(*ruuuby*) reflected in this source code + VERSION = '0.1.0.pre.3'.freeze - # @type [String] the version of Gem{`rubygem-update`} utilized and recommended + # @type [String] the version of Ruby utilized and minimum required + VERSION_RUBY = ::Gem.ruby_version.to_s.freeze + + # @type [String] the version of Gem{*rubygem-update*} utilized and recommended VERSION_BUNDLER = '3.2.0.rc.2'.freeze end diff --git a/ruuuby.gemspec b/ruuuby.gemspec index 50364e9..5f28b77 100644 --- a/ruuuby.gemspec +++ b/ruuuby.gemspec @@ -5,26 +5,28 @@ gem.name = 'ruuuby' gem.version = ::Ruuuby::VERSION - gem.summary = 'wip: increase quality of Ruby coding life' - gem.description = '{wip: flavored modifications & extensions for increased quality of Ruby coding life}' + gem.summary = 'migration wip' + gem.description = 'migration wip' gem.authors = ["Uladzislau Tarsunou"] gem.homepage = 'https://github.com/utarsuno/ruuuby' gem.license = 'MIT' - gem.required_ruby_version = ">= #{Gem.ruby_version.to_s}" + gem.required_ruby_version = ">= #{::Ruuuby::VERSION_RUBY}" gem.required_rubygems_version = ">= #{::Ruuuby::VERSION_BUNDLER}" - gem.installed_by_version = "#{::Ruuuby::VERSION_BUNDLER}" + gem.installed_by_version = ::Ruuuby::VERSION_BUNDLER gem.platform = ::Gem::Platform.local gem.post_install_message = "Gem{ruuuby, v#{::Ruuuby::VERSION}} has just been installed, cheers!" _md = gem.metadata _md['homepage_uri'] = gem.homepage - _md['source_code_uri'] = "#{gem.homepage}.git" - _md['changelog_uri'] = "#{gem.homepage}/blob/master/CHANGELOG.md" - _md['documentation_uri'] = "#{gem.homepage}/tree/master/help" + #_md['source_code_uri'] = "#{gem.homepage}.git" + _md['source_code_uri'] = "#{gem.homepage}/tree/v#{::Ruuuby::VERSION}" + _md['changelog_uri'] = "https://raw.githubusercontent.com/utarsuno/ruuuby/master/History.txt" + _md['documentation_uri'] = gem.homepage gem.requirements = [ 'mac or Linux based OS', - 'C-compiler' + 'C-compiler', + '(atm) building gem requires working from git code source, not just gem', ] gem.bindir = 'bin' @@ -54,6 +56,8 @@ gem.add_development_dependency(:pg, '~> 1.2.3') gem.add_development_dependency(:activerecord, '~> 6.1.0.rc1') + gem.add_development_dependency(:open3, '~> 0.1.0') + gem.add_runtime_dependency(:'tty-command', '~> 0.10.0') gem.add_runtime_dependency(:finite_machine, '~> 0.14.0') end diff --git a/services/dev_configs/mac/spec/locale/f43_spec.rb b/services/dev_configs/mac/spec/locale/f43_spec.rb new file mode 100644 index 0000000..8556817 --- /dev/null +++ b/services/dev_configs/mac/spec/locale/f43_spec.rb @@ -0,0 +1,19 @@ +# encoding: UTF-8 + +RSpec.describe 'ruby' do + context 'locale', :preferences do + + context 'recommended settings for {iconv}' do + it 'passes all health checks' do + expect(💎.engine.api_locale.api_iconv.healthy?).to eq(true) + end + it 'has needed version{1.11}' do + expect_needed_version(💎.engine.api_locale.api_iconv, 'iconv (GNU libiconv 1.11)') + end + it 'supports needed encoding{UTF-8}' do + expect(💎.engine.api_locale.api_iconv.∃_encoding?('UTF-8')).to eq(true) + end + end + + end +end diff --git a/services/dev_configs/mac/spec/locale/f44_spec.rb b/services/dev_configs/mac/spec/locale/f44_spec.rb new file mode 100644 index 0000000..b8a5858 --- /dev/null +++ b/services/dev_configs/mac/spec/locale/f44_spec.rb @@ -0,0 +1,13 @@ +# encoding: UTF-8 + +RSpec.describe 'ruby' do + context 'locale', :preferences do + + context 'recommended settings for {zsh}' do + it 'expected version{5.8} matches' do + expect(💻('zsh --version')).to eq('zsh 5.8 (x86_64-apple-darwin18.7.0)') + end + end + + end +end diff --git a/services/dev_configs/mac/spec/locale/f45_spec.rb b/services/dev_configs/mac/spec/locale/f45_spec.rb new file mode 100644 index 0000000..5c24e0b --- /dev/null +++ b/services/dev_configs/mac/spec/locale/f45_spec.rb @@ -0,0 +1,13 @@ +# encoding: UTF-8 + +RSpec.describe 'ruby' do + context 'locale', :preferences do + + context 'recommended settings for {curl}' do + it 'expected version{7.64.1} matches' do + expect(💻('curl --version')).to eq(["curl 7.64.1 (x86_64-apple-darwin19.0) libcurl/7.64.1 (SecureTransport) LibreSSL/2.8.3 zlib/1.2.11 nghttp2/1.39.2", "Release-Date: 2019-03-27", "Protocols: dict file ftp ftps gopher http https imap imaps ldap ldaps pop3 pop3s rtsp smb smbs smtp smtps telnet tftp ", "Features: AsynchDNS GSS-API HTTP2 HTTPS-proxy IPv6 Kerberos Largefile libz MultiSSL NTLM NTLM_WB SPNEGO SSL UnixSockets"]) + end + end + + end +end diff --git a/services/dev_configs/mac/spec/locale/f46_spec.rb b/services/dev_configs/mac/spec/locale/f46_spec.rb new file mode 100644 index 0000000..0c01031 --- /dev/null +++ b/services/dev_configs/mac/spec/locale/f46_spec.rb @@ -0,0 +1,34 @@ +# encoding: UTF-8 + +RSpec.describe 'ruby' do + context 'locale', :preferences do + + context 'for gem{bundler}' do + it 'passes all health checks' do + expect(::Bundler.healthy?).to eq(true) + end + it 'has correct version' do + expect_needed_version(::Bundler, '2.2.0.rc.2', ::Bundler::VERSION) + end + it 'as defined by {Gem}' do + expect(::Gem::BundlerVersionFinder.bundler_version.to_s).to eq(::Bundler.version_current) + end + it 'w/ needed ENV_VARs' do + expected_path = "#{💎.engine.path_base}Gemfile" + expect(::ENV['BUNDLE_GEMFILE']).to eq(expected_path) + expect(::Bundler.path_gemfile).to eq(expected_path) + end + it 'does not require sudo (depending on OS)' do + if 💎.engine.os.mac? + expect(::Bundler.requires_sudo?).to eq(false) + elsif 💎.engine.os.unix + # currently, only Alpine-Linux is supported/expected, which will run w/ user{`root`} + expect(::Bundler.requires_sudo?).to eq(true) + else + # ¯\_(ツ)_/¯ + end + end + end # end: {for gem{bundler}} + + end +end diff --git a/services/dev_configs/mac/spec/locale/f47_spec.rb b/services/dev_configs/mac/spec/locale/f47_spec.rb new file mode 100644 index 0000000..e216c67 --- /dev/null +++ b/services/dev_configs/mac/spec/locale/f47_spec.rb @@ -0,0 +1,16 @@ +# encoding: UTF-8 + +RSpec.describe 'ruby' do + context 'locale', :preferences do + + context 'for gem{rubygems-update}' do + it 'has correct version' do + expect_needed_version(::Gem, '3.2.0.rc.2', ::Gem.rubygems_version.to_s) + end + it 'matching output of cmd{gem -v}' do + expect(::Gem.version_current).to eq(💻('gem -v')) + end + end + + end +end diff --git a/services/dev_configs/mac/spec/locale/f92_b00_spec.rb b/services/dev_configs/mac/spec/locale/f92_b00_spec.rb new file mode 100644 index 0000000..4ffff26 --- /dev/null +++ b/services/dev_configs/mac/spec/locale/f92_b00_spec.rb @@ -0,0 +1,17 @@ +# encoding: UTF-8 + +RSpec.describe 'ruby' do + context 'locale', :preferences do + + context 'recommended settings for {f93_b00}' do + + context 'for gem{activerecord}' do + it 'has correct version{5.2.4.3}' do + expect(::ActiveRecord::VERSION::STRING).to eq('6.0.3.4') + end + end + + end + + end +end diff --git a/services/dev_configs/mac/spec/locale/f98_spec.rb b/services/dev_configs/mac/spec/locale/f98_spec.rb new file mode 100644 index 0000000..68ddd3e --- /dev/null +++ b/services/dev_configs/mac/spec/locale/f98_spec.rb @@ -0,0 +1,24 @@ +# encoding: UTF-8 + +RSpec.describe 'ruby' do + context 'locale', :preferences do + + context 'recommended settings for {compiler}' do + + it '${clang --version} matches ${cc --version}' do + expect(💻('clang --version')).to eq(💻('cc --version')) + end + + it '${gcc --version} has correct version' do + out, err = 💻('gcc --version', true) + + expect(out[0]).to eq("Apple clang version 12.0.0 (clang-1200.0.32.21)") + expect(out[1]).to eq("Target: x86_64-apple-darwin19.6.0") + expect(out[2]).to eq("Thread model: posix") + expect(out[3]).to eq("InstalledDir: /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin") + end + + end + + end +end diff --git a/services/dev_configs/mac/spec/locale/locale_full_verification_spec.rb b/services/dev_configs/mac/spec/locale/locale_full_verification_spec.rb new file mode 100644 index 0000000..4d8eb17 --- /dev/null +++ b/services/dev_configs/mac/spec/locale/locale_full_verification_spec.rb @@ -0,0 +1,40 @@ +# encoding: UTF-8 + +RSpec.describe 'ruby' do + context 'locale', :preferences do + + # @see https://stackoverflow.com/questions/17980759/xcode-select-active-developer-directory-error + context 'configs for xcode' do + context 'xcode-select' do + it 'has needed version' do + expect(💻('xcode-select --version')).to eq('xcode-select version 2373.') + end + it 'has needed path' do + # @see https://github.com/nodejs/node-gyp/issues/569 + # to change path after fresh xcode installation: `sudo xcode-select -s /Applications/Xcode.app/Contents/Developer` + expect(💻('xcode-select --print-path')).to eq('/Applications/Xcode.app/Contents/Developer') + end + end + context 'xcodebuild' do + it 'has needed version' do + expect(💻('xcodebuild -version')).to eq(["Xcode 12.1", "Build version 12A7403"]) + end + end + end + + # @see https://en.wikipedia.org/wiki/History_of_Python + context 'other coding languages' do + context 'python' do + it 'has expected version{3.9.0}' do + expect(💻('python3 --version')).to eq('Python 3.9.0') + end + end + context 'java' do + it 'has correct version{13.0.2}' do + expect(💻('java --version')).to eq(['openjdk 13.0.2 2020-01-14', 'OpenJDK Runtime Environment (build 13.0.2+8)', 'OpenJDK 64-Bit Server VM (build 13.0.2+8, mixed mode, sharing)']) + end + end + end + + end +end diff --git a/services/message_bot/models/entity_channel.rb b/services/message_bot/models/entity_channel.rb new file mode 100644 index 0000000..aceed92 --- /dev/null +++ b/services/message_bot/models/entity_channel.rb @@ -0,0 +1,22 @@ +# encoding: UTF-8 + +class CreateEntityChannel < RuuubyDBMigration + + def self.up + create_table :entity_channels do |t| + t.string :name, :null => false + t.json :meta_data, :null => true + end + + add_index :entity_channels, :name, unique: true + end + + def self.down + ♻️index(:entity_channels, :name) + ♻️table!(:entity_channels) + end +end + +class EntityChannel < ApplicationRecord + +end diff --git a/services/message_bot/models/entity_user.rb b/services/message_bot/models/entity_user.rb new file mode 100644 index 0000000..ec6d978 --- /dev/null +++ b/services/message_bot/models/entity_user.rb @@ -0,0 +1,22 @@ +# encoding: UTF-8 + +class CreateEntityUser < RuuubyDBMigration + + def self.up + create_table :entity_users do |t| + t.string :name, :null => false + t.json :meta_data, :null => true + end + + add_index :entity_users, :name, unique: true + end + + def self.down + ♻️index(:entity_users, :name) + ♻️table!(:entity_users) + end +end + +class EntityUser < ApplicationRecord + +end diff --git a/services/nginx/Dockerfile b/services/nginx/Dockerfile index 8bbe19a..0887a9d 100644 --- a/services/nginx/Dockerfile +++ b/services/nginx/Dockerfile @@ -8,6 +8,7 @@ RUN apk add --no-cache curl wget \ && mkdir /etc/nginx/ruuuby \ && mkdir /etc/nginx/ruuuby/caching \ && mkdir /etc/nginx/ruuuby/gzip \ + && mkdir /etc/nginx/ruuuby/proxy_pass \ && mkdir /etc/nginx/ruuuby/unsorted \ && rm /etc/nginx/conf.d/default.conf \ && rm -rf /var/cache/apk/* diff --git a/services/nginx/includes/unsorted/proxy_pass.nginx b/services/nginx/includes/proxy_pass/default.nginx similarity index 100% rename from services/nginx/includes/unsorted/proxy_pass.nginx rename to services/nginx/includes/proxy_pass/default.nginx diff --git a/services/nginx/includes/proxy_pass/pgadmin.nginx b/services/nginx/includes/proxy_pass/pgadmin.nginx new file mode 100644 index 0000000..b8a90f6 --- /dev/null +++ b/services/nginx/includes/proxy_pass/pgadmin.nginx @@ -0,0 +1,6 @@ +proxy_redirect off; +proxy_set_header Host $http_host; +proxy_set_header X-Forwarded-Host $http_host; +proxy_set_header X-Real-IP $remote_addr; +proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; +proxy_http_version 1.1; \ No newline at end of file diff --git a/services/nginx/includes/proxy_pass/rabbitmq.nginx b/services/nginx/includes/proxy_pass/rabbitmq.nginx new file mode 100644 index 0000000..ebdd565 --- /dev/null +++ b/services/nginx/includes/proxy_pass/rabbitmq.nginx @@ -0,0 +1,4 @@ +proxy_http_version 1.1; +proxy_set_header Host $host; +proxy_set_header X-Real-IP $remote_addr; +proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; diff --git a/services/nginx/includes/unsorted/cors.nginx b/services/nginx/includes/unsorted/cors.nginx index 32c7ac1..6b15086 100644 --- a/services/nginx/includes/unsorted/cors.nginx +++ b/services/nginx/includes/unsorted/cors.nginx @@ -1,14 +1,15 @@ # Thanks to original author: https://gist.github.com/Stanback/7145487 set $cors ''; -if ($http_origin ~ '^https?://(localhost|www\.nexuslocal\.com|www\.quasarsource\.com|www\.ruuuby\.com)') { +if ($http_origin ~ '^https?://(localhost\.com|www\.nexuslocal\.com|www\.quasarsource\.com|www\.ruuuby\.com)') { set $cors 'true'; } if ($cors = 'true') { add_header 'Access-Control-Allow-Origin' "$http_origin" always; add_header 'Access-Control-Allow-Credentials' 'true' always; - add_header 'Access-Control-Allow-Methods' 'GET, POST, PUT, DELETE, OPTIONS' always; +# add_header 'Access-Control-Allow-Methods' 'GET, POST, PUT, DELETE, OPTIONS' always; + add_header 'Access-Control-Allow-Methods' 'GET, POST, PUT, DELETE, OPTIONS, PATCH' always; add_header 'Access-Control-Allow-Headers' 'Accept,Authorization,Cache-Control,Content-Type,DNT,If-Modified-Since,Keep-Alive,Origin,User-Agent,X-Requested-With' always; # required to be able to read Authorization header in frontend add_header 'Access-Control-Expose-Headers' 'Authorization' always; @@ -21,3 +22,11 @@ if ($request_method = 'OPTIONS') { add_header 'Content-Length' 0; return 204; } + +if ($request_method = 'PATCH') { + # tell client that this pre-flight info is valid for 20 days + add_header 'Access-Control-Max-Age' 1728000; + add_header 'Content-Type' 'text/plain charset=UTF-8'; + add_header 'Content-Length' 0; + return 204; +} diff --git a/services/nginx/ruuuby.dev.nginx b/services/nginx/ruuuby.dev.nginx index ecc5daf..505a7e3 100644 --- a/services/nginx/ruuuby.dev.nginx +++ b/services/nginx/ruuuby.dev.nginx @@ -43,20 +43,19 @@ http { add_header X-Frame-Options ""; - upstream docker_pgadmin { - server service_pgadmin; + upstream docker_pgadmin_dev { + server service_pgadmin_dev:13337; } - upstream docker_js { - server service_js:8080; + upstream docker_js_dev { + server service_js_dev:8080; } - upstream docker_rabbitmq { - server service_rabbitmq:15672; + upstream docker_rabbitmq_dev { + server service_rabbitmq_dev:15672; } server { - listen 80; listen 1337 reuseport; server_name localhost ruuuby.com www.ruuuby.com; @@ -77,22 +76,27 @@ http { root /; autoindex on; } + } + + # __ __ __ + # |__) / _` /\ | \ |\/| | |\ | + # | \__> /~~\ |__/ | | | | \| + server { + listen 13337; + + server_name localhost pgadmin_dev; - # __ __ __ - # |__) / _` /\ | \ |\/| | |\ | - # | \__> /~~\ |__/ | | | | \| location /pgadmin4/ { - proxy_pass http://docker_pgadmin; - include /etc/nginx/ruuuby/unsorted/proxy_pass.nginx; - include /etc/nginx/ruuuby/unsorted/cors.nginx; - add_header X-Frame-Options ""; - proxy_set_header X-Frame-Options ""; + proxy_pass http://docker_pgadmin_dev; + + include /etc/nginx/ruuuby/proxy_pass/pgadmin.nginx; + include /etc/nginx/ruuuby/unsorted/cors.nginx; + proxy_set_header X-Script-Name /pgadmin4; } # TODO: for when needed: SSL example for pgadmin4: https://www.pgadmin.org/docs/pgadmin4/latest/container_deployment.html } - server { listen 8080 reuseport; @@ -100,52 +104,21 @@ http { # | /\ \ / /\ /__` / ` |__) | |__) | # \__/ /~~\ \/ /~~\ .__/ \__, | \ | | | location / { - #resolver 127.0.0.11 valid=30s; - #set $upstream_bar foo; - #proxy_pass http://$upstream_bar:8080; - - proxy_pass http://docker_js; - include /etc/nginx/ruuuby/unsorted/proxy_pass.nginx; - #include /etc/nginx/ruuuby/unsorted/docker_dns_fix; - - #add_header X-Frame-Options ""; - #proxy_set_header X-Frame-Options ""; - #proxy_set_header X-Script-Name /js; + proxy_pass http://docker_js_dev; + include /etc/nginx/ruuuby/proxy_pass/default.nginx; } # TODO: https://serverfault.com/questions/655067/is-it-possible-to-make-nginx-listen-to-different-ports } server { - #listen 5672 reuseport; listen 15672 reuseport; # __ __ __ ___ __ # |__) /\ |__) |__) | | |\/| / \ # | \ /~~\ |__) |__) | | | | \__X location / { - #resolver 127.0.0.11 valid=30s; - #set $upstream_bar foo; - #proxy_pass http://$upstream_bar:8080; - - #proxy_set_header X-Script-Name /rabbitmq; - #proxy_pass http://docker_rabbitmq:15672/; - proxy_pass http://docker_rabbitmq; - #include /etc/nginx/ruuuby/unsorted/proxy_pass.nginx; - #include /etc/nginx/ruuuby/unsorted/cors.nginx; - - proxy_http_version 1.1; - proxy_set_header Host $host; - proxy_set_header X-Real-IP $remote_addr; - proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; - - #add_header X-Frame-Options ""; - #proxy_set_header X-Frame-Options ""; - #proxy_set_header X-Script-Name /rabbitmq; - #include /etc/nginx/ruuuby/unsorted/docker_dns_fix; - - #add_header X-Frame-Options ""; - #proxy_set_header X-Frame-Options ""; - #proxy_set_header X-Script-Name /js; + proxy_pass http://docker_rabbitmq_dev; + include /etc/nginx/ruuuby/proxy_pass/rabbitmq.nginx; } } diff --git a/services/nginx/ruuuby.prod.nginx b/services/nginx/ruuuby.prod.nginx index 16d778f..715448b 100644 --- a/services/nginx/ruuuby.prod.nginx +++ b/services/nginx/ruuuby.prod.nginx @@ -1,30 +1,16 @@ -# main context {configurations that apply on a broad application level} - -# ideally (at max) 1 worker per 1 CPU worker_processes auto; - -# number of file descriptors that can be used by NGINX (default is 2000) worker_rlimit_nofile 1048575; - -# @see: https://www.keycdn.com/support/nginx-error-log error_log /var/log/nginx/error.log warn; -# this context is used for setting global options that affect general behavior of handling connections events { - # max clients = worker_connections * worker_processes worker_connections 1024; - # NON-PROD-SAFE:{an optimization for serving many clients in each thread (esp. for Linux)} use epoll; - # NON-PROD-SAFE:{accept as many connections as possible, ideally requires more worker_processes} multi_accept on; - - # since 'reuseport' is being used, 'accept_mutex' should be set off accept_mutex off; } -# sibling of the events context http { default_type application/octet-stream; @@ -35,12 +21,6 @@ http { include /etc/nginx/ruuuby/unsorted/timeouts.nginx; include /etc/nginx/ruuuby/unsorted/docker_dns_fix.nginx; - #log_format main '$remote_addr - $remote_user [$time_local] "$request" ' - # '$status $body_bytes_sent "$http_referer" ' - # '"$http_user_agent" "$http_x_forwarded_for"'; - - #access_log logs/access.log main; - add_header X-Frame-Options ""; upstream docker_pgadmin { @@ -48,16 +28,16 @@ http { } upstream docker_js { - server service_js:8080; + server service_js:8082; } upstream docker_rabbitmq { - server service_rabbitmq:15672; + server service_rabbitmq:15674; } server { listen 80; - listen 1337 reuseport; + listen 1339 reuseport; server_name localhost ruuuby.com www.ruuuby.com; @@ -82,45 +62,36 @@ http { # |__) / _` /\ | \ |\/| | |\ | # | \__> /~~\ |__/ | | | | \| location /pgadmin4/ { - proxy_pass http://docker_pgadmin; - include /etc/nginx/ruuuby/unsorted/proxy_pass.nginx; - include /etc/nginx/ruuuby/unsorted/cors.nginx; - add_header X-Frame-Options ""; - proxy_set_header X-Frame-Options ""; - proxy_set_header X-Script-Name /pgadmin4; + proxy_pass http://docker_pgadmin; + include /etc/nginx/ruuuby/proxy_pass/pgadmin.nginx; + #include /etc/nginx/ruuuby/unsorted/cors.nginx; + #add_header X-Frame-Options ""; + #proxy_set_header X-Frame-Options ""; + #proxy_set_header X-Script-Name /pgadmin4; } - # TODO: for when needed: SSL example for pgadmin4: https://www.pgadmin.org/docs/pgadmin4/latest/container_deployment.html } - server { - listen 8080 reuseport; + listen 8082 reuseport; # __ __ __ __ ___ # | /\ \ / /\ /__` / ` |__) | |__) | # \__/ /~~\ \/ /~~\ .__/ \__, | \ | | | location / { - proxy_pass http://docker_js; - include /etc/nginx/ruuuby/unsorted/proxy_pass.nginx; + proxy_pass http://docker_js; + include /etc/nginx/ruuuby/proxy_pass/default.nginx; } } server { - #listen 5672 reuseport; - listen 15672 reuseport; + listen 15674 reuseport; # __ __ __ ___ __ # |__) /\ |__) |__) | | |\/| / \ # | \ /~~\ |__) |__) | | | | \__X location / { - - proxy_pass http://docker_rabbitmq; - - proxy_http_version 1.1; - proxy_set_header Host $host; - proxy_set_header X-Real-IP $remote_addr; - proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; - + proxy_pass http://docker_rabbitmq; + include /etc/nginx/ruuuby/proxy_pass/rabbitmq.nginx; } } diff --git a/services/nginx/ruuuby.test.nginx b/services/nginx/ruuuby.test.nginx index a29cfa5..efceaec 100644 --- a/services/nginx/ruuuby.test.nginx +++ b/services/nginx/ruuuby.test.nginx @@ -1,30 +1,16 @@ -# main context {configurations that apply on a broad application level} +worker_processes auto; -# ideally (at max) 1 worker per 1 CPU -worker_processes auto; - -# number of file descriptors that can be used by NGINX (default is 2000) worker_rlimit_nofile 1048575; -# @see: https://www.keycdn.com/support/nginx-error-log error_log /var/log/nginx/error.log warn; -# this context is used for setting global options that affect general behavior of handling connections events { - # max clients = worker_connections * worker_processes - worker_connections 1024; - - # NON-PROD-SAFE:{an optimization for serving many clients in each thread (esp. for Linux)} + worker_connections 512; use epoll; - - # NON-PROD-SAFE:{accept as many connections as possible, ideally requires more worker_processes} multi_accept on; - - # since 'reuseport' is being used, 'accept_mutex' should be set off accept_mutex off; } -# sibling of the events context http { default_type application/octet-stream; @@ -35,29 +21,22 @@ http { include /etc/nginx/ruuuby/unsorted/timeouts.nginx; include /etc/nginx/ruuuby/unsorted/docker_dns_fix.nginx; - #log_format main '$remote_addr - $remote_user [$time_local] "$request" ' - # '$status $body_bytes_sent "$http_referer" ' - # '"$http_user_agent" "$http_x_forwarded_for"'; - - #access_log logs/access.log main; - add_header X-Frame-Options ""; - upstream docker_pgadmin { - server service_pgadmin; + upstream docker_pgadmin_test { + server service_pgadmin_test:13338; } - upstream docker_js { - server service_js:8080; + upstream docker_js_test { + server service_js_test:8081; } - upstream docker_rabbitmq { - server service_rabbitmq:15672; + upstream docker_rabbitmq_test { + server service_rabbitmq_test:15673; } server { - listen 80; - listen 1337 reuseport; + listen 1338 reuseport; server_name localhost ruuuby.com www.ruuuby.com; @@ -77,48 +56,47 @@ http { root /; autoindex on; } + } + + # __ __ __ + # |__) / _` /\ | \ |\/| | |\ | + # | \__> /~~\ |__/ | | | | \| + server { + listen 13338; + + server_name localhost pgadmin_dev; - # __ __ __ - # |__) / _` /\ | \ |\/| | |\ | - # | \__> /~~\ |__/ | | | | \| location /pgadmin4/ { - proxy_pass http://docker_pgadmin; - include /etc/nginx/ruuuby/unsorted/proxy_pass.nginx; - include /etc/nginx/ruuuby/unsorted/cors.nginx; - add_header X-Frame-Options ""; - proxy_set_header X-Frame-Options ""; + proxy_pass http://docker_pgadmin_test; + + include /etc/nginx/ruuuby/proxy_pass/pgadmin.nginx; + include /etc/nginx/ruuuby/unsorted/cors.nginx; + proxy_set_header X-Script-Name /pgadmin4; } - # TODO: for when needed: SSL example for pgadmin4: https://www.pgadmin.org/docs/pgadmin4/latest/container_deployment.html } - server { - listen 8080 reuseport; + listen 8081 reuseport; # __ __ __ __ ___ # | /\ \ / /\ /__` / ` |__) | |__) | # \__/ /~~\ \/ /~~\ .__/ \__, | \ | | | location / { - proxy_pass http://docker_js; - include /etc/nginx/ruuuby/unsorted/proxy_pass.nginx; + proxy_pass http://docker_js_test; + include /etc/nginx/ruuuby/proxy_pass/default.nginx; } } server { - #listen 5672 reuseport; - listen 15672 reuseport; + listen 15673 reuseport; # __ __ __ ___ __ # |__) /\ |__) |__) | | |\/| / \ # | \ /~~\ |__) |__) | | | | \__X location / { - proxy_pass http://docker_rabbitmq; - - proxy_http_version 1.1; - proxy_set_header Host $host; - proxy_set_header X-Real-IP $remote_addr; - proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; + proxy_pass http://docker_rabbitmq_test; + include /etc/nginx/ruuuby/proxy_pass/rabbitmq.nginx; } } diff --git a/services/pgadmin/Dockerfile b/services/pgadmin/Dockerfile new file mode 100644 index 0000000..dd4979c --- /dev/null +++ b/services/pgadmin/Dockerfile @@ -0,0 +1,5 @@ +FROM dpage/pgadmin4 + +ENV SERVICE_NAME="service_pgadmin" +ENV SERVICE_OS="alpine" +ENV SERVICE_OS_VERSION="3.11.6" diff --git a/services/rabbitmq/Dockerfile b/services/rabbitmq/Dockerfile index 27bda2e..9f3efe4 100644 --- a/services/rabbitmq/Dockerfile +++ b/services/rabbitmq/Dockerfile @@ -1 +1,3 @@ FROM rabbitmq:3.8.8-management-alpine + +ENV SERVICE_NAME 'service_rabbitmq' diff --git a/services/rabbitmq/definitions.json b/services/rabbitmq/dev/definitions.json similarity index 100% rename from services/rabbitmq/definitions.json rename to services/rabbitmq/dev/definitions.json diff --git a/services/rabbitmq/rabbitmq.config b/services/rabbitmq/dev/rabbitmq.config similarity index 100% rename from services/rabbitmq/rabbitmq.config rename to services/rabbitmq/dev/rabbitmq.config diff --git a/services/rabbitmq/prod/definitions.json b/services/rabbitmq/prod/definitions.json new file mode 100644 index 0000000..0c3ffd0 --- /dev/null +++ b/services/rabbitmq/prod/definitions.json @@ -0,0 +1,59 @@ +{ + "rabbit_version":"3.8.8", + "users": [ + { + "name":"guest", + "password_hash":"fd0GyzAf6C6hmgCJ5VU+TSyzUNlzypPlGb7VDKkqUvJqVxyd", + "hashing_algorithm":"rabbit_password_hashing_sha256", + "tags":"administrator" + } + ], + "vhosts": [ + { + "name":"/" + } + ], + "permissions":[ + { + "user":"guest", + "vhost":"/", + "configure":".*", + "write":".*", + "read":".*" + } + ], + "parameters":[], + "policies":[ + {"vhost":"/","name":"ha","pattern":"", "definition":{"ha-mode":"all","ha-sync-mode":"automatic","ha-sync-batch-size":5}} + ], + "queues":[ + { + "name":"queue_hello", + "vhost":"/", + "durable":true, + "auto_delete":false, + "arguments":{} + } + ], + "exchanges":[ + { + "name":"exchange_hello", + "vhost":"/", + "type":"topic", + "durable":false, + "auto_delete":false, + "internal":false, + "arguments":{} + } + ], + "bindings":[ + { + "source":"exchange_hello", + "vhost":"/", + "destination":"queue_nexus_courier", + "destination_type":"queue", + "routing_key":"routing_key", + "arguments":{} + } + ] +} \ No newline at end of file diff --git a/services/rabbitmq/prod/rabbitmq.config b/services/rabbitmq/prod/rabbitmq.config new file mode 100644 index 0000000..20ebad7 --- /dev/null +++ b/services/rabbitmq/prod/rabbitmq.config @@ -0,0 +1,20 @@ +[ + { rabbit, [ + {cluster_nodes, {[ 'service_rabbitmq@service_rabbitmq' ], disc}}, + {tcp_listen_options, [binary, {backlog, 1024}, {nodelay, true}, {keepalive, true} ]}, + {vm_memory_high_watermark, 0.6}, + { loopback_users, [ ] }, + { tcp_listeners, [ 5674 ] }, + { ssl_listeners, [ ] }, + { default_pass, <<"guest">> }, + { default_user, <<"guest">> }, + { hipe_compile, false } + ] }, + + { rabbitmq_management, [ { listener, [ + { port, 15674 }, + { ssl, false } + ] }, + {load_definitions, "/etc/rabbitmq/definitions.json"} + ] } +]. diff --git a/services/rabbitmq/test/definitions.json b/services/rabbitmq/test/definitions.json new file mode 100644 index 0000000..0c3ffd0 --- /dev/null +++ b/services/rabbitmq/test/definitions.json @@ -0,0 +1,59 @@ +{ + "rabbit_version":"3.8.8", + "users": [ + { + "name":"guest", + "password_hash":"fd0GyzAf6C6hmgCJ5VU+TSyzUNlzypPlGb7VDKkqUvJqVxyd", + "hashing_algorithm":"rabbit_password_hashing_sha256", + "tags":"administrator" + } + ], + "vhosts": [ + { + "name":"/" + } + ], + "permissions":[ + { + "user":"guest", + "vhost":"/", + "configure":".*", + "write":".*", + "read":".*" + } + ], + "parameters":[], + "policies":[ + {"vhost":"/","name":"ha","pattern":"", "definition":{"ha-mode":"all","ha-sync-mode":"automatic","ha-sync-batch-size":5}} + ], + "queues":[ + { + "name":"queue_hello", + "vhost":"/", + "durable":true, + "auto_delete":false, + "arguments":{} + } + ], + "exchanges":[ + { + "name":"exchange_hello", + "vhost":"/", + "type":"topic", + "durable":false, + "auto_delete":false, + "internal":false, + "arguments":{} + } + ], + "bindings":[ + { + "source":"exchange_hello", + "vhost":"/", + "destination":"queue_nexus_courier", + "destination_type":"queue", + "routing_key":"routing_key", + "arguments":{} + } + ] +} \ No newline at end of file diff --git a/services/rabbitmq/test/rabbitmq.config b/services/rabbitmq/test/rabbitmq.config new file mode 100644 index 0000000..62db39e --- /dev/null +++ b/services/rabbitmq/test/rabbitmq.config @@ -0,0 +1,20 @@ +[ + { rabbit, [ + {cluster_nodes, {[ 'service_rabbitmq@service_rabbitmq' ], disc}}, + {tcp_listen_options, [binary, {backlog, 1024}, {nodelay, true}, {keepalive, true} ]}, + {vm_memory_high_watermark, 0.6}, + { loopback_users, [ ] }, + { tcp_listeners, [ 5673 ] }, + { ssl_listeners, [ ] }, + { default_pass, <<"guest">> }, + { default_user, <<"guest">> }, + { hipe_compile, false } + ] }, + + { rabbitmq_management, [ { listener, [ + { port, 15673 }, + { ssl, false } + ] }, + {load_definitions, "/etc/rabbitmq/definitions.json"} + ] } +]. diff --git a/services/ruuuby/Dockerfile b/services/ruuuby/Dockerfile index 021104e..c3392e2 100644 --- a/services/ruuuby/Dockerfile +++ b/services/ruuuby/Dockerfile @@ -3,3 +3,30 @@ # |__) /~~\ .__/ |___ |__) \__/ | |___ |__/ # FROM alpine:3.12 + +ENV LC_ALL en_US.UTF-8 +ENV LANG en_US.UTF-8 +ENV LANGUAGE en_US.UTF-8 +ENV LC_CTYPE en_US.UTF-8 +ENV LC_MESSAGES en_US.UTF-8 + +ENV CC "clang" +ENV CXX "clang++" +ENV ARCHFLAGS "-arch x86_64" + +ENV BUILD_CORE_LIBS git wget curl vim build-base readline readline-dev openssl-dev zlib-dev gmp-dev +ENV BUILD_COMPILERS clang clang-dev musl-dev gcc cmake make +ENV BUILD_LINUX_CORE linux-headers imagemagick-dev +ENV BUILD_LINUX_CORE linux-headers imagemagick-dev + + +ENV BUNDLE_SILENCE_ROOT_WARNING=1 +ENV RUUUBY_OS_CURRENT "linux" + +ENV RUUUBY_F01 "b01|b03|b04{debug}" +ENV RUUUBY_F12 "b00" +ENV RUUUBY_F26 "b00" +ENV RUUUBY_F43 "b00" +ENV RUUUBY_F98 "11" + + diff --git a/services/ruuuby_db/Dockerfile b/services/ruuuby_db/Dockerfile new file mode 100644 index 0000000..0ebcff7 --- /dev/null +++ b/services/ruuuby_db/Dockerfile @@ -0,0 +1,10 @@ +FROM amd64/postgres:13-alpine + +ENV SERVICE_NAME=service_postgresql +ENV SERVICE_OS=alpine +ENV BUILD_ENV=env_dev +ENV SERVICE_OS_VERSION='3.12.1' + +#WORKDIR /docker-entrypoint-initdb.d +#ADD init.sql /docker-entrypoint-initdb.d/ +#EXPOSE 5432 diff --git a/services/ruuuby_db/bin/db b/services/ruuuby_db/bin/db index b9f5233..d7c743d 100755 --- a/services/ruuuby_db/bin/db +++ b/services/ruuuby_db/bin/db @@ -4,17 +4,20 @@ require 'bundler/setup' require 'ruuuby' + #require_relative '../../lib/ruuuby/ruuuby/api/git/conditional' $ruuuby = 💎 -$ruuuby.engine.stats_ext['RUUUBY_ENV'] = 'test' +$ruuuby.engine.stats_ext['RUUUBY_ENV'] = 'test' +$ruuuby.engine.stats_ext['RUUUBY_CONFIGS'] = 'configs_local/db/test.yml' require_relative '../../../lib/ruuuby/db/migrations/migration_ext' require_relative '../../../lib/ruuuby/db/migrations/ruuuby_gem' -require_relative '../../../lib/ruuuby/db/migrations/ruuuby_resource' -💎.engine.orm.db_orm.obtain_connection +#💎.engine.orm.db_orm.obtain_connection $orm = 💎.engine.orm +$gems = CreateRuuubyGem.new + require 'irb' IRB.start(__FILE__) diff --git a/services/ruuuby_db/init.sql b/services/ruuuby_db/init.sql new file mode 100644 index 0000000..5a2ac68 --- /dev/null +++ b/services/ruuuby_db/init.sql @@ -0,0 +1,145 @@ + +--| ___ __ +--| /'___\ /\ \__ __ +--| /\ \__/ __ __ ___ ___\ \ ,_\/\_\ ___ ___ ____ +--| \ \ ,__\/\ \/\ \ /' _ `\ /'___\ \ \/\/\ \ / __`\ /' _ `\ /',__\ +--| \ \ \_/\ \ \_\ \/\ \/\ \/\ \__/\ \ \_\ \ \/\ \L\ \/\ \/\ \/\__, `\ +--| \ \_\ \ \____/\ \_\ \_\ \____\\ \__\\ \_\ \____/\ \_\ \_\/\____/ +--| \/_/ \/___/ \/_/\/_/\/____/ \/__/ \/_/\/___/ \/_/\/_/\/___/ + +-- @see https://dataedo.com/kb/query/postgresql/list-user-defined-functions +CREATE OR REPLACE FUNCTION get_all_funcs () + RETURNS TABLE ( + function_schema NAME, + function_name NAME, + function_language NAME, + definition TEXT, + function_arguments TEXT, + return_type NAME + ) AS $$ +BEGIN + RETURN QUERY + SELECT n.nspname AS function_schema, + p.proname AS function_name, + l.lanname AS function_language, + CASE WHEN l.lanname = 'internal' THEN p.prosrc + ELSE pg_get_functiondef(p.oid) + END AS definition, + pg_get_function_arguments(p.oid) AS function_arguments, + t.typname AS return_type + FROM pg_proc p + LEFT JOIN pg_namespace n ON p.pronamespace = n.oid + LEFT JOIN pg_language l ON p.prolang = l.oid + LEFT JOIN pg_type t ON t.oid = p.prorettype + WHERE n.nspname NOT IN ('pg_catalog', 'information_schema') + ORDER BY function_schema, function_name; +END; $$ LANGUAGE plpgsql; + +-- --------------------------------------------------------------------------------------------------------------------- + +CREATE OR REPLACE FUNCTION does_func_exist(_func_name TEXT) RETURNS BOOLEAN AS $$ +BEGIN + RETURN (SELECT COUNT(*) FROM get_all_funcs() AS data_src WHERE data_src.function_name = _func_name LIMIT 1) > 0; +END; $$ LANGUAGE plpgsql; + +-- --------------------------------------------------------------------------------------------------------------------- + +CREATE OR REPLACE FUNCTION does_func_schema_match(_func_name TEXT, _func_args TEXT, _func_return_type NAME) RETURNS BOOLEAN AS $$ +BEGIN + RETURN ( + SELECT COUNT(*) FROM get_all_funcs() AS f + WHERE f.function_name = _func_name AND f.function_arguments = _func_args AND f.return_type = _func_return_type + ) > 0; +END; $$ LANGUAGE plpgsql; + +-- --------------------------------------------------------------------------------------------------------------------- + +--| __ __ ___ +--| /\ \__ /\ \ /\_ \ +--| \ \ ,_\ __ \ \ \____\//\ \ __ ____ +--| \ \ \/ /'__`\ \ \ '__`\ \ \ \ /'__`\ /',__\ +--| \ \ \_/\ \L\.\_\ \ \L\ \ \_\ \_/\ __//\__, `\ +--| \ \__\ \__/.\_\\ \_,__/ /\____\ \____\/\____/ +--| \/__/\/__/\/_/ \/___/ \/____/\/____/\/___/ + +CREATE OR REPLACE FUNCTION does_table_exist(_table_name TEXT) RETURNS BOOLEAN AS $$ +BEGIN + RETURN ( + SELECT COUNT(*) FROM get_all_table_names() AS t WHERE t.table_name = _table_name + ) > 0; +END; $$ LANGUAGE plpgsql; + +-- --------------------------------------------------------------------------------------------------------------------- + +CREATE OR REPLACE FUNCTION get_all_table_names () RETURNS TABLE(table_name TEXT) AS $$ + SELECT t.table_name FROM information_schema.tables AS t + WHERE t.table_type = 'BASE TABLE' AND t.table_schema NOT IN ('pg_catalog', 'information_schema'); +$$ LANGUAGE SQL; + +-- --------------------------------------------------------------------------------------------------------------------- + +CREATE OR REPLACE FUNCTION get_all_table_name_schema_pairs () RETURNS SETOF TEXT AS $$ +BEGIN + RETURN QUERY (SELECT table_schema || '.' || table_name + FROM information_schema.tables WHERE table_type = 'BASE TABLE' AND table_schema NOT IN ('pg_catalog', 'information_schema')); +END; $$ language plpgsql; + +-- --------------------------------------------------------------------------------------------------------------------- + +CREATE OR REPLACE FUNCTION table_size_stats(_table_name TEXT) + RETURNS TABLE ( + table_size_data_in_bytes BIGINT, + table_size_indexes_in_bytes BIGINT, + table_size_total_in_bytes BIGINT, + table_size_data_readable TEXT, + table_size_indexes_readable TEXT, + table_size_total_readable TEXT + ) AS $$ +BEGIN + RETURN QUERY + SELECT + pg_relation_size(_table_name) AS table_size_data_in_bytes, + pg_indexes_size(_table_name) AS table_size_indexes_in_bytes, + pg_total_relation_size(_table_name) AS table_size_total_in_bytes, + pg_size_pretty(pg_relation_size(_table_name)) AS table_size_data_readable, + pg_size_pretty(pg_indexes_size(_table_name)) AS table_size_indexes_readable, + pg_size_pretty(pg_total_relation_size(_table_name)) AS table_size_total_readable + ; +END; $$ LANGUAGE plpgsql; + +-- --------------------------------------------------------------------------------------------------------------------- + +--| __ __ __ +--| /\ \ /\ \__ /\ \ +--| \_\ \ __ \ \ ,_\ __ \ \ \____ __ ____ __ ____ +--| /'_` \ /'__`\ \ \ \/ /'__`\ \ \ '__`\ /'__`\ /',__\ /'__`\ /',__\ +--| /\ \L\ \/\ \L\.\_\ \ \_/\ \L\.\_\ \ \L\ \/\ \L\.\_/\__, `\/\ __//\__, `\ +--| \ \___,_\ \__/.\_\\ \__\ \__/.\_\\ \_,__/\ \__/.\_\/\____/\ \____\/\____/ +--| \/__,_ /\/__/\/_/ \/__/\/__/\/_/ \/___/ \/__/\/_/\/___/ \/____/\/___/ + +CREATE OR REPLACE FUNCTION db_size_stats() + RETURNS TABLE ( + dat_name NAME, + db_size_bytes BIGINT, + db_size_readable TEXT + ) AS $$ +BEGIN + RETURN QUERY + SELECT + pg_database.datname AS dat_name, + pg_database_size(pg_database.datname) AS db_size_bytes, + pg_size_pretty(pg_database_size(pg_database.datname)) AS db_size_readable + FROM pg_database + ; +END; $$ LANGUAGE plpgsql; + +--| __ +--| /\ \__ __ +--| __ __ _\ \ ,_\ __ ___ ____/\_\ ___ ___ ____ +--| /'__`\/\ \/'\\ \ \/ /'__`\/' _ `\ /',__\/\ \ / __`\ /' _ `\ /',__\ +--| /\ __/\/> false + end + + add_index :mock_data, :mock_data, unique: true + end + + def self.down + ♻️index(:mock_data, :mock_data) + ♻️table(:mock_data) + end +end + +class MockData < ApplicationRecord + +end + +RSpec.describe 'db/db.rb' do + let(:api){Ruuuby::MetaData.engine.orm.db_orm} + + context 'db_new', :db_new do + + before :all do + @mock = CreateMockData.new + @mock.down + end + + context 'has utility funcs from{init.sql}' do + + context 'func{does_func_exit}' do + context 'handles needed scenarios' do + it 'cases: positive' do + expect(api.sql("SELECT does_func_exist('does_func_exist');").values[0][0]).to eq(true) + expect(api.sql("SELECT does_func_exist('get_all_funcs');").values[0][0]).to eq(true) + expect(api.sql("SELECT does_func_exist('does_func_schema_match');").values[0][0]).to eq(true) + expect(api.sql("SELECT does_func_exist('does_table_exist');").values[0][0]).to eq(true) + expect(api.sql("SELECT does_func_exist('get_all_table_names');").values[0][0]).to eq(true) + expect(api.sql("SELECT does_func_exist('get_all_table_name_schema_pairs');").values[0][0]).to eq(true) + expect(api.sql("SELECT does_func_exist('table_size_stats');").values[0][0]).to eq(true) + expect(api.sql("SELECT does_func_exist('db_size_stats');").values[0][0]).to eq(true) + end + it 'cases: negative' do + expect(api.sql("SELECT does_func_exist('does_func_existdoes_func_exist');").values[0][0]).to eq(false) + expect(api.sql("SELECT does_func_exist('');").values[0][0]).to eq(false) + expect(api.sql("SELECT does_func_exist('1');").values[0][0]).to eq(false) + expect(api.sql("SELECT does_func_exist(' ');").values[0][0]).to eq(false) + expect(api.sql("SELECT does_func_exist('fake_func_name');").values[0][0]).to eq(false) + end + end + end + + context 'func{does_func_schema_match}' do + context 'handles needed scenario' do + it 'cases: positive' do + expect(api.sql("SELECT does_func_schema_match( +'does_func_schema_match', +'_func_name text, _func_args text, _func_return_type name', +'bool'); +").values[0][0]).to eq(true) + end + it 'cases: negative' do + expect(api.sql("SELECT does_func_schema_match( +'does_func_schema_match', +'_fake_param text, _func_arg name, _func_return_type text', +'bigint'); +").values[0][0]).to eq(false) + end + end + end + + end + + context 'can create tables w/ migrations' do + it 'can be created' do + expect(@mock.∃table?('mock_data')).to eq(false) + @mock.up + expect(@mock.∃table?('mock_data')).to eq(true) + end + it 'and populate data' do + a = MockData.new({mock_data: 'hello world'}) + a.💾! + b = MockData.find(1) + expect(b.ⓣ).to eq(::MockData) + expect(b.mock_data).to eq('hello world') + a.♻️! + end + it 'throwing error for unique constraint' do + a = MockData.new({mock_data: 'hello world'}) + b = MockData.new({mock_data: 'hello world'}) + a.💾! + expect{b.💾!}.to raise_error(::ActiveRecord::RecordNotUnique) + a.♻️! + end + end + + context 'can drop tables w/ migrations' do + it 'can be removed' do + @mock.down + expect(@mock.∃table?('mock_data')).to eq(false) + end + end + + after :all do + + end + + end + +end diff --git a/services/ruuuby_db/spec/test/migration_spec.rb b/services/ruuuby_db/spec/test/migration_spec.rb new file mode 100644 index 0000000..dd55d69 --- /dev/null +++ b/services/ruuuby_db/spec/test/migration_spec.rb @@ -0,0 +1 @@ +# encoding: UTF-8 diff --git a/services/web_assets/package.json b/services/web_assets/package.json index 48b3090..2baaf8b 100644 --- a/services/web_assets/package.json +++ b/services/web_assets/package.json @@ -18,7 +18,7 @@ "html-minifier": "^4.0.0", "imports-loader": "^1.1.0", "jsonminify": "^0.4.1", - "mocha": "^8.1.3", + "mocha": "^8.2.1", "three": "^0.119.1", "webpack": "^4.44.2", "webpack-cli": "^3.3.12" diff --git a/spec/app/models/application_record/data_spec.rb b/spec/app/models/application_record/data_spec.rb deleted file mode 100644 index 1214524..0000000 --- a/spec/app/models/application_record/data_spec.rb +++ /dev/null @@ -1,59 +0,0 @@ -# encoding: UTF-8 - -RSpec.describe 'application_record.rb' do - - context 'ApplicationRecord', :db do - - context 'adds static functions' do - let(:flag_wip){::RuuubyFeature::EnumFlagState::STATE_WIP} - let(:flag_stable){::RuuubyFeature::EnumFlagState::STATE_STABLE} - let(:flag_todo){::RuuubyFeature::EnumFlagState::STATE_NULL} - let(:flag_needs_merge){::RuuubyFeature::EnumFlagState::STATE_NEEDS_MERGE} - let(:expected_wip){RuuubyFeature.where('flag_state = ?', flag_wip).count} - let(:expected_stable){::RuuubyFeature.where('flag_state = ?', flag_stable).count} - let(:expected_todo){::RuuubyFeature.where('flag_state = ?', flag_todo).count} - let(:expected_needs_merge){::RuuubyFeature.where('flag_state = ?', flag_needs_merge).count} - - context 'func{length}' do - context 'handles needed scenarios' do - it 'cases: positive' do - expect(::RuuubyFeature.length).to eq(expected_wip + expected_stable + expected_todo + expected_needs_merge) - end - end - end - - context 'func{num_where}' do - context 'handles needed scenarios' do - context 'cases: positive' do - it 'w/ 1 group' do - expect(::RuuubyFeature.num_where(*['flag_state = ?', flag_wip])).to eq(expected_wip) - expect(::RuuubyFeature.num_where(*['flag_state = ?', flag_stable])).to eq(expected_stable) - expect(::RuuubyFeature.num_where(*['flag_state = ?', flag_todo])).to eq(expected_todo) - expect(::RuuubyFeature.num_where(*['flag_state = ?', flag_needs_merge])).to eq(expected_needs_merge) - end - it 'w/ 2 groups' do - expect(::RuuubyFeature.num_where(*['flag_state = ? OR flag_state = ?', flag_wip, flag_needs_merge])).to eq(expected_wip + expected_needs_merge) - expect(::RuuubyFeature.num_where(*['flag_state = ? OR flag_state = ?', flag_wip, flag_stable])).to eq(expected_wip + expected_stable) - expect(::RuuubyFeature.num_where(*['flag_state = ? OR flag_state = ?', flag_wip, flag_todo])).to eq(expected_wip + expected_todo) - - expect(::RuuubyFeature.num_where(*['flag_state = ? OR flag_state = ?', flag_needs_merge, flag_stable])).to eq(expected_needs_merge + expected_stable) - expect(::RuuubyFeature.num_where(*['flag_state = ? OR flag_state = ?', flag_needs_merge, flag_todo])).to eq(expected_needs_merge + expected_todo) - - expect(::RuuubyFeature.num_where(*['flag_state = ? OR flag_state = ?', flag_stable, flag_todo])).to eq(expected_stable + expected_todo) - end - it 'w/ 3 groups' do - expect(::RuuubyFeature.num_where(*['flag_state = ? OR flag_state = ? OR flag_state = ?', flag_wip, flag_needs_merge, flag_todo])).to eq(expected_wip + expected_needs_merge + expected_todo) - expect(::RuuubyFeature.num_where(*['flag_state = ? OR flag_state = ? OR flag_state = ?', flag_wip, flag_needs_merge, flag_stable])).to eq(expected_wip + expected_needs_merge + expected_stable) - end - it 'w/ 4 groups' do - expect(::RuuubyFeature.num_where(*['flag_state = ? OR flag_state = ? OR flag_state = ? OR flag_state = ?', flag_wip, flag_needs_merge, flag_todo, flag_stable])).to eq(expected_wip + expected_needs_merge + expected_todo + expected_stable) - end - end - end - end - - end # end: {adds static functions} - - end - -end diff --git a/spec/app/models/application_record/orm_spec.rb b/spec/app/models/application_record/orm_spec.rb deleted file mode 100644 index 1d391de..0000000 --- a/spec/app/models/application_record/orm_spec.rb +++ /dev/null @@ -1,61 +0,0 @@ -# encoding: UTF-8 - -RSpec.describe 'application_record.rb' do - let(:data_orm_all_classes){[::RuuubyFeature, ::RuuubyRelease, ::RuuubyFeatureBehavior, ::RuuubyGem, ::RuuubyFile, ::RuuubyDir, ::RuuubyChangelog]} - - context 'class{ApplicationRecord}', :db do - - context 'is defined as needed' do - it 'w/o ability to be instantiated' do - expect{::ApplicationRecord.new}.to raise_error(::NotImplementedError) - end - context 'w/ needed funcs' do - it 'for runtime' do - data_orm_all_classes.∀{|scenario| expect(scenario.respond_to?(:empty?)).to eq(true)} - data_orm_all_classes.∀{|scenario| expect(scenario.respond_to?(:∅?)).to eq(true)} - data_orm_all_classes.∀{|scenario| expect(scenario.respond_to?(:orm_Ⓣ_🐍)).to eq(true)} - data_orm_all_classes.∀{|scenario| expect(scenario.respond_to?(:num_where)).to eq(true)} - end - it 'for development' do - data_orm_all_classes.∀{|scenario| expect(scenario.respond_to?(:orm_class)).to eq(true)} - data_orm_all_classes.∀{|scenario| expect(scenario.respond_to?(:str2ormⓣ?)).to eq(true)} - end - end - end - - context 'adds static functions' do - - context 'func{orm_class}' do - context 'handles needed scenarios' do - it 'cases: all' do - data_orm_all_classes.∀{|scenario| expect(scenario.orm_class).to eq(scenario)} - end - end - end # end: {func{orm_class}} - - context 'func{orm_Ⓣ_🐍}' do - context 'handles needed scenarios' do - it 'cases: all' do - expect(::RuuubyFeature.orm_Ⓣ_🐍).to eq('ruuuby_feature') - expect(::RuuubyFeatureBehavior.orm_Ⓣ_🐍).to eq('ruuuby_feature_behavior') - expect(::RuuubyGem.orm_Ⓣ_🐍).to eq('ruuuby_gem') - expect(::RuuubyDir.orm_Ⓣ_🐍).to eq('ruuuby_dir') - expect(::RuuubyFile.orm_Ⓣ_🐍).to eq('ruuuby_file') - expect(::RuuubyChangelog.orm_Ⓣ_🐍).to eq('ruuuby_changelog') - end - end - end # end: {func{orm_Ⓣ_🐍}} - - context 'func{empty?}' do - context 'handles needed scenarios' do - it 'cases: all' do - data_orm_all_classes.∀{|scenario| expect(scenario.empty?).to eq(scenario.count == 0); expect(scenario.∅?).to eq(scenario.empty?)} - end - end - end # end: {func{empty?}} - - end # end: {adds static functions} - - end # end: {db} - -end diff --git a/spec/app/models/ruuuby_features/orm_spec.rb b/spec/app/models/ruuuby_features/orm_spec.rb index ad6f007..fd389cb 100644 --- a/spec/app/models/ruuuby_features/orm_spec.rb +++ b/spec/app/models/ruuuby_features/orm_spec.rb @@ -16,13 +16,6 @@ fake_feature.♻️! end - # - # flag_wip = ::RuuubyFeature::EnumFlagState::STATE_WIP - # flag_needs_merge = ::RuuubyFeature::EnumFlagState::STATE_NEEDS_MERGE - # flag_todo = ::RuuubyFeature::EnumFlagState::STATE_NULL - # flag_stable = ::RuuubyFeature::EnumFlagState::STATE_STABLE - # - it 'prevents duplicate id_nums from being created' do expect{ RuuubyFeature.spawn(1337, '1337') diff --git a/spec/app/models/ruuuby_releases/data_spec.rb b/spec/app/models/ruuuby_releases/data_spec.rb index 95f33bf..7279331 100644 --- a/spec/app/models/ruuuby_releases/data_spec.rb +++ b/spec/app/models/ruuuby_releases/data_spec.rb @@ -4,13 +4,6 @@ context 'ApplicationRecord{RuuubyRelease}', :db do - #context 'version wip' do - # it 'reports correct prev version' do - # expect(::RuuubyRelease::Version.wip).to eq(::RuuubyRelease::Version.curr.next) - # expect(::RuuubyRelease::Version.wip).to eq(v0_0_50) - # end - #end - context 'integration tests w/ modules{Version, Remote}' do context 'additional checks' do diff --git a/spec/app/models/ruuuby_releases/integration_spec.rb b/spec/app/models/ruuuby_releases/integration_spec.rb deleted file mode 100644 index 13165bb..0000000 --- a/spec/app/models/ruuuby_releases/integration_spec.rb +++ /dev/null @@ -1,17 +0,0 @@ -# encoding: UTF-8 - -RSpec.describe 'ruuuby_release.rb' do - - context 'ApplicationRecord{RuuubyRelease}', :db do - - context 'hybrid tests against{api_git}' do - - it 'RuuubyRelease{num_released} should match number of found release tags' do - expect(::RuuubyRelease.num_released).to eq($git.release_tags.length) - end - - end - - end - -end diff --git a/spec/class/enumerable/hsh_spec.rb b/spec/class/enumerable/hsh_spec.rb index fdce3d0..6c5fab8 100644 --- a/spec/class/enumerable/hsh_spec.rb +++ b/spec/class/enumerable/hsh_spec.rb @@ -1,10 +1,70 @@ # encoding: UTF-8 RSpec.describe 'hsh' do + let(:hsh_data_0){{a: 0, b: 1, c: 2, x: 0, y: 1, z: 2}} context 'extends class{Hash}' do context 'by adding the following' do + context 'func{∀🔑∃_value?}' do + context 'handles needed scenarios' do + context 'cases: positive' do + context 'regular data' do + it 'w/ single key searched' do + expect(hsh_data_0.∀🔑∃_value?([:a], 0)).to eq(true) + expect(hsh_data_0.∀🔑∃_value?([:b], 1)).to eq(true) + expect(hsh_data_0.∀🔑∃_value?([:c], 2)).to eq(true) + + expect(hsh_data_0.∀🔑∃_value?([:x], 0)).to eq(true) + expect(hsh_data_0.∀🔑∃_value?([:y], 1)).to eq(true) + expect(hsh_data_0.∀🔑∃_value?([:z], 2)).to eq(true) + end + it 'w/ multiple keys searched' do + expect(hsh_data_0.∀🔑∃_value?([:a, :x], 0)).to eq(true) + expect(hsh_data_0.∀🔑∃_value?([:b, :y], 1)).to eq(true) + expect(hsh_data_0.∀🔑∃_value?([:c, :z], 2)).to eq(true) + end + end + end + context 'cases: negative' do + context 'regular data' do + it 'w/ single key searched' do + expect(hsh_data_0.∀🔑∃_value?([:a], 2)).to eq(false) + expect(hsh_data_0.∀🔑∃_value?([:b], 0)).to eq(false) + expect(hsh_data_0.∀🔑∃_value?([:c], 1)).to eq(false) + + expect(hsh_data_0.∀🔑∃_value?([:r], 0)).to eq(false) + expect(hsh_data_0.∀🔑∃_value?([:h], 1)).to eq(false) + expect(hsh_data_0.∀🔑∃_value?([:g], 2)).to eq(false) + + expect(hsh_data_0.∀🔑∃_value?([:aa], 0)).to eq(false) + expect(hsh_data_0.∀🔑∃_value?([:bb], 1)).to eq(false) + expect(hsh_data_0.∀🔑∃_value?(['a'], 0)).to eq(false) + end + it 'w/ multiple keys searched' do + expect(hsh_data_0.∀🔑∃_value?([:a, :y], 0)).to eq(false) + expect(hsh_data_0.∀🔑∃_value?([:b, :z], 1)).to eq(false) + expect(hsh_data_0.∀🔑∃_value?([:c, :x], 2)).to eq(false) + + expect(hsh_data_0.∀🔑∃_value?([:a, :x], 2)).to eq(false) + expect(hsh_data_0.∀🔑∃_value?([:b, :y], 0)).to eq(false) + expect(hsh_data_0.∀🔑∃_value?([:c, :z], 1)).to eq(false) + + expect(hsh_data_0.∀🔑∃_value?([:a, :c, :z], 1)).to eq(false) + end + end + context 'bad args' do + it 'bad param type' do + expect{hsh_data_0.∀🔑∃_value?(:a, 2)}.to raise_error(::ArgumentError) + expect{hsh_data_0.∀🔑∃_value?(nil, 2)}.to raise_error(::ArgumentError) + expect{hsh_data_0.∀🔑∃_value?({}, 2)}.to raise_error(::ArgumentError) + expect{hsh_data_0.∀🔑∃_value?({:a => []}, 2)}.to raise_error(::ArgumentError) + end + end + end + end + end + context 'func{λ𝑓∀🔑:₍🔑∉₎}' do context 'handles needed scenarios' do context 'cases: positive' do diff --git a/spec/class/enumerable/set_spec.rb b/spec/class/enumerable/set_spec.rb index f4d2b50..48fb265 100644 --- a/spec/class/enumerable/set_spec.rb +++ b/spec/class/enumerable/set_spec.rb @@ -23,6 +23,4 @@ end - end - diff --git a/spec/class/str_spec.rb b/spec/class/str_spec.rb index a50ce8e..8e1243e 100644 --- a/spec/class/str_spec.rb +++ b/spec/class/str_spec.rb @@ -55,6 +55,11 @@ expect('0101b0'.palindrome?).to eq(false) end end + context 'tech_debt', :tech_debt do + it 'offers arg to give deal with "visual palindromeness"' do + expect('∃12321∃'.palindrome?).to eq(true) + end + end end # end: {func{palindrome?}} context 'func{in_quotes?}' do diff --git a/spec/db/db_spec.rb b/spec/db/db_spec.rb deleted file mode 100644 index 24e608f..0000000 --- a/spec/db/db_spec.rb +++ /dev/null @@ -1,31 +0,0 @@ -# encoding: UTF-8 - -=begin -RSpec.describe 'db/db.rb' do - - context 'db', :db do - context 'defines expected schemas' do - - context 'tables found are as defined' do - let(:db_tables){💎.engine.orm.db_orm.connection.tables} - - it 'for needed tables' do - 💎.engine.orm.expected_tables[:orm].∀{|table_name| expect(db_tables.∋?(table_name)).to eq(true)} - end - - it 'for the additional table created by libraries (not SQLite3)' do - expect(db_tables.∋?('ar_internal_metadata')).to eq(true) - end - - it 'w/o any additional (un-expected) tables' do - num_tables_generated_by_external_libs = 💎.engine.orm.expected_tables[:application_record].length - num_tables_generated_by_orm = 💎.engine.orm.expected_tables[:orm].length - expect(num_tables_generated_by_external_libs).to eq(1) - expect(db_tables.length - num_tables_generated_by_external_libs).to eq(num_tables_generated_by_orm) - end - end - - end - end -end -=end diff --git a/spec/db/seed_data_spec.rb b/spec/db/seed_data_spec.rb index 4ce3355..5b002d6 100644 --- a/spec/db/seed_data_spec.rb +++ b/spec/db/seed_data_spec.rb @@ -336,12 +336,6 @@ end end - #context 'v0.0.50' do - # it 'as expected' do - # audit_version(v0_0_50, 'v0.0.50', 1, 0) - # end - #end - end # end{versions} end end diff --git a/spec/feature/f11/f11_b00_spec.rb b/spec/feature/f11/f11_b00_spec.rb deleted file mode 100644 index 9abc29e..0000000 --- a/spec/feature/f11/f11_b00_spec.rb +++ /dev/null @@ -1,25 +0,0 @@ -# encoding: UTF-8 - -RSpec.describe 'f11_b00' do - - context 'audit', :audit do - - context 'feature-behavior(f11_b00) is defined correctly' do - it 'creates module{SetTheory} under module{Math}' do - expect_∃ᵐ(:SetTheory, ::Math) - end - - context 'creates inner-module{AlephNumbers}' do - it 'as expected' do - expect_∃ᵐ(:AlephNumbers, ::Math::SetTheory::NumberSet) - end - it 'w/ needed constants' do - expect_∃const_w_type(:ZERO, Symbol, ::Math::SetTheory::NumberSet::AlephNumbers) - expect_∃const_w_type(:ONE, Symbol, ::Math::SetTheory::NumberSet::AlephNumbers) - end - end - end - - end # end: {audit} - -end diff --git a/spec/feature/f11/f11_b01_spec.rb b/spec/feature/f11/f11_b01_spec.rb deleted file mode 100644 index 05eb9f0..0000000 --- a/spec/feature/f11/f11_b01_spec.rb +++ /dev/null @@ -1,16 +0,0 @@ -# encoding: UTF-8 - -RSpec.describe 'f11_b01' do - - context 'audit', :audit do - - context 'feature-behavior(f11_b01) is defined correctly' do - it 'creates class{Closure} under module{Math::SetTheory}' do - expect_∃ᶜ(:Closure, ::Math::SetTheory) - end - - end - - end # end: {audit} - -end \ No newline at end of file diff --git a/spec/feature/f11/f11_b02_spec.rb b/spec/feature/f11/f11_b02_spec.rb deleted file mode 100644 index dd6aa83..0000000 --- a/spec/feature/f11/f11_b02_spec.rb +++ /dev/null @@ -1,320 +0,0 @@ -# encoding: UTF-8 - -RSpec.describe 'f11_b02' do - - context 'audit', :audit do - - context 'feature-behavior{f11_b02} is defined correctly' do - it 'creates class{NumberSet} under module{Math::SetTheory}' do - expect(🧬.∃ᶜ?(:NumberSet, ::Math::SetTheory)).to eq(true) - end - - context 'discrete implementations exist' do - - context '∅' do - it 'in correct location' do - expect(🧬.∃ᶜ?(:EmptySet, ::Math::SetTheory)).to eq(true) - end - it 'defined correctly' do - expect_number_set(∅, :∅, ::Math::SetTheory::EmptySet, 'empty set') - end - context 'w/ correct set ordering' do - it 'compared w/ self' do - expect_equal_sets(∅, ∅) - end - end - end # end: {∅} - - context '𝔹' do - it 'in correct location' do - expect(🧬.∃ᶜ?(:BooleanNumbers, ::Math::SetTheory)).to eq(true) - end - it 'defined correctly' do - expect_number_set(𝔹, :𝔹, ::Math::SetTheory::BooleanNumbers, 'boolean numbers') - end - context 'w/ correct set ordering' do - it 'compared w/ self' do - expect_equal_sets(𝔹, 𝔹) - end - end - end # end: {𝔹} - - context 'ℕ' do - it 'in correct location' do - expect(🧬.∃ᶜ?(:NaturalNumbers, ::Math::SetTheory)).to eq(true) - end - it 'defined correctly' do - expect_number_set(ℕ, :ℕ, ::Math::SetTheory::NaturalNumbers, 'natural numbers') - end - context 'w/ correct set ordering' do - it 'compared w/ self' do - expect_equal_sets(ℕ, ℕ) - end - end - end # end: {ℕ} - - context '𝕎' do - it 'in correct location' do - expect(🧬.∃ᶜ?(:WholeNumbers, ::Math::SetTheory)).to eq(true) - end - it 'defined correctly' do - expect_number_set(𝕎, :𝕎, ::Math::SetTheory::WholeNumbers, 'whole numbers') - end - context 'w/ correct set ordering' do - it 'compared w/ self' do - expect_equal_sets(𝕎, 𝕎) - end - end - end # end: {𝕎} - - context 'ℤ' do - it 'in correct location' do - expect(🧬.∃ᶜ?(:IntegerNumbers, ::Math::SetTheory)).to eq(true) - end - it 'defined correctly' do - expect_number_set(ℤ, :ℤ, ::Math::SetTheory::IntegerNumbers, 'integer numbers') - end - context 'w/ correct set ordering' do - it 'compared w/ self' do - expect_equal_sets(ℤ, ℤ) - end - end - end # end: {ℤ} - - context 'ℚ' do - it 'in correct location' do - expect(🧬.∃ᶜ?(:RationalNumbers, ::Math::SetTheory)).to eq(true) - end - it 'defined correctly' do - expect_number_set(ℚ, :ℚ, ::Math::SetTheory::RationalNumbers, 'rational numbers') - end - context 'w/ correct set ordering' do - it 'compared w/ self' do - expect_equal_sets(ℚ, ℚ) - end - end - end # end: {ℚ} - - context '𝔸ᵣ' do - it 'in correct location' do - expect(🧬.∃ᶜ?(:RealAlgebraicNumbers, ::Math::SetTheory)).to eq(true) - end - it 'defined correctly' do - expect_number_set(𝔸ᵣ, :𝔸ᵣ, ::Math::SetTheory::RealAlgebraicNumbers, 'real algebraic numbers') - end - context 'w/ correct set ordering' do - it 'compared w/ self' do - expect_equal_sets(𝔸ᵣ, 𝔸ᵣ) - end - end - end # end: {𝔸ᵣ} - - context '𝔸' do - it 'in correct location' do - expect(🧬.∃ᶜ?(:AlgebraicNumbers, ::Math::SetTheory)).to eq(true) - end - it 'defined correctly' do - expect_number_set(𝔸, :𝔸, ::Math::SetTheory::AlgebraicNumbers, 'algebraic numbers') - end - context 'w/ correct set ordering' do - it 'compared w/ self' do - expect_equal_sets(𝔸, 𝔸) - end - end - end # end: {𝔸} - - context '𝕀' do - it 'in correct location' do - expect(🧬.∃ᶜ?(:IrrationalNumbers, ::Math::SetTheory)).to eq(true) - end - it 'defined correctly' do - expect_number_set(𝕀, :𝕀, ::Math::SetTheory::IrrationalNumbers, 'irrational numbers') - end - context 'w/ correct set ordering' do - it 'compared w/ self' do - expect_equal_sets(𝕀, 𝕀) - end - it 'compared w/ others', :tech_debt do - [𝕌, ℂ, ℝ].∀{|scenario| expect(expect_proper_subset(𝕀, scenario))} - end - end - end # end: {𝕀} - - context 'ℝ' do - it 'in correct location' do - expect(🧬.∃ᶜ?(:RealNumbers, ::Math::SetTheory)).to eq(true) - end - it 'defined correctly' do - expect_number_set(ℝ, :ℝ, ::Math::SetTheory::RealNumbers, 'real numbers') - end - context 'w/ correct set ordering' do - it 'compared w/ self' do - expect_equal_sets(ℝ, ℝ) - end - end - end # end: {ℝ} - - context 'ℂ' do - it 'in correct location' do - expect(🧬.∃ᶜ?(:ComplexNumbers, ::Math::SetTheory)).to eq(true) - end - it 'defined correctly' do - expect_number_set(ℂ, :ℂ, ::Math::SetTheory::ComplexNumbers, 'complex numbers') - end - context 'w/ correct set ordering' do - it 'compared w/ self' do - expect_equal_sets(ℂ, ℂ) - end - end - end - - context '𝕌' do - it 'in correct location' do - expect(🧬.∃ᶜ?(:UniversalSet, ::Math::SetTheory)).to eq(true) - end - it 'defined correctly' do - expect_number_set(𝕌, :𝕌, ::Math::SetTheory::UniversalSet, 'universal set') - end - context 'w/ correct set ordering' do - it 'compared w/ self' do - expect_equal_sets(𝕌, 𝕌) - end - end - end - - end - - end - - end # end: {audit} - - context 'tech_debt', :tech_debt do - it 'broader test for extra confirmation', :tech_debt do - expect(true).to eq(true) - #expect(ℕ.⊂?(𝕎)).to eq(false) - #expect(𝕎.⊂?(ℤ)).to eq(false) - #expect(ℤ.⊂?(ℚ)).to eq(false) - #expect(ℚ.⊂?(𝔸ᵣ)).to eq(false) - #expect(𝔸ᵣ.⊂?(ℝ)).to eq(false) - #expect(ℝ.⊂?(ℂ)).to eq(false) - end - - context '𝔹' do - context 'compared w/ others' do - it 'subset to' do - expect(true).to eq(true) - #[𝕌, 𝔸ᵣ, 𝔸, ℝ, ℂ, ℚ, ℤ, 𝕎].∀{|scenario| expect(expect_proper_subset(𝔹, scenario))} - end - end - end - - context 'ℕ' do - context 'compared w/ others' do - it 'subset to' do - expect(true).to eq(true) - #[𝕌, 𝔸ᵣ, 𝔸, ℝ, ℂ, ℚ, ℤ, 𝕎].∀{|scenario| expect(expect_proper_subset(ℕ, scenario))} - end - end - end - - context '𝕎' do - context 'compared w/ others' do - it 'subset to' do - expect(true).to eq(true) - #[𝕌, 𝔸ᵣ, 𝔸, ℝ, ℂ, ℚ, ℤ].∀{|scenario| expect(expect_proper_subset(𝕎, scenario))} - end - it 'superset to' do - expect(true).to eq(true) - #[𝔹, ℕ].∀{|scenario| expect(expect_proper_subset(scenario, 𝕎))} - end - end - end - - context '𝕌' do - context 'compared w/ others' do - it 'superset to' do - expect(true).to eq(true) - #[𝔹, ℕ, 𝕎, ℤ, 𝔸ᵣ, ℚ, 𝕀, ℝ, ℂ].∀{|scenario| expect(expect_proper_subset(scenario, 𝕌))} - end - end - end - - context 'ℂ' do - context 'compared w/ others' do - it 'subset to' do - expect_proper_subset(ℂ, 𝕌) - end - it 'superset to' do - expect(true).to eq(true) - #[𝔹, ℕ, 𝕎, ℤ, 𝔸ᵣ, ℚ, 𝕀, ℝ].∀{|scenario| expect(expect_proper_subset(scenario, ℂ))} - end - end - end - - context 'ℝ' do - context 'compared w/ others' do - it 'subset to' do - expect(true).to eq(true) - #[𝕌, ℂ].∀{|scenario| expect(expect_proper_subset(ℝ, scenario))} - end - it 'superset to' do - expect(true).to eq(true) - #[𝔹, ℕ, 𝕎, ℤ, 𝔸ᵣ, ℚ, 𝕀].∀{|scenario| expect(expect_proper_subset(scenario, ℝ))} - end - end - end - - context 'ℤ' do - context 'compared w/ others' do - it 'subset to' do - expect(true).to eq(true) - #[𝕌, 𝔸ᵣ, 𝔸, ℝ, ℂ, ℚ].∀{|scenario| expect(expect_proper_subset(ℤ, scenario))} - end - it 'superset to' do - expect(true).to eq(true) - #[𝔹, ℕ, 𝕎].∀{|scenario| expect(expect_proper_subset(scenario, ℤ))} - end - end - end - - context 'ℚ' do - context 'compared w/ others' do - it 'subset to' do - expect(true).to eq(true) - #[𝕌, ℂ, ℝ, 𝔸].∀{|scenario| expect(expect_proper_subset(ℚ, scenario))} - end - it 'superset to' do - expect(true).to eq(true) - #[𝔹, ℕ, 𝕎, ℤ].∀{|scenario| expect(expect_proper_subset(scenario, ℚ))} - end - end - end - - context '𝔸ᵣ' do - context 'compared w/ others' do - it 'subset to' do - expect(true).to eq(true) - #[𝕌, ℂ, ℝ, 𝔸].∀{|scenario| expect(expect_proper_subset(𝔸ᵣ, scenario))} - end - it 'superset to' do - expect(true).to eq(true) - #[𝔹, ℕ, 𝕎, ℤ, ℚ].∀{|scenario| expect(expect_proper_subset(scenario, 𝔸ᵣ))} - end - end - end - - context '𝔸' do - context 'compared w/ others' do - it 'subset to' do - expect(true).to eq(true) - #[𝕌, ℂ].∀{|scenario| expect(expect_proper_subset(𝔸, scenario))} - end - it 'superset to' do - expect(true).to eq(true) - #[𝔹, ℕ, 𝕎, ℤ, ℚ, 𝔸ᵣ].∀{|scenario| expect(expect_proper_subset(scenario, 𝔸))} - end - end - end - end - -end \ No newline at end of file diff --git a/spec/feature/f11/f11_db_orm_spec.rb b/spec/feature/f11/f11_db_orm_spec.rb deleted file mode 100644 index edbb962..0000000 --- a/spec/feature/f11/f11_db_orm_spec.rb +++ /dev/null @@ -1,27 +0,0 @@ -# encoding: UTF-8 - -RSpec.describe 'f11_db_orm' do - - context 'db_orm', :db do - context 'defines f11' do - it 'passes ORM audit' do - audit_feature(f11, 'f11', 3, 'abstract `SetTheory` and offer discrete singleton objs which reference various groups of numbers') - end - - context 'defines behaviors' do - it 'has b00' do - audit_feature_behavior(f11, f11_b00, 'b00', 'create module{SetTheory}') - end - - it 'has b01' do - audit_feature_behavior(f11, f11_b01, 'b01', 'create class{Closure}') - end - - it 'has b02' do - audit_feature_behavior(f11, f11_b02, 'b02', 'create class{NumberSet}') - end - end - end - end - -end diff --git a/spec/feature/f11/f11_spec.rb b/spec/feature/f11/f11_spec.rb deleted file mode 100644 index 5865f53..0000000 --- a/spec/feature/f11/f11_spec.rb +++ /dev/null @@ -1,489 +0,0 @@ -# encoding: UTF-8 - -RSpec.describe 'f11' do - - context 'functionality' do - let(:num_sets_aleph_one){[𝕌, 𝕀, ℂ]} - let(:num_sets_aleph_zero){[ℕ, 𝕎, ℤ, ℚ, 𝔸, 𝔸ᵣ]} - let(:num_sets_finite){[∅, 𝔹]} - - context 'global aliases for all instances of `NumberSet`' do - - context 'aleph cardinality' do - context 'finite cardinality' do - it 'checked through func{𝔠}' do - num_sets_finite.∀{|scenario| expect(scenario.𝔠.ⓣ).to eq(::Integer)} - end - it 'funcs{finite?}' do - num_sets_finite.∀{|scenario| expect(scenario.finite?).to eq(true)} - end - it 'funcs{countable?}' do - num_sets_finite.∀{|scenario| expect(scenario.countable?).to eq(true)} - end - it 'funcs{countably_infinite?}' do - num_sets_finite.∀{|scenario| expect(scenario.countably_infinite?).to eq(false)} - end - it 'funcs{uncountable?}' do - num_sets_finite.∀{|scenario| expect(scenario.uncountable?).to eq(false)} - end - end # end: {finite cardinality} - context 'ℵ₀' do - it 'checked through func{𝔠}' do - num_sets_aleph_zero.∀{|scenario| expect(scenario.𝔠).to eq(::Math::SetTheory::NumberSet::AlephNumbers::ZERO)} - end - it 'funcs{finite?}' do - num_sets_aleph_zero.∀{|scenario| expect(scenario.finite?).to eq(false)} - end - it 'funcs{countable?}' do - num_sets_aleph_zero.∀{|scenario| expect(scenario.countable?).to eq(true)} - end - it 'funcs{countably_infinite?}' do - num_sets_aleph_zero.∀{|scenario| expect(scenario.countably_infinite?).to eq(true)} - end - it 'funcs{uncountable?}' do - num_sets_aleph_zero.∀{|scenario| expect(scenario.uncountable?).to eq(false)} - end - end # end: {ℵ₀} - context 'ℵ₁' do - it 'checked through func{𝔠}' do - num_sets_aleph_one.∀{|scenario| expect(scenario.𝔠).to eq(::Math::SetTheory::NumberSet::AlephNumbers::ONE)} - end - it 'funcs{finite?}' do - num_sets_aleph_one.∀{|scenario| expect(scenario.finite?).to eq(false)} - end - it 'funcs{countable?}' do - num_sets_aleph_one.∀{|scenario| expect(scenario.countable?).to eq(false)} - end - it 'funcs{countably_infinite?}' do - num_sets_aleph_one.∀{|scenario| expect(scenario.countably_infinite?).to eq(false)} - end - it 'funcs{uncountable?}' do - num_sets_aleph_one.∀{|scenario| expect(scenario.uncountable?).to eq(true)} - end - end # end: {ℵ₁} - end - - context '∅' do - context 'handles needed scenarios' do - it 'cases: negative' do - [[], Set[], {}, '', nil, [1], Set[1], {a: 1}, '1', 1, 1.0, 1i, true, false].∀{|scenario| expect(∅.∋?(scenario)).to eq(false)} - end - end - end # end: {∅} - - context '𝔹' do - context 'handles needed scenarios' do - it 'cases: positive' do - scenarios = [0, 0.0, -0.0, 1, 1.0, Rational(10, 10), Rational(0, 1337), Complex(0, 0), Complex(1, 0), BigDecimal('0.0'), BigDecimal('1.0')] - scenarios.∀{|n| expect(𝔹.∋?(n)).to eq(true)} - end - it 'cases: negative' do - scenarios = [-1337, -1, -1.0, 0.000000001, 1.0000000001, 0.99999999999999, Complex(1, 2), Rational(Complex(-1, 2), 2), data_float_nan, data_float_inf, ::Float::INFINITY_NEGATIVE] - scenarios.∀{|n| expect(𝔹.∋?(n)).to eq(false)} - end - end - end # end: {𝔹} - - context '𝔸ᵣ' do - context 'handles needed scenarios' do - context 'cases: positive' do - it 'w/ int' do - data_range_ints.∀{|n| expect(𝔸ᵣ.∋?(n)).to eq(true)} - end - context 'w/ floats' do - context 'more symbolic data', :tech_debt do - it 'does not currently pass' do - expect(𝔸ᵣ.∋?(√(2))).to eq(nil) - expect(𝔸ᵣ.∋?(𝚽)).to eq(nil) - end - end - end - end - it 'cases: negative', :tech_debt do - data_float_error_cases.∀{|n| expect(𝔸ᵣ.∋?(n)).to eq(false)} - end - context 'converted cases to tech_debt', :tech_debt do - it 'for floats w/ symbolic-like traits' do - [π, ℮, Ω].∀{|n| expect(𝔸ᵣ.∋?(n)).to eq(nil)} - end - end - end - end # end: {𝔸ᵣ} - - context '𝔸' do - context 'handles needed scenarios' do - context 'cases: positive' do - it 'w/ int' do - data_range_ints.∀{|n| expect(𝔸ᵣ.∋?(n)).to eq(true)} - end - end - it 'cases: negative', :tech_debt do - expect(𝔸.∋?(π)).to_not eq(false) - end - context 'converted cases to tech_debt', :tech_debt do - it 'for floats w/ symbolic-like traits' do - expect(𝔸.∋?(√(2))).to eq(nil) - expect(𝔸.∋?(𝚽)).to eq(nil) - expect(𝔸.∋?(℮)).to eq(nil) - end - end - end - end # end: {𝔸} - - context 'ℕ' do - context 'handles needed scenarios' do - context 'cases: positive' do - it 'w/ complex' do - expect(ℕ.∋?(data_complex_one)).to eq(true) - expect(ℕ.∋?(data_complex_leet)).to eq(true) - end - it 'w/ big decimal' do - expect(ℕ.∋?(BigDecimal('1.0'))).to eq(true) - expect(ℕ.∋?(BigDecimal('1337.0'))).to eq(true) - end - it 'w/ rational' do - data_range_rational_positive.∀{|n| expect(ℕ.∋?(n)).to eq(true)} - end - end - context 'cases: negative' do - it 'w/ complex' do - expect(ℕ.∋?(data_complex_zero)).to eq(false) - expect(ℕ.∋?(data_complex_1i)).to eq(false) - expect(ℕ.∋?(Complex(-1))).to eq(false) - expect(ℕ.∋?(Complex(1337.1337))).to eq(false) - data_range_complex_nan_and_infs.∀{|c| expect(ℕ.∋?(c)).to eq(false)} - end - it 'w/ big decimal' do - expect(ℕ.∋?(BigDecimal('-1.0'))).to eq(false) - expect(ℕ.∋?(BigDecimal('0.0'))).to eq(false) - expect(ℕ.∋?(BigDecimal('-1.1'))).to eq(false) - expect(ℕ.∋?(BigDecimal('0.1'))).to eq(false) - expect(ℕ.∋?(BigDecimal('1.1'))).to eq(false) - end - it 'w/ rational' do - expect(ℕ.∋?(data_rational_zero)).to eq(false) - data_range_rational_negative.∀{|n| expect(ℕ.∋?(n)).to eq(false)} - end - end - end - end # end: {ℕ} - - context '𝕎' do - context 'handles needed scenarios' do - context 'cases: positive' do - it 'w/ int' do - expect(data_range_ints_whole_nums.∀{|n| expect(𝕎.∋?(n)).to eq(true)}) - end - it 'w/ float' do - expect(data_range_floats_zero_to_positive.∀{|n| expect(𝕎.∋?(n)).to eq(true)}) - end - it 'w/ complex' do - expect(𝕎.∋?(data_complex_zero)).to eq(true) - expect(𝕎.∋?(data_complex_one)).to eq(true) - expect(𝕎.∋?(data_complex_leet)).to eq(true) - end - it 'w/ rational' do - data_range_rational_zero_to_positive.∀{|n| expect(𝕎.∋?(n)).to eq(true)} - end - it 'w/ big decimal' do - expect(𝕎.∋?(BigDecimal('1.0'))).to eq(true) - expect(𝕎.∋?(BigDecimal('1337.0'))).to eq(true) - expect(𝕎.∋?(BigDecimal('0.0'))).to eq(true) - end - end - context 'cases: negative' do - it 'w/ int' do - data_range_ints_negative.∀{|n| expect(𝕎.∋?(n)).to eq(false)} - end - it 'w/ float' do - data_range_floats_negative.∀{|n| expect(𝕎.∋?(n)).to eq(false)} - data_range_complex_nan_and_infs.∀{|c| expect(𝕎.∋?(c)).to eq(false)} - end - it 'w/ complex' do - expect(𝕎.∋?(data_complex_1i)).to eq(false) - expect(𝕎.∋?(-1i)).to eq(false) - end - it 'w/ rational' do - data_range_rational_negative.∀{|n| expect(𝕎.∋?(n)).to eq(false)} - end - it 'w/ big decimal' do - expect(𝕎.∋?(BigDecimal('-1.0'))).to eq(false) - expect(𝕎.∋?(BigDecimal('-1337.0'))).to eq(false) - end - end - end - end # end: {𝕎} - - context 'ℤ' do - context 'handles needed scenarios' do - context 'cases: positive' do - it 'w/ int' do - data_range_ints.∀{|n| expect(ℤ.∋?(n)).to eq(true)} - end - it 'w/ float' do - data_range_floats.∀{|n| expect(ℤ.∋?(n)).to eq(true)} - end - it 'w/ big decimal' do - expect(ℤ.∋?(data_big_decimal_negative_leet)).to eq(true) - expect(ℤ.∋?(data_big_decimal_negative_one)).to eq(true) - expect(ℤ.∋?(data_big_decimal_zero)).to eq(true) - expect(ℤ.∋?(data_big_decimal_one)).to eq(true) - expect(ℤ.∋?(data_big_decimal_leet)).to eq(true) - end - it 'w/ rational' do - expect(ℤ.∋?(data_rational_negative_leet)).to eq(true) - expect(ℤ.∋?(data_rational_negative_one)).to eq(true) - expect(ℤ.∋?(data_rational_zero)).to eq(true) - expect(ℤ.∋?(data_rational_one)).to eq(true) - expect(ℤ.∋?(data_rational_leet)).to eq(true) - expect(ℤ.∋?(Rational(Complex(3, 0), 1))).to eq(true) - end - it 'w/ complex' do - expect(ℤ.∋?(data_minus_leet)).to eq(true) - expect(ℤ.∋?(Complex(-1))).to eq(true) - expect(ℤ.∋?(data_complex_zero)).to eq(true) - expect(ℤ.∋?(data_complex_one)).to eq(true) - expect(ℤ.∋?(data_complex_leet)).to eq(true) - end - it 'w/ rational' do - data_range_rational.∀{|n| expect(ℤ.∋?(n)).to eq(true)} - end - end - it 'cases: negative' do - data_big_decimal_error_cases.∀{|n| expect(ℤ.∋?(n)).to eq(false)} - expect(ℤ.∋?(BigDecimal('1.1'))).to eq(false) - expect(ℤ.∋?(data_with_complex)).to eq(false) - data_float_error_cases.∀{|n| expect(ℤ.∋?(n)).to eq(false)} - - # complex - data_range_complex_nan_and_infs.∀{|c| expect(ℤ.∋?(c)).to eq(false)} - expect(ℤ.∋?(data_complex_1i)).to eq(false) - expect(ℤ.∋?(datac_one)).to eq(false) - expect(ℤ.∋?(Complex(1337.1337))).to eq(false) - end - end - end # end: {ℤ} - - context '𝕌' do - context 'handles needed scenarios' do - context 'cases: positive' do - it 'w/ int' do - data_range_ints.∀{|n| expect(𝕌.∋?(n)).to eq(true)} - end - it 'w/ floats' do - expect(𝕌.∋?(0.0)).to eq(true) - expect(𝕌.∋?(0.0)).to eq(true) - expect(𝕌.∋?(1.0)).to eq(true) - expect(𝕌.∋?(-1.0)).to eq(true) - [π, ℮, 𝚽].∀{|n| expect(𝕌.∋?(n)).to eq(true)} - end - it 'w/ big decimal' do - expect(𝕌.∋?(data_big_decimal_leet_kinda)).to eq(true) - end - it 'w/ complex' do - expect(𝕌.∋?(data_with_complex)).to eq(true) - expect(𝕌.∋?(data_with_complex_only_real_component)).to eq(true) - expect(𝕌.∋?(Complex(1, 2))).to eq(true) - expect(𝕌.∋?(Rational(Complex(-1, 2), 2))).to eq(true) - expect(𝕌.∋?(data_complex_one)).to eq(true) - end - it 'w/ rational' do - expect(𝕌.∋?(data_rational_default)).to eq(true) - end - end - it 'cases: negative' do - data_float_error_cases.∀{|n| expect(𝕌.∋?(n)).to eq(false)} - data_big_decimal_error_cases.∀{|n| expect(𝕌.∋?(n)).to eq(false)} - data_range_complex_nan_and_infs.∀{|c| expect(𝕌.∋?(c)).to eq(false)} - end - end - end # end: {𝕌} - - context 'ℝ' do - context 'handles needed scenarios' do - it 'cases: positive' do - data_range_ints.∀{|n| expect(ℝ.∋?(n)).to eq(true)} - expect(ℝ.∋?(0.0)).to eq(true) - expect(ℝ.∋?(data_rational_default)).to eq(true) - expect(ℝ.∋?(data_with_complex_only_real_component)).to eq(true) - expect(ℝ.∋?(data_big_decimal_leet_kinda)).to eq(true) - expect(ℝ.∋?(data_complex_one)).to eq(true) - end - it 'cases: negative' do - data_float_error_cases.∀{|n| expect(ℝ.∋?(n)).to eq(false)} - data_big_decimal_error_cases.∀{|n| expect(ℝ.∋?(n)).to eq(false)} - expect(ℝ.∋?(datac_one)).to eq(false) - data_range_complex_nan_and_infs.∀{|c| expect(ℝ.∋?(c)).to eq(false)} - expect(ℝ.∋?(data_with_complex)).to eq(false) - end - end - end # end: {ℝ} - - context 'ℂ' do - context 'handles needed scenarios' do - it 'cases: positive' do - expect(ℂ.∋?(data_rational_default)).to eq(true) - expect(ℂ.∋?(data_with_complex)).to eq(true) - data_range_ints.∀{|n| expect(ℂ.∋?(n)).to eq(true)} - expect(ℂ.∋?(data_big_decimal_leet_kinda)).to eq(true) - expect(ℂ.∋?(datac_one)).to eq(true) - expect(ℂ.∋?(1.337)).to eq(true) - end - it 'cases: negative' do - data_float_error_cases.∀{|n| expect(ℂ.∋?(n)).to eq(false)} - data_big_decimal_error_cases.∀{|n| expect(ℂ.∋?(n)).to eq(false)} - data_range_complex_nan_and_infs.∀{|c| expect(ℂ.∋?(c)).to eq(false)} - data_float_error_cases.∀{|n| expect(ℂ.∋?(n)).to eq(false)} - end - end - end # end: {ℂ} - - context 'ℚ' do - context 'handles needed scenarios' do - context 'cases: positive' do - it 'w/ ints' do - data_range_ints.∀{|n| expect(ℚ.∋?(n)).to eq(true)} - end - context 'w/ float' do - it 'regular data' do - expect(ℚ.∋?(1.0)).to eq(true) - end - it 'cases: un-covered scope' do - expect(ℚ.∋?(1.1337)).to eq(nil) - expect(ℚ.∋?(2.0/3)).to eq(nil) - end - end - it 'w/ rational' do - expect(ℚ.∋?(data_rational_default)).to eq(true) - end - it 'w/ big decimal' do - expect(ℚ.∋?(data_big_decimal_one)).to eq(true) - end - context 'w/ complex' do - it 'regular data' do - expect(ℚ.∋?(dataf_one)).to eq(true) - end - it 'cases: un-covered scope' do - expect(ℚ.∋?(Complex(2.0/3))).to eq(nil) - end - end - end - it 'cases: negative' do - expect(ℚ.∋?(data_with_complex)).to eq(false) - data_big_decimal_error_cases.∀{|n| expect(ℚ.∋?(n)).to eq(false)} - data_range_complex_nan_and_infs.∀{|c| expect(ℚ.∋?(c)).to eq(false)} - data_float_error_cases.∀{|n| expect(ℚ.∋?(n)).to eq(false)} - end - context 'converted cases to tech_debt', :tech_debt do - it 'for floats w/ symbolic-like traits' do - [π, ℮, 𝚽].∀{|n| expect(ℚ.∋?(n)).to eq(nil)} - end - end - end - end # end: {ℚ} - end - end - - # __ ___ __ ___ __ __ __ ___ - # |__) |__ |__) |__ / \ |__) |\/| /\ |\ | / ` |__ - # | |___ | \ | \__/ | \ | | /~~\ | \| \__, |___ - context 'performance', :performance do - context 'expression{𝔹.∋?(arg)}: performs very quickly' do - it 'for cases: positive' do - expect{𝔹.∋?(0)}.to perform_very_quickly - expect{𝔹.∋?(1.0)}.to perform_very_quickly - end - it 'cases: negative' do - scenarios = [data_float_error_cases + data_big_decimal_error_cases + data_complex_error_cases] - scenarios.∀{|n| expect{𝔹.∋?(n)}.to perform_very_quickly} - end - end - context 'expression{ℕ.∋?(arg)}: performs very quickly' do - it 'for cases: positive' do - expect{ℕ.∋?(data_complex_zero)}.to perform_very_quickly - end - it 'for cases: negative' do - expect{ℕ.∋?(data_complex_nan)}.to perform_very_quickly - end - end - context 'expression{𝕌.∋?(arg)}: performs very quickly' do - it 'for cases: positive' do - expect{𝕌.∋?(data_int_leet)}.to perform_very_quickly - expect{𝕌.∋?(0.0)}.to perform_very_quickly - expect{𝕌.∋?(data_rational_default)}.to perform_very_quickly - expect{𝕌.∋?(data_big_decimal_leet_kinda)}.to perform_very_quickly - expect{𝕌.∋?(55)}.to perform_very_quickly - expect{𝕌.∋?(-1)}.to perform_very_quickly - expect{𝕌.∋?(data_complex_one)}.to perform_very_quickly - end - it 'for cases: negative' do - data_float_error_cases.∀{|n| expect{𝕌.∋?(n)}.to perform_very_quickly} - data_big_decimal_error_cases.∀{|n| expect{𝕌.∋?(n)}.to perform_very_quickly} - data_complex_error_cases.∀{|n| expect{𝕌.∋?(n)}.to perform_very_quickly} - expect{𝕌.∋?(data_complex_nan)}.to perform_very_quickly - end - end - context 'expression{ℝ.∋?(arg)}: performs very quickly' do - it 'for cases: positive' do - expect{ℝ.∋?(data_int_leet)}.to perform_very_quickly - expect{ℝ.∋?(0.0)}.to perform_very_quickly - expect{ℝ.∋?(data_rational_default)}.to perform_very_quickly - expect{ℝ.∋?(data_big_decimal_leet_kinda)}.to perform_very_quickly - expect{ℝ.∋?(data_complex_one)}.to perform_very_quickly - end - it 'for cases: negative' do - data_float_error_cases.∀{|n| expect{ℝ.∋?(n)}.to perform_very_quickly} - data_big_decimal_error_cases.∀{|n| expect{ℝ.∋?(n)}.to perform_very_quickly} - expect{ℝ.∋?(data_complex_nan)}.to perform_very_quickly - expect{ℝ.∋?(data_with_complex)}.to perform_very_quickly - end - end - context 'expression{ℂ.∋?(arg)}: performs very quickly' do - it 'for cases: positive' do - expect{ℂ.∋?(data_rational_default)}.to perform_very_quickly - expect{ℂ.∋?(data_with_complex)}.to perform_very_quickly - expect{ℂ.∋?(1)}.to perform_very_quickly - expect{ℂ.∋?(1.337)}.to perform_very_quickly - expect{ℂ.∋?(data_big_decimal_zero)}.to perform_very_quickly - expect{ℂ.∋?(datac_one)}.to perform_very_quickly - end - it 'for cases: negative' do - expect{ℂ.∋?(data_big_decimal_negative_one)}.to perform_very_quickly - data_big_decimal_error_cases.∀{|n| expect{ℂ.∋?(n)}.to perform_very_quickly} - expect{ℂ.∋?(data_complex_nan)}.to perform_very_quickly - expect{ℂ.∋?(data_float_nan)}.to perform_very_quickly - end - end - context 'expression{ℤ.∋?(arg)}: performs very quickly' do - it 'for cases: positive' do - expect{ℤ.∋?(data_int_negative_one)}.to perform_very_quickly - expect{ℤ.∋?(data_big_decimal_negative_leet)}.to perform_very_quickly - expect{ℤ.∋?(-1337.0)}.to perform_very_quickly - expect{ℤ.∋?(data_rational_negative_leet)}.to perform_very_quickly - expect{ℤ.∋?(data_minus_leet)}.to perform_very_quickly - end - it 'for cases: negative' do - data_big_decimal_error_cases.∀{|n| expect{ℤ.∋?(n)}.to perform_very_quickly} - expect{ℤ.∋?(data_float_nan)}.to perform_very_quickly - expect{ℤ.∋?(data_minus_leet2)}.to perform_very_quickly - expect{ℤ.∋?(data_complex_nan)}.to perform_very_quickly - end - end - context 'expression{ℚ.∋?(arg)}: performs very quickly' do - it 'for cases: positive' do - expect{ℚ.∋?(data_rational_default)}.to perform_very_quickly - expect{ℚ.∋?(data_big_decimal_one)}.to perform_very_quickly - expect{ℚ.∋?(1.0)}.to perform_very_quickly - expect{ℚ.∋?(dataf_one)}.to perform_very_quickly - expect{ℚ.∋?(data_int_leet)}.to perform_extremely_quickly - end - it 'for cases: negative' do - expect{ℚ.∋?(data_with_complex)}.to perform_very_quickly - data_big_decimal_error_cases.∀{|n| expect{ℚ.∋?(n)}.to perform_very_quickly} - expect{ℚ.∋?(data_float_nan)}.to perform_very_quickly - expect{ℚ.∋?(data_complex_nan)}.to perform_very_quickly - end - end - end - -end diff --git a/spec/feature/f15/readme_spec.rb b/spec/feature/f15/readme_spec.rb index 0453877..66c7bcd 100644 --- a/spec/feature/f15/readme_spec.rb +++ b/spec/feature/f15/readme_spec.rb @@ -3,6 +3,9 @@ using ::ThetaAngle::ContextRuuuby using ::String::ContextF24 using ::Object::ContextSuperscripts +include( + ::Math::Trig +) RSpec.describe 'README.md' do diff --git a/spec/feature/f30/f30_b00_spec.rb b/spec/feature/f30/f30_b00_spec.rb deleted file mode 100644 index 667842a..0000000 --- a/spec/feature/f30/f30_b00_spec.rb +++ /dev/null @@ -1,15 +0,0 @@ -# encoding: UTF-8 - -RSpec.describe 'f30_b00' do - - context 'feature{f30} functionality for' do - context 'behavior{b00}' do - - it 'exists as needed' do - expect_feature_behavior_as_needed(🅱, ::Math::Space::BooleanSpace) - end - - end - end - -end diff --git a/spec/feature/f30/f30_b02_spec.rb b/spec/feature/f30/f30_b02_spec.rb index 227eb45..7128a28 100644 --- a/spec/feature/f30/f30_b02_spec.rb +++ b/spec/feature/f30/f30_b02_spec.rb @@ -5,10 +5,6 @@ context 'feature{f30} functionality for' do context 'behavior{b02}' do - it 'exists as needed' do - expect_feature_behavior_as_needed(🧬, ::Math::Space::NucleotideSpace) - end - context 'func{∃ᶜ?}' do context 'handling needed scenarios' do context 'cases: positive' do diff --git a/spec/feature/f30/f30_b03_spec.rb b/spec/feature/f30/f30_b03_spec.rb deleted file mode 100644 index 4eb09b0..0000000 --- a/spec/feature/f30/f30_b03_spec.rb +++ /dev/null @@ -1,13 +0,0 @@ -# encoding: UTF-8 - -RSpec.describe 'f30_b03' do - - context 'feature{f30} functionality for' do - context 'behavior{b03}' do - it 'exists as needed' do - expect_feature_behavior_as_needed(🔢, ::Math::Space::NumberSpace) - end - end - end - -end diff --git a/spec/feature/f30/f30_b04_spec.rb b/spec/feature/f30/f30_b04_spec.rb index 9788be1..43d555d 100644 --- a/spec/feature/f30/f30_b04_spec.rb +++ b/spec/feature/f30/f30_b04_spec.rb @@ -4,9 +4,6 @@ context 'feature{f34} functionality for' do context 'behavior{b04}' do - it 'exists as needed' do - expect_feature_behavior_as_needed(𝕊, ::Math::Space::SymbolicNumbers) - end context 'handles all needed scenarios' do context 'cases: positive' do diff --git a/spec/feature/f34/f34_b00_spec.rb b/spec/feature/f34/f34_b00_spec.rb deleted file mode 100644 index 0bff134..0000000 --- a/spec/feature/f34/f34_b00_spec.rb +++ /dev/null @@ -1,13 +0,0 @@ -# encoding: UTF-8 - -RSpec.describe 'f34_b00' do - - context 'feature{f34} behavior{b00} functionality' do - let(:geo){::Math::Geometry} - - context 'class{Shape}' do - - end - - end -end diff --git a/spec/feature/f34/f34_b01_spec.rb b/spec/feature/f34/f34_b01_spec.rb deleted file mode 100644 index 68736ad..0000000 --- a/spec/feature/f34/f34_b01_spec.rb +++ /dev/null @@ -1,13 +0,0 @@ -# encoding: UTF-8 - -RSpec.describe 'f34_b01' do - - context 'feature{f34} behavior{b01} functionality' do - let(:geo){::Math::Geometry} - - context 'class{PlaneFigure}' do - - end - - end -end diff --git a/spec/feature/f34/f34_b02_spec.rb b/spec/feature/f34/f34_b02_spec.rb deleted file mode 100644 index 81985bf..0000000 --- a/spec/feature/f34/f34_b02_spec.rb +++ /dev/null @@ -1,63 +0,0 @@ -# encoding: UTF-8 - -RSpec.describe 'f34_b02' do - - context 'feature{f34} behavior{b02} functionality' do - let(:geo){::Math::Geometry} - - context 'class{Triangle}' do - - context 'adds func{◣?}' do - context 'handling needed scenarios' do - it 'cases: positive' do - expect(geo::Triangle.new(3, 4, 5).◣?).to eq(true) - end - it 'cases: negative' do - expect(geo::Triangle.new_equilateral(1).◣?).to eq(false) - end - end - end - - context 'adds func{golden?}' do - context 'handling needed scenarios' do - it 'cases: positive' do - side_length = 2 * (Math.sqrt(5) + 1) - side_base = 4 - scenario = geo::Triangle.new(side_length, side_length, side_base) - expect(scenario.golden?).to eq(true) - end - it 'cases: negative' do - expect(geo::Triangle.new(3, 4, 5).golden?).to eq(false) - end - end - end - - end - - end - - context 'hybrid test', :integration do - let(:geo){::Math::Geometry} - - context '{f28_b00, f34_b02}' do - - it 'Kepler triangle' do - expect(::Math::Trig::ℕ³.pythagorean?(a: 1, b: √(𝚽), c: 𝚽)).to eq(true) - triangle = geo::Triangle.new(1, √(𝚽), 𝚽) - expect(triangle.◣?).to eq(true) - expect(triangle.scalene?).to eq(true) - expect(triangle.isosceles?).to eq(false) - expect(triangle.perimeter).to eq(𝚽 + 1 + √(𝚽)) - expect(triangle.obtuse?).to eq(false) - expect(triangle.equiangular?).to eq(false) - expect(triangle.equilateral?).to eq(false) - expect(triangle.acute?).to eq(false) - - #2 * (Math::PI / (Math.sin(θ°(72).ʳ))) - end - - end - - end - -end diff --git a/spec/feature/f34/f34_b03_spec.rb b/spec/feature/f34/f34_b03_spec.rb deleted file mode 100644 index 68b9c36..0000000 --- a/spec/feature/f34/f34_b03_spec.rb +++ /dev/null @@ -1,13 +0,0 @@ -# encoding: UTF-8 - -RSpec.describe 'f34_b03' do - - context 'feature{f34} behavior{b03} functionality' do - let(:geo){::Math::Geometry} - - context 'class{Quadrilateral}' do - - end - - end -end diff --git a/spec/feature/f34/f34_b04_spec.rb b/spec/feature/f34/f34_b04_spec.rb deleted file mode 100644 index de576b9..0000000 --- a/spec/feature/f34/f34_b04_spec.rb +++ /dev/null @@ -1,13 +0,0 @@ -# encoding: UTF-8 - -RSpec.describe 'f34_b04' do - - context 'feature{f34} behavior{b04} functionality' do - let(:geo){::Math::Geometry} - - context 'class{Circle}' do - - end - - end -end diff --git a/spec/feature/f34/f34_db_orm_spec.rb b/spec/feature/f34/f34_db_orm_spec.rb deleted file mode 100644 index baa3594..0000000 --- a/spec/feature/f34/f34_db_orm_spec.rb +++ /dev/null @@ -1,39 +0,0 @@ -# encoding: UTF-8 - -RSpec.describe 'f34_db_orm' do - - context 'db_orm', :db do - - context 'defines{f34}' do - it 'passes ORM audit' do - audit_feature(f34, 'f34', 5, 'abstract `Geometry`; offering static math functions; esp. those for `Shapes`') - end - - context 'defines behaviors' do - it 'defines{b00}' do - audit_feature_behavior(f34, f34_b00, 'b00', 'offer basic abstractions to `Shape`') - end - - it 'defines{b01}' do - audit_feature_behavior(f34, f34_b01, 'b01', 'offer basic abstractions to `Shape::PlaneFigure`') - end - - it 'defines{b02}' do - audit_feature_behavior(f34, f34_b02, 'b02', 'offer basic abstractions to `Shape::Triangle`') - end - - it 'defines{b03}' do - audit_feature_behavior(f34, f34_b03, 'b03', 'offer basic abstractions to `Shape::Quadrilateral`') - end - - it 'defines{b04}' do - audit_feature_behavior(f34, f34_b04, 'b04', 'offer basic abstractions to `Shape::Circle`') - end - - end # end: {defines behaviors} - - end # end: {defines{f34}} - - end - -end diff --git a/spec/feature/f34/f34_spec.rb b/spec/feature/f34/f34_spec.rb deleted file mode 100644 index 3ce0d7c..0000000 --- a/spec/feature/f34/f34_spec.rb +++ /dev/null @@ -1,87 +0,0 @@ -# encoding: UTF-8 - -using ::ThetaAngle::ContextRuuuby -using ::ThetaAngle::ContextParamCheck - -::RSpec.describe 'f34' do - - context 'feature{f34} functionality' do - let(:geo){::Math::Geometry} - - context 'hybrid tests', :integration do - let(:a_triangle){geo::Triangle.new(3, 4, 5)} - let(:a_square){geo::Square.new(3)} - - context 'func{sum_of_interior_angles}' do - context 'handles needed scenarios' do - it 'cases: positive' do - expect_sum_of_interior_angles(a_triangle, 3) - expect_sum_of_interior_angles(a_square, 4) - end - end - end - - end - end - - context 'extends module{Math}' do - - context 'by adding needed functions & aliases' do - - context 'module{Math::Ratio}' do - - context 'func{golden?}' do - context 'handles needed scenarios' do - context 'cases: positive' do - it 'w/ regular data' do - expect(::Math::Ratio.golden?(a: 1 + √(5), b: 2)).to eq(true) - end - it 'w/ ThetaAngles' do - expect(::Math::Ratio.golden?(a: θ°(360.0).° - Ⴔ.°, b: Ⴔ.°)).to eq(true) - end - end - context 'cases: negative' do - it 'bad params' do - expect{::Math::Ratio.golden?(1, 2, 3)}.to raise_error(ArgumentError) - expect{::Math::Ratio.golden?(a: 1, b: 2, c: nil)}.to raise_error(ArgumentError) - expect{::Math::Ratio.golden?(1, a: 1, b: 2)}.to raise_error(ArgumentError) - end - it 'not τ² golden-ratio tuples' do - expect(::Math::Ratio.golden?(a: 1, b: 2)).to eq(false) - expect(::Math::Ratio.golden?(a: 1, b: 2.0)).to eq(false) - end - end - end - end # end: {func{golden?}} - - end # end: {module{Math::Ratio}} - - context 'func{pythagorean??}' do - context 'handles needed scenarios' do - context 'cases: positive' do - it 'w/ ints & floats' do - expect(::Math::Trig::ℕ³.pythagorean?(a: 3, b: 4, c: 5)).to eq(true) - expect(::Math::Trig::ℕ³.pythagorean?(a: 3.0, b: 4.0, c: 5.0)).to eq(true) - expect(::Math::Trig::ℕ³.pythagorean?(a: 3.0, b: 4, c: 5)).to eq(true) - end - it 'w/ theta angles' do - expect(::Math::Trig::ℕ³.pythagorean?(a: θ°(30), b: θ°(60), c: θ°(90))).to eq(true) - end - end - context 'cases: negative' do - it 'bad params' do - expect{::Math::Trig::ℕ³.pythagorean?(1, 2, 3)}.to raise_error(ArgumentError) - expect{::Math::Trig::ℕ³.pythagorean?(a: 1, b: 2, c: nil)}.to raise_error(ArgumentError) - expect{::Math::Trig::ℕ³.pythagorean?(1, a: 1, b: 2, c: 3)}.to raise_error(ArgumentError) - end - it 'not pythagoras_τ³ tuples' do - expect(::Math::Trig::ℕ³.pythagorean?(a: 1, b: 2, c: 3)).to eq(false) - end - end - end - end # end: {func{pythagorean?}} - - end - end - -end diff --git a/spec/feature/f37/f37_b00_spec.rb b/spec/feature/f37/f37_b00_spec.rb index c8cea5a..1f39ebe 100644 --- a/spec/feature/f37/f37_b00_spec.rb +++ b/spec/feature/f37/f37_b00_spec.rb @@ -1,6 +1,18 @@ # encoding: UTF-8 =begin + +::RSpec.shared_context 'shared_context_f38' do + # @param [PseudoGraph] graph + # @param [Integer] num_nodes + def expect_pseudo_graph(graph, num_nodes) + expect(graph.ⓣ).to eq(::PseudoGraph) + expect(graph.num_nodes.ⓣ).to eq(::Integer) + expect(graph.num_nodes).to eq(num_nodes) + end +end + + RSpec.describe 'f37_b00' do context 'functionality' do diff --git a/spec/helpers/helper_db.rb b/spec/helpers/db/autoload_me.rb similarity index 97% rename from spec/helpers/helper_db.rb rename to spec/helpers/db/autoload_me.rb index 0416261..85499d6 100644 --- a/spec/helpers/helper_db.rb +++ b/spec/helpers/db/autoload_me.rb @@ -1,5 +1,14 @@ # encoding: UTF-8 +$ruuuby = 💎 +$ruuuby.engine.stats_ext['RUUUBY_ENV'] = 'dev' +$ruuuby.engine.stats_ext['RUUUBY_CONFIGS'] = 'configs_local/db/dev.yml' + +require_relative '../../../lib/ruuuby/db/migrations/migration_ext' +require_relative '../../../lib/ruuuby/db/migrations/ruuuby_gem' + +$orm = 💎.engine.orm + module HelpersDB def audit_feature(the_feature, feature_str, expected_num_feats, description) diff --git a/spec/helpers/helper_math.rb b/spec/helpers/helper_math.rb deleted file mode 100644 index ef0d0a2..0000000 --- a/spec/helpers/helper_math.rb +++ /dev/null @@ -1,57 +0,0 @@ -# encoding: UTF-8 - -module HelpersMath - - def expect_not_subset(a, b) - expect(a.⊂?(b)).to eq(false) - expect(a.⊆?(b)).to eq(false) - expect(a.⊄?(b)).to eq(true) - end - - def expect_proper_subset(a, b) - expect(a.⊂?(b)).to eq(true) - expect(a.⊆?(b)).to eq(true) - expect(b.⊃?(a)).to eq(true) - expect(b.⊇?(a)).to eq(true) - - expect(b.⊂?(a)).to eq(false) - - expect(a.⊄?(b)).to eq(false) - expect(b.⊄?(a)).to eq(true) - expect(a.⊅?(b)).to eq(true) - expect(b.⊅?(a)).to eq(false) - end - - def expect_equal_sets(a, b) - expect(a.⊂?(b)).to eq(false) - expect(b.⊂?(a)).to eq(false) - expect(a.⊃?(b)).to eq(false) - expect(b.⊃?(a)).to eq(false) - - expect(a.⊆?(b)).to eq(true) - expect(b.⊆?(a)).to eq(true) - expect(b.⊇?(a)).to eq(true) - expect(a.⊇?(b)).to eq(true) - - expect(a.⊄?(b)).to eq(true) - expect(b.⊅?(a)).to eq(true) - expect(b.⊄?(a)).to eq(true) - expect(a.⊅?(b)).to eq(true) - end - - def _compared_to_empty_set(set) - expect(∅.⊂?(set)).to eq(false) - expect(∅.⊆?(set)).to eq(set == ∅) - expect(set.⊆?(set)).to eq(true) - end - - def expect_number_set(obj, symbol, kclass, name) - expect(obj).to eq(kclass.instance) - expect(obj.ⓣ).to eq(kclass) - expect(obj.🆔).to eq(kclass.instance.🆔) - expect(obj.name).to eq(name) - expect(obj.symbol).to eq(symbol) - _compared_to_empty_set(obj) - end - -end \ No newline at end of file diff --git a/spec/helpers/helper_ruuuby.rb b/spec/helpers/helper_ruuuby.rb index 1abe7ac..65aa85a 100644 --- a/spec/helpers/helper_ruuuby.rb +++ b/spec/helpers/helper_ruuuby.rb @@ -2,18 +2,6 @@ using ::ThetaAngle::ContextRuuuby -::RSpec.shared_context 'shared_context_f38' do - - # @param [PseudoGraph] graph - # @param [Integer] num_nodes - def expect_pseudo_graph(graph, num_nodes) - expect(graph.ⓣ).to eq(::PseudoGraph) - expect(graph.num_nodes.ⓣ).to eq(::Integer) - expect(graph.num_nodes).to eq(num_nodes) - end - -end - ::RSpec.shared_context 'shared_context_f40' do # @param [String] container_name @@ -37,7 +25,14 @@ def audit_container(container_name, expect_tty, expected_os, expected_os_version expect(container.env_vars).to eq(container_by_id.env_vars) - expect(container.env_vars['SERVICE_NAME']).to eq(container_name) + short_name = container.env_vars['SERVICE_NAME'] + if short_name.end_with?('_dev') + short_name = short_name[0..short_name.length-5] + elsif short_name.end_with?('_test') || short_name.end_with?('_prod') + short_name = short_name[0..short_name.length-6] + end + + expect(container.env_vars['SERVICE_NAME']).to eq(short_name) if expected_os == 'alpine' expect(container.alpine?).to eq(true) @@ -51,7 +46,9 @@ def audit_container(container_name, expect_tty, expected_os, expected_os_version expect(os_release['HOME_URL']).to eq('https://alpinelinux.org/') expect(os_release['BUG_REPORT_URL']).to eq('https://bugs.alpinelinux.org/') - expect(container.os_architecture).to eq('musl-linux-amd64') + unless container_name.include?('pgadmin') || container_name.include?('postgres') + expect(container.os_architecture).to eq('musl-linux-amd64') + end else expect(container.alpine?).to eq(false) expect(container.debian?).to eq(true) @@ -65,23 +62,6 @@ def audit_container(container_name, expect_tty, expected_os, expected_os_version end -::RSpec.shared_context 'shared_context_f34' do - - def expect_sum_of_interior_angles(the_shape, expected_number_of_sides) - result = the_shape.sum_of_interior_angles - expect(result.ⓣ).to eq(::ThetaAngle) - if the_shape.is_a?(::Math::Geometry::Circle) - expect(the_shape.num_sides).to eq(::Float::INFINITY) - expect(θ°(360)).to eq(result) - else - expect(the_shape.num_sides.ⓣ).to eq(::Integer) - expect(the_shape.num_sides).to eq(expected_number_of_sides) - expect((θ°(180.0 * (the_shape.num_sides - 2)))).to eq(result) - end - end - -end - ::RSpec.shared_context 'shared_context_f32' do let(:f𝕎¹_error_scenarios){[10.1, 0.1, -1, nil, '1']} let(:fℕ¹_error_scenarios){[10.1, 0.1, 0, -0.0, 0.0, -1, nil, '1']} @@ -109,17 +89,6 @@ def expect_error_f32_sequence(the_sequence) end -::RSpec.shared_context 'shared_context_f30' do - - def expect_feature_behavior_as_needed(the_ref, kclass) - the_id = the_ref.🆔 - expect(the_ref.ⓣ).to eq(kclass) - expect(the_ref.🆔).to eq(kclass.instance.🆔) - expect(the_ref.🆔).to eq(the_id) - end - -end - ::RSpec.shared_context 'shared_context_f27' do let(:as_degrees){θ°(360)} diff --git a/spec/helpers/integration/autoload_me.rb b/spec/helpers/integration/autoload_me.rb new file mode 100644 index 0000000..2888044 --- /dev/null +++ b/spec/helpers/integration/autoload_me.rb @@ -0,0 +1,3 @@ +# encoding: UTF-8 + +ENV['RUUUBY_RSPEC_INTEGRATION'] = 'true' diff --git a/spec/helpers/load_benchmark.rb b/spec/helpers/load_benchmark.rb deleted file mode 100644 index 6d0706e..0000000 --- a/spec/helpers/load_benchmark.rb +++ /dev/null @@ -1,3 +0,0 @@ -# encoding: UTF-8 - -require 'benchmark' diff --git a/spec/helpers/locale/autoload_me.rb b/spec/helpers/locale/autoload_me.rb new file mode 100644 index 0000000..cf6663c --- /dev/null +++ b/spec/helpers/locale/autoload_me.rb @@ -0,0 +1,15 @@ +# encoding: UTF-8 + +require_relative '../../../lib/ruuuby/module/gem' +require_relative '../../../lib/ruuuby/module/bundler' + +module ::TTY + class Command + attribute_versionable('0.10.0'){::TTY::Command::VERSION} + + # @return [Boolean] + def self.healthy? + ::TTY::Command.record_separator == $/ && !::TTY::Command.windows? && ::TTY::Command.∃version? + end + end +end diff --git a/spec/helpers/helper_performance.rb b/spec/helpers/performance/autoload_me.rb similarity index 99% rename from spec/helpers/helper_performance.rb rename to spec/helpers/performance/autoload_me.rb index cd9467f..d22a61c 100644 --- a/spec/helpers/helper_performance.rb +++ b/spec/helpers/performance/autoload_me.rb @@ -1,5 +1,7 @@ # encoding: UTF-8 +require 'benchmark' + RSpec.shared_context 'shared_context_performance' do let(:tΔ_within){PerformanceTestHelper::Configs::DEFAULT_WITHIN * 2} diff --git a/spec/locale/ag_gem_configs_spec.rb b/spec/locale/ag_gem_configs_spec.rb index bb099b2..30070e8 100644 --- a/spec/locale/ag_gem_configs_spec.rb +++ b/spec/locale/ag_gem_configs_spec.rb @@ -1,6 +1,5 @@ # encoding: UTF-8 -# wip RSpec.describe '[AutomaticGeneration]: gem configs' do context 'locale', :locale do @@ -59,18 +58,6 @@ end end # end: {for gem{tty-command}} - #context 'for gem{sqlite3}' do - # it 'has correct version{1.4.2}' do - # expect(::SQLite3::VERSION).to eq('1.4.2') - # end - #end # end: {for gem{sqlite3}} - - #context 'for gem{activerecord}' do - # it 'has correct version{5.2.4.3}' do - # expect(::ActiveRecord::VERSION::STRING).to eq('5.2.4.3') - # end - #end # end: {for gem{activerecord}} - end # end: {by having correct configs} end # end: {all gems are healthy} diff --git a/spec/locale/locale_full_verification_spec.rb b/spec/locale/locale_full_verification_spec.rb index f179f2d..dda15b4 100644 --- a/spec/locale/locale_full_verification_spec.rb +++ b/spec/locale/locale_full_verification_spec.rb @@ -49,46 +49,6 @@ end # end: {web protocol} - context 'recommended configs' do - - context 'for gem{rubygems-update}' do - it 'has correct version' do - expect_needed_version(::Gem, '3.2.0.rc.2', ::Gem.rubygems_version.to_s) - end - it 'matching output of cmd{gem -v}' do - expect(::Gem.version_current).to eq(💻('gem -v')) - end - end # end: {for gem{rubygems-update}} - - context 'for gem{bundler}' do - it 'passes all health checks' do - expect(::Bundler.healthy?).to eq(true) - end - it 'has correct version' do - expect_needed_version(::Bundler, '2.2.0.rc.2', ::Bundler::VERSION) - end - it 'as defined by {Gem}' do - expect(::Gem::BundlerVersionFinder.bundler_version.to_s).to eq(::Bundler.version_current) - end - it 'w/ needed ENV_VARs' do - expected_path = "#{💎.engine.path_base}Gemfile" - expect(::ENV['BUNDLE_GEMFILE']).to eq(expected_path) - expect(::Bundler.path_gemfile).to eq(expected_path) - end - it 'does not require sudo (depending on OS)' do - if 💎.engine.os.mac? - expect(::Bundler.requires_sudo?).to eq(false) - elsif 💎.engine.os.unix - # currently, only Alpine-Linux is supported/expected, which will run w/ user{`root`} - expect(::Bundler.requires_sudo?).to eq(true) - else - # ¯\_(ツ)_/¯ - end - end - end # end: {for gem{bundler}} - - end # end: {recommended configs} - context 'additional configs for GCC' do context 'needed libs for GCC can be found' do context 'brew based, see lib{ruby-build}' do @@ -112,10 +72,6 @@ #it 'for{git}' do # expect($git.version).to eq('git version 2.24.3 (Apple Git-128)') #end - it '${clang --version} matches ${cc --version}' do - expect(💻('clang --version')).to eq(💻('cc --version')) - end - # TODO: test having #{gcc -v} match too end # end: {correct version tests from CLI-APIs} end # end: {optional tests} end @@ -145,55 +101,11 @@ end end # end: {current user} - context 'recommended settings for lib' do - context '{zsh}' do - it 'expected version{5.8} matches' do - expect(💻('zsh --version')).to eq('zsh 5.8 (x86_64-apple-darwin18.7.0)') - end - end # end: {ZSH} - context '{curl}' do - it 'expected version{7.64.1} matches' do - expect(💻('curl --version')).to eq(["curl 7.64.1 (x86_64-apple-darwin19.0) libcurl/7.64.1 (SecureTransport) LibreSSL/2.8.3 zlib/1.2.11 nghttp2/1.39.2", "Release-Date: 2019-03-27", "Protocols: dict file ftp ftps gopher http https imap imaps ldap ldaps pop3 pop3s rtsp smb smbs smtp smtps telnet tftp ", "Features: AsynchDNS GSS-API HTTP2 HTTPS-proxy IPv6 Kerberos Largefile libz MultiSSL NTLM NTLM_WB SPNEGO SSL UnixSockets"]) - end - end # end: {curl} - end - - context 'recommended settings for {iconv}' do - it 'passes all health checks' do - expect(💎.engine.api_locale.api_iconv.healthy?).to eq(true) - end - it 'has needed version{1.11}' do - expect_needed_version(💎.engine.api_locale.api_iconv, 'iconv (GNU libiconv 1.11)') - end - it 'supports needed encoding{UTF-8}' do - expect(💎.engine.api_locale.api_iconv.∃_encoding?('UTF-8')).to eq(true) - end - end # end: {iconv} - context 'misc configs are as needed' do it '$PATH separator is defined as{:}' do expect(build_configs['PATH_SEPARATOR']).to eq(':') end end - # @see https://stackoverflow.com/questions/17980759/xcode-select-active-developer-directory-error - context 'configs for xcode' do - context 'xcode-select' do - it 'has needed version' do - expect(💻('xcode-select --version')).to eq('xcode-select version 2373.') - end - it 'has needed path' do - # @see https://github.com/nodejs/node-gyp/issues/569 - # to change path after fresh xcode installation: `sudo xcode-select -s /Applications/Xcode.app/Contents/Developer` - expect(💻('xcode-select --print-path')).to eq('/Applications/Xcode.app/Contents/Developer') - end - end - context 'xcodebuild' do - it 'has needed version' do - expect(💻('xcodebuild -version')).to eq(["Xcode 12.1", "Build version 12A7403"]) - end - end - end - end end diff --git a/spec/locale/ruby_locale_spec.rb b/spec/locale/ruby_locale_spec.rb index 636fa3d..084ec53 100644 --- a/spec/locale/ruby_locale_spec.rb +++ b/spec/locale/ruby_locale_spec.rb @@ -14,7 +14,6 @@ expect(RUBY_REVISION).to eq('0096d2b895395df5ab8696d3b6d444dc1b7730b6') end it 'w/ needed ENV_VARs set' do - #expect(ENV['RBENV_VERSION']).to eq(RUBY_VERSION) expect(ENV['RBENV_VERSION']).to eq('3.0.0-preview1') end it 'w/ build configs' do @@ -52,8 +51,6 @@ context 'runtime configs' do it 'is currently not using safe mode' do - # @see https://docs.ruby-lang.org/en/2.6.0/security_rdoc.html#label-24SAFE - # TODO: change w/ Ruby 3.0 expect($SAFE).to eq(nil) end context 'rubygems' do diff --git a/spec/spec_helper.rb b/spec/spec_helper.rb index 941ea6e..f5a5452 100644 --- a/spec/spec_helper.rb +++ b/spec/spec_helper.rb @@ -3,11 +3,8 @@ require 'bundler/setup' require 'ruuuby' -require_relative 'helpers/helper_performance' require_relative 'helpers/helper_ruuuby' require_relative 'helpers/static_test_data' -require_relative 'helpers/helper_db' -require_relative 'helpers/helper_math' require 'rdoc' require 'rake' @@ -183,47 +180,42 @@ def expect_∄ᴹ(kmodule) RSpec.configure do |config| - # Enable flags like --only-failures and --next-failure + # enable flags like --only-failures and --next-failure config.example_status_persistence_file_path = '.rspec_status' #config.add_setting(:start_time) - # Disable RSpec exposing methods globally on `Module` and `main` - #config.disable_monkey_patching! - config.expect_with :rspec do |c| c.syntax = :expect end config.profile_examples = 4 - config.include ::Math::Trig + if ENV['RUUUBY_RSPEC_INTEGRATION'] == 'on' + config.include ::Math::Trig + end config.include_context 'shared_context_general' config.include_context 'shared_context_f24' config.include_context 'shared_context_f27' - config.include_context 'shared_context_f30' config.include_context 'shared_context_f32' - config.include_context 'shared_context_f34' - config.include_context 'shared_context_f38' config.include_context 'shared_context_f40' config.include HelpersGeneral config.include HelpersFeature16 config.include HelpersSyntaxCache - config.include HelpersMath - - config.include HelpersDB, :db - config.include_context 'shared_context_db', :db - config.include PerformanceTestHelper, :performance + stats = ::Ruuuby::MetaData.engine.stats_ext - config.include RSpec::Benchmark::Matchers, :performance - config.include_context 'shared_context_performance', :performance - - #config.filter_run_excluding :performance => lambda {|v| v == 'slow'} + if ENV['RUUUBY_AUTOLOAD_DB'] == 'on' && (stats['F92_B00'] || stats['F92_B01'] || stats['F92_B02']) + config.include HelpersDB, :db + config.include_context 'shared_context_db', :db + end - #config.filter_run_excluding :performance => 'slow' - # https://github.com/rspec/rspec-core/issues/2567 + if ENV['RUUUBY_PERFORMANCE_LIMIT'] == 'off' + config.include PerformanceTestHelper, :performance + config.include RSpec::Benchmark::Matchers, :performance + config.include_context 'shared_context_performance', :performance + end end diff --git a/spec/system/javascript_docker_service_spec.rb b/spec/system/javascript_docker_service_spec.rb index edd5894..acf91db 100644 --- a/spec/system/javascript_docker_service_spec.rb +++ b/spec/system/javascript_docker_service_spec.rb @@ -30,7 +30,7 @@ # webpack -v expect(versions[2]).to eq('4.44.2') # mocha --version - expect(versions[3]).to eq('8.1.3') + expect(versions[3]).to eq('8.2.1') # gulp -v expect(versions[4]).to eq('CLI version: 2.3.0') expect(versions[5]).to eq('Local version: 4.0.2') diff --git a/spec/system/nginx_docker_service_spec.rb b/spec/system/nginx_docker_service_spec.rb index a73b671..2bf8bf8 100644 --- a/spec/system/nginx_docker_service_spec.rb +++ b/spec/system/nginx_docker_service_spec.rb @@ -24,7 +24,7 @@ expect(env_vars['PKG_RELEASE']).to eq('1') expect(container_nginx.volumes.length).to eq(1) - expect(container_nginx.volumes[0]).to eq(%w(ruuuby_nginx_data /var/lib/docker/volumes/ruuuby_nginx_data/_data /v)) + expect(container_nginx.volumes[0]).to eq(%w(vol_nginx_dev /var/lib/docker/volumes/vol_nginx_dev/_data /v)) #expect(container_nginx.mounts.length).to eq(1) #expect(container_nginx.mounts[0].ⓣ).to eq(::Hash) #expect(container_nginx.mounts[0]['Destination']).to eq('/v') diff --git a/spec/system/pgadmin_docker_service_spec.rb b/spec/system/pgadmin_docker_service_spec.rb index 37f57ba..9859645 100644 --- a/spec/system/pgadmin_docker_service_spec.rb +++ b/spec/system/pgadmin_docker_service_spec.rb @@ -1,7 +1,7 @@ # encoding: UTF-8 RSpec.describe 'docker_service_pgadmin' do - let(:service_name){'service_pgadmin'} + let(:service_name){'service_pgadmin_dev'} context 'system tests for docker-service{pgadmin}', :system do @@ -12,12 +12,13 @@ end it 'can find the container{service_pgadmin}, matching against expected versions & configs' do - container_pgadmin = audit_container(service_name, false, 'alpine', '3.9.4') - - env_vars = container_pgadmin.env_vars - expect(env_vars['PYTHON_PIP_VERSION']).to eq('19.1.1') - expect(env_vars['PYTHON_VERSION']).to eq('3.7.3') + container_pgadmin = audit_container(service_name, false, 'alpine', '3.11.6') + env_vars = container_pgadmin.env_vars + expect(env_vars['PYTHON_PIP_VERSION']).to eq('20.2.3') + expect(env_vars['PYTHON_VERSION']).to eq('3.8.6') expect(env_vars['LANG']).to eq('C.UTF-8') + expect(env_vars['PGADMIN_LISTEN_PORT']).to eq('13337') + expect(env_vars['GUNICORN_THREADS']).to eq('15') end end diff --git a/spec/system/postgres_docker_service_spec.rb b/spec/system/postgres_docker_service_spec.rb index 46f2ae2..f3ec9da 100644 --- a/spec/system/postgres_docker_service_spec.rb +++ b/spec/system/postgres_docker_service_spec.rb @@ -1,7 +1,7 @@ # encoding: UTF-8 -RSpec.describe 'docker_service_postgres' do - let(:service_name){'service_postgres'} +RSpec.describe 'docker_service_postgresql' do + let(:service_name){'service_postgresql'} context 'system tests for docker-service{postgres}', :system do @@ -11,17 +11,17 @@ expect(🐋.∃🐋?(service_name)).to eq(true) end - it 'can find the container{service_postgres}, matching against expected versions & configs' do - container_postgres = audit_container(service_name, false, 'alpine', '3.12.0') + it 'can find the container{service_postgresql}, matching against expected versions & configs' do + container_postgres = audit_container(service_name, false, 'alpine', '3.12.1') - expect(container_postgres.cmd!(%w(postgres --version))).to eq("postgres (PostgreSQL) 13beta3") + expect(container_postgres.cmd!(%w(postgres --version))).to eq("postgres (PostgreSQL) 13.1") env_vars = container_postgres.env_vars expect(env_vars['PGDATA']).to eq('/var/lib/postgresql/data') expect(env_vars['LANG']).to eq('en_US.utf8') expect(env_vars['PG_MAJOR']).to eq('13') - expect(env_vars['PG_VERSION']).to eq('13beta3') - expect(env_vars['PG_SHA256']).to eq('863e33ee9d1099e2a0f1cab6dbd015789b2c2af75cfbad814a3acdf7c8eeaf9d') + expect(env_vars['PG_VERSION']).to eq('13.1') + expect(env_vars['PG_SHA256']).to eq('12345c83b89aa29808568977f5200d6da00f88a035517f925293355432ffe61f') end context 'expected configs' do