From 96b554bb5bf8fd3f386fe0e4baeac017f53c57d7 Mon Sep 17 00:00:00 2001 From: Ahmad Farhat Date: Fri, 12 Feb 2021 18:35:00 -0500 Subject: [PATCH 01/67] added sqlite to Gemfile (#2528) --- Gemfile | 5 +++-- scripts/image_build.sh | 7 ------- 2 files changed, 3 insertions(+), 9 deletions(-) diff --git a/Gemfile b/Gemfile index 1fe7ac8c..9f066b20 100644 --- a/Gemfile +++ b/Gemfile @@ -85,6 +85,9 @@ gem 'pluck_to_hash', '~> 1.0.2' gem 'local_time', '~> 2.1.0' +# Use a sqlite database in test and development. +gem 'sqlite3', '~> 1.3.6' + group :production do # Use a postgres database in production. gem 'pg', '~> 0.18' @@ -106,8 +109,6 @@ group :development, :test do gem 'byebug', platform: :mri # Environment configuration. gem 'dotenv-rails' - # Use a sqlite database in test and development. - gem 'sqlite3', '~> 1.3.6' end group :test do diff --git a/scripts/image_build.sh b/scripts/image_build.sh index 47566a43..1cba0377 100755 --- a/scripts/image_build.sh +++ b/scripts/image_build.sh @@ -55,13 +55,6 @@ if [ "$CD_REF_NAME" != "master" ] && [[ "$CD_REF_NAME" != *"release"* ]] && [[ " exit 0 fi -# Include sqlite for production -sqliteCount="$(grep "gem 'sqlite3'" Gemfile | wc -l)" - -if [ $sqliteCount -lt 2 ]; then - sed -i "/^group :production do/a\ \ gem 'sqlite3', '~> 1.3.6'" Gemfile -fi - # Set the version tag when it is a release or the commit sha was included. if [[ "$CD_REF_NAME" == *"release"* ]]; then export CD_VERSION_CODE=${CD_REF_NAME:8} From 3614d0fc5ed6ef1a71324e12e65dff16ccee1c47 Mon Sep 17 00:00:00 2001 From: Fred Dixon Date: Sat, 13 Feb 2021 23:09:56 -0400 Subject: [PATCH 02/67] Point to Greenlight mailing list --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 454102cc..ca26cd35 100644 --- a/README.md +++ b/README.md @@ -33,4 +33,4 @@ Greenlight is built using Ruby on Rails. Many developers already know Rails well We invite you to build upon Greenlight and help make it better. See [Contributing to BigBlueButton](http://docs.bigbluebutton.org/support/faq.html#contributing-to-bigbluebutton). -We invite your feedback, questions, and suggests about Greenlight too. Please post them to the [developer mailing list](https://groups.google.com/forum/#!forum/bigbluebutton-dev). +We invite your feedback, questions, and suggests about Greenlight too. Please post them to the [Greenlight mailing list](https://groups.google.com/forum/#!forum/bigbluebutton-greenlight). From 51cc00bcffe2baa89f110c7952ba6686d2793a72 Mon Sep 17 00:00:00 2001 From: Ahmad Farhat Date: Sun, 14 Feb 2021 14:01:12 -0500 Subject: [PATCH 03/67] Only build image on release (#2530) --- .github/workflows/build.release.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.github/workflows/build.release.yml b/.github/workflows/build.release.yml index f77fa761..3f8fa9c9 100644 --- a/.github/workflows/build.release.yml +++ b/.github/workflows/build.release.yml @@ -5,6 +5,7 @@ env: name: Build Release on: release: + types: [released] jobs: main: From 7c547c36ecc23c92759847a7085da168838f14ee Mon Sep 17 00:00:00 2001 From: Ahmad Farhat Date: Sun, 14 Feb 2021 14:06:19 -0500 Subject: [PATCH 04/67] Removed old travis stuff (#2531) --- .dockerignore | 1 - README.md | 1 - 2 files changed, 2 deletions(-) diff --git a/.dockerignore b/.dockerignore index eb2c7816..5da345a5 100644 --- a/.dockerignore +++ b/.dockerignore @@ -25,6 +25,5 @@ vendor/bundle Dockerfile .gitlab-ci.yml .rubocop.yml -.travis.yml spec test \ No newline at end of file diff --git a/README.md b/README.md index ca26cd35..375b9968 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,5 @@ # Greenlight -![Travis CI](https://travis-ci.org/bigbluebutton/greenlight.svg?branch=master) ![Coverage !Status](https://coveralls.io/repos/github/bigbluebutton/greenlight/badge.svg?branch=master) ![Docker Pulls](https://img.shields.io/docker/pulls/bigbluebutton/greenlight.svg) From 19434df22c06a50927b4e47097ae122841d3f96e Mon Sep 17 00:00:00 2001 From: Jesus Federico Date: Wed, 17 Feb 2021 10:40:31 -0500 Subject: [PATCH 05/67] added rake task for checking livness on k8s deployments (#2537) --- lib/tasks/liveness.rake | 6 ++++++ 1 file changed, 6 insertions(+) create mode 100644 lib/tasks/liveness.rake diff --git a/lib/tasks/liveness.rake b/lib/tasks/liveness.rake new file mode 100644 index 00000000..dd1a7b31 --- /dev/null +++ b/lib/tasks/liveness.rake @@ -0,0 +1,6 @@ +# frozen_string_literal: true + +desc('livenessProbe') +task liveness: :environment do + puts "success" +end From c5b00e89aab2622cb206733b632acfb4225dd3b7 Mon Sep 17 00:00:00 2001 From: Lars Kiesow Date: Tue, 23 Feb 2021 00:14:33 +0100 Subject: [PATCH 06/67] Update to Ruby 2.7 (#2292) * Update to Ruby 2.7 The currently used Ruby 2.5 is pretty old and is nearing its end of life [1]. This patch updates the used Ruby version to the current stable version. [1] https://www.ruby-lang.org/en/downloads/branches/ * Update .ruby-version to 2.7.2 Co-authored-by: Ahmad Farhat --- .ruby-version | 2 +- Dockerfile | 10 +++++----- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/.ruby-version b/.ruby-version index 73462a5a..37c2961c 100644 --- a/.ruby-version +++ b/.ruby-version @@ -1 +1 @@ -2.5.1 +2.7.2 diff --git a/Dockerfile b/Dockerfile index d2fbe32e..ad0a5e2e 100644 --- a/Dockerfile +++ b/Dockerfile @@ -1,4 +1,4 @@ -FROM ruby:2.5.1-alpine AS base +FROM ruby:2.7.2-alpine AS base # Set a variable for the install location. ARG RAILS_ROOT=/usr/src/app @@ -24,9 +24,9 @@ COPY Gemfile Gemfile.lock $RAILS_ROOT/ RUN bundle config --global frozen 1 \ && bundle install --deployment --without development:test:assets -j4 --path=vendor/bundle \ - && rm -rf vendor/bundle/ruby/2.5.0/cache/*.gem \ - && find vendor/bundle/ruby/2.5.0/gems/ -name "*.c" -delete \ - && find vendor/bundle/ruby/2.5.0/gems/ -name "*.o" -delete + && rm -rf vendor/bundle/ruby/2.7.0/cache/*.gem \ + && find vendor/bundle/ruby/2.7.0/gems/ -name "*.c" -delete \ + && find vendor/bundle/ruby/2.7.0/gems/ -name "*.o" -delete # Adding project files. COPY . . @@ -36,7 +36,7 @@ RUN rm -rf tmp/cache spec ############### Build step done ############### -FROM ruby:2.5.1-alpine +FROM ruby:2.7.2-alpine # Set a variable for the install location. ARG RAILS_ROOT=/usr/src/app From 09ab074aaf1c0d2b6a00921721692adb5ed8915b Mon Sep 17 00:00:00 2001 From: Ahmad Farhat Date: Fri, 26 Feb 2021 17:34:07 -0500 Subject: [PATCH 07/67] Complete refactor of Gemfile and upgraded gems (#2553) --- .rubocop.yml | 22 +- Gemfile | 163 +++----- Gemfile.lock | 353 +++++++++--------- .../account_activations_controller.rb | 2 +- app/controllers/admins_controller.rb | 2 +- app/controllers/application_controller.rb | 17 +- app/controllers/concerns/authenticator.rb | 2 +- app/controllers/concerns/rolify.rb | 5 +- app/controllers/health_check_controller.rb | 8 +- app/controllers/rooms_controller.rb | 10 +- app/controllers/sessions_controller.rb | 7 +- app/helpers/application_helper.rb | 9 +- app/helpers/users_helper.rb | 2 +- app/mailers/user_mailer.rb | 2 +- app/models/user.rb | 2 +- config/application.rb | 5 +- config/environments/production.rb | 2 +- config/puma.rb | 8 +- db/migrate/20190726153012_add_custom_roles.rb | 11 +- lib/bbb_api.rb | 2 +- lib/omniauth_options.rb | 12 +- lib/tasks/migrate_old_office365_users.rake | 2 +- lib/tasks/room.rake | 2 +- lib/tasks/user.rake | 8 +- spec/controllers/rooms_controller_spec.rb | 20 +- spec/controllers/users_controller_spec.rb | 6 +- spec/spec_helper.rb | 14 +- test/mailers/previews/user_mailer_preview.rb | 5 +- test/test_helper.rb | 0 29 files changed, 327 insertions(+), 376 deletions(-) delete mode 100644 test/test_helper.rb diff --git a/.rubocop.yml b/.rubocop.yml index 0e7a2d4f..9dcae9ac 100644 --- a/.rubocop.yml +++ b/.rubocop.yml @@ -5,9 +5,7 @@ AllCops: DisabledByDefault: false TargetRubyVersion: 2.5 -# Gems within groups in the Gemfile should be alphabetically sorted. -Bundler/OrderedGems: - Enabled: false + NewCops: enable Style/BlockDelimiters: Enabled: false @@ -138,7 +136,7 @@ Metrics/AbcSize: # A complexity metric that is strongly correlated to the number # of test cases needed to validate a method. Metrics/CyclomaticComplexity: - Max: 17 + Max: 20 # Checks for method parameter names that contain capital letters, end in numbers, or do not meet a minimal length. Naming/MethodParameterName: @@ -176,4 +174,18 @@ Style/HashTransformValues: Style/SlicingWithRange: Enabled: true - \ No newline at end of file + +Style/OptionalBooleanParameter: + Enabled: false + +Lint/DuplicateBranch: + Enabled: false + +Lint/ConstantDefinitionInBlock: + Enabled: false + +Lint/EmptyBlock: + Enabled: false + +Style/HashLikeCase: + Enabled: false \ No newline at end of file diff --git a/Gemfile b/Gemfile index 9f066b20..1039e975 100644 --- a/Gemfile +++ b/Gemfile @@ -8,139 +8,72 @@ git_source(:github) do |repo_name| end # Bundle edge Rails instead: gem 'rails', github: 'rails/rails' -gem 'rails', '~> 5.2.4.4' - -# Use Puma as the app server -gem 'puma', '~> 3.12' - -# Use SCSS for stylesheets -gem 'sassc-rails' - -# Use Uglifier as compressor for JavaScript assets -gem 'uglifier', '>= 1.3.0' - -# Use CoffeeScript for .coffee assets and views -gem 'coffee-rails', '~> 4.2' - -# See https://github.com/rails/execjs#readme for more supported runtimes -# gem 'mini_racer', platforms: :ruby - -# Use jquery as the JavaScript library -gem 'jquery-rails', '~> 4.4' -gem 'jquery-ui-rails' - -# Turbolinks makes navigating your web application faster. Read more: https://github.com/turbolinks/turbolinks -gem 'turbolinks', '~> 5' - -# Build JSON APIs with ease. Read more: https://github.com/rails/jbuilder -gem 'jbuilder', '~> 2.5' - -# Use Redis adapter to run Action Cable in production -# gem 'redis', '~> 3.0' - -# Use ActiveModel has_secure_password +gem 'aws-sdk-s3', '~> 1.88.1' gem 'bcrypt', '~> 3.1.7' - -# Reduces boot times through caching; required in config/boot.rb -gem 'bootsnap', '>= 1.1.0', require: false - -gem 'sprockets', '< 4.0.0' - -# Authentication. -gem 'omniauth' -gem 'omniauth-twitter' -gem 'omniauth-google-oauth2' -gem 'omniauth_openid_connect' -gem 'omniauth-bn-launcher', '~> 0.1.3' -gem 'net-ldap' -gem 'bn-ldap-authentication', '~> 0.1.4' -gem 'omniauth-bn-office365', '~> 0.1.1' - -# BigBlueButton API wrapper. gem 'bigbluebutton-api-ruby', git: 'https://github.com/mconf/bigbluebutton-api-ruby.git', branch: 'master' - -# Front-end. +gem 'bn-ldap-authentication', '~> 0.1.4' +gem 'bootsnap', '~> 1.7.2', require: false gem 'bootstrap', '~> 4.3.1' -gem 'tabler-rubygem', git: 'https://github.com/blindsidenetworks/tabler-rubygem.git', tag: '0.1.4.1' -gem 'pagy' +gem 'cancancan', '~> 2.3.0' +gem 'coveralls', '~> 0.8.23', require: false gem 'font-awesome-sass', '~> 5.9.0' - -# For detecting the users preferred language. -gem 'http_accept_language' - -# Use Capistrano for deployment -# gem 'capistrano-rails', group: :development - -# Markdown parsing. -gem 'redcarpet' - -# For limiting access based on user roles -gem 'cancancan', '~> 2.0' - -# Active Storage gems -gem 'aws-sdk-s3', '~> 1.75' -gem 'google-cloud-storage', '~> 1.26' - -gem 'pluck_to_hash', '~> 1.0.2' - +gem 'google-cloud-storage', '~> 1.30.0' +gem 'http_accept_language', '~> 2.1.1' +gem 'i18n-language-mapping', '~> 0.1.1' +gem 'jbuilder', '~> 2.11.2' +gem 'jquery-rails', '~> 4.4.0' +gem 'jquery-ui-rails', '~> 6.0.1' gem 'local_time', '~> 2.1.0' - -# Use a sqlite database in test and development. +gem 'net-ldap', '~> 0.17.0' +gem 'omniauth', '~> 1.9.1' +gem 'omniauth-bn-launcher', '~> 0.1.3' +gem 'omniauth-bn-office365', '~> 0.1.1' +gem 'omniauth-google-oauth2', '~> 0.7.0' +gem 'omniauth_openid_connect', '~> 0.3.5' +gem 'omniauth-twitter', '~> 1.4.0' +gem 'pagy', '~> 3.11.0' +gem 'pluck_to_hash', '~> 1.0.2' +gem 'puma', '~> 3.12.6' +gem 'rails', '~> 5.2.4.4' +gem 'random_password', '~> 0.1.1' +gem "recaptcha", '~> 5.7.0' +gem 'redcarpet', '~> 3.5.1' +gem 'remote_syslog_logger', '~> 1.0.4' +gem 'rubocop', '~> 1.10.0' +gem 'sassc-rails', '~> 2.1.2' +gem 'sprockets', '~> 3.7.2' gem 'sqlite3', '~> 1.3.6' +gem 'tabler-rubygem', git: 'https://github.com/blindsidenetworks/tabler-rubygem.git', tag: '0.1.4.1' +gem 'turbolinks', '~> 5.2.1' +gem 'tzinfo-data', '~> 1.2021.1' +gem 'uglifier', '~> 4.2.0' group :production do - # Use a postgres database in production. + gem 'hiredis', '~> 0.6.3' + gem "lograge", '~> 0.11.2' gem 'pg', '~> 0.18' - gem 'sequel' - - # For a better logging library in production - gem "lograge" - - # Use for the cache store in production - gem 'redis' - gem 'hiredis' + gem 'redis', '~> 4.2.5' + gem 'sequel', '~> 5.41.0' end -# Ruby linting. -gem 'rubocop' - group :development, :test do - # Call 'byebug' anywhere in the code to stop execution and get a debugger console - gem 'byebug', platform: :mri - # Environment configuration. - gem 'dotenv-rails' + gem 'byebug', '~> 11.1', platform: :mri + gem 'dotenv-rails', '~> 2.7' end group :test do - # Include Rspec and other testing utilities. + gem 'action-cable-testing', '~> 0.6' + gem "factory_bot_rails", '~> 6.1' + gem 'faker', '~> 2.16' + gem 'rails-controller-testing', '~> 1.0' gem 'rspec-rails', '~> 3.7' - gem 'action-cable-testing' - gem 'rails-controller-testing' gem 'shoulda-matchers', '~> 3.1' - gem 'faker' - gem "factory_bot_rails" - gem 'webmock' + gem 'webmock', '~> 3.11' end group :development do - # Access an IRB console on exception pages or by using <%= console %> anywhere in the code. - gem 'web-console', '>= 3.3.0' - gem 'listen', '~> 3.0.5' - # Spring speeds up development by keeping your application running in the background. Read more: https://github.com/rails/spring - gem 'spring' - gem 'spring-watcher-listen', '~> 2.0.0' + gem 'listen', '~> 3.0' + gem 'spring', '~> 2.1' + gem 'spring-watcher-listen', '~> 2.0' + gem 'web-console', '~> 3.7' end - -gem 'remote_syslog_logger' - -# Windows does not include zoneinfo files, so bundle the tzinfo-data gem -gem 'tzinfo-data' - -gem 'coveralls', require: false - -gem 'random_password' - -# Adds helpers for the Google reCAPTCHA API -gem "recaptcha" - -gem 'i18n-language-mapping', '~> 0.1.1' diff --git a/Gemfile.lock b/Gemfile.lock index d0c5d412..b81c24b5 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -25,43 +25,43 @@ GEM specs: action-cable-testing (0.6.1) actioncable (>= 5.0) - actioncable (5.2.4.4) - actionpack (= 5.2.4.4) + actioncable (5.2.4.5) + actionpack (= 5.2.4.5) nio4r (~> 2.0) websocket-driver (>= 0.6.1) - actionmailer (5.2.4.4) - actionpack (= 5.2.4.4) - actionview (= 5.2.4.4) - activejob (= 5.2.4.4) + actionmailer (5.2.4.5) + actionpack (= 5.2.4.5) + actionview (= 5.2.4.5) + activejob (= 5.2.4.5) mail (~> 2.5, >= 2.5.4) rails-dom-testing (~> 2.0) - actionpack (5.2.4.4) - actionview (= 5.2.4.4) - activesupport (= 5.2.4.4) + actionpack (5.2.4.5) + actionview (= 5.2.4.5) + activesupport (= 5.2.4.5) rack (~> 2.0, >= 2.0.8) rack-test (>= 0.6.3) rails-dom-testing (~> 2.0) rails-html-sanitizer (~> 1.0, >= 1.0.2) - actionview (5.2.4.4) - activesupport (= 5.2.4.4) + actionview (5.2.4.5) + activesupport (= 5.2.4.5) builder (~> 3.1) erubi (~> 1.4) rails-dom-testing (~> 2.0) rails-html-sanitizer (~> 1.0, >= 1.0.3) - activejob (5.2.4.4) - activesupport (= 5.2.4.4) + activejob (5.2.4.5) + activesupport (= 5.2.4.5) globalid (>= 0.3.6) - activemodel (5.2.4.4) - activesupport (= 5.2.4.4) - activerecord (5.2.4.4) - activemodel (= 5.2.4.4) - activesupport (= 5.2.4.4) + activemodel (5.2.4.5) + activesupport (= 5.2.4.5) + activerecord (5.2.4.5) + activemodel (= 5.2.4.5) + activesupport (= 5.2.4.5) arel (>= 9.0) - activestorage (5.2.4.4) - actionpack (= 5.2.4.4) - activerecord (= 5.2.4.4) + activestorage (5.2.4.5) + actionpack (= 5.2.4.5) + activerecord (= 5.2.4.5) marcel (~> 0.3.1) - activesupport (5.2.4.4) + activesupport (5.2.4.5) concurrent-ruby (~> 1.0, >= 1.0.2) i18n (>= 0.7, < 2) minitest (~> 5.1) @@ -70,32 +70,32 @@ GEM public_suffix (>= 2.0.2, < 5.0) aes_key_wrap (1.1.0) arel (9.0.0) - ast (2.4.0) + ast (2.4.2) attr_required (1.0.1) - autoprefixer-rails (9.7.6) + autoprefixer-rails (10.2.4.0) execjs aws-eventstream (1.1.0) - aws-partitions (1.343.0) - aws-sdk-core (3.104.1) + aws-partitions (1.429.0) + aws-sdk-core (3.112.0) aws-eventstream (~> 1, >= 1.0.2) aws-partitions (~> 1, >= 1.239.0) aws-sigv4 (~> 1.1) jmespath (~> 1.0) - aws-sdk-kms (1.36.0) - aws-sdk-core (~> 3, >= 3.99.0) + aws-sdk-kms (1.42.0) + aws-sdk-core (~> 3, >= 3.112.0) aws-sigv4 (~> 1.1) - aws-sdk-s3 (1.75.0) - aws-sdk-core (~> 3, >= 3.104.1) + aws-sdk-s3 (1.88.1) + aws-sdk-core (~> 3, >= 3.112.0) aws-sdk-kms (~> 1) aws-sigv4 (~> 1.1) - aws-sigv4 (1.2.1) + aws-sigv4 (1.2.2) aws-eventstream (~> 1, >= 1.0.2) - bcrypt (3.1.13) + bcrypt (3.1.16) bindata (2.4.8) bindex (0.8.1) bn-ldap-authentication (0.1.4) net-ldap (~> 0) - bootsnap (1.4.6) + bootsnap (1.7.2) msgpack (~> 1.0) bootstrap (4.3.1) autoprefixer-rails (>= 9.1.0) @@ -105,71 +105,74 @@ GEM byebug (11.1.3) cancancan (2.3.0) childprocess (4.0.0) - coffee-rails (4.2.2) - coffee-script (>= 2.2.0) - railties (>= 4.0.0) - coffee-script (2.4.1) - coffee-script-source - execjs - coffee-script-source (1.12.2) - concurrent-ruby (1.1.7) + concurrent-ruby (1.1.8) coveralls (0.8.23) json (>= 1.8, < 3) simplecov (~> 0.16.1) term-ansicolor (~> 1.3) thor (>= 0.19.4, < 2.0) tins (~> 1.6) - crack (0.4.3) - safe_yaml (~> 1.0.0) + crack (0.4.5) + rexml crass (1.0.6) declarative (0.0.20) declarative-option (0.1.0) - diff-lcs (1.3) - digest-crc (0.6.1) - rake (~> 13.0) - docile (1.3.2) - dotenv (2.7.5) - dotenv-rails (2.7.5) - dotenv (= 2.7.5) - railties (>= 3.2, < 6.1) - erubi (1.9.0) + diff-lcs (1.4.4) + digest-crc (0.6.3) + rake (>= 12.0.0, < 14.0.0) + docile (1.3.5) + dotenv (2.7.6) + dotenv-rails (2.7.6) + dotenv (= 2.7.6) + railties (>= 3.2) + erubi (1.10.0) execjs (2.7.0) - factory_bot (5.2.0) - activesupport (>= 4.2.0) - factory_bot_rails (5.2.0) - factory_bot (~> 5.2.0) - railties (>= 4.2.0) - faker (2.11.0) + factory_bot (6.1.0) + activesupport (>= 5.0.0) + factory_bot_rails (6.1.0) + factory_bot (~> 6.1.0) + railties (>= 5.0.0) + faker (2.16.0) i18n (>= 1.6, < 2) - faraday (1.0.1) + faraday (1.3.0) + faraday-net_http (~> 1.0) multipart-post (>= 1.2, < 3) - ffi (1.12.2) + ruby2_keywords + faraday-net_http (1.0.1) + ffi (1.14.2) font-awesome-sass (5.9.0) sassc (>= 1.11) globalid (0.4.2) activesupport (>= 4.2.0) - google-api-client (0.42.1) + google-apis-core (0.2.1) addressable (~> 2.5, >= 2.5.1) - googleauth (~> 0.9) + googleauth (~> 0.14) httpclient (>= 2.8.1, < 3.0) mini_mime (~> 1.0) representable (~> 3.0) retriable (>= 2.0, < 4.0) - signet (~> 0.12) + rexml + signet (~> 0.14) + webrick + google-apis-iamcredentials_v1 (0.1.0) + google-apis-core (~> 0.1) + google-apis-storage_v1 (0.2.0) + google-apis-core (~> 0.1) google-cloud-core (1.5.0) google-cloud-env (~> 1.0) google-cloud-errors (~> 1.0) - google-cloud-env (1.3.3) + google-cloud-env (1.4.0) faraday (>= 0.17.3, < 2.0) google-cloud-errors (1.0.1) - google-cloud-storage (1.26.2) + google-cloud-storage (1.30.0) addressable (~> 2.5) digest-crc (~> 0.4) - google-api-client (~> 0.33) + google-apis-iamcredentials_v1 (~> 0.1) + google-apis-storage_v1 (~> 0.1) google-cloud-core (~> 1.2) googleauth (~> 0.9) mini_mime (~> 1.0) - googleauth (0.13.0) + googleauth (0.15.1) faraday (>= 0.17.3, < 2.0) jwt (>= 1.4, < 3.0) memoist (~> 0.16) @@ -181,10 +184,10 @@ GEM hiredis (0.6.3) http_accept_language (2.1.1) httpclient (2.8.3) - i18n (1.8.5) + i18n (1.8.9) concurrent-ruby (~> 1.0) i18n-language-mapping (0.1.2) - jbuilder (2.10.0) + jbuilder (2.11.2) activesupport (>= 5.0.0) jmespath (1.4.0) jquery-rails (4.4.0) @@ -193,22 +196,22 @@ GEM thor (>= 0.14, < 2.0) jquery-ui-rails (6.0.1) railties (>= 3.2.16) - json (2.3.0) + json (2.5.1) json-jwt (1.13.0) activesupport (>= 4.2) aes_key_wrap bindata - jwt (2.2.1) - listen (3.0.8) - rb-fsevent (~> 0.9, >= 0.9.4) - rb-inotify (~> 0.9, >= 0.9.7) + jwt (2.2.2) + listen (3.4.1) + rb-fsevent (~> 0.10, >= 0.10.3) + rb-inotify (~> 0.9, >= 0.9.10) local_time (2.1.0) lograge (0.11.2) actionpack (>= 4) activesupport (>= 4) railties (>= 4) request_store (~> 1.0) - loofah (2.7.0) + loofah (2.9.0) crass (~> 1.0.2) nokogiri (>= 1.5.9) mail (2.7.1) @@ -220,17 +223,17 @@ GEM mimemagic (0.3.5) mini_mime (1.0.2) mini_portile2 (2.5.0) - minitest (5.14.2) - msgpack (1.3.3) - multi_json (1.14.1) + minitest (5.14.4) + msgpack (1.4.2) + multi_json (1.15.0) multi_xml (0.6.0) multipart-post (2.1.1) - net-ldap (0.16.2) - nio4r (2.5.4) + net-ldap (0.17.0) + nio4r (2.5.5) nokogiri (1.11.1) mini_portile2 (~> 2.5.0) racc (~> 1.4) - oauth (0.5.4) + oauth (0.5.5) oauth2 (1.4.4) faraday (>= 0.8, < 2.0) jwt (>= 1.0, < 3.0) @@ -250,9 +253,9 @@ GEM jwt (>= 2.0) omniauth (>= 1.1.1) omniauth-oauth2 (>= 1.5) - omniauth-oauth (1.1.0) + omniauth-oauth (1.2.0) oauth - omniauth (~> 1.0) + omniauth (>= 1.0, < 3) omniauth-oauth2 (1.5.0) oauth2 (~> 1.1) omniauth (~> 1.2) @@ -273,17 +276,17 @@ GEM validate_email validate_url webfinger (>= 1.0.1) - os (1.1.0) - pagy (3.8.1) - parallel (1.19.1) - parser (2.7.1.3) - ast (~> 2.4.0) + os (1.1.1) + pagy (3.11.0) + parallel (1.20.1) + parser (3.0.0.0) + ast (~> 2.4.1) pg (0.21.0) pluck_to_hash (1.0.2) activerecord (>= 4.0.2) activesupport (>= 4.0.2) popper_js (1.16.0) - public_suffix (4.0.5) + public_suffix (4.0.6) puma (3.12.6) racc (1.5.2) rack (2.2.3) @@ -295,44 +298,45 @@ GEM rack (>= 2.1.0) rack-test (1.1.0) rack (>= 1.0, < 3) - rails (5.2.4.4) - actioncable (= 5.2.4.4) - actionmailer (= 5.2.4.4) - actionpack (= 5.2.4.4) - actionview (= 5.2.4.4) - activejob (= 5.2.4.4) - activemodel (= 5.2.4.4) - activerecord (= 5.2.4.4) - activestorage (= 5.2.4.4) - activesupport (= 5.2.4.4) + rails (5.2.4.5) + actioncable (= 5.2.4.5) + actionmailer (= 5.2.4.5) + actionpack (= 5.2.4.5) + actionview (= 5.2.4.5) + activejob (= 5.2.4.5) + activemodel (= 5.2.4.5) + activerecord (= 5.2.4.5) + activestorage (= 5.2.4.5) + activesupport (= 5.2.4.5) bundler (>= 1.3.0) - railties (= 5.2.4.4) + railties (= 5.2.4.5) sprockets-rails (>= 2.0.0) - rails-controller-testing (1.0.4) - actionpack (>= 5.0.1.x) - actionview (>= 5.0.1.x) - activesupport (>= 5.0.1.x) + rails-controller-testing (1.0.5) + actionpack (>= 5.0.1.rc1) + actionview (>= 5.0.1.rc1) + activesupport (>= 5.0.1.rc1) rails-dom-testing (2.0.3) activesupport (>= 4.2.0) nokogiri (>= 1.6) rails-html-sanitizer (1.3.0) loofah (~> 2.3) - railties (5.2.4.4) - actionpack (= 5.2.4.4) - activesupport (= 5.2.4.4) + railties (5.2.4.5) + actionpack (= 5.2.4.5) + activesupport (= 5.2.4.5) method_source rake (>= 0.8.7) thor (>= 0.19.0, < 2.0) rainbow (3.0.0) - rake (13.0.1) + rake (13.0.3) random_password (0.1.1) rb-fsevent (0.10.4) rb-inotify (0.10.1) ffi (~> 1.0) - recaptcha (5.5.0) + recaptcha (5.7.0) json redcarpet (3.5.1) - redis (4.1.4) + redis (4.2.5) + regexp_parser (2.1.1) remote_syslog_logger (1.0.4) syslog_protocol representable (3.0.4) @@ -343,9 +347,9 @@ GEM rack (>= 1.4) retriable (3.1.2) rexml (3.2.4) - rspec-core (3.9.2) + rspec-core (3.9.3) rspec-support (~> 3.9.3) - rspec-expectations (3.9.2) + rspec-expectations (3.9.4) diff-lcs (>= 1.2.0, < 2.0) rspec-support (~> 3.9.0) rspec-mocks (3.9.1) @@ -359,21 +363,22 @@ GEM rspec-expectations (~> 3.9.0) rspec-mocks (~> 3.9.0) rspec-support (~> 3.9.0) - rspec-support (3.9.3) - rubocop (0.84.0) + rspec-support (3.9.4) + rubocop (1.10.0) parallel (~> 1.10) - parser (>= 2.7.0.1) + parser (>= 3.0.0.0) rainbow (>= 2.2.2, < 4.0) + regexp_parser (>= 1.8, < 3.0) rexml - rubocop-ast (>= 0.0.3) + rubocop-ast (>= 1.2.0, < 2.0) ruby-progressbar (~> 1.7) - unicode-display_width (>= 1.4.0, < 2.0) - rubocop-ast (0.0.3) - parser (>= 2.7.0.1) - ruby-progressbar (1.10.1) + unicode-display_width (>= 1.4.0, < 3.0) + rubocop-ast (1.4.1) + parser (>= 2.7.1.5) + ruby-progressbar (1.11.0) + ruby2_keywords (0.0.4) rubyzip (2.3.0) - safe_yaml (1.0.5) - sassc (2.3.0) + sassc (2.4.0) ffi (~> 1.9) sassc-rails (2.1.2) railties (>= 4.0.0) @@ -381,10 +386,10 @@ GEM sprockets (> 3.0) sprockets-rails tilt - sequel (5.32.0) + sequel (5.41.0) shoulda-matchers (3.1.3) activesupport (>= 4.0.0) - signet (0.14.0) + signet (0.14.1) addressable (~> 2.3) faraday (>= 0.17.3, < 2.0) jwt (>= 1.5, < 3.0) @@ -394,7 +399,7 @@ GEM json (>= 1.8, < 3) simplecov-html (~> 0.10.0) simplecov-html (0.10.2) - spring (2.1.0) + spring (2.1.1) spring-watcher-listen (2.0.1) listen (>= 2.7, < 4.0) spring (>= 1.2, < 3.0) @@ -414,22 +419,22 @@ GEM syslog_protocol (0.9.2) term-ansicolor (1.7.1) tins (~> 1.0) - thor (1.0.1) + thor (1.1.0) thread_safe (0.3.6) tilt (2.0.10) - tins (1.25.0) + tins (1.28.0) sync turbolinks (5.2.1) turbolinks-source (~> 5.2) turbolinks-source (5.2.0) - tzinfo (1.2.7) + tzinfo (1.2.9) thread_safe (~> 0.1) - tzinfo-data (1.2020.1) + tzinfo-data (1.2021.1) tzinfo (>= 1.0.0) uber (0.1.0) uglifier (4.2.0) execjs (>= 0.3.0, < 3) - unicode-display_width (1.7.0) + unicode-display_width (2.0.0) validate_email (0.1.6) activemodel (>= 3.0) mail (>= 2.2.5) @@ -444,74 +449,74 @@ GEM webfinger (1.1.0) activesupport httpclient (>= 2.4) - webmock (3.8.3) + webmock (3.11.2) addressable (>= 2.3.6) crack (>= 0.3.2) hashdiff (>= 0.4.0, < 2.0.0) + webrick (1.7.0) websocket-driver (0.7.3) websocket-extensions (>= 0.1.0) websocket-extensions (0.1.5) - xml-simple (1.1.5) + xml-simple (1.1.8) PLATFORMS ruby DEPENDENCIES - action-cable-testing - aws-sdk-s3 (~> 1.75) + action-cable-testing (~> 0.6) + aws-sdk-s3 (~> 1.88.1) bcrypt (~> 3.1.7) bigbluebutton-api-ruby! bn-ldap-authentication (~> 0.1.4) - bootsnap (>= 1.1.0) + bootsnap (~> 1.7.2) bootstrap (~> 4.3.1) - byebug - cancancan (~> 2.0) - coffee-rails (~> 4.2) - coveralls - dotenv-rails - factory_bot_rails - faker + byebug (~> 11.1) + cancancan (~> 2.3.0) + coveralls (~> 0.8.23) + dotenv-rails (~> 2.7) + factory_bot_rails (~> 6.1) + faker (~> 2.16) font-awesome-sass (~> 5.9.0) - google-cloud-storage (~> 1.26) - hiredis - http_accept_language + google-cloud-storage (~> 1.30.0) + hiredis (~> 0.6.3) + http_accept_language (~> 2.1.1) i18n-language-mapping (~> 0.1.1) - jbuilder (~> 2.5) - jquery-rails (~> 4.4) - jquery-ui-rails - listen (~> 3.0.5) + jbuilder (~> 2.11.2) + jquery-rails (~> 4.4.0) + jquery-ui-rails (~> 6.0.1) + listen (~> 3.0) local_time (~> 2.1.0) - lograge - net-ldap - omniauth + lograge (~> 0.11.2) + net-ldap (~> 0.17.0) + omniauth (~> 1.9.1) omniauth-bn-launcher (~> 0.1.3) omniauth-bn-office365 (~> 0.1.1) - omniauth-google-oauth2 - omniauth-twitter - omniauth_openid_connect - pagy + omniauth-google-oauth2 (~> 0.7.0) + omniauth-twitter (~> 1.4.0) + omniauth_openid_connect (~> 0.3.5) + pagy (~> 3.11.0) pg (~> 0.18) pluck_to_hash (~> 1.0.2) - puma (~> 3.12) + puma (~> 3.12.6) rails (~> 5.2.4.4) - rails-controller-testing - random_password - recaptcha - redcarpet - redis - remote_syslog_logger + rails-controller-testing (~> 1.0) + random_password (~> 0.1.1) + recaptcha (~> 5.7.0) + redcarpet (~> 3.5.1) + redis (~> 4.2.5) + remote_syslog_logger (~> 1.0.4) rspec-rails (~> 3.7) - rubocop - sassc-rails - sequel + rubocop (~> 1.10.0) + sassc-rails (~> 2.1.2) + sequel (~> 5.41.0) shoulda-matchers (~> 3.1) - spring - spring-watcher-listen (~> 2.0.0) - sprockets (< 4.0.0) + spring (~> 2.1) + spring-watcher-listen (~> 2.0) + sprockets (~> 3.7.2) sqlite3 (~> 1.3.6) tabler-rubygem! - turbolinks (~> 5) - tzinfo-data - uglifier (>= 1.3.0) - web-console (>= 3.3.0) - webmock + turbolinks (~> 5.2.1) + tzinfo-data (~> 1.2021.1) + uglifier (~> 4.2.0) + web-console (~> 3.7) + webmock (~> 3.11) diff --git a/app/controllers/account_activations_controller.rb b/app/controllers/account_activations_controller.rb index 0de5e776..7fa4f1dc 100644 --- a/app/controllers/account_activations_controller.rb +++ b/app/controllers/account_activations_controller.rb @@ -41,7 +41,7 @@ class AccountActivationsController < ApplicationController flash: { success: I18n.t("registration.approval.signup") } if @user.has_role?(:pending) # Redirect user to sign in path with success flash - redirect_to signin_path, flash: { success: I18n.t("verify.activated") + " " + I18n.t("verify.signin") } + redirect_to signin_path, flash: { success: "#{I18n.t('verify.activated')} #{I18n.t('verify.signin')}" } else redirect_to root_path, flash: { alert: I18n.t("verify.invalid") } end diff --git a/app/controllers/admins_controller.rb b/app/controllers/admins_controller.rb index f8412ccc..dc7bcc40 100644 --- a/app/controllers/admins_controller.rb +++ b/app/controllers/admins_controller.rb @@ -228,7 +228,7 @@ class AdminsController < ApplicationController flash_message = I18n.t("administrator.flash.settings") if params[:value] == "Default Recording Visibility" - flash_message += ". " + I18n.t("administrator.site_settings.recording_visibility.warning") + flash_message += ". #{I18n.t('administrator.site_settings.recording_visibility.warning')}" end redirect_to admin_site_settings_path(tab: tab), flash: { success: flash_message } diff --git a/app/controllers/application_controller.rb b/app/controllers/application_controller.rb index f3cb5248..d58f5d8d 100644 --- a/app/controllers/application_controller.rb +++ b/app/controllers/application_controller.rb @@ -29,13 +29,11 @@ class ApplicationController < ActionController::Base def current_user @current_user ||= User.includes(:role, :main_room).find_by(id: session[:user_id]) - if Rails.configuration.loadbalanced_configuration - if @current_user && !@current_user.has_role?(:super_admin) && - @current_user.provider != @user_domain + if Rails.configuration.loadbalanced_configuration && (@current_user && !@current_user.has_role?(:super_admin) && + @current_user.provider != @user_domain) @current_user = nil session.clear end - end @current_user end @@ -86,8 +84,8 @@ class ApplicationController < ActionController::Base end maintenance_string = @settings.get_value("Maintenance Banner").presence || Rails.configuration.maintenance_window - if maintenance_string.present? - flash.now[:maintenance] = maintenance_string unless cookies[:maintenance_window] == maintenance_string + if maintenance_string.present? && cookies[:maintenance_window] != maintenance_string + flash.now[:maintenance] = maintenance_string end end @@ -268,17 +266,18 @@ class ApplicationController < ActionController::Base rescue => e logger.error "Error in retrieve provider info: #{e}" @hide_signin = true - if e.message.eql? "No user with that id exists" + case e.message + when "No user with that id exists" set_default_settings render "errors/greenlight_error", locals: { message: I18n.t("errors.not_found.user_not_found.message"), help: I18n.t("errors.not_found.user_not_found.help") } - elsif e.message.eql? "Provider not included." + when "Provider not included." set_default_settings render "errors/greenlight_error", locals: { message: I18n.t("errors.not_found.user_missing.message"), help: I18n.t("errors.not_found.user_missing.help") } - elsif e.message.eql? "That user has no configured provider." + when "That user has no configured provider." if Setting.exists?(provider: @user_domain) # Keep the branding @settings = Setting.find_by(provider: @user_domain) diff --git a/app/controllers/concerns/authenticator.rb b/app/controllers/concerns/authenticator.rb index 577bf571..10b1eee6 100644 --- a/app/controllers/concerns/authenticator.rb +++ b/app/controllers/concerns/authenticator.rb @@ -113,7 +113,7 @@ module Authenticator old_user.rooms.each do |room| room.owner = user - room.name = "Old " + room.name if room.id == old_user.main_room.id + room.name = "Old #{room.name}" if room.id == old_user.main_room.id room.save! end diff --git a/app/controllers/concerns/rolify.rb b/app/controllers/concerns/rolify.rb index f580ed2f..a49092f8 100644 --- a/app/controllers/concerns/rolify.rb +++ b/app/controllers/concerns/rolify.rb @@ -123,9 +123,10 @@ module Rolify :can_manage_rooms_recordings, :can_appear_in_share_list, :colour) permission_params.transform_values! do |v| - if v == "0" + case v + when "0" "false" - elsif v == "1" + when "1" "true" else v diff --git a/app/controllers/health_check_controller.rb b/app/controllers/health_check_controller.rb index 0c2fbb2d..8ecc0414 100644 --- a/app/controllers/health_check_controller.rb +++ b/app/controllers/health_check_controller.rb @@ -47,9 +47,7 @@ class HealthCheckController < ApplicationController end def database_check - if defined?(ActiveRecord) - raise "Database not responding" unless ActiveRecord::Migrator.current_version - end + raise "Database not responding" if defined?(ActiveRecord) && !ActiveRecord::Migrator.current_version raise "Pending migrations" unless ActiveRecord::Migration.check_pending!.nil? end @@ -61,9 +59,7 @@ class HealthCheckController < ApplicationController settings = ActionMailer::Base.smtp_settings smtp = Net::SMTP.new(settings[:address], settings[:port]) - if settings[:enable_starttls_auto] == "true" - smtp.enable_starttls_auto if smtp.respond_to?(:enable_starttls_auto) - end + smtp.enable_starttls_auto if settings[:enable_starttls_auto] == ("true") && smtp.respond_to?(:enable_starttls_auto) if settings[:authentication].present? && settings[:authentication] != "none" smtp.start(settings[:domain]) do |s| diff --git a/app/controllers/rooms_controller.rb b/app/controllers/rooms_controller.rb index c63d989f..cc06e4a5 100644 --- a/app/controllers/rooms_controller.rb +++ b/app/controllers/rooms_controller.rb @@ -332,11 +332,11 @@ class RoomsController < ApplicationController def create_room_settings_string(options) room_settings = { - "muteOnStart": options[:mute_on_join] == "1", - "requireModeratorApproval": options[:require_moderator_approval] == "1", - "anyoneCanStart": options[:anyone_can_start] == "1", - "joinModerator": options[:all_join_moderator] == "1", - "recording": options[:recording] == "1", + muteOnStart: options[:mute_on_join] == "1", + requireModeratorApproval: options[:require_moderator_approval] == "1", + anyoneCanStart: options[:anyone_can_start] == "1", + joinModerator: options[:all_join_moderator] == "1", + recording: options[:recording] == "1", } room_settings.to_json diff --git a/app/controllers/sessions_controller.rb b/app/controllers/sessions_controller.rb index dcf014f2..4fc9d014 100644 --- a/app/controllers/sessions_controller.rb +++ b/app/controllers/sessions_controller.rb @@ -125,13 +125,14 @@ class SessionsController < ApplicationController def ldap ldap_config = {} ldap_config[:host] = ENV['LDAP_SERVER'] - ldap_config[:port] = ENV['LDAP_PORT'].to_i != 0 ? ENV['LDAP_PORT'].to_i : 389 + ldap_config[:port] = ENV['LDAP_PORT'].to_i.zero? ? 389 : ENV['LDAP_PORT'].to_i ldap_config[:bind_dn] = ENV['LDAP_BIND_DN'] ldap_config[:password] = ENV['LDAP_PASSWORD'] ldap_config[:auth_method] = ENV['LDAP_AUTH'] - ldap_config[:encryption] = if ENV['LDAP_METHOD'] == 'ssl' + ldap_config[:encryption] = case ENV['LDAP_METHOD'] + when 'ssl' 'simple_tls' - elsif ENV['LDAP_METHOD'] == 'tls' + when 'tls' 'start_tls' end ldap_config[:base] = ENV['LDAP_BASE'] diff --git a/app/helpers/application_helper.rb b/app/helpers/application_helper.rb index 5691cedf..f1d4c2a3 100644 --- a/app/helpers/application_helper.rb +++ b/app/helpers/application_helper.rb @@ -75,13 +75,14 @@ module ApplicationHelper end def translated_role_name(role) - if role.name == "denied" + case role.name + when "denied" I18n.t("roles.banned") - elsif role.name == "pending" + when "pending" I18n.t("roles.pending") - elsif role.name == "admin" + when "admin" I18n.t("roles.admin") - elsif role.name == "user" + when "user" I18n.t("roles.user") else role.name diff --git a/app/helpers/users_helper.rb b/app/helpers/users_helper.rb index 1d691d49..7cc01984 100644 --- a/app/helpers/users_helper.rb +++ b/app/helpers/users_helper.rb @@ -44,7 +44,7 @@ module UsersHelper # Returns language selection options for user edit def language_options locales = I18n.available_locales - language_opts = [['<<<< ' + t("language_default") + ' >>>>', "default"]] + language_opts = [["<<<< #{t('language_default')} >>>>", "default"]] locales.each do |locale| language_mapping = I18n::Language::Mapping.language_mapping_list[locale.to_s.gsub("_", "-")] language_opts.push([language_mapping["nativeName"], locale.to_s]) diff --git a/app/mailers/user_mailer.rb b/app/mailers/user_mailer.rb index f7ac797a..41d9a046 100644 --- a/app/mailers/user_mailer.rb +++ b/app/mailers/user_mailer.rb @@ -43,7 +43,7 @@ class UserMailer < ApplicationMailer def user_promoted(user, role, url, settings) @settings = settings @url = url - @admin_url = url + "admins" + @admin_url = "#{url}admins" @image = logo_image @color = user_color @role = translated_role_name(role) diff --git a/app/models/user.rb b/app/models/user.rb index 66f6fc31..679cbdd1 100644 --- a/app/models/user.rb +++ b/app/models/user.rb @@ -41,7 +41,7 @@ class User < ApplicationRecord validate :check_if_email_can_be_blank validates :email, length: { maximum: 256 }, allow_blank: true, uniqueness: { case_sensitive: false, scope: :provider }, - format: { with: /\A[\w+\-\'.]+@[a-z\d\-.]+\.[a-z]+\z/i } + format: { with: /\A[\w+\-'.]+@[a-z\d\-.]+\.[a-z]+\z/i } validates :password, length: { minimum: 6 }, confirmation: true, if: :greenlight_account?, on: :create diff --git a/config/application.rb b/config/application.rb index e47e7543..92943bf9 100644 --- a/config/application.rb +++ b/config/application.rb @@ -149,9 +149,10 @@ module Greenlight config.primary_color_darken_default = "#316cbe" # Default registration method if the user does not specify one - config.registration_method_default = if ENV["DEFAULT_REGISTRATION"] == "invite" + config.registration_method_default = case ENV["DEFAULT_REGISTRATION"] + when "invite" config.registration_methods[:invite] - elsif ENV["DEFAULT_REGISTRATION"] == "approval" + when "approval" config.registration_methods[:approval] else config.registration_methods[:open] diff --git a/config/environments/production.rb b/config/environments/production.rb index 07a3251b..f92ff48e 100644 --- a/config/environments/production.rb +++ b/config/environments/production.rb @@ -148,7 +148,7 @@ Rails.application.configure do config.log_tags = [:request_id] if ENV["RAILS_LOG_TO_STDOUT"] == "true" - logger = ActiveSupport::Logger.new(STDOUT) + logger = ActiveSupport::Logger.new($stdout) logger.formatter = config.log_formatter config.logger = ActiveSupport::TaggedLogging.new(logger) elsif ENV["RAILS_LOG_REMOTE_NAME"] && ENV["RAILS_LOG_REMOTE_PORT"] diff --git a/config/puma.rb b/config/puma.rb index 44bed0b5..8c27eac3 100644 --- a/config/puma.rb +++ b/config/puma.rb @@ -6,16 +6,16 @@ # the maximum value specified for Puma. Default is set to 5 threads for minimum # and maximum; this matches the default thread size of Active Record. # -threads_count = ENV.fetch("RAILS_MAX_THREADS") { 5 } +threads_count = ENV.fetch("RAILS_MAX_THREADS", 5) threads threads_count, threads_count # Specifies the `port` that Puma will listen on to receive requests; default is 3000. # -port ENV.fetch("PORT") { 80 } +port ENV.fetch("PORT", 80) # Specifies the `environment` that Puma will run in. # -environment ENV.fetch("RAILS_ENV") { "development" } +environment ENV.fetch("RAILS_ENV", "development") # Specifies the number of `workers` to boot in clustered mode. # Workers are forked webserver processes. If using threads and workers together @@ -23,7 +23,7 @@ environment ENV.fetch("RAILS_ENV") { "development" } # Workers do not work on JRuby or Windows (both of which do not support # processes). # -workers ENV.fetch("WEB_CONCURRENCY") { 1 } +workers ENV.fetch("WEB_CONCURRENCY", 1) # Use the `preload_app!` method when specifying a `workers` number. # This directive tells Puma to first boot the application and load code diff --git a/db/migrate/20190726153012_add_custom_roles.rb b/db/migrate/20190726153012_add_custom_roles.rb index 1c0b1fd6..2d82e3e5 100644 --- a/db/migrate/20190726153012_add_custom_roles.rb +++ b/db/migrate/20190726153012_add_custom_roles.rb @@ -12,15 +12,16 @@ class AddCustomRoles < ActiveRecord::Migration[5.2] # Determine what ids corresponded to what roles in the old table old_roles.each do |role| - if role["name"] == "super_admin" + case role["name"] + when "super_admin" super_admin_id = role["id"] - elsif role["name"] == "user" + when "user" user_id = role["id"] - elsif role["name"] == "admin" + when "admin" admin_id = role["id"] - elsif role["name"] == "denied" + when "denied" denied_id = role["id"] - elsif role["name"] == "pending" + when "pending" pending_id = role["id"] end end diff --git a/lib/bbb_api.rb b/lib/bbb_api.rb index dedfdd88..29938c5b 100644 --- a/lib/bbb_api.rb +++ b/lib/bbb_api.rb @@ -33,7 +33,7 @@ module BbbApi # Build the URI. uri = encode_bbb_url( - Rails.configuration.loadbalancer_endpoint + api + '/', + "#{Rails.configuration.loadbalancer_endpoint}#{api}/", Rails.configuration.loadbalancer_secret, { name: provider }, route diff --git a/lib/omniauth_options.rb b/lib/omniauth_options.rb index 43b80aa1..61996ecd 100644 --- a/lib/omniauth_options.rb +++ b/lib/omniauth_options.rb @@ -20,11 +20,11 @@ module OmniauthOptions module_function def omniauth_options(env) - if env['omniauth.strategy'].options[:name] == "bn_launcher" + case env['omniauth.strategy'].options[:name] + when "bn_launcher" protocol = Rails.env.production? ? "https" : env["rack.url_scheme"] - customer_redirect_url = protocol + "://" + env["SERVER_NAME"] + ":" + - env["SERVER_PORT"] + customer_redirect_url = "#{protocol}://#{env['SERVER_NAME']}:#{env['SERVER_PORT']}" user_domain = parse_user_domain(env["SERVER_NAME"]) env['omniauth.strategy'].options[:customer] = user_domain env['omniauth.strategy'].options[:customer_redirect_url] = customer_redirect_url @@ -33,11 +33,11 @@ module OmniauthOptions # This is only used in the old launcher and should eventually be removed env['omniauth.strategy'].options[:checksum] = generate_checksum(user_domain, customer_redirect_url, Rails.configuration.launcher_secret) - elsif env['omniauth.strategy'].options[:name] == "google" + when "google" set_hd(env, ENV['GOOGLE_OAUTH2_HD']) - elsif env['omniauth.strategy'].options[:name] == "office365" + when "office365" set_hd(env, ENV['OFFICE365_HD']) - elsif env['omniauth.strategy'].options[:name] == "openid_connect" + when "openid_connect" set_hd(env, ENV['OPENID_CONNECT_HD']) end end diff --git a/lib/tasks/migrate_old_office365_users.rake b/lib/tasks/migrate_old_office365_users.rake index aaf3cdbc..a0a6d60b 100644 --- a/lib/tasks/migrate_old_office365_users.rake +++ b/lib/tasks/migrate_old_office365_users.rake @@ -20,7 +20,7 @@ namespace :office365 do old_user.save! else old_main_room = old_user.main_room - old_main_room.name = "Old " + old_main_room.name + old_main_room.name = "Old #{old_main_room.name}" old_main_room.save! new_user.rooms << old_user.rooms diff --git a/lib/tasks/room.rake b/lib/tasks/room.rake index 7deec6a9..b5d900e9 100644 --- a/lib/tasks/room.rake +++ b/lib/tasks/room.rake @@ -39,7 +39,7 @@ namespace :room do next if room.uid.split("-").length > 3 begin - new_uid = room.uid + "-" + SecureRandom.alphanumeric(3).downcase + new_uid = "#{room.uid}-#{SecureRandom.alphanumeric(3).downcase}" puts "Updating #{room.uid} to #{new_uid}" room.update_attributes(uid: new_uid) rescue => e diff --git a/lib/tasks/user.rake b/lib/tasks/user.rake index 21b8ecea..b26e0427 100644 --- a/lib/tasks/user.rake +++ b/lib/tasks/user.rake @@ -35,7 +35,10 @@ namespace :user do u[:email].prepend "superadmin-" if args[:role] == "super_admin" # Create account if it doesn't exist - if !User.exists?(email: u[:email], provider: u[:provider]) + if User.exists?(email: u[:email], provider: u[:provider]) + puts "Account with that email already exists" + puts "Email: #{u[:email]}" + else user = User.create(name: u[:name], email: u[:email], password: u[:password], provider: u[:provider], email_verified: true, accepted_terms: true) @@ -52,9 +55,6 @@ namespace :user do puts "Password: #{u[:password]}" puts "Role: #{u[:role]}" puts "PLEASE CHANGE YOUR PASSWORD IMMEDIATELY" if u[:password] == Rails.configuration.admin_password_default - else - puts "Account with that email already exists" - puts "Email: #{u[:email]}" end end end diff --git a/spec/controllers/rooms_controller_spec.rb b/spec/controllers/rooms_controller_spec.rb index 675bd92d..f427a279 100644 --- a/spec/controllers/rooms_controller_spec.rb +++ b/spec/controllers/rooms_controller_spec.rb @@ -182,8 +182,8 @@ describe RoomsController, type: :controller do @request.session[:user_id] = @owner.id name = Faker::Games::Pokemon.name - room_params = { name: name, "mute_on_join": "1", - "require_moderator_approval": "1", "anyone_can_start": "1", "all_join_moderator": "1" } + room_params = { name: name, mute_on_join: "1", + require_moderator_approval: "1", anyone_can_start: "1", all_join_moderator: "1" } json_room_settings = "{\"muteOnStart\":true,\"requireModeratorApproval\":true," \ "\"anyoneCanStart\":true,\"joinModerator\":true,\"recording\":false}" @@ -199,8 +199,8 @@ describe RoomsController, type: :controller do it "should respond with JSON object of the room_settings" do @request.session[:user_id] = @owner.id - @owner.main_room.update_attribute(:room_settings, { "muteOnStart": true, "requireModeratorApproval": true, - "anyoneCanStart": true, "joinModerator": true }.to_json) + @owner.main_room.update_attribute(:room_settings, { muteOnStart: true, requireModeratorApproval: true, + anyoneCanStart: true, joinModerator: true }.to_json) json_room_settings = { "anyoneCanStart" => true, "joinModerator" => true, @@ -224,7 +224,7 @@ describe RoomsController, type: :controller do it "should redirect back to main room with error if it fails" do @request.session[:user_id] = @owner.id - room_params = { name: "", "mute_on_join": "1" } + room_params = { name: "", mute_on_join: "1" } post :create, params: { room: room_params } @@ -237,7 +237,7 @@ describe RoomsController, type: :controller do @request.session[:user_id] = @owner.id - room_params = { name: Faker::Games::Pokemon.name, "mute_on_join": "1" } + room_params = { name: Faker::Games::Pokemon.name, mute_on_join: "1" } post :create, params: { room: room_params } @@ -583,7 +583,7 @@ describe RoomsController, type: :controller do @request.session[:user_id] = @user.id name = Faker::Name.first_name - room_params = { room_uid: @secondary_room.uid, room: { "name": name } } + room_params = { room_uid: @secondary_room.uid, room: { name: name } } expect { post :update_settings, params: room_params }.to change { @secondary_room.reload.name } .from(@secondary_room.name).to(name) @@ -593,7 +593,7 @@ describe RoomsController, type: :controller do it "properly updates room settings through the room settings modal and redirects to current page" do @request.session[:user_id] = @user.id - room_params = { "mute_on_join": "1", "name": @secondary_room.name, "recording": "1" } + room_params = { mute_on_join: "1", name: @secondary_room.name, recording: "1" } formatted_room_params = "{\"muteOnStart\":true,\"requireModeratorApproval\":false," \ "\"anyoneCanStart\":false,\"joinModerator\":false,\"recording\":true}" # JSON string format @@ -616,7 +616,7 @@ describe RoomsController, type: :controller do @admin.set_role :admin @request.session[:user_id] = @admin.id - room_params = { "mute_on_join": "1", "name": @secondary_room.name } + room_params = { mute_on_join: "1", name: @secondary_room.name } formatted_room_params = "{\"muteOnStart\":true,\"requireModeratorApproval\":false," \ "\"anyoneCanStart\":false,\"joinModerator\":false,\"recording\":false}" # JSON string format @@ -632,7 +632,7 @@ describe RoomsController, type: :controller do @admin.set_role :admin @request.session[:user_id] = @admin.id - room_params = { "mute_on_join": "1", "name": @secondary_room.name } + room_params = { mute_on_join: "1", name: @secondary_room.name } expect { post :update_settings, params: { room_uid: @secondary_room.uid, room: room_params } } .not_to change { @secondary_room.reload.room_settings } diff --git a/spec/controllers/users_controller_spec.rb b/spec/controllers/users_controller_spec.rb index 9b37d5a9..feabd28c 100644 --- a/spec/controllers/users_controller_spec.rb +++ b/spec/controllers/users_controller_spec.rb @@ -416,7 +416,7 @@ describe UsersController, type: :controller do tmp_role1.update_permission("send_promoted_email", "true") params = random_valid_user_params - params = params.merge!(user_uid: user, user: { role_id: tmp_role1.id.to_s }) + params.merge!(user_uid: user, user: { role_id: tmp_role1.id.to_s }) expect { post :update, params: params }.to change { ActionMailer::Base.deliveries.count }.by(1) @@ -440,7 +440,7 @@ describe UsersController, type: :controller do @request.session[:user_id] = admin.id params = random_valid_user_params - params = params.merge!(user_uid: user, user: { role_id: new_role.id.to_s }) + params.merge!(user_uid: user, user: { role_id: new_role.id.to_s }) expect(user.role.name).to eq("test1") expect(user.main_room).to be_nil @@ -503,7 +503,7 @@ describe UsersController, type: :controller do user: { password: "incorrect_password", new_password: @password, - password_confirmation: @password + "_random_string", + password_confirmation: "#{@password}_random_string", } } post :update_password, params: params.merge!(user_uid: @user) diff --git a/spec/spec_helper.rb b/spec/spec_helper.rb index c8c43a17..efc0cfb4 100644 --- a/spec/spec_helper.rb +++ b/spec/spec_helper.rb @@ -54,27 +54,27 @@ RSpec.configure do |config| .with( headers: { - 'Accept': '*/*', + Accept: '*/*', 'Accept-Encoding': 'gzip;q=1.0,deflate;q=0.6,identity;q=0.3', 'User-Agent': 'Ruby', } ) .to_return(status: 200, body: "", headers: {}) - stub_request(:any, /#{ENV['LOADBALANCER_ENDPOINT'] + 'api'}/) + stub_request(:any, /#{"#{ENV['LOADBALANCER_ENDPOINT']}api"}/) .with( headers: { - 'Accept': '*/*', + Accept: '*/*', 'Accept-Encoding': 'gzip;q=1.0,deflate;q=0.6,identity;q=0.3', 'User-Agent': 'Ruby', } ) .to_return(status: 200, body: "", headers: {}) if ENV['LOADBALANCER_ENDPOINT'] - stub_request(:any, /#{ENV['LOADBALANCER_ENDPOINT'] + 'api\/getUser'}/) + stub_request(:any, /#{"#{ENV['LOADBALANCER_ENDPOINT']}api\\/getUser"}/) .with( headers: { - 'Accept': '*/*', + Accept: '*/*', 'Accept-Encoding': 'gzip;q=1.0,deflate;q=0.6,identity;q=0.3', 'User-Agent': 'Ruby', } @@ -90,11 +90,11 @@ RSpec.configure do |config| secret ", headers: {}) if ENV['LOADBALANCER_ENDPOINT'] - stub_request(:any, /#{ENV['LOADBALANCER_ENDPOINT'] + 'api2\/getUserGreenlightCredentials'}/) + stub_request(:any, /#{"#{ENV['LOADBALANCER_ENDPOINT']}api2\\/getUserGreenlightCredentials"}/) .with( headers: { - 'Accept': '*/*', + Accept: '*/*', 'Accept-Encoding': 'gzip;q=1.0,deflate;q=0.6,identity;q=0.3', 'User-Agent': 'Ruby', } diff --git a/test/mailers/previews/user_mailer_preview.rb b/test/mailers/previews/user_mailer_preview.rb index ae8d1d33..4cab5da0 100644 --- a/test/mailers/previews/user_mailer_preview.rb +++ b/test/mailers/previews/user_mailer_preview.rb @@ -2,6 +2,7 @@ class UserMailerPreview < ActionMailer::Preview def initialize(_params) + super @logo = "https://raw.githubusercontent.com/bigbluebutton/greenlight/master/app/assets/images/logo_with_text.png" @color = "#467fcf" end @@ -11,7 +12,7 @@ class UserMailerPreview < ActionMailer::Preview def password_reset user = User.first user.reset_token = User.new_token - url = "http://example.com" + "/password_resets/" + user.reset_token + "/edit?email=" + user.email + url = "http://example.com/password_resets/#{user.reset_token}/edit?email=#{user.email}" UserMailer.password_reset(user, url, @logo, @color) end @@ -19,7 +20,7 @@ class UserMailerPreview < ActionMailer::Preview # http://localhost:3000/rails/mailers/user_mailer/verify_email def verify_email user = User.first - url = "http://example.com" + "/u/verify/confirm/" + user.uid + url = "http://example.com/u/verify/confirm/#{user.uid}" UserMailer.verify_email(user, url, @logo, @color) end diff --git a/test/test_helper.rb b/test/test_helper.rb deleted file mode 100644 index e69de29b..00000000 From 3eaa61a46350f6a5a7725199ee3110b5f0dd6532 Mon Sep 17 00:00:00 2001 From: Mitsutaka Sato Date: Sun, 28 Feb 2021 07:21:38 +1300 Subject: [PATCH 08/67] Set timeout for valid_url (#2552) Co-authored-by: Ahmad Farhat --- app/helpers/application_helper.rb | 1 + 1 file changed, 1 insertion(+) diff --git a/app/helpers/application_helper.rb b/app/helpers/application_helper.rb index f1d4c2a3..2725e60d 100644 --- a/app/helpers/application_helper.rb +++ b/app/helpers/application_helper.rb @@ -110,6 +110,7 @@ module ApplicationHelper # Make a GET request and validate content type http = Net::HTTP.new(url.host, url.port) http.use_ssl = (url.scheme == "https") + http.read_timeout = 10 http.start do |web| response = web.head(url.request_uri) From c113b5e456624f37979fe2192afd594742d413c1 Mon Sep 17 00:00:00 2001 From: Lars Kiesow Date: Sun, 28 Feb 2021 18:43:57 +0100 Subject: [PATCH 09/67] More Resilient Parsing of Booleans (#1840) This patch makes parsing booleans from configuration settings more resilient to ensure no accidental errors occur e.g. due to the use of upper or lowercase letters. Example: Without this patch, the following configuration would disable Greenlight accounts which is quite unexpected behavior from a users perspective: ALLOW_GREENLIGHT_ACCOUNTS=True Co-authored-by: Ahmad Farhat --- config/application.rb | 17 +++++++++++------ 1 file changed, 11 insertions(+), 6 deletions(-) diff --git a/config/application.rb b/config/application.rb index 92943bf9..e683c15e 100644 --- a/config/application.rb +++ b/config/application.rb @@ -33,6 +33,11 @@ module Greenlight # Application configuration should go into files in config/initializers # -- all .rb files in that directory are automatically loaded. + def parse_bool(val, default = false) + val = ActiveModel::Type::Boolean.new.cast(val) + val.nil? ? default : val + end + # Use custom error routes. config.exceptions_app = routes @@ -87,16 +92,16 @@ module Greenlight config.smtp_sender = ENV['SMTP_SENDER'] || "notifications@example.com" # Determine if GreenLight should enable email verification - config.enable_email_verification = (ENV['ALLOW_MAIL_NOTIFICATIONS'] == "true") + config.enable_email_verification = parse_bool(ENV['ALLOW_MAIL_NOTIFICATIONS']) # Determine if GreenLight should allow non-omniauth signup/login. - config.allow_user_signup = (ENV['ALLOW_GREENLIGHT_ACCOUNTS'] == "true") + config.allow_user_signup = parse_bool(ENV['ALLOW_GREENLIGHT_ACCOUNTS']) # Configure custom banner message. config.banner_message = ENV['BANNER_MESSAGE'] # Enable/disable recording thumbnails. - config.recording_thumbnails = (ENV['RECORDING_THUMBNAILS'] != "false") + config.recording_thumbnails = parse_bool(ENV['RECORDING_THUMBNAILS'], true) # Configure which settings are available to user on room creation/edit after creation config.room_features = ENV['ROOM_FEATURES'] || "" @@ -111,7 +116,7 @@ module Greenlight config.recaptcha_enabled = ENV['RECAPTCHA_SITE_KEY'].present? && ENV['RECAPTCHA_SECRET_KEY'].present? # Show/hide "Add to Google Calendar" button in the room page - config.enable_google_calendar_button = (ENV['ENABLE_GOOGLE_CALENDAR_BUTTON'] == "true") + config.enable_google_calendar_button = parse_bool(ENV['ENABLE_GOOGLE_CALENDAR_BUTTON']) # Enum containing the different possible registration methods config.registration_methods = { open: "0", invite: "1", approval: "2" } @@ -119,11 +124,11 @@ module Greenlight config.google_analytics = ENV["GOOGLE_ANALYTICS_TRACKING_ID"].present? # Will always be true unless explicitly set to false - config.enable_cache = ENV["ENABLE_CACHED_PROVIDER"] != "false" + config.enable_cache = parse_bool(ENV["ENABLE_CACHED_PROVIDER"], true) # MAINTENANCE config.maintenance_window = ENV["MAINTENANCE_WINDOW"] - config.maintenance_mode = ENV["MAINTENANCE_MODE"] == "true" + config.maintenance_mode = parse_bool(ENV["MAINTENANCE_MODE"]) config.report_issue_url = ENV["REPORT_ISSUE_URL"] config.help_url = ENV["HELP_URL"].nil? ? "https://docs.bigbluebutton.org/greenlight/gl-overview.html" : ENV["HELP_URL"] From c754447598a2e1541f440156d15bb69ab28acfbf Mon Sep 17 00:00:00 2001 From: "transifex-integration[bot]" <43880903+transifex-integration[bot]@users.noreply.github.com> Date: Mon, 1 Mar 2021 18:43:20 -0500 Subject: [PATCH 10/67] Translate /config/locales/en.yml in ca (#2549) translation completed for the source file '/config/locales/en.yml' on the 'ca' language. Co-authored-by: transifex-integration[bot] <43880903+transifex-integration[bot]@users.noreply.github.com> --- config/locales/ca.yml | 590 +++++++++++++++++++++--------------------- 1 file changed, 300 insertions(+), 290 deletions(-) diff --git a/config/locales/ca.yml b/config/locales/ca.yml index 82c00445..3719ad4e 100644 --- a/config/locales/ca.yml +++ b/config/locales/ca.yml @@ -32,13 +32,13 @@ ca: administrator: site_settings: authentication: - disabled: Deshabilitada + disabled: Inhabilitada enabled: Habilitada info: Permetre només a usuaris autenticats unir-se a una sala title: Requerir autenticació per a utilitzar les sales - user-info: Cal registrar-se a la part superior pare a accedir a aquesta sala + user-info: Cal registrar-se a la part superior per a accedir a aquesta sala branding: - change: Canviar imatge + change: Canvia la imatge info: Canviar la imatge personalitzada que es mostra a la cantonada superior esquerra placeholder: Enllaç de la imatge... title: Imatge personalitzada @@ -57,102 +57,109 @@ ca: invalid: Enllaç no vàlid cache: info: "Neteja la memòria cau de proveïdors emmagatzemats, el que força una petició de la informació actualitzada" - title: Netejar memòria cau de proveïdor - button: Netejar memòria cau + title: Neteja memòria cau de proveïdor + button: Neteja memòria cau clear_auth: info: "Esborra l'autenticador actual pels usuaris, permetent-els tornar a iniciar sessió amb un mètode d'autenticació diferent" - title: Netejar l'autenticador actual - button: Netejar autenticació + title: Neteja l'autenticador actual + button: Neteja l'autenticació color: - info: Netejar el color regular cambiarà tant el color clar como el fosc. Els valors d'Aclarir i Enfosquir es poden canviar individualment + info: Netejar el color normal canviarà tant el color clar com el fosc. Els valors clar i fosc es poden canviar individualment title: Color principal - regular: Regular - lighten: Aclarir - darken: Enfosquir + regular: Normal + lighten: Clar + darken: Fosc + email_mapping: + info: "Indica com han d'acabar les adreces de correu que vulguis donar-lis un rol pre-existent, amb aquesta sintaxi: @elmeudomini.com=Nom de rol,@unaltredomini.org=Un altre rol" + title: Rols per defecte per a certes adreces de correu (o dominis de correu) d'usuaris que es registrin + update: log_level: title: Nivell de registre - information: Canviar el nivell de registre per a toda la implementació - debug: Depurar + information: Canvia el nivell de registre per a toda la implementació + debug: Depuració info: Informació warn: Advertència error: Error fatal: Fatal unknown: Desconegut recording_visibility: - info: Establir la visibilitat per defecte de les noves gravacions - title: Visibilitat per defecte de gravacions - warning: Aquesta configuració només serà aplicada a les noves sessiones + info: Estableix la visibilitat predeterminada dels nous enregistraments + title: Visibilitat per defecte dels enregistraments + warning: Aquesta configuració només s'aplicarà a les sales que no s'està executant require_consent: - info: "Aquesta configuració habilita una configuració de sala, que permet als propietaris de sales especificar quines sales poden ser gravades. Els usuaris que accedeixen a una sala amb gravació han de donar el seu consentiment abans d'unir-se." - title: Requerir el consentiment del propietari de la sala i la persona que accedeix per a realitzar la gravació + info: "Aquesta configuració habilita una configuració de sala, que permet als propietaris de sales especificar quines sales poden ser enregistrades. Els usuaris que accedeixen a una sala amb enregistrament han de donar el seu consentiment abans d'unir-s'hi." + title: Requereix el consentiment del propietari de la sala i la persona que accedeix per a realitzar l'enregistrament maintenance_banner: - info: Mostra un banner per a informar a l'usuari d'un manteniment programat - title: Banner de manteniment + info: Mostra un bàner per a informar a l'usuari d'un manteniment programat + title: Bàner de manteniment display: Estableix clear: Neteja - time: "Exemple: actualització programada pel 13 de desembre a las 23:00h. Els usuaris poden experimentar problemes per a iniciar sessió." + time: "Exemple: actualització programada pel 13 de desembre a les 23:00h. Els usuaris poden experimentar problemes per a iniciar sessió." preupload: info: Els usuaris poden carregar prèviament una presentació per a utilitzar-la com a presentació predeterminada per a aquesta sala específica - title: Permetre als usuaris carregar prèviament presentacions + title: Permet als usuaris carregar prèviament presentacions registration: - info: Canviar la forma de registre d'usuaris + info: Canvia la forma de registre d'usuaris title: Mètode de registre methods: - approval: Autoritzar/Denegar + approval: Autoritza o denega invite: Registre per invitació open: Registre obert rooms: info: Estableix el límit de sales que un usuari pot tenir (incloent la sala principal). Aquesta configuració no s'aplica als administradors. title: Número de sales per usuari shared_access: - info: "Si s'estableix en deshabilitat, s'eliminarà el botó del menú desplegable d'opcions de sala, el que evitarà que els usuaris comparteixin sales" - title: Permetre els usuaris compartir sales - subtitle: Personalitzar Greenlight + info: "Si s'estableix en inhabilitat, s'eliminarà el botó del menú desplegable d'opcions de sala, el que evitarà que els usuaris comparteixin sales" + title: Permet que els usuaris comparteixin sales + subtitle: Personalitza Greenlight tabs: appearance: Apariència administration: Administració + registration: Registrar-se settings: Configuració title: Configuració del lloc web flash: - approved: L'usuari ha estat autoritzat - banned: L'usuari ha estat bloquejat. - unbanned: L'usuari ha estat desbloquejat. - delete: L'usuari ha estat eliminat. - delete_fail: L'usuari no s'ha pogut eliminar. - demoted: L'usuari ha estat degradat. - invite: "Invitació enviada correctament a %{email}" - invite_email_verification: "L'enviament de correus electrònics ha d'estar habilitat per a poder fer ús d'aquest mètode de registre. Si us plau, contacta amb l'administrador del sistema." - merge_fail: S'ha produït un problema al fusionar els comptes d'usuari. Comprova els usuaris seleccionats i torna a provar-ho + approved: S'ha autoritzat l'usuari correctament. + banned: S'ha blocat l'usuari correctament. + unbanned: S'ha desblocat l'usuari correctament. + delete: S'ha eliminat l'usuari correctament. + delete_fail: No s'ha pogut eliminar l'usuari. + demoted: S'ha degradat l'usuari correctament. + invite: "La Invitació s'ha enviat correctament a %{email}" + invite_email_verification: L'enviament de correus electrònics ha d'estar habilitat per a poder fer ús d'aquest mètode de registre. Contacteu amb l'administrador del sistema. + merge_fail: S'ha produït un problema en fusionar els comptes d'usuari. Comproveu els usuaris seleccionats i torneu a provar-ho merge_success: Els comptes d'usuari s'han fusionat correctament - perm_deleted: L'usuari ha estat eliminat permanentement + perm_deleted: S'ha eliminat l'usuari permanentment promoted: L'usuari ha estat promogut. registration_method_updated: Mètode de registre actualitzat - reset_password: S'ha enviat a l'usuari un missatge de correu per a recuperar la contrasenya. (Demana-li revisar la carpeta de correu brossa si no l'ha rebut) - restored: L'usuari ha estat recuperat amb èxit + reset_password: S'ha enviat a l'usuari un missatge de correu per a recuperar la contrasenya. (Demaneu-li revisar la carpeta de correu brossa si no l'ha rebut) + restored: S'ha recuperat l'usuari amb èxit room_configuration: La configuració de la sala s'ha modificat correctament - settings: La configuració de sistema ha estat actualitzada - unauthorized: No està autoritzat per a executar operacions sobre aquest usuari. + settings: S'ha actualitzat la configuració de sistema correctament + unauthorized: No esteu autoritzat per a executar operacions sobre aquest usuari. recordings: - title: Gravacions - no_recordings: Aquest servidor no te gravacions. + latest: Darrers enregistraments + title: Servidor d'enregistraments + no_recordings: Aquest servidor no té cap enregistrament. + search_info: "Escriviu l'adreça de correu completa d'un usuari o el UID d'una sala (ex.: cao-k2t-xhf)" roles: - appear_in_share_list: Aquest servidor no te gravacions + appear_in_share_list: Inclou els usuaris amb aquest rol en el desplegable per a compartir sales can_create_rooms: Pot crear sales - delete: Eliminar rol - invalid_create: Ha hagut un error al crear el nou rol. Verifica els valors assignats i torna a intentar-ho - invalid_order: Ha hagut un error a l'actualitzar la prioritat del rol. Verifica els valors assignats i torna a intentar-ho - invalid_update: Ha hagut un error a l'actualitzar els permissos del rol. Verifica els valors assignats i torna a intentar-ho - manage_rooms_recordings: Permetre que els usuaris amb aquest rol administrin servidors de sala i gravacions + delete: Elimina el rol + invalid_create: S'ha produït un error en crear el nou rol. Verifiqueu els valors assignats i torneu a intentar-ho + invalid_order: S'ha produït un error en actualitzar la prioritat del rol. Verifiqueu els valors assignats i torneu a intentar-ho + invalid_update: S'ha produït un error en actualitzar els permisos del rol. Verifiqueu els valors assignats i torneu a intentar-ho + manage_rooms_recordings: Permet que els usuaris amb aquest rol administrin servidors de sala i enregistraments name: Nom del rol new_role: Crea un nou rol - role_has_users: "Aquest rol es troba assignado a %{user_count} comptes d'usuari. Cal esborrar tots els comptes associats a aquest rol abans d'eliminar-lo." + role_has_users: "Aquest rol es troba assignat a %{user_count} comptes d'usuari. Cal esborrar tots els comptes associats a aquest rol abans d'eliminar-lo." title: Rols - promote_email: Enviar un missatge als usuaris als que s'hagi assignat aquest rol - demote_email: Enviar un missatge als usuaris als que s'hagi eliminat aquest rol - edit_site_settings: Permetre als usuaris amb aquest rol editar configuracions - edit_roles: Permetre als usuaris amb aquest rol editar altres rols - manage_users: Permetre als usuaris amb aquest rol gestionar altres usuaris - invalid_assignment: Ha hagut un error a l'assignar el rol o els rols a l'usuari. Verifica els valors assignats i torna a provar + promote_email: Envia un missatge als usuaris a qui s'hagi assignat aquest rol + demote_email: Envia un missatge als usuaris a qui s'hagi eliminat aquest rol + edit_site_settings: Permet als usuaris amb aquest rol editar configuracions + edit_roles: Permet als usuaris amb aquest rol editar altres rols + manage_users: Permet als usuaris amb aquest rol gestionar altres usuaris + invalid_assignment: S'ha produït un error en assignar el rol o els rols a l'usuari. Verifiqueu els valors assignats i torneu a provar colour: title: Color del rol info: Defineix el color que s'associarà al rol @@ -165,11 +172,11 @@ ca: allow_any: info: "Permet a qualsevol usuari iniciar la reunió en qualsevol moment. De forma predeterminada, només el propietari de la sala pot iniciar la reunió." all_moderator: - info: Otorga a tots els usuaris els privilegis d'usuari moderador a BigBlueButton quan s'uneixen a la reunió. + info: Atorga a tots els usuaris els privilegis d'usuari moderador a BigBlueButton quan s'uneixen a la reunió. recordings: - info: "Permet als propietaris de sales especificar si desitgen l'opció de gravar una sala o no. Si está habilitada, el moderador encara ha de fer hacer clic al botó \"Grava\" una vegada hagi començat la reunió." + info: "Permet als propietaris de sales especificar si desitgen l'opció d'enregistrar una sala o no. Si està habilitada, el moderador encara ha de fer clic en el botó «Enregsitra» una vegada hagi començat la reunió." options: - disabled: Deshabilitada + disabled: Inhabilitada enabled: Sempre habilitada optional: Opcional rooms: @@ -183,67 +190,67 @@ ca: running: En funcionamient started: "Iniciada: %{session}" status: Estat - view: Mostrar + view: Mostra title: Configuració de l'organització users: - invite: Convidar usuari + invite: Convida un usuari edit: - title: Editar detalls d'usuari + title: Edita detalls de l'usuari settings: - approve: Autoritzar - decline: Denegar - ban: Bloquejar usuari - delete: Eliminar - edit: Editar - edit_roles: Editar els rols d'usuari - merge: Fusionar - perm_delete: Eliminar permanentment - unban: Desbloquejar usuari - undelete: Recuperar + approve: Autoritza + decline: Denega + ban: Bloca l'usuari + delete: Elimina + edit: Edita + edit_roles: Edita els rols d'usuari + merge: Fusiona + perm_delete: Elimina permanentment + unban: Desbloca l'usuari + undelete: Recupera table: authenticator: Verificador created: Creat time: Temps enviat name: Nom - not_found: No s'han trobat usuaris amb aquest criteri - no_users: No s'han trobat usuaris + not_found: No s'ha trobat cap usuari amb aquest criteri + no_users: No s'ha trobat cap usuari role: Rol uid: Identificador d'usuari username: Nom d'usuari - valid: Valid - title: Administrar usuaris - add_to_google_calendar: "Afegir al Calendari de Google" + valid: Vàlid + title: Administrar els usuaris + add_to_google_calendar: "Afegeix al Calendari de Google" bigbluebutton: BigBlueButton - bigbluebutton_exception: Os pedrer! Ha hagut un error a l'iniciar la sessió. - cancel: Cancel·lar + bigbluebutton_exception: Os pedrer! S'ha produït un error en iniciar la sessió. + cancel: Cancel·la cookies: - cookie_info: "Les cookies (galetes) ens ajuden a proveir els nostres serveis. En utilitzar els nostres serveis, aceptes la nostra utlització de les cookies." + cookie_info: "Les galetes ens ajuden a proveir els nostres serveis. En utilitzar els nostres serveis, accepteu l'ús que fem de les galetes." cookie_button: Accepto - copied: Copiada - copy: Copiar + copied: S'ha copiat + copy: Copia date: - month_names: [~, Gener, Febrer, Març, Abril, Maig, Juny, Juliol, Agost, Setembre, Octubre, Novembre, Decembre] - default_admin: "Estàs utilitzant la contrasenya per defecte per aquest compte d'usuari. Fes clic aquí per a canviar-la" - delete: Eliminar - delivery_error: "Ha hagut un error durant l'enviament de correu electrònic. Si us plau, contacta amb un administrador." + month_names: [~, Gener, Febrer, Març, Abril, Maig, Juny, Juliol, Agost, Setembre, Octubre, Novembre, Desembre] + default_admin: "Esteu utilitzant la contrasenya per defecte d'aquest compte d'usuari. Feu clic aquí per a canviar-la" + delete: Elimina + delivery_error: S'ha produït un error durant l'enviament de correu electrònic. Contacteu amb un administrador. docs: Documentació email: Compte de correu - email_sent: "El seu %{email_type} correu electrònic ha estat enviat. (Revisa la teva carpeta de correu brossa si no l'has rebut)" - enter_your_name: Introdueix el teu nom + email_sent: "S'ha enviat el vostre %{email_type} correu electrònic. (Reviseu la carpeta de correu brossa si no l'heu rebut)" + enter_your_name: Indiqueu el vostre nom! errors: bigbluebutton: - help: "Assegura't de que has seguit els passos correctament. Més informació" - message: La URL o clau secreta del servidor BigBlueButton no són vàlids + help: "Assegureu-vos que heu seguit els passos correctament. Més informació" + message: L'URL o clau secreta del servidor BigBlueButton no són vàlids title: Error del servidor internal: message: Sembla que alguna cosa ha fallat del nostre costat. - help: "L'error ha estat registrat, el revisarem en breu." - report: Reportar problema + help: "S'ha enregistrat l'error, el revisarem aviat." + report: Reporta un problema maintenance: message: El sistema es troba en manteniment. - help: Tornarem aviat. + help: Tornarem aviat! migration_error: - contact_admin: "Si no ets administrador, si us plau, contacta amb un d'ells." + contact_admin: "Si no sou administrador, contacteu amb un d'ells." continue: M'agradaria continuar utilitzant la versió 1.0 notice: > Greenlight ha trobat un error al migrar la base de dades.
Això pot estar provocat perquè no ha actualitzat Greenlight a la versió 2.0 @@ -254,236 +261,237 @@ ca: too_short: és massa curta invalid: es invàlida taken: ja existeix - accepted: ha de ser aceptat + accepted: ha de ser acceptat confirmation: "no coincideix %{attribute}" inclusion: no està inclòs a la lista no_provider: message: El lloc al que està intentant accedir no es troba actiu - help: "Si us plau, contacta amb l'administrador del sistema per a configurar Greenlight" + help: Contacteu amb l'administrador del sistema per a configurar Greenlight not_found: - message: "Ens sap greu, la pàgina que estàs buscant no existe." - help: "¿És possible que hagi estat eliminada?" + message: "Ens sap greu, la pàgina que esteu cercant no existeix." + help: "És possible que s'hagi eliminat?" user_not_found: - help: "Si us plau, contacta amb l'administrador." + help: Contacteu amb l'administrador. message: "Ens sap greu, aquest usuari no està registrat." user_missing: - help: "Si us plau, verifica l'enllaç i torna a provar." + help: Verifiqueu l'enllaç i torneu a provar. message: L'enllaç que introduït no és vàlid. title: Errors unauthorized: - message: No te accés a aquesta aplicació - help: "Si creus que és un error, si us plau, contacta amb l'administrador del sistema." + message: No té accés a aquesta aplicació + help: "Si penseu que és un error, contacteu amb l'administrador del sistema." expired_reset_token: L'enllaç per a recuperar la contrasenya ha caducat. features: title: Funcions rooms: Sales personalitzades - recordings: Administració de gravacions + recordings: Administració d'enregistraments designs: Diseny personalitzat authentication: Autenticació d'usuari footer: - legal: Termes legales + legal: Termes legals privpolicy: Política de privacitat powered_by: "Funciona amb %{href}" forgot_password: subtitle: He oblidat la contrasenya email: Compte de correu - submit: Enviar - go_back: Enrera + submit: Envia + go_back: Enrere greenlight: Greenlight header: - all_recordings: Totes les gravacions + all_recordings: Tots els enregistraments dropdown: account_settings: Organització - help: "Necessites ajuda?" + help: "Us cal ajuda?" home: Inici settings: Perfil d'usuari - signout: Sortir + signout: Surt home_room: Sala principal info_update_success: Informació actualitzada amb èxit. - invalid_credentials: El correu electrònic i contrasenya introduïts no coincideixen amb els registres. Inténtelo de nou o haga clic en recuperar contrasenya. - invalid_login_method: L'inici de sessió ha fallat per la falta de coincidència de compte. Necessites iniciar sessió amb un dels proveïdors. - invite_message: "Per a convidar a algú a la sessió, envia-li aquest enllaç:" + invalid_credentials: El correu electrònic i contrasenya introduïts no coincideixen amb els registres. Torneu a intentar o feu clic a «Recupera la contrasenya». + invalid_login_method: L'inici de sessió ha fallat per la falta de coincidència de compte. Cal que inicieu sessió amb un dels proveïdors. + invite_message: "Per a convidar a algú a la sessió, enveu-li aquest enllaç:" javascript: room: mailer: - subject: 'convidat a veure una gravació.' - body: 'Fes clic a enllaç per a veure la gravació:' - autogenerated: 'Aquest correu electrònic s ha generat automàticament per BigBlueButton' - footer: 'BigBlueButton és un sistema open source, basat en web, per a videoconferència. Per a més informació, visita https://bigbluebutton.org/.' + subject: 'us ha convidat a veure un enregistrament.' + body: 'Feu clic a enllaç per a veure l''enregistrament:' + autogenerated: 'Aquest correu electrònic s''ha generat automàticament per BigBlueButton' + footer: 'BigBlueButton és un sistema de codi obert, basat en web, per a videoconferència. Per a més informació, visiteu https://bigbluebutton.org/.' search: - start: Començar la cerca... + start: Comença la cerca... landing: - about: "%{href} és una interfície web per al teu servidor de conferències de codi obert BigBlueButton. Pots crear les teves pròpies sales per a ser anfitrió de sessions o unir-te a altres utilitzant un enllaç curt adequat." + about: "%{href} és una interfície web per al vostre servidor de conferències de codi obert BigBlueButton. Podeu crear les vostres pròpies sales per a ser amfitrió de sessions o unir-vos a altres utilitzant un enllaç curt adequat." welcome: Benvingut a Greenlight. - video: Mira el nostre tutorial sobre com utilizar Greenlight + video: Mireu el nostre tutorial sobre com utilitzar Greenlight upgrade: Mostra'm com actualitzar a la versió 2.0 - version: "Hem publicat una nova versió de Greenlight, però la teva base de dades no és compatible." - language_default: Per omissió (idioma del navegador) - ldap_error: No es pot connectar al servidor LDAP. Comprova la configuració de LDAP a l'arxiu "env" i assegurat de que el teu servidor s'està executant. - login: Iniciar sessió - login_title: Iniciar sessió al teu compte + version: "Hem publicat una nova versió de Greenlight, però la vostra base de dades no és compatible." + language_default: Per omissió (llengua del navegador) + ldap_error: No es pot connectar al servidor LDAP. Comproveu la configuració de LDAP en el fitxer «env» i assegureu-vos que el vostre servidor s'està executant. + login: Inicia sessió + login_title: Inicieu sessió al vostre compte mailer: user: approve: - info: El teu compte ha estat autoritzat. - signin: "Per accedir a les teves sales personals, fes clic al botó inferior i inicia sessió." - signin_link: Iniciar sessió + info: El vostre compte ha estat autoritzat. + signin: "Per a accedir a les vostres sales personals, feu clic al botó inferior i inicieu sessió." + signin_link: Inicia sessió signup: - info: S'ha registrat un nou usuari. - more-info: Per a permetre l'accés d'aquest usuari has d'aprovar el seu compte d'usuari a través de la configuració de l'organització. - admins_link: Anar a la pàgina de l'organització - subject: Registre d'usuari nou + info: S'ha enregistrat un nou usuari. + more-info: Per a permetre l'accés d'aquest usuari heu d'aprovar-ne el compte d'usuari a través de la configuració de l'organització. + admins_link: Vés a la pàgina de l'organització + subject: Registre d'usuari Greenlight nou username: "L'usuari s'ha registrat com a %{name} amb el correu electrònic %{email}." subject: Compte d'usuari autoritzat - username: "El teu nom d'usuari és %{email}." + username: "El vostre nom d'usuari és %{email}." demoted: - info: "Ja no ets %{role} a %{url}." - more-info: Des d'aquest moment tens els mateixos privilegis que un usuari regular. - root_link: Iniciar sessió + info: "Ja no sou %{role} a %{url}." + more-info: Des d'aquest moment teniu els mateixos privilegis que un usuari normal. + root_link: Inicia sessió subtitle: "Permís de %{role} eliminat" invite: - info: "Has estat convidat a tenir el teu espai personal amb %{name}" - signup_info: "Per a registrar-te utilizant el teu compte de correu, fes clic al botó inferior i segueix els passos indicats." - signup_link: Registrar-se + info: "Heu estat convidat a tenir el vostre espai personal amb %{name}" + signup_info: "Per a registrar-vos utilizant el vostre compte de correu, feu clic al botó inferior i seguiu els passos indicats." + signup_link: Registre signup: info: Un usuari que va ser convidat a registrar-se ha completat el seu registre. - admins_link: Anar a la pàgina de l'organització - subject: Registre d'usuari nou - username: "L'usuari s'ha registrado com a %{name} amb el correu electrònic %{email}. " + admins_link: Vés a la pàgina de l'organització + subject: Registre d'usuari Greenlight nou + username: "L'usuari s'ha registrat com a %{name} amb el correu electrònic %{email}. " subject: Invitació per a unir-se a BigBlueButton - username: "El teu nom d'usuari és %{email}." + username: "El vostre nom d'usuari és %{email}." password_reset: - title: 'La contrasenya ha estat reiniciada' - welcome: "S'ha sol·licitat un canvi de contrasenya pel correu electrònic %{email}" - message: 'Si vas fer una sol·licitud per a reiniciar la teva contrasenya, fes clic a aquest enllaç per a iniciar el procés.' - reset_link: Reiniciar la contrasenya + title: 'S''ha restablert la contrasenya' + welcome: "S'ha sol·licitat un canvi de contrasenya per al correu electrònic %{email}" + message: 'Si vau fer una sol·licitud per a restablir la contrasenya, feu clic en aquest enllaç per a iniciar el procés.' + reset_link: Restablir la contrasenya expire: Aquest enllaç caduca en dues hores - ignore: Pots ignorar aquest missatge sense problemes si no has estat tu qui va sol·licitar el canvi de contrasenya. + ignore: Podeu ignorar aquest missatge sense problemes si no sou qui heu sol·licitat el canvi de contrasenya. promoted: - admins_link: Anar a la pàgina de l'organització - info: "El teu rol ha canviat a %{role} a %{url}." - more-info: "Per a veure les noves funcions que se t'han activat visita %{url}" + admins_link: Vés a la pàgina de l'organització + info: "El vostre rol ha canviat a %{role} a %{url}." + more-info: "Per a veure les noves funcions que se us han activat visiteu %{url}" subtitle: "Permisos de %{role} assignats" verify_email: - welcome: "Benvingut al teu espa personal %{name}" - success: "Fent ús de %{bigbluebutton}, pots crear les teves pròpies sales per a realitzar reunions i col·laborar amb altres." - username: "El teu nom d'usuari és %{email}" - verify: "Per a verificar el compte, fes clic al botó inferior." - verify_text: 'Utiliza aquest enllaç per a verificar el teu compte: %{url}' - verify_link: Verificar el compte d'usuari - thanks: Gràcies per unir-te i que tinguis bon dia! - max_concurrent: S'ha arribat al número màxim de sessions permeses + welcome: "Benvingut al vostre espai personal %{name}" + success: "Fent ús de %{bigbluebutton}, podeu crear les vostres pròpies sales per a fer reunions i col·laborar amb altres usuaris." + username: "El vostre nom d'usuari és %{email}" + verify: "Per a verificar el compte, feu clic al botó inferior." + verify_text: 'Utilitzeu aquest enllaç per a verificar el vostre compte: %{url}' + verify_link: Verifica el compte d'usuari + thanks: Gràcies per unir-vos i que tingueu bon dia! + max_concurrent: S'ha arribat al nombre màxim de sessions permeses merged: Fusionat modal: create_role: - create: Crear un nou rol - footer_text: Pots modificar els permisos per a aquest rol de manera individual una vez que haya estat creado - name_placeholder: Introdueix el nom del rol + create: Crea un nou rol + footer_text: Podeu modificar els permisos per a aquest rol de manera individual una vegada que l'hàgiu creat + name_placeholder: Introduïu el nom del rol not_blank: El nom de rol no pot estar buit - title: Crear un nou rol + title: Crea un nou rol create_room: access_code: Codi d'accés - access_code_placeholder: Generar un nou codi d'accés + access_code_placeholder: Genera un nou codi d'accés auto_join: Envia'm a la sala automàticament quan comenci la sessió - create: Crea sala - free_delete: Podràs eliminar la sala en el moment que vulguis - name_placeholder: Introdueix un nom per a la sala + create: Crea una sala + free_delete: Podreu eliminar la sala en el moment que vulgueu + name_placeholder: Introduïu un nom per a la sala not_blank: El nom de la sala no pot estar buit - title: Crear una sala nova + title: Crea una sala nova delete_account: - confirm: "Estàs segur d'eliminar aquest compte d'usuari?" + confirm: "Esteu segur de voler eliminar aquest compte d'usuari?" delete: Estic segur d'eliminar aquest compte keep: "De fet, la mantindré" - delete_warning: Aquesta acció desactiva el compte d'usuari. Tos els usuaris desactivats es mostren a la pestanya d'eliminats. - warning: "Aquesta decisió és irrevesible, No podràs recuperar la informació associada" + delete_warning: Aquesta acció desactiva el compte d'usuari. Tots els usuaris desactivats es mostren a la pestanya d'eliminats. + warning: "Aquesta decisió és irreversible, No podreu recuperar la informació associada" delete_rec: - delete: "Estic segur, elimina aquesta gravació." - header: "Estàs segur de voler eliminar aquesta gravació?" - warning: No podràs recuperar aquesta gravació + delete: "N'estic segur, elimina aquest enregistrament." + header: "Esteu segur de voler eliminar aquest enregistrament?" + warning: No podreu recuperar aquest enregistrament delete_room: - confirm: "Estàs segur de voler eliminar %{room}?" + confirm: "Esteu segur de voler eliminar %{room}?" delete: "Estc segur, elimina aquesta sala" keep: "He canviat de parer, la mantindré" - warning: No podràs recuperar aquesta sala - recording_warning: "o qualsevol de les teves %{recordings_num} gravacions associades." + warning: No podreu recuperar aquesta sala + recording_warning: "o qualsevol dels vostres %{recordings_num} enregistraments associats." invite_user: - email_placeholder: Introdueix els correus electrònics d'usuari (separats per coma) + email_placeholder: Introduïu els correus electrònics d'usuari (separats per coma) footer: L'usuari rebrà un correu electrònic amb instruccions de com registrar-se - send: Enviar invitació - title: Convidar usuari + send: Envia la invitació + title: Convida l'usuari login: or: o - with: "Iniciar sessió amb %{provider}" - forgot_password: "Has oblidat la teva contrasenya?" + with: "Inicia sessió amb %{provider}" + forgot_password: "Heu oblidat la contrasenya?" preupload: change: Substitueix la presentació - choose: Selecciona un arxiu + choose: Trieu un fitxer... current: "Presentació actual:" footer: "En funció de la mida de la presentació, és possible que es necessiti més temps per a carregar-la abans de poder utilitzar-la." - invalid: "Mida o tipus d'arxiu no vàlids. Si us plau, consulta les restriccions a continuación." - title: Afegir presentació - use: Utilitzar presentació + invalid: Mida o tipus de fitxer no vàlids. Consulteu les restriccions a continuació. + title: Afegir una presentació + use: Utilitza una presentació rename_recording: remove_shared: - title: "Estàs segur de voler eliminar aquesta sala de la teva llista de sales?" + title: "Esteu segur de voler eliminar aquesta sala de la llista de sales?" delete: "Estic segur, elimina aquesta sala." - warning: NO podràs accedir a aquesta sala en el futur. + warning: NO podreu accedir a aquesta sala en el futur. room_settings: title: Configuració de la sala - update: Actualitzar la sala - client: Seleccionar el tipus de client + update: Actualitza la sala + client: Seleccioneu el tipus de client join_moderator: Tots els usuaris s'uneixen com a moderadors - mute: Deshabilitar micròfon d'usuaris al entrar - require_approval: Requerir aprovació del moderador abans de unir-se a la sessió - start: Permetre als usuaris iniciar aquesta sessió - footer_text: Pots fer canvis a la teva sala en qualsevol moment - recording: Permetre a aquesta sala ser gravada + mute: Desactiva micròfon d'usuaris a l'entrar + require_approval: Requereix l'aprovació del moderador abans d'unir-se a la sessió + start: Permet als usuaris iniciar aquesta sessió + footer_text: Podeu fer canvis a la sala en qualsevol moment + recording: Permet l'enregistrament d'aquesta sala rename_room: - name_placeholder: Introdueix un nou nom per a la sala... + name_placeholder: Introduïu un nou nom per a la sala... share_access: - footer: Compartir una sala amb un usuari permet que iniciï la sala i veure les gravacions de la sala. + footer: Compartir una sala amb un usuari permet que iniciï la sala i veure els enregistraments de la sala. list: Compartit amb - title: Compartir accés a la sala - save: Guardar canvis - cancel_changes: Cancel·lar canvis - select: Seleccionar usuari + title: Comparteix l'accés a la sala + save: Desa els canvis + cancel_changes: Cancel·la els canvis + select: Seleccioneu un usuari merge_user: - cancel: Cancel·lar - from: Compte per a ser fusionada - title: Fusionar comptes d'usuari + cancel: Cancel·la + from: Compte per a ser fusionat + title: Fusiona els comptes d'usuari to: Compte principal - save: Fusionar + save: Fusiona footer: Les sales del compte que es fusionarà es transferiran a la llista de sales del compte principal i posteriorment s'eliminarà el compte. - name_update_success: El nom de la sala ha estat actualitzat correctament - no_user_email_exists: "No hi ha cap usuari existent amb el correu electrònic especificat. Si us plau, assegura't de que l'has escrit correctament." - omniauth_error: "Ha hagut un error a l'intentar autenticar utilitzant OmniAuth. Si us plau, torna a intentar-ho o contacta amb un administrador!" - omniauth_specific_error: "Error %{error} a l'intentar autenticar utilitzant OmniAuth. Si us plau, torna a intentar-ho o contacta amb un administrador!" + name_update_success: El nom de la sala s'ha actualitzat correctament + no_user_email_exists: No hi ha cap usuari existent amb el correu electrònic especificat. Assegureu-vos que l'heu escrit correctament. + omniauth_error: S'ha produït un error en intentar autenticar utilitzant OmniAuth. Torneu a intentar-ho o contacteu amb un administrador! + omniauth_specific_error: "Error %{error} en intentar autenticar utilitzant OmniAuth. Torneu a intentar-ho o contacteu amb un administrador!" pagy: nav: - prev: "‹ Anterior" - next: "Següent ›" + prev: "‹ Enrere" + next: "Endavant ›" gap: "…" password: Contrasenya password_empty_notice: La contrasenya no pot estar buida - password_reset_success: La contrasenya ha estat canviada - password_different_notice: La contrasenyes introduïdes no coincideix + password_reset_success: S'ha canviat la contrasenya. + password_different_notice: Les contrasenyes introduïdes no coincideixen provider: google: Google office365: Office 365 twitter: Twitter ldap: LDAP + openid_connect: OpenID Connect recaptcha: errors: - recaptcha_unreachable: Os pedrer! La resposta del teu reCAPTCHA ha fallat. Torna a intentar-ho. - verification_failed: "La verificació reCAPTCHA ha fallat, torna a intentar-ho." + recaptcha_unreachable: Os pedrer! La resposta del reCAPTCHA ha fallat. Torneu a intentar-ho. + verification_failed: "La verificació reCAPTCHA ha fallat, torneu a intentar-ho." recording: - all_recordings: Totes les gravacions - email: Enviar correu electrònic amb la gravació - error: "Ha hagut un error al recuperar %{count} gravació(ns)." - no_recordings: "Aquesta sala no te gravacions %{inject}" - no_user_recordings: No tens gravacions - no_matched_recordings: "No hi ha %{inject} gravacions que coincideixin amb la teva cerca." - recorded_on: "Gravada el %{date}" + all_recordings: Tots els enregistraments + email: Envia un correu electrònic amb l'enregistrament + error: "S'ha produït un error en recuperar %{count} enregsitrament(s)." + no_recordings: "Aquesta sala no té cap registrament %{inject}." + no_user_recordings: No teniu cap enregisrament + no_matched_recordings: "No hi ha %{inject} enregistraments que coincideixin amb la cerca." + recorded_on: "Enregsitrada el %{date}" table: name: Nom thumbnails: Miniatures d'imatge @@ -502,27 +510,28 @@ ca: video: Vídeo registration: approval: - fail: "El teu compte d'usuari encara no ha estat autorizat. Si han passat varis dies des del teu registre, et recomanem contactar amb l'administrador." - signup: El teu compte d'usuari ha estat creat i se li ha enviat una notificació a l'administrador per a la seva autorització. + fail: "El vostre compte d'usuari encara no ha estat autoritzat. Si han passat alguns dies des del vostre registre, us recomanem contactar amb l'administrador." + signup: El vostre compte d'usuari ha estat creat i se li ha enviat una notificació a l'administrador per a la seva autorització. banned: - fail: "No tens accés a aquesta aplicació. Si creus que es tracta d'un error, contacta l'administrador del sistema." + fail: "No teniu accés a aquesta aplicació. Si penseu que es tracta d'un error, contacteu amb l'administrador del sistema." deprecated: - new_signin: Selecciona un nou mètode de autenticació. Todes les sales vinculades al teu compte anterior seran migrades al nou compte - twitter_signin: "L'accés a través de Twitter és obsolet i serà eliminat a la següent versió. Fes clic aquí per a moure el teu compte d'usuari i el seu contingut a un compte vinculat a un altre mètode d'autenticació" - twitter_signup: "El registre de nous comptes amb Twitter és obsolet. Si us plau, utiliza un mètode d'autenticació diferent per a registrar-te." - merge_success: El teu compte vinculat a Twitter s'ha fusionat correctament amb el teu nou compte. El compte vinculat amb Twitter ha estat eliminat. + new_signin: Seleccioneu un nou mètode d'autenticació. Totes les sales vinculades al vostre compte anterior es migraran al compte nou + twitter_signin: "L'accés a través de Twitter és obsolet i serà eliminat a la següent versió. Feu clic aquí per a moure el vostre compte d'usuari i el seu contingut a un compte vinculat a un altre mètode d'autenticació" + twitter_signup: El registre de nous comptes amb Twitter és obsolet. Utilitzeu un mètode d'autenticació diferent per a registrar-vos + merge_success: El vostre compte vinculat a Twitter s'ha fusionat correctament amb el compte nou. El compte vinculat amb Twitter ha estat eliminat. invite: - fail: "El teu codi ha caducat o no és vàlid. Si creus que es tracta d'un error, contacta amb l'administrador del sistema." - no_invite: No tens una invitació per a ingresar. Contacta amb l'administrador del sistema per a obtenir-ne una. - remove: Eliminar - rename: Canviar nom + fail: "El codi ha caducat o no és vàlid. Si penseu que es tracta d'un error, contacteu amb l'administrador del sistema." + no_invite: No teniu una invitació per a ingressar. Contacteu amb l'administrador del sistema per a obtenir-ne una. + remove: Elimina + rename: Canvia el nom reset_password: - invalid_token: El token de restabliment de contrasenya no és vàlid. Intenta restablir la teva contrasenya de nou. - subtitle: Reiniciar contrasenya - password: Nova contrasenya - confirm: Confirmació de nova contrasenya - update: Actualitzar contrasenya - auth_change: "El mètode d'autenticación ha canviat. Si us plau, consulta el teu correu electrònic per a configurar la teva contrasenya." + captcha: "La verificació reCAPTCHA ha fallat, torneu a intentar-ho." + invalid_token: El token de restabliment de contrasenya no és vàlid. Intenteu restablir la contrasenya de nou. + subtitle: Restableix la contrasenya + password: Contrasenya nova + confirm: Confirmació de la contrasenya nova + update: Actualitza la contrasenya + auth_change: El mètode d'autenticació ha canviat. Consulteu el correu electrònic per a configurar la contrasenya. roles: active: Actiu admin: Administrador @@ -531,102 +540,103 @@ ca: pending: Pendent user: Usuari room: - access_code_required: Introdueix un codi d'accés vàlid per a unir-te a la sala - add_presentation: Afegir presentació + access_code_required: Introduïu un codi d'accés vàlid per a unir-vos a la sala + add_presentation: Afegeix una presentació copy_access: Copia el codi d'accés - create_room: Crear una sala - create_room_error: Ha hagut un error al crear la sala + create_room: Crea una sala + create_room_error: S'ha produït un error en crear la sala create_room_success: La sala s'ha creat correctament delete: home_room: No és possible eliminar la sala principal - success: Sala eliminada correctament - fail: "S'ha produït un error a l'eliminar la sala (%{error})" - enter_the_access_code: Introdueix el codi d'accés de la sala - invalid_provider: L'enllaç introduït no és vàlid. Comprova'l i torna a intentar-ho. - invitation_description: "Ha estat convidat a unir-te a %{name} utilitzant BigBlueButton. Per a unir-te, fes clic a l'enllaç superior i introdueix el teu nom." - invited: Ha estat convidat a unir-te - recording_present: Reconec que aquesta sessió es gravarà. Això pot incloure la meva veu i el meu vídeo si està activat. - invite_participants: Convidar participants - join: Entrar + success: S'ha eliminat la sala correctament + fail: "S'ha produït un error en eliminar la sala (%{error})" + enter_the_access_code: Introduïu el codi d'accés de la sala + invalid_provider: L'enllaç introduït no és vàlid. Comproveu-lo i torneu a intentar-ho. + invitation_description: "Heu estat convidat a unir-vos a %{name} utilitzant BigBlueButton. Per a unir-vos-hi, feu clic a l'enllaç superior i introduïu el vostre nom." + invited: Heu estat convidat a unir-vos + recording_present: Reconec que aquesta sessió s'enregistrarà. Això pot incloure la meva veu i el meu vídeo si està activat. + invite_participants: Convida participants + join: Entra last_session: "Última sessió a %{session}" - login: Entrar + login: Entra owner: Propietari owner_banned: Aquesta sala no és accessible actualment no_room: - description: Introdueix l'enllaç o ID de la sala a la que vols unir-te. + description: Introduïu l'enllaç o ID de la sala a la qual voleu unir-vos. edit_profile: Edita el perfil d'usuari - go_to: Anar a sala - invalid_room_uid: L'enllaç o UID que has introduït no és vàlid. + go_to: Vés a la sala + invalid_room_uid: L'enllaç o UID que heu introduït no és vàlid. placeholder: Enllaç/uid de la sala - no_recent_rooms: No has utilitzat cap sala recientement - recent_rooms: Ves a Sales utilizadas recentement - title: Uneix-te a una Sala - no_sessions: Aquesta sala encara no te sessions - preupload_success: Presentació afegida correctament - preupload_error: Ha hagut un error actualitzant la presentació de la sala + no_recent_rooms: No heu utilitzat cap sala recientement + recent_rooms: Vés a les sales utilitzades recentment + title: Uneix-te a una sala + no_sessions: Aquesta sala encara no té cap sessió + preupload_success: La presentació s'ha afegit correctament + preupload_error: S'ha produït un error en actualitzar la presentació de la sala preupload_remove_success: Eliminació de presentació correcta - preupload_remove_error: Ha hagut un error eliminant la presentació de la sala - recordings: Gravacions de sala - room_limit: Has arribat al número límit de sales permeses - room_limit_exceeded: "Has arribat al número límit de sales permeses. Si us plau, elimina %{difference} sala(es) per poder accedir a aquesta." + preupload_remove_error: S'ha produït un error en eliminar la presentació de la sala + recordings: Enregistraments de sala + room_limit: Heu arribat al nombre límit de sales permeses + room_limit_exceeded: "Heu superat el nombre de sales permeses. Elimineu %{difference} sales per a poder accedir a aquesta." sessions: Sessions settings: Configuració de sala - share: Gestionar accés + share: Gestiona l'accés shared_by: "Compartit per %{email}" - remove_shared_access_success: S'ha eliminat correctament la sala compartida de la teva llista de sales - remove_shared_access_error: Ha hagut un error eliminant la sala compartida de la teva llista de sales + remove_shared_access_success: S'ha eliminat correctament la sala compartida de la llista de sales + remove_shared_access_error: S'ha produït un error en eliminar la sala compartida de la llista de sales shared_access_success: Sala compartida correctament - shared_access_error: Ha hagut un error compartint la sala + shared_access_error: S'ha produït un error en compartir la sala start: Inicia - unavailable: Aquesta sala no es troba disponible perquè el compte de correu del seu propietari no ha estat verificat. - update_settings_error: Ha hagut un error a l'actualitzar la configuració de la sala + search: Cerca sala... + unavailable: Aquesta sala no es troba disponible perquè el compte de correu del seu propietari no s'ha verificat. + update_settings_error: S'ha produït un error en actualitzar la configuració de la sala update_settings_success: La configuració de la sala ha estat actualitzada correctament wait: message: La sessió encara no ha començat. - auto: Seràs enviat a la sala automàticament quan comenci la sessió + auto: Se us enviarà cap a la sala automàticament quan comenci la sessió settings: account: fullname: Nom complet - language: Idioma + language: Llengua provider: Proveïdor image: Imatge image_url: Enllaç a la imatge de perfil roles: Rol d'usuari - subtitle: Actualitzar informació d'usuari + subtitle: Actualitzeu la vostra informació d'usuari title: Informació del compte - reset_password: Restablir contrasenya d'usuari + reset_password: Restableix la contrasenya d'usuari delete: button: "Sí, m'agradaria eliminar el meu compte d'usuari." - disclaimer: "Si tries eliminar el teu compte d'usuari, no podrà recuperar-se. Tota la informació relacionada amb el teu compte, incloses configuració, sales y gravacions, serà eliminada." + disclaimer: "Si trieu eliminar el vostre compte d'usuari, no podrà recuperar-se. Tota la informació relacionada amb el compte, incloses la configuració, sales i enregistraments, s'eliminarà." subtitle: Eliminar el compte de forma permanent - title: Eliminar compte + title: Elimina el compte password: confirmation: Confirmació de contrasenya nova new: Contrasenya nova old: Contrasenya anterior - subtitle: Canviar la teva contrasenya + subtitle: Canvia la contrasenya title: Contrasenya title: Perfil d'usuari search: Cerca signup: password_confirm: Confirmació de contrasenya - subtitle: Crear un compte - title: Registrar-se - with: "Registrar-se utilitzant %{provider}" + subtitle: Crea un compte + title: Registre + with: "Registre amb %{provider}" terms: - accept: Accepto els termes y condicions d'ús + accept: "Accepto els %{href}" accept_existing: Accepto els termes y condicions d'ús - title: Termes y condicions d'ús + title: Termes i condicions d'ús test_install: > - Aquesta instal·lació està utilitzant el servidor de proves pre-configurat. Hauria de ser substituït amb el teu propi servidor. Per a més detalls consulta %{href}. + Aquesta instal·lació està utilitzant el servidor de proves pre-configurat. Hauria de ser substituït amb el vostre propi servidor. Per a més detalls consulta %{href}. update: Actualitza verify: accept: Verifica - activated: Compte de correu verificada. - already_verified: Compte de correu verificada amb anterioritat + activated: Compte verificat. + already_verified: El compte ja s'ha verificat invalid: Enllaç de verificació no vàlid - not_verified: El teu compte de correu no ha estat verificat - resend: Reenviar enllaç per a verificació de compte de correu - signin: "Inicia sessió per a tenir accés al teu compte " - title: Verifica el teu compte de correu + not_verified: El compte encara no s'ha verificat + resend: Torna a enviar l'enllaç de verificació + signin: "Inicieu sessió per a tenir accés al vostre compte " + title: Verifiqueu l'adreça electrònica verification: Verificació From ba0ec6ba71a12fa90a364f8ceea8132ee24e7acf Mon Sep 17 00:00:00 2001 From: zimmersi <74589100+zimmersi@users.noreply.github.com> Date: Tue, 2 Mar 2021 00:50:00 +0100 Subject: [PATCH 11/67] enable SMTPS: SMTP over direct TLS connection (#2485) * enable SMTPS: SMTP over direct TLS connection * remove gem 'sqlite3', '~> 1.3.6' as requested * enable SMTPS: SMTP over direct TLS connection * remove gem 'sqlite3', '~> 1.3.6' as requested * changed image name to kwgl * rebase and rubocop -a * removed gem 'sqlite3', '~> 1.3.6' --- config/environments/production.rb | 3 +++ sample.env | 3 +++ 2 files changed, 6 insertions(+) diff --git a/config/environments/production.rb b/config/environments/production.rb index f92ff48e..12e84b39 100644 --- a/config/environments/production.rb +++ b/config/environments/production.rb @@ -107,6 +107,9 @@ Rails.application.configure do } end + # enable SMTPS: SMTP over direct TLS connection + ActionMailer::Base.smtp_settings[:tls] = true if ENV['SMTP_TLS'].present? && ENV['SMTP_TLS'] != "false" + # If configured to 'none' don't check the smtp servers certificate ActionMailer::Base.smtp_settings[:openssl_verify_mode] = ENV['SMTP_OPENSSL_VERIFY_MODE'] if ENV['SMTP_OPENSSL_VERIFY_MODE'].present? diff --git a/sample.env b/sample.env index 12a76e03..2d62c0c7 100644 --- a/sample.env +++ b/sample.env @@ -135,6 +135,9 @@ GOOGLE_ANALYTICS_TRACKING_ID= # SMTP_AUTH=plain # SMTP_STARTTLS_AUTO=true # +# enable SMTPS: SMTP over direct TLS connection; usually port 465 +# SMTP_TLS=true +# # If your mail server has a self-signed certificate, you'll also need to include the line below. # Please note that enable this presents its own security risks and should not be done unless necessary. # SMTP_OPENSSL_VERIFY_MODE=none From 779b41a64a6eea815ca99efdc6dcbb0b263e7ddb Mon Sep 17 00:00:00 2001 From: Mitsutaka Sato Date: Thu, 4 Mar 2021 11:41:10 +1300 Subject: [PATCH 12/67] Add open_timeout (#2555) --- app/helpers/application_helper.rb | 1 + 1 file changed, 1 insertion(+) diff --git a/app/helpers/application_helper.rb b/app/helpers/application_helper.rb index 2725e60d..57d683f3 100644 --- a/app/helpers/application_helper.rb +++ b/app/helpers/application_helper.rb @@ -111,6 +111,7 @@ module ApplicationHelper http = Net::HTTP.new(url.host, url.port) http.use_ssl = (url.scheme == "https") http.read_timeout = 10 + http.open_timeout = 10 http.start do |web| response = web.head(url.request_uri) From cd4433798c49b3272decaf14a662312c6778ff17 Mon Sep 17 00:00:00 2001 From: Ahmad Farhat Date: Thu, 4 Mar 2021 18:01:01 -0500 Subject: [PATCH 13/67] GRN2-354: Switch default database to Postgres 13.2 (#2563) * Switch default database to Postgres 13.2 * Update pg version in Github Actions --- .github/workflows/main.yml | 2 +- docker-compose.yml | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 435439aa..c7342457 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -21,7 +21,7 @@ jobs: services: postgres: - image: postgres + image: postgres:13.2-alpine env: POSTGRES_DB: postgres POSTGRES_PASSWORD: postgres diff --git a/docker-compose.yml b/docker-compose.yml index d334c9ee..e6a4b4bf 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -24,7 +24,7 @@ services: links: - db db: - image: postgres:9.5 + image: postgres:13.2-alpine restart: unless-stopped ports: - 127.0.0.1:5432:5432 From 32da1ee206ebc5ff33e89da1dd5c37678649e3f2 Mon Sep 17 00:00:00 2001 From: Ahmad Farhat Date: Sun, 7 Mar 2021 14:30:11 -0500 Subject: [PATCH 14/67] Forked the workflows to avoid potential disruption (#2565) --- .github/workflows/build.push.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/build.push.yml b/.github/workflows/build.push.yml index e281d7ba..3f05b819 100644 --- a/.github/workflows/build.push.yml +++ b/.github/workflows/build.push.yml @@ -22,13 +22,13 @@ jobs: password: ${{ secrets.DOCKER_PASSWORD }} - name: Compute Short SHA - uses: benjlevesque/short-sha@v1.2 + uses: farhatahmad/short-sha@v1.2 id: short-sha with: length: 7 - name: Get Branch Name - uses: tj-actions/branch-names@v2 + uses: farhatahmad/branch-names@v2 id: branch-name - name: Build and Push latest From 4cd41f5aa8fdc04fc0070532c050bddd09f8e12b Mon Sep 17 00:00:00 2001 From: Ahmad Farhat Date: Sun, 14 Mar 2021 14:06:11 -0400 Subject: [PATCH 15/67] Replace all CRLF files to LF (#2572) --- .github/workflows/build.release.yml | 64 ++-- app/views/rooms/show.html.erb | 280 +++++++++--------- .../shared/modals/_invite_user_modal.html.erb | 88 +++--- .../shared/modals/_share_room_modal.html.erb | 86 +++--- app/views/user_mailer/invite_email.html.erb | 86 +++--- app/views/user_mailer/invite_email.text.erb | 54 ++-- 6 files changed, 329 insertions(+), 329 deletions(-) diff --git a/.github/workflows/build.release.yml b/.github/workflows/build.release.yml index 3f8fa9c9..46cecd08 100644 --- a/.github/workflows/build.release.yml +++ b/.github/workflows/build.release.yml @@ -1,32 +1,32 @@ -env: - RUBY_VERSION: 2.7.2 - - -name: Build Release -on: - release: - types: [released] - -jobs: - main: - name: Build Docker Image - runs-on: ubuntu-18.04 - steps: - - name: Set up Docker Buildx - uses: docker/setup-buildx-action@v1 - - - name: Login to Github Container Registry - uses: docker/login-action@v1 - with: - username: ${{ secrets.DOCKER_USERNAME }} - password: ${{ secrets.DOCKER_PASSWORD }} - - - name: Build and Push release - uses: docker/build-push-action@v2 - with: - push: true - tags: | - bigbluebutton/greenlight:latest - bigbluebutton/greenlight:v2 - bigbluebutton/greenlight:${{ github.event.release.tag_name }} - build-args: version_code=${{ github.event.release.tag_name }} +env: + RUBY_VERSION: 2.7.2 + + +name: Build Release +on: + release: + types: [released] + +jobs: + main: + name: Build Docker Image + runs-on: ubuntu-18.04 + steps: + - name: Set up Docker Buildx + uses: docker/setup-buildx-action@v1 + + - name: Login to Github Container Registry + uses: docker/login-action@v1 + with: + username: ${{ secrets.DOCKER_USERNAME }} + password: ${{ secrets.DOCKER_PASSWORD }} + + - name: Build and Push release + uses: docker/build-push-action@v2 + with: + push: true + tags: | + bigbluebutton/greenlight:latest + bigbluebutton/greenlight:v2 + bigbluebutton/greenlight:${{ github.event.release.tag_name }} + build-args: version_code=${{ github.event.release.tag_name }} diff --git a/app/views/rooms/show.html.erb b/app/views/rooms/show.html.erb index 0d8903df..3feb5219 100644 --- a/app/views/rooms/show.html.erb +++ b/app/views/rooms/show.html.erb @@ -1,140 +1,140 @@ -<% -# BigBlueButton open source conferencing system - http://www.bigbluebutton.org/. -# Copyright (c) 2018 BigBlueButton Inc. and by respective authors (see below). -# This program is free software; you can redistribute it and/or modify it under the -# terms of the GNU Lesser General Public License as published by the Free Software -# Foundation; either version 3.0 of the License, or (at your option) any later -# version. -# -# BigBlueButton is distributed in the hope that it will be useful, but WITHOUT ANY -# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A -# PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. -# You should have received a copy of the GNU Lesser General Public License along -# with BigBlueButton; if not, see . -%> - -<% exceeds_limit = current_room_exceeds_limit(@room)%> -<% if exceeds_limit%> -
- <%= t("room.room_limit_exceeded", difference: @diff) %> -
-<% end %> -
-
-
-
-
-

<%= title(@room.name) %>

- <% if current_user.main_room == @room %> - - <% else %> - - <% end %> -
-

<%= @room.sessions %> <%= t("room.sessions") %><% unless hide_recording_tables %> | <%= @recordings.length %> <%= t("room.recordings") %><% end %>

- <% unless exceeds_limit %> - -
-
- -
-
-
-
- -
-
- <% if @room.access_code.present? %> - - - <% end %> - <% if Rails.configuration.enable_google_calendar_button %> - - - <%= t("add_to_google_calendar") %> - - <% end %> -
-
-
-
- <% end %> -
-
- <% if @room_running %> - <%= button_to t("room.join"), room_path(@room), class: "btn btn-primary btn-block px-7 start-button float-right", "data-disable": "" %> - <% else %> - <% unless exceeds_limit %> - <%= button_to t("room.start"), start_room_path(@room), class: "btn btn-primary btn-block px-7 start-button float-right", "data-disable": "" %> - <% end %> - <% end %> -
-
- - <% if total_room_count(current_user) > 5 %> - - <% end %> - -
- <% if current_user.role.get_permission("can_create_rooms") %> - <% current_user.ordered_rooms.each do |room| %> -
- <%= link_to room do %> - <%= render "rooms/components/room_block", room: room %> - <% end %> -
- <% end %> - <% end %> - - <% if shared_access_allowed %> - <% current_user.shared_rooms.each do |room| %> -
- <%= link_to room do %> - <%= render "rooms/components/shared_room_block", room: room %> - <% end %> -
- <% end %> - <% end %> - - <% if current_user.role.get_permission("can_create_rooms") && !room_limit_exceeded %> - <%= render "rooms/components/create_room_block"%> - <% end %> -
-
-
- -<% unless hide_recording_tables %> - <%= render "shared/sessions", recordings: @recordings, pagy: @pagy, only_public: false, shared_room: @shared_room, user_recordings: false, title: t("room.recordings")%> -<% end %> - -<%= render "shared/modals/delete_room_modal" %> - -<%= render "shared/modals/create_room_modal" %> - -<% if preupload_allowed? %> - <%= render "shared/modals/preupload_presentation_modal" %> -<% end %> - -<% if shared_access_allowed %> - <%= render "shared/modals/share_room_modal" %> - <%= render "shared/modals/remove_access_modal" %> -<% end %> +<% +# BigBlueButton open source conferencing system - http://www.bigbluebutton.org/. +# Copyright (c) 2018 BigBlueButton Inc. and by respective authors (see below). +# This program is free software; you can redistribute it and/or modify it under the +# terms of the GNU Lesser General Public License as published by the Free Software +# Foundation; either version 3.0 of the License, or (at your option) any later +# version. +# +# BigBlueButton is distributed in the hope that it will be useful, but WITHOUT ANY +# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A +# PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. +# You should have received a copy of the GNU Lesser General Public License along +# with BigBlueButton; if not, see . +%> + +<% exceeds_limit = current_room_exceeds_limit(@room)%> +<% if exceeds_limit%> +
+ <%= t("room.room_limit_exceeded", difference: @diff) %> +
+<% end %> +
+
+
+
+
+

<%= title(@room.name) %>

+ <% if current_user.main_room == @room %> + + <% else %> + + <% end %> +
+

<%= @room.sessions %> <%= t("room.sessions") %><% unless hide_recording_tables %> | <%= @recordings.length %> <%= t("room.recordings") %><% end %>

+ <% unless exceeds_limit %> + +
+
+ +
+
+
+
+ +
+
+ <% if @room.access_code.present? %> + + + <% end %> + <% if Rails.configuration.enable_google_calendar_button %> + + + <%= t("add_to_google_calendar") %> + + <% end %> +
+
+
+
+ <% end %> +
+
+ <% if @room_running %> + <%= button_to t("room.join"), room_path(@room), class: "btn btn-primary btn-block px-7 start-button float-right", "data-disable": "" %> + <% else %> + <% unless exceeds_limit %> + <%= button_to t("room.start"), start_room_path(@room), class: "btn btn-primary btn-block px-7 start-button float-right", "data-disable": "" %> + <% end %> + <% end %> +
+
+ + <% if total_room_count(current_user) > 5 %> + + <% end %> + +
+ <% if current_user.role.get_permission("can_create_rooms") %> + <% current_user.ordered_rooms.each do |room| %> +
+ <%= link_to room do %> + <%= render "rooms/components/room_block", room: room %> + <% end %> +
+ <% end %> + <% end %> + + <% if shared_access_allowed %> + <% current_user.shared_rooms.each do |room| %> +
+ <%= link_to room do %> + <%= render "rooms/components/shared_room_block", room: room %> + <% end %> +
+ <% end %> + <% end %> + + <% if current_user.role.get_permission("can_create_rooms") && !room_limit_exceeded %> + <%= render "rooms/components/create_room_block"%> + <% end %> +
+
+
+ +<% unless hide_recording_tables %> + <%= render "shared/sessions", recordings: @recordings, pagy: @pagy, only_public: false, shared_room: @shared_room, user_recordings: false, title: t("room.recordings")%> +<% end %> + +<%= render "shared/modals/delete_room_modal" %> + +<%= render "shared/modals/create_room_modal" %> + +<% if preupload_allowed? %> + <%= render "shared/modals/preupload_presentation_modal" %> +<% end %> + +<% if shared_access_allowed %> + <%= render "shared/modals/share_room_modal" %> + <%= render "shared/modals/remove_access_modal" %> +<% end %> diff --git a/app/views/shared/modals/_invite_user_modal.html.erb b/app/views/shared/modals/_invite_user_modal.html.erb index b7680877..b8e5a768 100644 --- a/app/views/shared/modals/_invite_user_modal.html.erb +++ b/app/views/shared/modals/_invite_user_modal.html.erb @@ -1,44 +1,44 @@ -<% -# BigBlueButton open source conferencing system - http://www.bigbluebutton.org/. -# Copyright (c) 2018 BigBlueButton Inc. and by respective authors (see below). -# This program is free software; you can redistribute it and/or modify it under the -# terms of the GNU Lesser General Public License as published by the Free Software -# Foundation; either version 3.0 of the License, or (at your option) any later -# version. -# -# BigBlueButton is distributed in the hope that it will be useful, but WITHOUT ANY -# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A -# PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. -# You should have received a copy of the GNU Lesser General Public License along -# with BigBlueButton; if not, see . -%> - - +<% +# BigBlueButton open source conferencing system - http://www.bigbluebutton.org/. +# Copyright (c) 2018 BigBlueButton Inc. and by respective authors (see below). +# This program is free software; you can redistribute it and/or modify it under the +# terms of the GNU Lesser General Public License as published by the Free Software +# Foundation; either version 3.0 of the License, or (at your option) any later +# version. +# +# BigBlueButton is distributed in the hope that it will be useful, but WITHOUT ANY +# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A +# PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. +# You should have received a copy of the GNU Lesser General Public License along +# with BigBlueButton; if not, see . +%> + + diff --git a/app/views/shared/modals/_share_room_modal.html.erb b/app/views/shared/modals/_share_room_modal.html.erb index 57a50c6d..038917e1 100644 --- a/app/views/shared/modals/_share_room_modal.html.erb +++ b/app/views/shared/modals/_share_room_modal.html.erb @@ -1,43 +1,43 @@ -<% -# BigBlueButton open source conferencing system - http://www.bigbluebutton.org/. -# Copyright (c) 2018 BigBlueButton Inc. and by respective authors (see below). -# This program is free software; you can redistribute it and/or modify it under the -# terms of the GNU Lesser General Public License as published by the Free Software -# Foundation; either version 3.0 of the License, or (at your option) any later -# version. -# -# BigBlueButton is distributed in the hope that it will be useful, but WITHOUT ANY -# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A -# PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. -# You should have received a copy of the GNU Lesser General Public License along -# with BigBlueButton; if not, see . -%> - - +<% +# BigBlueButton open source conferencing system - http://www.bigbluebutton.org/. +# Copyright (c) 2018 BigBlueButton Inc. and by respective authors (see below). +# This program is free software; you can redistribute it and/or modify it under the +# terms of the GNU Lesser General Public License as published by the Free Software +# Foundation; either version 3.0 of the License, or (at your option) any later +# version. +# +# BigBlueButton is distributed in the hope that it will be useful, but WITHOUT ANY +# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A +# PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. +# You should have received a copy of the GNU Lesser General Public License along +# with BigBlueButton; if not, see . +%> + + diff --git a/app/views/user_mailer/invite_email.html.erb b/app/views/user_mailer/invite_email.html.erb index 6f7c6505..a822b6ce 100644 --- a/app/views/user_mailer/invite_email.html.erb +++ b/app/views/user_mailer/invite_email.html.erb @@ -1,43 +1,43 @@ -<% -# BigBlueButton open source conferencing system - http://www.bigbluebutton.org/. -# -# Copyright (c) 2018 BigBlueButton Inc. and by respective authors (see below). -# -# This program is free software; you can redistribute it and/or modify it under the -# terms of the GNU Lesser General Public License as published by the Free Software -# Foundation; either version 3.0 of the License, or (at your option) any later -# version. -# -# BigBlueButton is distributed in the hope that it will be useful, but WITHOUT ANY -# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A -# PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. -# -# You should have received a copy of the GNU Lesser General Public License along -# with BigBlueButton; if not, see . -%> - -
-
- <%= image_tag(@image, height: '70') %> - -

- <%= t('mailer.user.invite.subject') %> -

- -

- <%= t('mailer.user.invite.info', name: @name) %> -

- -

- <%= t('mailer.user.invite.username', email: @email) %> -

- -

- <%= t('mailer.user.invite.signup_info') %> -

- - - <%= t('mailer.user.invite.signup_link') %> - -
-
+<% +# BigBlueButton open source conferencing system - http://www.bigbluebutton.org/. +# +# Copyright (c) 2018 BigBlueButton Inc. and by respective authors (see below). +# +# This program is free software; you can redistribute it and/or modify it under the +# terms of the GNU Lesser General Public License as published by the Free Software +# Foundation; either version 3.0 of the License, or (at your option) any later +# version. +# +# BigBlueButton is distributed in the hope that it will be useful, but WITHOUT ANY +# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A +# PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public License along +# with BigBlueButton; if not, see . +%> + +
+
+ <%= image_tag(@image, height: '70') %> + +

+ <%= t('mailer.user.invite.subject') %> +

+ +

+ <%= t('mailer.user.invite.info', name: @name) %> +

+ +

+ <%= t('mailer.user.invite.username', email: @email) %> +

+ +

+ <%= t('mailer.user.invite.signup_info') %> +

+ + + <%= t('mailer.user.invite.signup_link') %> + +
+
diff --git a/app/views/user_mailer/invite_email.text.erb b/app/views/user_mailer/invite_email.text.erb index 0cef70c2..f5f259d1 100644 --- a/app/views/user_mailer/invite_email.text.erb +++ b/app/views/user_mailer/invite_email.text.erb @@ -1,27 +1,27 @@ -<% -# BigBlueButton open source conferencing system - http://www.bigbluebutton.org/. -# -# Copyright (c) 2018 BigBlueButton Inc. and by respective authors (see below). -# -# This program is free software; you can redistribute it and/or modify it under the -# terms of the GNU Lesser General Public License as published by the Free Software -# Foundation; either version 3.0 of the License, or (at your option) any later -# version. -# -# BigBlueButton is distributed in the hope that it will be useful, but WITHOUT ANY -# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A -# PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. -# -# You should have received a copy of the GNU Lesser General Public License along -# with BigBlueButton; if not, see . -%> - -<%= t('mailer.user.invite.subject') %> - -<%= t('mailer.user.invite.info', name: @name) %> - -<%= t('mailer.user.invite.username', email: @email) %> - -<%= t('mailer.user.invite.signup_info') %> - -<%= @url %> +<% +# BigBlueButton open source conferencing system - http://www.bigbluebutton.org/. +# +# Copyright (c) 2018 BigBlueButton Inc. and by respective authors (see below). +# +# This program is free software; you can redistribute it and/or modify it under the +# terms of the GNU Lesser General Public License as published by the Free Software +# Foundation; either version 3.0 of the License, or (at your option) any later +# version. +# +# BigBlueButton is distributed in the hope that it will be useful, but WITHOUT ANY +# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A +# PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public License along +# with BigBlueButton; if not, see . +%> + +<%= t('mailer.user.invite.subject') %> + +<%= t('mailer.user.invite.info', name: @name) %> + +<%= t('mailer.user.invite.username', email: @email) %> + +<%= t('mailer.user.invite.signup_info') %> + +<%= @url %> From 9dc59b12112c2b586738203517b555b5358a2c2b Mon Sep 17 00:00:00 2001 From: zechmeister Date: Sun, 14 Mar 2021 19:24:30 +0100 Subject: [PATCH 16/67] Add optional moderator codes (#2413) * add column for moderator code * add interface for moderator access code * add support for write and update moderator access * check if correct moderator_code in session * move access code form into own component * add support for moderator access code * add support for moderator access code * add copy code button for moderator code * freeze all the things * add tests for moderator access code * add helpfer for moderator_access setting * add setting for moderator access code * show setting for moderator access code * add checks for moderator code setting * use method from room controller for moderator password check * add tests for login with moderator access code * add check for moderator code setting * check if moderator codes are enabled in settings * only display form for moderator code if enabled in settings * add newline at end of file * make check for moderator code available as helper * align style of join button and access code button * add localization for moderator codes * add field for moderator codes * add field for moderator access code to rooms * fixes for rubocop * fix LineLenghts for rubocop * fix double space Co-authored-by: Ahmad Farhat --- app/assets/javascripts/room.js | 44 ++- app/assets/stylesheets/rooms.scss | 4 +- app/controllers/application_controller.rb | 6 + app/controllers/concerns/joiner.rb | 5 +- app/controllers/rooms_controller.rb | 30 +- app/helpers/admins_helper.rb | 8 + app/models/setting.rb | 2 + .../site_settings/_settings.html.erb | 21 ++ .../_enter_access_code_form.html.erb | 29 ++ .../rooms/components/_room_block.html.erb | 2 +- app/views/rooms/join.html.erb | 29 +- app/views/rooms/show.html.erb | 287 +++++++++--------- .../shared/modals/_create_room_modal.html.erb | 13 + config/application.rb | 3 + config/locales/de_DE.yml | 10 + config/locales/en.yml | 10 + ...2132_add_moderator_access_code_to_rooms.rb | 7 + db/schema.rb | 3 +- spec/controllers/rooms_controller_spec.rb | 108 +++++++ 19 files changed, 447 insertions(+), 174 deletions(-) create mode 100644 app/views/rooms/components/_enter_access_code_form.html.erb create mode 100644 db/migrate/20210108032132_add_moderator_access_code_to_rooms.rb diff --git a/app/assets/javascripts/room.js b/app/assets/javascripts/room.js index d5861d8f..d953f613 100644 --- a/app/assets/javascripts/room.js +++ b/app/assets/javascripts/room.js @@ -184,17 +184,19 @@ function copyInvite() { } } -function copyAccess() { - $('#copy-code').attr("type", "text") - $('#copy-code').select() +function copyAccess(target) { + input = target ? $("#copy-" + target + "-code") : $("#copy-code") + input.attr("type", "text") + input.select() if (document.execCommand("copy")) { - $('#copy-code').attr("type", "hidden") - copy = $("#copy-access") + input.attr("type", "hidden") + copy = target ? $("#copy-" + target + "-access") : $("#copy-access") copy.addClass('btn-success'); copy.html("" + getLocalizedString("copied")) setTimeout(function(){ copy.removeClass('btn-success'); - copy.html("" + getLocalizedString("room.copy_access")) + originalString = target ? getLocalizedString("room.copy_" + target + "_access") : getLocalizedString("room.copy_access") + copy.html("" + originalString) }, 1000) } } @@ -202,7 +204,9 @@ function copyAccess() { function showCreateRoom(target) { $("#create-room-name").val("") $("#create-room-access-code").text(getLocalizedString("modal.create_room.access_code_placeholder")) + $("#create-room-moderator-access-code").text(getLocalizedString("modal.create_room.moderator_access_code_placeholder")) $("#room_access_code").val(null) + $("#room_moderator_access_code").val(null) $("#createRoomModal form").attr("action", $("body").data('relative-root')) $("#room_mute_on_join").prop("checked", $("#room_mute_on_join").data("default")) @@ -254,6 +258,16 @@ function showUpdateRoom(target) { $("#create-room-access-code").text(getLocalizedString("modal.create_room.access_code_placeholder")) $("#room_access_code").val(null) } + + var moderatorAccessCode = modal.closest(".room-block").data("room-moderator-access-code") + + if(moderatorAccessCode){ + $("#create-room-moderator-access-code").text(getLocalizedString("modal.create_room.moderator_access_code") + ": " + moderatorAccessCode) + $("#room_moderator_access_code").val(moderatorAccessCode) + } else { + $("#create-room-moderator-access-code").text(getLocalizedString("modal.create_room.moderator_access_code_placeholder")) + $("#room_moderator_access_code").val(null) + } } function showDeleteRoom(target) { @@ -291,6 +305,24 @@ function ResetAccessCode(){ $("#room_access_code").val(null) } +function generateModeratorAccessCode(){ + const accessCodeLength = 6 + var validCharacters = "abcdefghijklmopqrstuvwxyz" + var accessCode = "" + + for( var i = 0; i < accessCodeLength; i++){ + accessCode += validCharacters.charAt(Math.floor(Math.random() * validCharacters.length)); + } + + $("#create-room-moderator-access-code").text(getLocalizedString("modal.create_room.moderator_access_code") + ": " + accessCode) + $("#room_moderator_access_code").val(accessCode) +} + +function ResetModeratorAccessCode(){ + $("#create-room-moderator-access-code").text(getLocalizedString("modal.create_room.moderator_access_code_placeholder")) + $("#room_moderator_access_code").val(null) +} + function saveAccessChanges() { let listItemsToAdd = $("#user-list li:not(.remove-shared)").toArray().map(user => $(user).data("uid")) diff --git a/app/assets/stylesheets/rooms.scss b/app/assets/stylesheets/rooms.scss index 26709952..573ec5c4 100644 --- a/app/assets/stylesheets/rooms.scss +++ b/app/assets/stylesheets/rooms.scss @@ -32,8 +32,8 @@ font-size: 20px !important; } -.join-input { - height: 48px; +.moderator-code-label { + margin-top: 150px !important; } .home-indicator { diff --git a/app/controllers/application_controller.rb b/app/controllers/application_controller.rb index d58f5d8d..75ac36f0 100644 --- a/app/controllers/application_controller.rb +++ b/app/controllers/application_controller.rb @@ -186,6 +186,12 @@ class ApplicationController < ActionController::Base end helper_method :recording_consent_required? + # Indicates whether users are allowed to add moderator access codes to rooms + def moderator_code_allowed? + @settings.get_value("Moderator Access Codes") == "true" + end + helper_method :moderator_code_allowed? + # Returns a list of allowed file types def allowed_file_types Rails.configuration.allowed_file_types diff --git a/app/controllers/concerns/joiner.rb b/app/controllers/concerns/joiner.rb index 96958c05..6c6b016e 100644 --- a/app/controllers/concerns/joiner.rb +++ b/app/controllers/concerns/joiner.rb @@ -50,10 +50,11 @@ module Joiner def join_room(opts) @room_settings = JSON.parse(@room[:room_settings]) - if room_running?(@room.bbb_id) || @room.owned_by?(current_user) || room_setting_with_config("anyoneCanStart") + moderator_privileges = @room.owned_by?(current_user) || valid_moderator_access_code(session[:moderator_access_code]) + if room_running?(@room.bbb_id) || room_setting_with_config("anyoneCanStart") || moderator_privileges # Determine if the user needs to join as a moderator. - opts[:user_is_moderator] = @room.owned_by?(current_user) || room_setting_with_config("joinModerator") || @shared_room + opts[:user_is_moderator] = room_setting_with_config("joinModerator") || @shared_room || moderator_privileges opts[:record] = record_meeting opts[:require_moderator_approval] = room_setting_with_config("requireModeratorApproval") opts[:mute_on_start] = room_setting_with_config("muteOnStart") diff --git a/app/controllers/rooms_controller.rb b/app/controllers/rooms_controller.rb index cc06e4a5..2de6aac6 100644 --- a/app/controllers/rooms_controller.rb +++ b/app/controllers/rooms_controller.rb @@ -44,7 +44,9 @@ class RoomsController < ApplicationController return redirect_to current_user.main_room, flash: { alert: I18n.t("room.room_limit") } if room_limit_exceeded # Create room - @room = Room.new(name: room_params[:name], access_code: room_params[:access_code]) + @room = Room.new(name: room_params[:name], + access_code: room_params[:access_code], + moderator_access_code: room_params[:moderator_access_code]) @room.owner = current_user @room.room_settings = create_room_settings_string(room_params) @@ -109,8 +111,9 @@ class RoomsController < ApplicationController @shared_room = room_shared_with_user unless @room.owned_by?(current_user) || @shared_room - # Don't allow users to join unless they have a valid access code or the room doesn't have an access code - if @room.access_code && !@room.access_code.empty? && @room.access_code != session[:access_code] + # Don't allow users to join unless they have a valid access code or the room doesn't have an access codes + valid_access_code = !@room.access_code.present? || @room.access_code == session[:access_code] + if !valid_access_code && !valid_moderator_access_code(session[:moderator_access_code]) return redirect_to room_path(room_uid: params[:room_uid]), flash: { alert: I18n.t("room.access_code_required") } end @@ -203,7 +206,8 @@ class RoomsController < ApplicationController @room.update_attributes( name: options[:name], room_settings: room_settings_string, - access_code: options[:access_code] + access_code: options[:access_code], + moderator_access_code: options[:moderator_access_code] ) flash[:success] = I18n.t("room.update_settings_success") @@ -321,9 +325,16 @@ class RoomsController < ApplicationController # POST /:room_uid/login def login - session[:access_code] = room_params[:access_code] + # use same form for access_code and moderator_access_code + if valid_moderator_access_code(room_params[:access_code]) + session[:moderator_access_code] = room_params[:access_code] + else + session[:access_code] = room_params[:access_code] + end - flash[:alert] = I18n.t("room.access_code_required") if session[:access_code] != @room.access_code + if session[:access_code] != @room.access_code && !valid_moderator_access_code(session[:moderator_access_code]) + flash[:alert] = I18n.t("room.access_code_required") + end redirect_to room_path(@room.uid) end @@ -345,7 +356,7 @@ class RoomsController < ApplicationController def room_params params.require(:room).permit(:name, :auto_join, :mute_on_join, :access_code, :require_moderator_approval, :anyone_can_start, :all_join_moderator, - :recording, :presentation) + :recording, :presentation, :moderator_access_code) end # Find the room from the uid. @@ -412,6 +423,11 @@ class RoomsController < ApplicationController end helper_method :room_limit_exceeded + def valid_moderator_access_code(code) + code == @room.moderator_access_code && !@room.moderator_access_code.blank? && moderator_code_allowed? + end + helper_method :valid_moderator_access_code + def record_meeting # If the require consent setting is checked, then check the room setting, else, set to true if recording_consent_required? diff --git a/app/helpers/admins_helper.rb b/app/helpers/admins_helper.rb index 91f3a2e7..f21f877b 100644 --- a/app/helpers/admins_helper.rb +++ b/app/helpers/admins_helper.rb @@ -89,6 +89,14 @@ module AdminsHelper end end + def moderator_codes_string + if @settings.get_value("Moderator Access Codes") == "true" + I18n.t("administrator.site_settings.moderator_codes.enabled") + else + I18n.t("administrator.site_settings.moderator_codes.disabled") + end + end + def log_level_string case Rails.logger.level when 0 diff --git a/app/models/setting.rb b/app/models/setting.rb index 1ee18192..27cff084 100644 --- a/app/models/setting.rb +++ b/app/models/setting.rb @@ -66,6 +66,8 @@ class Setting < ApplicationRecord Rails.configuration.shared_access_default when "Preupload Presentation" Rails.configuration.preupload_presentation_default + when "Moderator Access Codes" + Rails.configuration.moderator_codes_default when "Room Configuration Mute On Join" room_config_setting("mute-on-join") when "Room Configuration Require Moderator" diff --git a/app/views/admins/components/site_settings/_settings.html.erb b/app/views/admins/components/site_settings/_settings.html.erb index 464d3088..fa4cf6eb 100644 --- a/app/views/admins/components/site_settings/_settings.html.erb +++ b/app/views/admins/components/site_settings/_settings.html.erb @@ -143,6 +143,27 @@ +
+
+
+ + + +
+
+
diff --git a/app/views/rooms/components/_enter_access_code_form.html.erb b/app/views/rooms/components/_enter_access_code_form.html.erb new file mode 100644 index 00000000..4f1beddd --- /dev/null +++ b/app/views/rooms/components/_enter_access_code_form.html.erb @@ -0,0 +1,29 @@ +<% +# BigBlueButton open source conferencing system - http://www.bigbluebutton.org/. +# Copyright (c) 2018 BigBlueButton Inc. and by respective authors (see below). +# This program is free software; you can redistribute it and/or modify it under the +# terms of the GNU Lesser General Public License as published by the Free Software +# Foundation; either version 3.0 of the License, or (at your option) any later +# version. +# +# BigBlueButton is distributed in the hope that it will be useful, but WITHOUT ANY +# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A +# PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. +# You should have received a copy of the GNU Lesser General Public License along +# with BigBlueButton; if not, see . +%> + +<%= form_for :room, url: login_room_path(@room.uid) do |f| %> +
+ <%= f.text_field :access_code, + required: true, + class: "form-control join-form", + placeholder: access_code_type == 'moderator' ? t("room.enter_the_moderator_access_code") : t("room.enter_the_access_code"), + value: "" , + autofocus: true, + maxlength: 26 %> + + <%= f.button t("room.login"), type: :submit, class: "btn btn-primary btn-sm px-7 form-control join-form" %> + +
+<% end %> diff --git a/app/views/rooms/components/_room_block.html.erb b/app/views/rooms/components/_room_block.html.erb index 4b57db74..d2a9baf2 100644 --- a/app/views/rooms/components/_room_block.html.erb +++ b/app/views/rooms/components/_room_block.html.erb @@ -13,7 +13,7 @@ # with BigBlueButton; if not, see . %> -
+
diff --git a/app/views/rooms/join.html.erb b/app/views/rooms/join.html.erb index cac7a022..f38f9e4d 100644 --- a/app/views/rooms/join.html.erb +++ b/app/views/rooms/join.html.erb @@ -15,23 +15,15 @@ <% content_for(:page_desc) { t("room.invitation_description", name: @room.name) } %> -<% valid_access_code = @room.access_code.nil? || @room.access_code.empty? || @room.access_code == session[:access_code] %> -<%= render 'rooms/components/room_event', render_recordings: valid_access_code do %> +<% access_code_set = @room.access_code.present? %> +<% valid_access_code = access_code_set && @room.access_code == session[:access_code] %> +<% moderator_access_code_set = @room.moderator_access_code.present? && moderator_code_allowed? %> +<% valid_moderator_access_code = valid_moderator_access_code(session[:moderator_access_code]) %> + +<%= render 'rooms/components/room_event', render_recordings: valid_access_code || valid_moderator_access_code do %> <% if room_authentication_required %>

<%= t("administrator.site_settings.authentication.user-info") %>

- <% elsif !valid_access_code %> - <%= form_for :room, url: login_room_path(@room.uid) do |f| %> -
- <%= f.text_field :access_code, - required: true, - class: "form-control join-form", - placeholder: t("room.enter_the_access_code"), - value: "" , - autofocus: true %> - <%= f.submit t("room.login"), class: "btn btn-primary btn-sm col-sm-3 form-control join-form" %> -
- <% end %> - <% else %> + <% elsif valid_moderator_access_code || valid_access_code || !access_code_set %> <%= form_for room_path(@room), method: :post do |f| %>
<%= f.hidden_field(:search, :value => params[:search])%> @@ -59,5 +51,12 @@ <% end %> <% end %> + <% if moderator_access_code_set && !valid_moderator_access_code %> + + + <%= render "rooms/components/enter_access_code_form", access_code_type: 'moderator' %> + <% end %> + <% else %> + <%= render "rooms/components/enter_access_code_form", access_code_type: 'standard_access' %> <% end %> <% end %> diff --git a/app/views/rooms/show.html.erb b/app/views/rooms/show.html.erb index 3feb5219..ab190452 100644 --- a/app/views/rooms/show.html.erb +++ b/app/views/rooms/show.html.erb @@ -1,140 +1,147 @@ -<% -# BigBlueButton open source conferencing system - http://www.bigbluebutton.org/. -# Copyright (c) 2018 BigBlueButton Inc. and by respective authors (see below). -# This program is free software; you can redistribute it and/or modify it under the -# terms of the GNU Lesser General Public License as published by the Free Software -# Foundation; either version 3.0 of the License, or (at your option) any later -# version. -# -# BigBlueButton is distributed in the hope that it will be useful, but WITHOUT ANY -# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A -# PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. -# You should have received a copy of the GNU Lesser General Public License along -# with BigBlueButton; if not, see . -%> - -<% exceeds_limit = current_room_exceeds_limit(@room)%> -<% if exceeds_limit%> -
- <%= t("room.room_limit_exceeded", difference: @diff) %> -
-<% end %> -
-
-
-
-
-

<%= title(@room.name) %>

- <% if current_user.main_room == @room %> - - <% else %> - - <% end %> -
-

<%= @room.sessions %> <%= t("room.sessions") %><% unless hide_recording_tables %> | <%= @recordings.length %> <%= t("room.recordings") %><% end %>

- <% unless exceeds_limit %> - -
-
- -
-
-
-
- -
-
- <% if @room.access_code.present? %> - - - <% end %> - <% if Rails.configuration.enable_google_calendar_button %> - - - <%= t("add_to_google_calendar") %> - - <% end %> -
-
-
-
- <% end %> -
-
- <% if @room_running %> - <%= button_to t("room.join"), room_path(@room), class: "btn btn-primary btn-block px-7 start-button float-right", "data-disable": "" %> - <% else %> - <% unless exceeds_limit %> - <%= button_to t("room.start"), start_room_path(@room), class: "btn btn-primary btn-block px-7 start-button float-right", "data-disable": "" %> - <% end %> - <% end %> -
-
- - <% if total_room_count(current_user) > 5 %> - - <% end %> - -
- <% if current_user.role.get_permission("can_create_rooms") %> - <% current_user.ordered_rooms.each do |room| %> -
- <%= link_to room do %> - <%= render "rooms/components/room_block", room: room %> - <% end %> -
- <% end %> - <% end %> - - <% if shared_access_allowed %> - <% current_user.shared_rooms.each do |room| %> -
- <%= link_to room do %> - <%= render "rooms/components/shared_room_block", room: room %> - <% end %> -
- <% end %> - <% end %> - - <% if current_user.role.get_permission("can_create_rooms") && !room_limit_exceeded %> - <%= render "rooms/components/create_room_block"%> - <% end %> -
-
-
- -<% unless hide_recording_tables %> - <%= render "shared/sessions", recordings: @recordings, pagy: @pagy, only_public: false, shared_room: @shared_room, user_recordings: false, title: t("room.recordings")%> -<% end %> - -<%= render "shared/modals/delete_room_modal" %> - -<%= render "shared/modals/create_room_modal" %> - -<% if preupload_allowed? %> - <%= render "shared/modals/preupload_presentation_modal" %> -<% end %> - -<% if shared_access_allowed %> - <%= render "shared/modals/share_room_modal" %> - <%= render "shared/modals/remove_access_modal" %> -<% end %> +<% +# BigBlueButton open source conferencing system - http://www.bigbluebutton.org/. +# Copyright (c) 2018 BigBlueButton Inc. and by respective authors (see below). +# This program is free software; you can redistribute it and/or modify it under the +# terms of the GNU Lesser General Public License as published by the Free Software +# Foundation; either version 3.0 of the License, or (at your option) any later +# version. +# +# BigBlueButton is distributed in the hope that it will be useful, but WITHOUT ANY +# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A +# PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. +# You should have received a copy of the GNU Lesser General Public License along +# with BigBlueButton; if not, see . +%> + +<% exceeds_limit = current_room_exceeds_limit(@room)%> +<% if exceeds_limit%> +
+ <%= t("room.room_limit_exceeded", difference: @diff) %> +
+<% end %> +
+
+
+
+
+

<%= title(@room.name) %>

+ <% if current_user.main_room == @room %> + + <% else %> + + <% end %> +
+

<%= @room.sessions %> <%= t("room.sessions") %><% unless hide_recording_tables %> | <%= @recordings.length %> <%= t("room.recordings") %><% end %>

+ <% unless exceeds_limit %> + +
+
+ +
+
+
+
+ +
+
+ <% if @room.access_code.present? %> + + + <% end %> + <% if moderator_code_allowed? && @room.moderator_access_code.present? %> + + + <% end %> + <% if Rails.configuration.enable_google_calendar_button %> + + + <%= t("add_to_google_calendar") %> + + <% end %> +
+
+
+
+ <% end %> +
+
+ <% if @room_running %> + <%= button_to t("room.join"), room_path(@room), class: "btn btn-primary btn-block px-7 start-button float-right", "data-disable": "" %> + <% else %> + <% unless exceeds_limit %> + <%= button_to t("room.start"), start_room_path(@room), class: "btn btn-primary btn-block px-7 start-button float-right", "data-disable": "" %> + <% end %> + <% end %> +
+
+ + <% if total_room_count(current_user) > 5 %> + + <% end %> + +
+ <% if current_user.role.get_permission("can_create_rooms") %> + <% current_user.ordered_rooms.each do |room| %> +
+ <%= link_to room do %> + <%= render "rooms/components/room_block", room: room %> + <% end %> +
+ <% end %> + <% end %> + + <% if shared_access_allowed %> + <% current_user.shared_rooms.each do |room| %> +
+ <%= link_to room do %> + <%= render "rooms/components/shared_room_block", room: room %> + <% end %> +
+ <% end %> + <% end %> + + <% if current_user.role.get_permission("can_create_rooms") && !room_limit_exceeded %> + <%= render "rooms/components/create_room_block"%> + <% end %> +
+
+
+ +<% unless hide_recording_tables %> + <%= render "shared/sessions", recordings: @recordings, pagy: @pagy, only_public: false, shared_room: @shared_room, user_recordings: false, title: t("room.recordings")%> +<% end %> + +<%= render "shared/modals/delete_room_modal" %> + +<%= render "shared/modals/create_room_modal" %> + +<% if preupload_allowed? %> + <%= render "shared/modals/preupload_presentation_modal" %> +<% end %> + +<% if shared_access_allowed %> + <%= render "shared/modals/share_room_modal" %> + <%= render "shared/modals/remove_access_modal" %> +<% end %> diff --git a/app/views/shared/modals/_create_room_modal.html.erb b/app/views/shared/modals/_create_room_modal.html.erb index cab6f6b4..e85d9ecb 100644 --- a/app/views/shared/modals/_create_room_modal.html.erb +++ b/app/views/shared/modals/_create_room_modal.html.erb @@ -43,6 +43,19 @@
+ <% if moderator_code_allowed? %> +
+ + + + <%= f.label :moderator_access_code, t("modal.create_room.moderator_access_code_placeholder"), id: "create-room-moderator-access-code", class: "form-control" %> + <%= f.hidden_field :moderator_access_code %> + + + +
+ <% end %> + <% mute = room_configuration("Room Configuration Mute On Join") %> <% if mute != "disabled" %>