Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,8 @@ Changes since the last non-beta release.

#### Added

- **Suppress Unused Component Warnings**: Added `suppress_unused_component_warnings` configuration option to disable console warnings about registered components that are not used on a page. This is useful for production environments where many components are registered globally but only a subset are used on each page. Set `config.suppress_unused_component_warnings = true` in your React on Rails initializer. Note: This only affects React on Rails Pro users. [PR 2136](https://github.com/shakacode/react_on_rails/pull/2136) by [justin808](https://github.com/justin808).

- **Service Dependency Checking for bin/dev**: Added optional `.dev-services.yml` configuration to validate required external services (Redis, PostgreSQL, Elasticsearch, etc.) are running before `bin/dev` starts the development server. Provides clear error messages with start commands and install hints when services are missing. Zero impact if not configured - backwards compatible with all existing installations. [PR 2098](https://github.com/shakacode/react_on_rails/pull/2098) by [justin808](https://github.com/justin808).

#### Changed
Expand Down
15 changes: 15 additions & 0 deletions docs/api-reference/configuration.md
Original file line number Diff line number Diff line change
Expand Up @@ -710,6 +710,21 @@ config.component_registry_timeout = 5000 # default (5 seconds)

Set to `0` to wait indefinitely (not recommended for production).

#### suppress_unused_component_warnings

**Type:** Boolean
**Default:** `false`

Suppress console warnings about registered components that are not used on a page:

```ruby
config.suppress_unused_component_warnings = true
```

When many React components are registered globally but only a subset are used on each page, React on Rails Pro will emit console warnings suggesting the unused components may be cleaned up. Set this option to `true` to suppress these warnings, which is useful in production environments where such warnings can be noisy.

> **Note:** This configuration option only affects React on Rails Pro users, as the warnings are generated by the Pro package's component registry timeout feature.

### I18n Configuration

These options are for applications using [react-intl](https://formatjs.io/docs/react-intl/) or similar internationalization libraries. If your application doesn't need i18n, you can skip this section.
Expand Down
15 changes: 10 additions & 5 deletions packages/react-on-rails-pro/src/CallbackRegistry.ts
Original file line number Diff line number Diff line change
Expand Up @@ -53,11 +53,16 @@ export default class CallbackRegistry<T> {
this.waitingPromises.forEach((waitingPromiseInfo, itemName) => {
waitingPromiseInfo.reject(this.createNotFoundError(itemName));
});
this.notUsedItems.forEach((itemName) => {
console.warn(
`Warning: ${this.registryType} '${itemName}' was registered but never used. This may indicate unused code that can be removed.`,
);
});

// Only log warnings if not suppressed via configuration
const suppressWarnings = getRailsContext()?.suppressUnusedComponentWarnings;
if (!suppressWarnings) {
this.notUsedItems.forEach((itemName) => {
console.warn(
`Warning: ${this.registryType} '${itemName}' was registered but never used. This may indicate unused code that can be removed.`,
);
});
}
};

onPageLoaded(() => {
Expand Down
1 change: 1 addition & 0 deletions packages/react-on-rails/src/types/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ type ReactComponent = ComponentType<any> | string;
// Keep these in sync with method lib/react_on_rails/helper.rb#rails_context
export type RailsContext = {
componentRegistryTimeout: number;
suppressUnusedComponentWarnings: boolean;
railsEnv: string;
inMailer: boolean;
i18nLocale: string;
Expand Down
4 changes: 4 additions & 0 deletions packages/react-on-rails/tests/ClientRenderer.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,7 @@ describe('ClientRenderer', () => {
httpAcceptLanguage: 'en',
serverSide: false,
componentRegistryTimeout: 0,
suppressUnusedComponentWarnings: false,
});
document.body.appendChild(railsContextElement);

Expand Down Expand Up @@ -116,6 +117,7 @@ describe('ClientRenderer', () => {
httpAcceptLanguage: 'en',
serverSide: false,
componentRegistryTimeout: 0,
suppressUnusedComponentWarnings: false,
});
document.body.appendChild(railsContextElement);

Expand Down Expand Up @@ -145,6 +147,7 @@ describe('ClientRenderer', () => {
httpAcceptLanguage: 'en',
serverSide: false,
componentRegistryTimeout: 0,
suppressUnusedComponentWarnings: false,
});
document.body.appendChild(railsContextElement);

Expand Down Expand Up @@ -195,6 +198,7 @@ describe('ClientRenderer', () => {
httpAcceptLanguage: 'en',
serverSide: false,
componentRegistryTimeout: 0,
suppressUnusedComponentWarnings: false,
});
document.body.appendChild(railsContextElement);

Expand Down
10 changes: 8 additions & 2 deletions react_on_rails/lib/react_on_rails/configuration.rb
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,10 @@ def self.configuration
# If exceeded, an error will be thrown for server-side rendered components not registered on the client.
# Set to 0 to disable the timeout and wait indefinitely for component registration.
component_registry_timeout: DEFAULT_COMPONENT_REGISTRY_TIMEOUT,
# Set to true to suppress warnings about registered components not being used on a page.
# This can be useful in production environments where many components are registered globally
# but only a subset are used on each page.
suppress_unused_component_warnings: false,
generated_component_packs_loading_strategy: nil,
server_bundle_output_path: DEFAULT_SERVER_BUNDLE_OUTPUT_PATH,
enforce_private_server_bundles: false
Expand All @@ -82,7 +86,7 @@ class Configuration
:same_bundle_for_client_and_server, :rendering_props_extension,
:make_generated_server_bundle_the_entrypoint,
:generated_component_packs_loading_strategy,
:component_registry_timeout,
:component_registry_timeout, :suppress_unused_component_warnings,
:server_bundle_output_path, :enforce_private_server_bundles

# Class instance variable and mutex to track if deprecation warning has been shown
Expand Down Expand Up @@ -144,7 +148,8 @@ def initialize(node_modules_location: nil, server_bundle_js_file: nil, prerender
i18n_dir: nil, i18n_yml_dir: nil, i18n_output_format: nil, i18n_yml_safe_load_options: nil,
random_dom_id: nil, server_render_method: nil, rendering_props_extension: nil,
components_subdirectory: nil, auto_load_bundle: nil,
component_registry_timeout: nil, server_bundle_output_path: nil, enforce_private_server_bundles: nil)
component_registry_timeout: nil, suppress_unused_component_warnings: nil,
server_bundle_output_path: nil, enforce_private_server_bundles: nil)
self.node_modules_location = node_modules_location.present? ? node_modules_location : Rails.root
self.generated_assets_dirs = generated_assets_dirs
self.generated_assets_dir = generated_assets_dir
Expand All @@ -169,6 +174,7 @@ def initialize(node_modules_location: nil, server_bundle_js_file: nil, prerender
self.skip_display_none = skip_display_none
self.rendering_props_extension = rendering_props_extension
self.component_registry_timeout = component_registry_timeout
self.suppress_unused_component_warnings = suppress_unused_component_warnings || false

# Server rendering:
self.server_bundle_js_file = server_bundle_js_file
Expand Down
1 change: 1 addition & 0 deletions react_on_rails/lib/react_on_rails/helper.rb
Original file line number Diff line number Diff line change
Expand Up @@ -274,6 +274,7 @@ def rails_context(server_side: true)
@rails_context ||= begin
result = {
componentRegistryTimeout: ReactOnRails.configuration.component_registry_timeout,
suppressUnusedComponentWarnings: ReactOnRails.configuration.suppress_unused_component_warnings,
railsEnv: Rails.env,
inMailer: in_mailer?,
# Locale settings
Expand Down
2 changes: 2 additions & 0 deletions react_on_rails/sig/react_on_rails/configuration.rbs
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@ module ReactOnRails
attr_accessor generated_component_packs_loading_strategy: Symbol?
attr_accessor immediate_hydration: bool
attr_accessor component_registry_timeout: Integer
attr_accessor suppress_unused_component_warnings: bool
attr_accessor server_bundle_output_path: String?
attr_accessor enforce_private_server_bundles: bool

Expand Down Expand Up @@ -68,6 +69,7 @@ module ReactOnRails
?auto_load_bundle: bool?,
?immediate_hydration: bool?,
?component_registry_timeout: Integer?,
?suppress_unused_component_warnings: bool?,
?server_bundle_output_path: String?,
?enforce_private_server_bundles: bool?
) -> void
Expand Down
21 changes: 21 additions & 0 deletions react_on_rails/spec/react_on_rails/configuration_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -506,6 +506,27 @@ module ReactOnRails
end
end

describe ".suppress_unused_component_warnings" do
it "defaults to false" do
ReactOnRails.configure {} # rubocop:disable Lint/EmptyBlock
expect(ReactOnRails.configuration.suppress_unused_component_warnings).to be(false)
end

it "can be set to true" do
ReactOnRails.configure do |config|
config.suppress_unused_component_warnings = true
end
expect(ReactOnRails.configuration.suppress_unused_component_warnings).to be(true)
end

it "can be set to false explicitly" do
ReactOnRails.configure do |config|
config.suppress_unused_component_warnings = false
end
expect(ReactOnRails.configuration.suppress_unused_component_warnings).to be(false)
end
end

describe "enforce_private_server_bundles validation" do
context "when enforce_private_server_bundles is true" do
before do
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -323,7 +323,7 @@ def response; end
end
let(:rails_context_tag) do
<<-SCRIPT.strip_heredoc
<script type="application/json" id="js-react-on-rails-context">{"componentRegistryTimeout":5000,"railsEnv":"test","inMailer":false,"i18nLocale":"en","i18nDefaultLocale":"en","rorVersion":"#{ReactOnRails::VERSION}","rorPro":true,"rorProVersion":"#{ReactOnRailsPro::VERSION}","rscPayloadGenerationUrlPath":"rsc_payload/","href":"http://foobar.com/development","location":"/development","scheme":"http","host":"foobar.com","port":null,"pathname":"/development","search":null,"httpAcceptLanguage":"en","somethingUseful":null,"serverSide":false}</script>
<script type="application/json" id="js-react-on-rails-context">{"componentRegistryTimeout":5000,"suppressUnusedComponentWarnings":false,"railsEnv":"test","inMailer":false,"i18nLocale":"en","i18nDefaultLocale":"en","rorVersion":"#{ReactOnRails::VERSION}","rorPro":true,"rorProVersion":"#{ReactOnRailsPro::VERSION}","rscPayloadGenerationUrlPath":"rsc_payload/","href":"http://foobar.com/development","location":"/development","scheme":"http","host":"foobar.com","port":null,"pathname":"/development","search":null,"httpAcceptLanguage":"en","somethingUseful":null,"serverSide":false}</script>
SCRIPT
end
let(:react_component_div_with_initial_chunk) do
Expand Down
Loading