From 050b8d15e733eb69b434040283d1a5fd65f08774 Mon Sep 17 00:00:00 2001 From: myronmarston-toast Date: Thu, 14 May 2026 17:43:16 -0700 Subject: [PATCH 01/14] Adopt yard-lint for structured YARD documentation linting Replaces the janky regex-based doc coverage check with yard-lint, a structured linter with per-check controls and gradual adoption support. https://github.com/block/elasticgraph/issues/913 The old `docs_coverage` task parsed YARD's text output to extract coverage % and warning/error counts. Now yard-lint handles doc quality (undocumented objects, tag validation, type checking, etc.) while the renamed `yard_warnings` task retains only YARD parser warning/error detection (e.g. "Undocumentable superclass" from Data.define) which yard-lint doesn't cover. Key details: - yard-lint is invoked via Ruby API (not CLI) so we can register custom YARD tags (@dynamic, @implements) before parsing -- YardOptions in .yard-lint.yml only affects visibility filtering, not tag registration - MinCoverage disabled because yard-lint counts all objects including private ones, which doesn't match YARD's --no-private behavior - .yard-lint-todo.yml baselines 892 existing violations for gradual fix-up across 12 validators Co-Authored-By: Claude Opus 4.6 (1M context) --- .yard-lint-todo.yml | 237 +++++++++++++++++++++++++++++++++++++++++++ .yard-lint.yml | 220 +++++++++++++++++++++++++++++++++++++++ Gemfile | 1 + Gemfile.lock | 5 + config/site/Rakefile | 64 ++++++++---- 5 files changed, 507 insertions(+), 20 deletions(-) create mode 100644 .yard-lint-todo.yml create mode 100644 .yard-lint.yml diff --git a/.yard-lint-todo.yml b/.yard-lint-todo.yml new file mode 100644 index 000000000..4b332d802 --- /dev/null +++ b/.yard-lint-todo.yml @@ -0,0 +1,237 @@ +# This file was auto-generated by yard-lint --auto-gen-config on 2026-05-15 00:38:03 UTC +# It contains exclusions for all current violations to establish a baseline. +# +# To gradually fix violations: +# 1. Remove files/patterns from the Exclude list below +# 2. Run yard-lint to see the violations for those files +# 3. Fix the violations +# 4. Commit the changes +# +# To regenerate this file, run: yard-lint --regenerate-todo + +# Documentation validators +Documentation/BlankLineBeforeDefinition: + Exclude: + - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/engine_extension.rb' + - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/entities_field_resolver.rb' + - 'elasticgraph-elasticsearch/lib/elastic_graph/elasticsearch/client.rb' + - 'elasticgraph-local/lib/elastic_graph/local/docker_runner.rb' + - 'elasticgraph-opensearch/lib/elastic_graph/opensearch/client.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/list_counts_state.rb' + - 'elasticgraph-support/lib/elastic_graph/support/from_yaml_file.rb' + +Documentation/EmptyCommentLine: + Exclude: + - 'elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb' + +Documentation/MarkdownSyntax: + Exclude: + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_reference.rb' + +Documentation/UndocumentedMethodArguments: + Exclude: + - 'elasticgraph-admin_lambda/lib/elastic_graph/admin_lambda/lambda_function.rb' + - 'elasticgraph-admin_lambda/lib/elastic_graph/admin_lambda/rake_adapter.rb' + - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/apollo_entity_ref_resolver.rb' + - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/entities_field_resolver.rb' + - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/http_endpoint_extension.rb' + - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/service_field_resolver.rb' + - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/api_extension.rb' + - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/apollo_directives.rb' + - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/factory_extension.rb' + - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/state_extension.rb' + - 'elasticgraph-elasticsearch/lib/elastic_graph/elasticsearch/client.rb' + - 'elasticgraph-graphiql/lib/elastic_graph/graphiql.rb' + - 'elasticgraph-graphql_lambda/lib/elastic_graph/graphql_lambda/graphql_endpoint.rb' + - 'elasticgraph-graphql_lambda/lib/elastic_graph/graphql_lambda/lambda_function.rb' + - 'elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda.rb' + - 'elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda/concurrency_scaler.rb' + - 'elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda/details_logger.rb' + - 'elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda/lambda_function.rb' + - 'elasticgraph-indexer_lambda/lib/elastic_graph/indexer_lambda/lambda_function.rb' + - 'elasticgraph-indexer_lambda/lib/elastic_graph/indexer_lambda/sqs_processor.rb' + - 'elasticgraph-local/lib/elastic_graph/local/docker_runner.rb' + - 'elasticgraph-local/lib/elastic_graph/local/indexing_coordinator.rb' + - 'elasticgraph-local/lib/elastic_graph/local/local_indexer.rb' + - 'elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb' + - 'elasticgraph-opensearch/lib/elastic_graph/opensearch/client.rb' + - 'elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/**/*' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/factory.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/derived_fields/field_initializer_support.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/json_schema_with_metadata.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/list_counts_mapping.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/relationship_resolver.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_factory.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_resolver.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/json_schema_pruner.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_derived_graphql_type_customizations.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_subtypes.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/implements_interfaces.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/supports_filtering_and_aggregation.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/results.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_artifact_manager.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/**/*' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/state.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/test_support.rb' + - 'elasticgraph-support/lib/elastic_graph/support/config.rb' + - 'elasticgraph-support/lib/elastic_graph/support/from_yaml_file.rb' + - 'elasticgraph-support/lib/elastic_graph/support/graphql_formatter.rb' + - 'elasticgraph-support/lib/elastic_graph/support/hash_util.rb' + - 'elasticgraph-support/lib/elastic_graph/support/logger.rb' + - 'elasticgraph-support/lib/elastic_graph/support/threading.rb' + - 'elasticgraph-support/lib/elastic_graph/support/time_set.rb' + - 'elasticgraph-support/lib/elastic_graph/support/time_util.rb' + - 'elasticgraph-support/lib/elastic_graph/support/untyped_encoder.rb' + - 'elasticgraph-warehouse/lib/elastic_graph/warehouse/schema_definition/factory_extension.rb' + - 'elasticgraph-warehouse_lambda/lib/elastic_graph/warehouse_lambda.rb' + - 'elasticgraph-warehouse_lambda/lib/elastic_graph/warehouse_lambda/lambda_function.rb' + - 'elasticgraph-warehouse_lambda/lib/elastic_graph/warehouse_lambda/warehouse_dumper.rb' + +Documentation/UndocumentedObjects: + Exclude: + - 'elasticgraph-admin_lambda/lib/elastic_graph/admin_lambda/lambda_function.rb' + - 'elasticgraph-admin_lambda/lib/elastic_graph/admin_lambda/rake_adapter.rb' + - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/apollo_entity_ref_resolver.rb' + - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/entities_field_resolver.rb' + - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/http_endpoint_extension.rb' + - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/service_field_resolver.rb' + - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/api_extension.rb' + - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/factory_extension.rb' + - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/state_extension.rb' + - 'elasticgraph-elasticsearch/lib/elastic_graph/elasticsearch/client.rb' + - 'elasticgraph-graphql_lambda/lib/elastic_graph/graphql_lambda/graphql_endpoint.rb' + - 'elasticgraph-graphql_lambda/lib/elastic_graph/graphql_lambda/lambda_function.rb' + - 'elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda.rb' + - 'elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda/concurrency_scaler.rb' + - 'elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda/details_logger.rb' + - 'elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda/lambda_function.rb' + - 'elasticgraph-indexer_lambda/lib/elastic_graph/indexer_lambda/lambda_function.rb' + - 'elasticgraph-indexer_lambda/lib/elastic_graph/indexer_lambda/sqs_processor.rb' + - 'elasticgraph-local/lib/elastic_graph/local/docker_runner.rb' + - 'elasticgraph-local/lib/elastic_graph/local/indexing_coordinator.rb' + - 'elasticgraph-local/lib/elastic_graph/local/local_indexer.rb' + - 'elasticgraph-opensearch/lib/elastic_graph/opensearch/client.rb' + - 'elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/**/*' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/factory.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/json_schema_with_metadata.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/relationship_resolver.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/rollover_config.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_factory.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_resolver.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/jruby_patches.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/json_schema_pruner.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_subtypes.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/supports_filtering_and_aggregation.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_artifact_manager.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value_namer.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enums_for_directly_queryable_types.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field_path.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/graphql_sdl_enumerator.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/input_field.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/input_type.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/list_counts_state.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/sub_aggregation_path.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_reference.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/scripting/script.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/state.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/test_support.rb' + - 'elasticgraph-support/lib/elastic_graph/errors.rb' + - 'elasticgraph-support/lib/elastic_graph/support/graphql_gem_loader.rb' + - 'elasticgraph-support/lib/elastic_graph/support/logger.rb' + - 'elasticgraph-support/lib/elastic_graph/support/time_set.rb' + - 'elasticgraph-support/lib/elastic_graph/support/time_util.rb' + - 'elasticgraph-warehouse_lambda/lib/elastic_graph/warehouse_lambda/lambda_function.rb' + - 'elasticgraph-warehouse_lambda/lib/elastic_graph/warehouse_lambda/warehouse_dumper.rb' + +Documentation/UndocumentedOptions: + Exclude: + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/namespace_type.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb' + - 'elasticgraph-support/lib/elastic_graph/support/config.rb' + - 'elasticgraph-support/lib/elastic_graph/support/graphql_formatter.rb' + +# Tags validators +Tags/CollectionType: + Exclude: + - 'elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb' + - 'elasticgraph-rack/lib/elastic_graph/rack/graphql_endpoint.rb' + - 'elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts.rb' + - 'elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/artifacts_helper_methods.rb' + - 'elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb' + - 'elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/schema.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/event_envelope.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/enum.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/object.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/scalar.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/union.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/index.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/json_schema_field_metadata.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_directives.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/rake_tasks.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/results.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/directive.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_type.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/object_type.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/relationship.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb' + - 'elasticgraph-support/lib/elastic_graph/support/config.rb' + - 'elasticgraph-support/lib/elastic_graph/support/json_schema/meta_schema_validator.rb' + - 'elasticgraph-support/lib/elastic_graph/support/json_schema/validator.rb' + - 'elasticgraph-support/lib/elastic_graph/support/json_schema/validator_factory.rb' + - 'elasticgraph-warehouse/lib/elastic_graph/warehouse/schema_definition/results_extension.rb' + +Tags/InvalidTypes: + Exclude: + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_derived_graphql_type_customizations.rb' + +Tags/OptionTags: + Exclude: + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb' + +Tags/Order: + Exclude: + - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/apollo_directives.rb' + - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/field_extension.rb' + - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/object_and_interface_extension.rb' + - 'elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb' + - 'elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/index.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_directives.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/implements_interfaces.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb' + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_with_subfields.rb' + - 'elasticgraph-support/lib/elastic_graph/support/config.rb' + - 'elasticgraph-support/lib/elastic_graph/support/json_schema/validator.rb' + +Tags/RedundantParamDescription: + Exclude: + - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/field_extension.rb' + +Tags/TagTypePosition: + Exclude: + - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb' diff --git a/.yard-lint.yml b/.yard-lint.yml new file mode 100644 index 000000000..b6276c9a4 --- /dev/null +++ b/.yard-lint.yml @@ -0,0 +1,220 @@ +# YARD-Lint Configuration +# See https://github.com/mensfeld/yard-lint for documentation + +inherit_from: .yard-lint-todo.yml + +AllValidators: + YardOptions: + - --no-private + - --tag dynamic + - --hide-tag dynamic + - --tag implements + - --hide-tag implements + - --markup markdown + - --markup-provider redcarpet + + Exclude: + - '\.git' + - 'vendor/**/*' + - 'node_modules/**/*' + - 'spec/**/*' + - 'spec_support/**/*' + - 'test/**/*' + - 'tmp/**/*' + - 'bundle/**/*' + - 'sig/**/*' + + FailOnSeverity: warning + + # yard-lint's coverage metric counts all objects including private ones, + # which doesn't match YARD's --no-private behavior. We rely on + # Documentation/UndocumentedObjects (which respects --no-private via + # YardOptions visibility filtering) to catch undocumented public objects instead. + # MinCoverage: 100.0 + +Documentation/UndocumentedObjects: + Enabled: true + Severity: warning + ExcludedMethods: + - 'initialize/0' + - '/^_/' + +Documentation/UndocumentedMethodArguments: + Enabled: true + Severity: warning + +Documentation/UndocumentedBooleanMethods: + Enabled: true + Severity: warning + +Documentation/UndocumentedOptions: + Enabled: true + Severity: warning + +Documentation/MissingReturn: + Enabled: false + +Documentation/MarkdownSyntax: + Enabled: true + Severity: warning + +Documentation/EmptyCommentLine: + Enabled: true + Severity: convention + +Documentation/BlankLineBeforeDefinition: + Enabled: true + Severity: convention + OrphanedSeverity: convention + EnabledPatterns: + SingleBlankLine: true + OrphanedDocs: true + +Tags/Order: + Enabled: true + Severity: convention + EnforcedOrder: + - param + - option + - yield + - yieldparam + - yieldreturn + - return + - raise + - see + - example + - note + - todo + +Tags/InvalidTypes: + Enabled: true + Severity: warning + ValidatedTags: + - param + - option + - return + +Tags/TypeSyntax: + Enabled: true + Severity: warning + ValidatedTags: + - param + - option + - return + - yieldreturn + +Tags/MeaninglessTag: + Enabled: true + Severity: warning + CheckedTags: + - param + - option + InvalidObjectTypes: + - class + - module + - constant + +Tags/CollectionType: + Enabled: true + Severity: convention + EnforcedStyle: long + ValidatedTags: + - param + - option + - return + - yieldreturn + +Tags/TagTypePosition: + Enabled: true + Severity: convention + CheckedTags: + - param + - option + EnforcedStyle: type_after_name + +Tags/ApiTags: + Enabled: false + +Tags/OptionTags: + Enabled: true + Severity: warning + +Tags/ExampleSyntax: + Enabled: true + Severity: warning + +Tags/ExampleStyle: + Enabled: false + +Tags/RedundantParamDescription: + Enabled: true + Severity: convention + CheckedTags: + - param + - option + Articles: + - The + - the + - A + - a + - An + - an + MaxRedundantWords: 6 + GenericTerms: + - object + - instance + - value + - data + - item + - element + EnabledPatterns: + ArticleParam: true + PossessiveParam: true + TypeRestatement: true + ParamToVerb: true + IdPattern: true + DirectionalDate: true + TypeGeneric: true + +Tags/InformalNotation: + Enabled: false + +Tags/NonAsciiType: + Enabled: true + Severity: warning + ValidatedTags: + - param + - option + - return + - yieldreturn + - yieldparam + +Tags/TagGroupSeparator: + Enabled: false + +Tags/ForbiddenTags: + Enabled: false + +Warnings/UnknownTag: + Enabled: true + Severity: error + +Warnings/UnknownDirective: + Enabled: true + Severity: error + +Warnings/InvalidTagFormat: + Enabled: true + Severity: error + +Warnings/DuplicatedParameterName: + Enabled: true + Severity: error + +Warnings/UnknownParameterName: + Enabled: true + Severity: error + +Semantic/AbstractMethods: + Enabled: true + Severity: warning diff --git a/Gemfile b/Gemfile index e4e9ca365..6df00839b 100644 --- a/Gemfile +++ b/Gemfile @@ -64,6 +64,7 @@ group :site do gem "yard", "~> 0.9", ">= 0.9.43" gem "yard-doctest", "~> 0.1", ">= 0.1.17" + gem "yard-lint", "~> 1.5" gem "yard-markdown", "~> 0.7", ">= 0.7.1" gem "irb", "~> 1.18" # Needed for yard on Ruby 4.0 end diff --git a/Gemfile.lock b/Gemfile.lock index d5960ac1f..4f43d5907 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -654,6 +654,9 @@ GEM yard-doctest (0.1.17) minitest yard + yard-lint (1.5.1) + yard (~> 0.9) + zeitwerk (~> 2.6) yard-markdown (0.7.1) csv rdoc @@ -737,6 +740,7 @@ DEPENDENCIES vcr (~> 6.4) yard (~> 0.9, >= 0.9.43) yard-doctest (~> 0.1, >= 0.1.17) + yard-lint (~> 1.5) yard-markdown (~> 0.7, >= 0.7.1) CHECKSUMS @@ -958,6 +962,7 @@ CHECKSUMS webrick (1.9.2) sha256=beb4a15fc474defed24a3bda4ffd88a490d517c9e4e6118c3edce59e45864131 yard (0.9.43) sha256=cf8733a8f0485df2a162927e9b5f182215a61f6d22de096b8f402c726a1c5821 yard-doctest (0.1.17) sha256=7cb35a75d99f58fc42ee72d3542a36e227237b621a40aebc391c95988b72847f + yard-lint (1.5.1) sha256=41d194855b4f54aa957a0337720c6f48e252e4a31d7412c46cc94a12399c0149 yard-markdown (0.7.1) sha256=06c378632dfe7ba053be9ba469eb4701aa0470e36bcf7e5546f353eb90c1bfd1 yell (2.2.2) sha256=1d166f3cc3b6dc49a59778ea7156ed6d8de794c15106d48ffd6cbb061b9b26bc zeitwerk (2.7.5) sha256=d8da92128c09ea6ec62c949011b00ed4a20242b255293dd66bf41545398f73dd diff --git a/config/site/Rakefile b/config/site/Rakefile index 22fef6f0f..839788f68 100644 --- a/config/site/Rakefile +++ b/config/site/Rakefile @@ -67,41 +67,65 @@ module ElasticGraph end end - desc "Check documentation coverage" - task :docs_coverage do + desc "Check for unexpected YARD parser warnings and errors" + task :yard_warnings do doc_output = run_yard_doc_ignoring_expected_warnings - coverage = doc_output[/([\d.]+)% documented/, 1] warning_count = doc_output.scan("[warn]:").count error_count = doc_output.scan("[error]:").count - if coverage.to_f < 100 - # Since we do not have 100% coverage, we want to list what is undocumented. - # - # Note: we don't use this as the main command above because we've observed that - # `stats` does not produce as many warnings as `doc`--so we'd rather run `doc` - # when detecting warnings, and use `stats --list-undoc` for supplemental output. - undoc_output = IO.popen(yard_cmd("stats --list-undoc")).read - - # Just print the output starting with `Undocumented Objects" - puts "\n#{undoc_output[/^Undocumented .*/m]}" - end - issues = [] - issues << "Missing documentation coverage (currently at #{coverage}%)." if coverage.to_f < 100 - issues << "YARD emitted #{warning_count} documentation warning(s)." if warning_count > 0 - issues << "YARD emitted #{error_count} documentation error(s)." if error_count > 0 + issues << "YARD emitted #{warning_count} unexpected warning(s)." if warning_count > 0 + issues << "YARD emitted #{error_count} error(s)." if error_count > 0 unless issues.empty? abort <<~EOS - Documentation has #{issues.size} issues: + YARD parser issues found: #{issues.map { |i| " - #{i}" }.join("\n")} EOS end end + desc "Lint YARD documentation for quality issues" + task :yard_lint do + require "yard-lint" + + # Register custom YARD tags so yard-lint's parser recognizes them. + # (YardOptions in .yard-lint.yml only affects visibility filtering, + # not tag registration during YARD parsing.) + ::YARD::Tags::Library.define_tag("Dynamic", :dynamic) + ::YARD::Tags::Library.define_tag("Implements", :implements) + + documented_gem_paths = DOCUMENTED_GEMS.map { |gem| "#{REPO_ROOT}/#{gem}/lib" } + config = ::Yard::Lint::Config.load || ::Yard::Lint::Config.new + result = ::Yard::Lint.run(path: documented_gem_paths, config: config, progress: $stdout.tty?) + + if result.clean? + puts "yard-lint: no offenses found" + else + stats = result.statistics + puts "Found #{result.count} offense(s):\n\n" + + result.offenses.each do |offense| + severity_symbol = case offense[:severity] + when "error" then "E" + when "warning" then "W" + when "convention" then "C" + else "?" + end + + puts "[#{severity_symbol}] #{offense[:location]}:#{offense[:location_line]}" + puts " #{offense[:name]}: #{offense[:message]}" + puts + end + + abort "yard-lint: #{result.count} offense(s) detected " \ + "(#{stats[:error]} error(s), #{stats[:warning]} warning(s), #{stats[:convention]} convention(s))" + end + end + desc "Tests all documentation examples." task :doctest do require "yard-doctest" @@ -380,7 +404,7 @@ module ElasticGraph end desc "Perform validations of the website, including doc tests and doc coverage" - task validate: [:build, :validate_no_empty_code_snippets, :docs_coverage, :doctest, :validate_page_frontmatter, :validate_html_output] + task validate: [:build, :validate_no_empty_code_snippets, :yard_warnings, :yard_lint, :doctest, :validate_page_frontmatter, :validate_html_output] task build_css: :npm_install do require "rouge" From 7636d58a01d9c114730d33a33f06cb1d406234fd Mon Sep 17 00:00:00 2001 From: myronmarston-toast Date: Thu, 14 May 2026 17:59:04 -0700 Subject: [PATCH 02/14] Filter @private-tagged objects from yard-lint offenses MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit yard-lint doesn't respect YARD's @private tag — it only checks Ruby visibility (public/private/protected). YARD's --no-private verifier checks both `obj.visibility` AND `obj.tag(:private)` (walking up ancestors), but yard-lint's QueryExecutor only does the former. This caused 614 false-positive offenses on @private classes. Fix: filter offenses in our rake task by checking the YARD registry after yard-lint runs. Regenerate .yard-lint-todo.yml with only the 278 real offenses (down from 892). Co-Authored-By: Claude Opus 4.6 (1M context) --- .yard-lint-todo.yml | 325 ++++++++++++++++++------------------------- config/site/Rakefile | 45 +++++- 2 files changed, 171 insertions(+), 199 deletions(-) diff --git a/.yard-lint-todo.yml b/.yard-lint-todo.yml index 4b332d802..0c1746744 100644 --- a/.yard-lint-todo.yml +++ b/.yard-lint-todo.yml @@ -1,237 +1,176 @@ -# This file was auto-generated by yard-lint --auto-gen-config on 2026-05-15 00:38:03 UTC -# It contains exclusions for all current violations to establish a baseline. +# This file was auto-generated on 2026-05-15 00:58:28 UTC +# It contains exclusions for current violations to establish a baseline. # # To gradually fix violations: # 1. Remove files/patterns from the Exclude list below # 2. Run yard-lint to see the violations for those files # 3. Fix the violations # 4. Commit the changes -# -# To regenerate this file, run: yard-lint --regenerate-todo # Documentation validators Documentation/BlankLineBeforeDefinition: Exclude: - - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/engine_extension.rb' - - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/entities_field_resolver.rb' - - 'elasticgraph-elasticsearch/lib/elastic_graph/elasticsearch/client.rb' - - 'elasticgraph-local/lib/elastic_graph/local/docker_runner.rb' - - 'elasticgraph-opensearch/lib/elastic_graph/opensearch/client.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/list_counts_state.rb' - - 'elasticgraph-support/lib/elastic_graph/support/from_yaml_file.rb' + - "elasticgraph-apollo/lib/elastic_graph/apollo/graphql/engine_extension.rb" + - "elasticgraph-apollo/lib/elastic_graph/apollo/graphql/entities_field_resolver.rb" + - "elasticgraph-elasticsearch/lib/elastic_graph/elasticsearch/client.rb" + - "elasticgraph-local/lib/elastic_graph/local/docker_runner.rb" + - "elasticgraph-opensearch/lib/elastic_graph/opensearch/client.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/list_counts_state.rb" + - "elasticgraph-support/lib/elastic_graph/support/from_yaml_file.rb" Documentation/EmptyCommentLine: Exclude: - - 'elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb' + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb" Documentation/MarkdownSyntax: Exclude: - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_reference.rb' + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_reference.rb" Documentation/UndocumentedMethodArguments: Exclude: - - 'elasticgraph-admin_lambda/lib/elastic_graph/admin_lambda/lambda_function.rb' - - 'elasticgraph-admin_lambda/lib/elastic_graph/admin_lambda/rake_adapter.rb' - - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/apollo_entity_ref_resolver.rb' - - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/entities_field_resolver.rb' - - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/http_endpoint_extension.rb' - - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/service_field_resolver.rb' - - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/api_extension.rb' - - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/apollo_directives.rb' - - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/factory_extension.rb' - - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/state_extension.rb' - - 'elasticgraph-elasticsearch/lib/elastic_graph/elasticsearch/client.rb' - - 'elasticgraph-graphiql/lib/elastic_graph/graphiql.rb' - - 'elasticgraph-graphql_lambda/lib/elastic_graph/graphql_lambda/graphql_endpoint.rb' - - 'elasticgraph-graphql_lambda/lib/elastic_graph/graphql_lambda/lambda_function.rb' - - 'elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda.rb' - - 'elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda/concurrency_scaler.rb' - - 'elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda/details_logger.rb' - - 'elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda/lambda_function.rb' - - 'elasticgraph-indexer_lambda/lib/elastic_graph/indexer_lambda/lambda_function.rb' - - 'elasticgraph-indexer_lambda/lib/elastic_graph/indexer_lambda/sqs_processor.rb' - - 'elasticgraph-local/lib/elastic_graph/local/docker_runner.rb' - - 'elasticgraph-local/lib/elastic_graph/local/indexing_coordinator.rb' - - 'elasticgraph-local/lib/elastic_graph/local/local_indexer.rb' - - 'elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb' - - 'elasticgraph-opensearch/lib/elastic_graph/opensearch/client.rb' - - 'elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/**/*' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/factory.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/derived_fields/field_initializer_support.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/json_schema_with_metadata.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/list_counts_mapping.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/relationship_resolver.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_factory.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_resolver.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/json_schema_pruner.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_derived_graphql_type_customizations.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_subtypes.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/implements_interfaces.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/supports_filtering_and_aggregation.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/results.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_artifact_manager.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/**/*' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/state.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/test_support.rb' - - 'elasticgraph-support/lib/elastic_graph/support/config.rb' - - 'elasticgraph-support/lib/elastic_graph/support/from_yaml_file.rb' - - 'elasticgraph-support/lib/elastic_graph/support/graphql_formatter.rb' - - 'elasticgraph-support/lib/elastic_graph/support/hash_util.rb' - - 'elasticgraph-support/lib/elastic_graph/support/logger.rb' - - 'elasticgraph-support/lib/elastic_graph/support/threading.rb' - - 'elasticgraph-support/lib/elastic_graph/support/time_set.rb' - - 'elasticgraph-support/lib/elastic_graph/support/time_util.rb' - - 'elasticgraph-support/lib/elastic_graph/support/untyped_encoder.rb' - - 'elasticgraph-warehouse/lib/elastic_graph/warehouse/schema_definition/factory_extension.rb' - - 'elasticgraph-warehouse_lambda/lib/elastic_graph/warehouse_lambda.rb' - - 'elasticgraph-warehouse_lambda/lib/elastic_graph/warehouse_lambda/lambda_function.rb' - - 'elasticgraph-warehouse_lambda/lib/elastic_graph/warehouse_lambda/warehouse_dumper.rb' + - "elasticgraph-admin_lambda/lib/elastic_graph/admin_lambda/rake_adapter.rb" + - "elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/api_extension.rb" + - "elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/apollo_directives.rb" + - "elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/state_extension.rb" + - "elasticgraph-graphiql/lib/elastic_graph/graphiql.rb" + - "elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda.rb" + - "elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/computation_detail.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/configured_graphql_resolver.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/enum.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/extension.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/graphql_extension.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/graphql_field.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/graphql_resolver.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/hash_dumper.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/index_definition.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/index_field.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/interface_verifier.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/object_type.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/params.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/relation.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/scalar_type.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/schema_element_names.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/sort_field.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/update_target.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/factory.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/derived_fields/field_initializer_support.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/list_counts_mapping.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_factory.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_resolver.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/json_schema_pruner.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_derived_graphql_type_customizations.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/implements_interfaces.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_type.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/list_counts_state.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/sub_aggregation_path.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_with_subfields.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/state.rb" + - "elasticgraph-support/lib/elastic_graph/support/config.rb" + - "elasticgraph-support/lib/elastic_graph/support/graphql_formatter.rb" + - "elasticgraph-support/lib/elastic_graph/support/hash_util.rb" + - "elasticgraph-support/lib/elastic_graph/support/logger.rb" + - "elasticgraph-support/lib/elastic_graph/support/threading.rb" + - "elasticgraph-support/lib/elastic_graph/support/time_set.rb" + - "elasticgraph-support/lib/elastic_graph/support/time_util.rb" + - "elasticgraph-support/lib/elastic_graph/support/untyped_encoder.rb" + - "elasticgraph-warehouse/lib/elastic_graph/warehouse/schema_definition/factory_extension.rb" + - "elasticgraph-warehouse_lambda/lib/elastic_graph/warehouse_lambda.rb" Documentation/UndocumentedObjects: Exclude: - - 'elasticgraph-admin_lambda/lib/elastic_graph/admin_lambda/lambda_function.rb' - - 'elasticgraph-admin_lambda/lib/elastic_graph/admin_lambda/rake_adapter.rb' - - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/apollo_entity_ref_resolver.rb' - - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/entities_field_resolver.rb' - - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/http_endpoint_extension.rb' - - 'elasticgraph-apollo/lib/elastic_graph/apollo/graphql/service_field_resolver.rb' - - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/api_extension.rb' - - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/factory_extension.rb' - - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/state_extension.rb' - - 'elasticgraph-elasticsearch/lib/elastic_graph/elasticsearch/client.rb' - - 'elasticgraph-graphql_lambda/lib/elastic_graph/graphql_lambda/graphql_endpoint.rb' - - 'elasticgraph-graphql_lambda/lib/elastic_graph/graphql_lambda/lambda_function.rb' - - 'elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda.rb' - - 'elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda/concurrency_scaler.rb' - - 'elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda/details_logger.rb' - - 'elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda/lambda_function.rb' - - 'elasticgraph-indexer_lambda/lib/elastic_graph/indexer_lambda/lambda_function.rb' - - 'elasticgraph-indexer_lambda/lib/elastic_graph/indexer_lambda/sqs_processor.rb' - - 'elasticgraph-local/lib/elastic_graph/local/docker_runner.rb' - - 'elasticgraph-local/lib/elastic_graph/local/indexing_coordinator.rb' - - 'elasticgraph-local/lib/elastic_graph/local/local_indexer.rb' - - 'elasticgraph-opensearch/lib/elastic_graph/opensearch/client.rb' - - 'elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/**/*' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/factory.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/json_schema_with_metadata.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/relationship_resolver.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/rollover_config.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_factory.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_resolver.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/jruby_patches.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/json_schema_pruner.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_subtypes.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/supports_filtering_and_aggregation.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_artifact_manager.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value_namer.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enums_for_directly_queryable_types.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field_path.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/graphql_sdl_enumerator.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/input_field.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/input_type.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/list_counts_state.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/sub_aggregation_path.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_reference.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/scripting/script.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/state.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/test_support.rb' - - 'elasticgraph-support/lib/elastic_graph/errors.rb' - - 'elasticgraph-support/lib/elastic_graph/support/graphql_gem_loader.rb' - - 'elasticgraph-support/lib/elastic_graph/support/logger.rb' - - 'elasticgraph-support/lib/elastic_graph/support/time_set.rb' - - 'elasticgraph-support/lib/elastic_graph/support/time_util.rb' - - 'elasticgraph-warehouse_lambda/lib/elastic_graph/warehouse_lambda/lambda_function.rb' - - 'elasticgraph-warehouse_lambda/lib/elastic_graph/warehouse_lambda/warehouse_dumper.rb' + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb" Documentation/UndocumentedOptions: Exclude: - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/namespace_type.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb' - - 'elasticgraph-support/lib/elastic_graph/support/config.rb' - - 'elasticgraph-support/lib/elastic_graph/support/graphql_formatter.rb' + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/namespace_type.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb" + - "elasticgraph-support/lib/elastic_graph/support/config.rb" + - "elasticgraph-support/lib/elastic_graph/support/graphql_formatter.rb" # Tags validators Tags/CollectionType: Exclude: - - 'elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb' - - 'elasticgraph-rack/lib/elastic_graph/rack/graphql_endpoint.rb' - - 'elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts.rb' - - 'elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/artifacts_helper_methods.rb' - - 'elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb' - - 'elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/schema.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/event_envelope.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/enum.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/object.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/scalar.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/union.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/index.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/json_schema_field_metadata.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_directives.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/rake_tasks.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/results.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/directive.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_type.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/object_type.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/relationship.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb' - - 'elasticgraph-support/lib/elastic_graph/support/config.rb' - - 'elasticgraph-support/lib/elastic_graph/support/json_schema/meta_schema_validator.rb' - - 'elasticgraph-support/lib/elastic_graph/support/json_schema/validator.rb' - - 'elasticgraph-support/lib/elastic_graph/support/json_schema/validator_factory.rb' - - 'elasticgraph-warehouse/lib/elastic_graph/warehouse/schema_definition/results_extension.rb' + - "elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb" + - "elasticgraph-rack/lib/elastic_graph/rack/graphql_endpoint.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/artifacts_helper_methods.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/schema.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/event_envelope.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/enum.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/object.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/scalar.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/union.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/index.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/json_schema_field_metadata.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_directives.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/rake_tasks.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/results.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/directive.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_type.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/object_type.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/relationship.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb" + - "elasticgraph-support/lib/elastic_graph/support/config.rb" + - "elasticgraph-support/lib/elastic_graph/support/json_schema/meta_schema_validator.rb" + - "elasticgraph-support/lib/elastic_graph/support/json_schema/validator.rb" + - "elasticgraph-support/lib/elastic_graph/support/json_schema/validator_factory.rb" + - "elasticgraph-warehouse/lib/elastic_graph/warehouse/schema_definition/results_extension.rb" Tags/InvalidTypes: Exclude: - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_derived_graphql_type_customizations.rb' + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_derived_graphql_type_customizations.rb" Tags/OptionTags: Exclude: - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb' + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb" Tags/Order: Exclude: - - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/apollo_directives.rb' - - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/field_extension.rb' - - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/object_and_interface_extension.rb' - - 'elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb' - - 'elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/index.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_directives.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/implements_interfaces.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb' - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_with_subfields.rb' - - 'elasticgraph-support/lib/elastic_graph/support/config.rb' - - 'elasticgraph-support/lib/elastic_graph/support/json_schema/validator.rb' + - "elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/apollo_directives.rb" + - "elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/field_extension.rb" + - "elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/object_and_interface_extension.rb" + - "elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb" + - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/index.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_directives.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/implements_interfaces.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb" + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_with_subfields.rb" + - "elasticgraph-support/lib/elastic_graph/support/config.rb" + - "elasticgraph-support/lib/elastic_graph/support/json_schema/validator.rb" Tags/RedundantParamDescription: Exclude: - - 'elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/field_extension.rb' + - "elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/field_extension.rb" Tags/TagTypePosition: Exclude: - - 'elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb' + - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb" diff --git a/config/site/Rakefile b/config/site/Rakefile index 839788f68..ad9fbe66b 100644 --- a/config/site/Rakefile +++ b/config/site/Rakefile @@ -102,13 +102,19 @@ module ElasticGraph config = ::Yard::Lint::Config.load || ::Yard::Lint::Config.new result = ::Yard::Lint.run(path: documented_gem_paths, config: config, progress: $stdout.tty?) - if result.clean? + # yard-lint doesn't filter objects tagged with YARD's @private tag the + # way `yard doc --no-private` does. YARD keeps @private objects in the + # registry and only hides them at output time, but yard-lint checks + # Ruby-level visibility (public/private/protected) without also checking + # the @private tag. We filter those offenses out here. + offenses = result.offenses.reject { |offense| yard_lint_offense_private?(offense) } + + if offenses.empty? puts "yard-lint: no offenses found" else - stats = result.statistics - puts "Found #{result.count} offense(s):\n\n" + puts "Found #{offenses.size} offense(s):\n\n" - result.offenses.each do |offense| + offenses.each do |offense| severity_symbol = case offense[:severity] when "error" then "E" when "warning" then "W" @@ -121,8 +127,11 @@ module ElasticGraph puts end - abort "yard-lint: #{result.count} offense(s) detected " \ - "(#{stats[:error]} error(s), #{stats[:warning]} warning(s), #{stats[:convention]} convention(s))" + by_severity = offenses.group_by { |o| o[:severity] } + abort "yard-lint: #{offenses.size} offense(s) detected " \ + "(#{(by_severity["error"] || []).size} error(s), " \ + "#{(by_severity["warning"] || []).size} warning(s), " \ + "#{(by_severity["convention"] || []).size} convention(s))" end end @@ -671,6 +680,30 @@ module ElasticGraph "cd #{REPO_ROOT} && bundle exec yard #{subcmd} #{yard_opts}" end + # Extracts a YARD registry path from a yard-lint offense and checks if it + # (or any ancestor) has the @private tag. Different offense types store the + # path in different fields. + def yard_lint_offense_private?(offense) + yard_path = offense[:element] # UndocumentedObject, BlankLineBeforeDefinition, etc. + yard_path ||= begin + path = offense[:class_name] + path = "#{path}##{offense[:method_name]}" if path && offense[:method_name] + path + end + yard_path && yard_private?(yard_path) + end + + # Checks if the YARD object at the given path (or any ancestor) has the @private tag. + # Mirrors YARD's --no-private verifier logic. + def yard_private?(yard_path) + obj = ::YARD::Registry.at(yard_path) + while obj + return true if obj.has_tag?(:private) + obj = obj.respond_to?(:parent) ? obj.parent : nil + end + false + end + private def stage_markdown_files From 8831323fb9f3baad480959451a83ff7390c34c04 Mon Sep 17 00:00:00 2001 From: myronmarston-toast Date: Thu, 14 May 2026 18:02:03 -0700 Subject: [PATCH 03/14] Fix EmptyCommentLine yard-lint offense Remove empty trailing comment line in doc block for FromDisk#graphql_schema_string. Co-Authored-By: Claude Opus 4.6 (1M context) --- .yard-lint-todo.yml | 4 ---- .../lib/elastic_graph/schema_artifacts/from_disk.rb | 1 - 2 files changed, 5 deletions(-) diff --git a/.yard-lint-todo.yml b/.yard-lint-todo.yml index 0c1746744..b90fc3876 100644 --- a/.yard-lint-todo.yml +++ b/.yard-lint-todo.yml @@ -18,10 +18,6 @@ Documentation/BlankLineBeforeDefinition: - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/list_counts_state.rb" - "elasticgraph-support/lib/elastic_graph/support/from_yaml_file.rb" -Documentation/EmptyCommentLine: - Exclude: - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb" - Documentation/MarkdownSyntax: Exclude: - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_reference.rb" diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb index 742c80503..ac5fb7866 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb @@ -38,7 +38,6 @@ class FromDisk < Support::MemoizableData.define(:artifacts_dir) # @example Print the GraphQL schema string # artifacts = ElasticGraph::SchemaArtifacts::FromDisk.new(schema_artifacts_dir) # puts artifacts.graphql_schema_string - # def graphql_schema_string @graphql_schema_string ||= read_artifact(GRAPHQL_SCHEMA_FILE) end From 559c06b7e082cb23257b85c52911de470336ebfc Mon Sep 17 00:00:00 2001 From: myronmarston-toast Date: Thu, 14 May 2026 18:02:38 -0700 Subject: [PATCH 04/14] Fix MarkdownSyntax yard-lint offense Close unclosed backtick in TypeReference#as_static_derived_type doc. Co-Authored-By: Claude Opus 4.6 (1M context) --- .yard-lint-todo.yml | 4 ---- .../schema_definition/schema_elements/type_reference.rb | 2 +- 2 files changed, 1 insertion(+), 5 deletions(-) diff --git a/.yard-lint-todo.yml b/.yard-lint-todo.yml index b90fc3876..c4e210962 100644 --- a/.yard-lint-todo.yml +++ b/.yard-lint-todo.yml @@ -18,10 +18,6 @@ Documentation/BlankLineBeforeDefinition: - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/list_counts_state.rb" - "elasticgraph-support/lib/elastic_graph/support/from_yaml_file.rb" -Documentation/MarkdownSyntax: - Exclude: - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_reference.rb" - Documentation/UndocumentedMethodArguments: Exclude: - "elasticgraph-admin_lambda/lib/elastic_graph/admin_lambda/rake_adapter.rb" diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_reference.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_reference.rb index 483d296bf..9958ad887 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_reference.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_reference.rb @@ -216,7 +216,7 @@ def to_final_form(as_input: false) renamed_with_same_wrappings(inner_name) end - # Builds a `TypeReference` for a statically named derived type for the given `category. + # Builds a `TypeReference` for a statically named derived type for the given `category`. # # In addition, a dynamic method `as_[category]` is also provided (defined further below). def as_static_derived_type(category) From a3526ddbae900b7faf9903850c14be73d40b6847 Mon Sep 17 00:00:00 2001 From: myronmarston-toast Date: Thu, 14 May 2026 18:03:16 -0700 Subject: [PATCH 05/14] Fix TagTypePosition yard-lint offense Move type annotation after param name per YARD convention: `@param updates [Hash{Symbol => Object}]` instead of `@param [Hash] updates`. Co-Authored-By: Claude Opus 4.6 (1M context) --- .yard-lint-todo.yml | 4 ---- .../schema_definition/schema_elements/enum_value.rb | 2 +- 2 files changed, 1 insertion(+), 5 deletions(-) diff --git a/.yard-lint-todo.yml b/.yard-lint-todo.yml index c4e210962..2b8de98b6 100644 --- a/.yard-lint-todo.yml +++ b/.yard-lint-todo.yml @@ -116,7 +116,6 @@ Tags/CollectionType: - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/results.rb" - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/directive.rb" - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_type.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb" - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb" - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/object_type.rb" - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/relationship.rb" @@ -163,6 +162,3 @@ Tags/RedundantParamDescription: Exclude: - "elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/field_extension.rb" -Tags/TagTypePosition: - Exclude: - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb" diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb index 43865f7fb..5e171d0a9 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb @@ -60,7 +60,7 @@ def duplicate_on(other_enum_type) # Updates the runtime metadata. # - # @param [Hash] updates to apply to the runtime metadata + # @param updates [Hash{Symbol => Object}] to apply to the runtime metadata # @return [void] def update_runtime_metadata(**updates) self.runtime_metadata = runtime_metadata.with(**updates) From 223638b92538a7309dad0dce5683ec67d7e18c50 Mon Sep 17 00:00:00 2001 From: myronmarston-toast Date: Thu, 14 May 2026 18:03:47 -0700 Subject: [PATCH 06/14] Fix RedundantParamDescription yard-lint offense Replace generic "element to check" param description with a more specific one describing what kinds of schema elements are expected. Co-Authored-By: Claude Opus 4.6 (1M context) --- .yard-lint-todo.yml | 4 ---- .../elastic_graph/apollo/schema_definition/field_extension.rb | 2 +- 2 files changed, 1 insertion(+), 5 deletions(-) diff --git a/.yard-lint-todo.yml b/.yard-lint-todo.yml index 2b8de98b6..cbbdf2957 100644 --- a/.yard-lint-todo.yml +++ b/.yard-lint-todo.yml @@ -158,7 +158,3 @@ Tags/Order: - "elasticgraph-support/lib/elastic_graph/support/config.rb" - "elasticgraph-support/lib/elastic_graph/support/json_schema/validator.rb" -Tags/RedundantParamDescription: - Exclude: - - "elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/field_extension.rb" - diff --git a/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/field_extension.rb b/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/field_extension.rb index e59ee5843..ba6ea09eb 100644 --- a/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/field_extension.rb +++ b/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/field_extension.rb @@ -64,7 +64,7 @@ def tag_with(tag_name) # Helper method that indicates if the given schema element has a specific tag. # - # @param element [Object] element to check + # @param element [Object] a schema type, field, or enum value that may have Apollo directives # @param tag_name [String] tag to check # @return [Boolean] def self.tagged_with?(element, tag_name) From 5b8fc2deb9c00d0d6526d2b54347bd5e48f5dcae Mon Sep 17 00:00:00 2001 From: myronmarston-toast Date: Thu, 14 May 2026 18:04:40 -0700 Subject: [PATCH 07/14] Fix UndocumentedObjects yard-lint offenses Add docs for Field#highlightable? and Indexing::Field#nullable?. Co-Authored-By: Claude Opus 4.6 (1M context) --- .yard-lint-todo.yml | 5 ----- .../lib/elastic_graph/schema_definition/indexing/field.rb | 3 +++ .../elastic_graph/schema_definition/schema_elements/field.rb | 3 +++ 3 files changed, 6 insertions(+), 5 deletions(-) diff --git a/.yard-lint-todo.yml b/.yard-lint-todo.yml index cbbdf2957..b8ecb8d45 100644 --- a/.yard-lint-todo.yml +++ b/.yard-lint-todo.yml @@ -73,11 +73,6 @@ Documentation/UndocumentedMethodArguments: - "elasticgraph-warehouse/lib/elastic_graph/warehouse/schema_definition/factory_extension.rb" - "elasticgraph-warehouse_lambda/lib/elastic_graph/warehouse_lambda.rb" -Documentation/UndocumentedObjects: - Exclude: - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb" - Documentation/UndocumentedOptions: Exclude: - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb" diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field.rb index 5b0c0db1c..51cf47b32 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field.rb @@ -108,6 +108,9 @@ def self.normalized_mapping_hash_for(fields) mapping_hash end + # Indicates if this field allows null values in the JSON schema. + # + # @return [Boolean] def nullable? json_schema_layers.include?(:nullable) end diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb index 3d66eeb62..8dd38c6d9 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb @@ -750,6 +750,9 @@ def sub_aggregatable? # @private HIGHLIGHTABLE_MAPPING_TYPES = %w[keyword text match_only_text] + # Indicates if this field supports highlighting in search results. + # + # @return [Boolean] def highlightable? return highlightable unless highlightable.nil? return false if relationship From 0e6b6441ae74c85f3f1963ade2869037f964ff10 Mon Sep 17 00:00:00 2001 From: myronmarston-toast Date: Thu, 14 May 2026 18:05:52 -0700 Subject: [PATCH 08/14] Fix InvalidTypes yard-lint offenses MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - `[bool]` → `[Boolean]` (YARD type, not Ruby keyword) - `Array` → `Array, :all` (Array takes one type param; `:all` is an alternate value, not a second type param) Co-Authored-By: Claude Opus 4.6 (1M context) --- .yard-lint-todo.yml | 5 ----- .../lib/elastic_graph/schema_definition/api.rb | 8 ++++---- .../mixins/has_derived_graphql_type_customizations.rb | 2 +- 3 files changed, 5 insertions(+), 10 deletions(-) diff --git a/.yard-lint-todo.yml b/.yard-lint-todo.yml index b8ecb8d45..5fc038574 100644 --- a/.yard-lint-todo.yml +++ b/.yard-lint-todo.yml @@ -122,11 +122,6 @@ Tags/CollectionType: - "elasticgraph-support/lib/elastic_graph/support/json_schema/validator_factory.rb" - "elasticgraph-warehouse/lib/elastic_graph/warehouse/schema_definition/results_extension.rb" -Tags/InvalidTypes: - Exclude: - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_derived_graphql_type_customizations.rb" - Tags/OptionTags: Exclude: - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb" diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb index 567cd1722..6762b468f 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb @@ -346,9 +346,9 @@ def register_graphql_extension(extension_module, defined_at:, **config) # @param name [Symbol] unique name of the resolver # @param klass [Class] resolver class # @param defined_at [String] the `require` path of the resolver - # @param built_in [bool] Whether this resolver is built-in to ElasticGraph or one of its extensions. + # @param built_in [Boolean] Whether this resolver is built-in to ElasticGraph or one of its extensions. # Built-in resolvers that are unused in a schema will not trigger a warning. - # @param resolver_config [Hash] configuration options for the resolver, to support parameterized resolvers + # @param resolver_config [Hash{Symbol => Object}] configuration options for the resolver, to support parameterized resolvers # @return [void] # @see Mixins::HasIndices#resolve_fields_with # @see SchemaElements::Field#resolve_with @@ -480,8 +480,8 @@ def json_schema_version(version) # publisher (but they can be nullable) and will ignore extra fields that are not defined in the schema. Use this method to # configure this behavior. # - # @param allow_omitted_fields [bool] Whether nullable fields can be omitted from indexing events. - # @param allow_extra_fields [bool] Whether extra fields (e.g. beyond fields defined in the schema) can be included in indexing events. + # @param allow_omitted_fields [Boolean] Whether nullable fields can be omitted from indexing events. + # @param allow_extra_fields [Boolean] Whether extra fields (e.g. beyond fields defined in the schema) can be included in indexing events. # @return [void] # # @note If you allow both omitted fields and extra fields, ElasticGraph's JSON schema validation will allow (and ignore) misspelled diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_derived_graphql_type_customizations.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_derived_graphql_type_customizations.rb index 5332dc3a3..34b42ae0f 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_derived_graphql_type_customizations.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_derived_graphql_type_customizations.rb @@ -17,7 +17,7 @@ module HasDerivedGraphQLTypeCustomizations # Registers a customization block for the named derived graphql types. The provided block will get run on the named derived GraphQL # types, allowing them to be customized. # - # @param type_names [Array] names of the derived types to customize, or `:all` to customize all derived types + # @param type_names [Array, :all] names of the derived types to customize, or `:all` to customize all derived types # @return [void] # # @example Customize named derived GraphQL types From a1828deba9085634fa93736f6338be706c6d4cb4 Mon Sep 17 00:00:00 2001 From: myronmarston-toast Date: Thu, 14 May 2026 18:09:01 -0700 Subject: [PATCH 09/14] Fix BlankLineBeforeDefinition yard-lint offenses Remove blank lines between doc comments and their definitions in 5 files. The elasticsearch/opensearch client files remain excluded because their offenses are section header comments (`# Cluster APIs`, etc.) that yard-lint misidentifies as orphaned documentation. Co-Authored-By: Claude Opus 4.6 (1M context) --- .yard-lint-todo.yml | 5 ----- .../lib/elastic_graph/apollo/graphql/engine_extension.rb | 1 - .../elastic_graph/apollo/graphql/entities_field_resolver.rb | 1 - elasticgraph-local/lib/elastic_graph/local/docker_runner.rb | 1 - .../schema_definition/schema_elements/list_counts_state.rb | 1 - .../lib/elastic_graph/support/from_yaml_file.rb | 1 - 6 files changed, 10 deletions(-) diff --git a/.yard-lint-todo.yml b/.yard-lint-todo.yml index 5fc038574..29005b05d 100644 --- a/.yard-lint-todo.yml +++ b/.yard-lint-todo.yml @@ -10,13 +10,8 @@ # Documentation validators Documentation/BlankLineBeforeDefinition: Exclude: - - "elasticgraph-apollo/lib/elastic_graph/apollo/graphql/engine_extension.rb" - - "elasticgraph-apollo/lib/elastic_graph/apollo/graphql/entities_field_resolver.rb" - "elasticgraph-elasticsearch/lib/elastic_graph/elasticsearch/client.rb" - - "elasticgraph-local/lib/elastic_graph/local/docker_runner.rb" - "elasticgraph-opensearch/lib/elastic_graph/opensearch/client.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/list_counts_state.rb" - - "elasticgraph-support/lib/elastic_graph/support/from_yaml_file.rb" Documentation/UndocumentedMethodArguments: Exclude: diff --git a/elasticgraph-apollo/lib/elastic_graph/apollo/graphql/engine_extension.rb b/elasticgraph-apollo/lib/elastic_graph/apollo/graphql/engine_extension.rb index e798195c1..8bad79226 100644 --- a/elasticgraph-apollo/lib/elastic_graph/apollo/graphql/engine_extension.rb +++ b/elasticgraph-apollo/lib/elastic_graph/apollo/graphql/engine_extension.rb @@ -5,7 +5,6 @@ # https://opensource.org/licenses/MIT. # # frozen_string_literal: true - module ElasticGraph module Apollo # Namespace for all Apollo GraphQL engine logic. diff --git a/elasticgraph-apollo/lib/elastic_graph/apollo/graphql/entities_field_resolver.rb b/elasticgraph-apollo/lib/elastic_graph/apollo/graphql/entities_field_resolver.rb index 83a480942..5c7b629bc 100644 --- a/elasticgraph-apollo/lib/elastic_graph/apollo/graphql/entities_field_resolver.rb +++ b/elasticgraph-apollo/lib/elastic_graph/apollo/graphql/entities_field_resolver.rb @@ -303,7 +303,6 @@ def index_search_hits(response) nil end # :nocov: - def identify_matching_hit(indexed_search_hits, representation, context:, index:) representation.representation_hash end diff --git a/elasticgraph-local/lib/elastic_graph/local/docker_runner.rb b/elasticgraph-local/lib/elastic_graph/local/docker_runner.rb index fc49ae5b3..6c1d902f6 100644 --- a/elasticgraph-local/lib/elastic_graph/local/docker_runner.rb +++ b/elasticgraph-local/lib/elastic_graph/local/docker_runner.rb @@ -32,7 +32,6 @@ def boot end end # :nocov: - def halt prepare_docker_compose_run "down --volumes" do |command| system(command) diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/list_counts_state.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/list_counts_state.rb index dc506d4e5..c22104889 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/list_counts_state.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/list_counts_state.rb @@ -19,7 +19,6 @@ class ListCountsState < ::Data.define( :path_from_list_counts ) # @dynamic path_to_list_counts, path_from_list_counts, with - def self.new_list_counts_field(at:) new(path_to_list_counts: at, path_from_list_counts: "") end diff --git a/elasticgraph-support/lib/elastic_graph/support/from_yaml_file.rb b/elasticgraph-support/lib/elastic_graph/support/from_yaml_file.rb index e190d854b..3473bb4fd 100644 --- a/elasticgraph-support/lib/elastic_graph/support/from_yaml_file.rb +++ b/elasticgraph-support/lib/elastic_graph/support/from_yaml_file.rb @@ -35,7 +35,6 @@ def from_yaml_file(yaml_file, datastore_client_customization_block: nil) # so that it happens lazily. class ForRakeTasks < ::Module # @dynamic from_yaml_file - def initialize(component_class) define_method :from_yaml_file do |yaml_file, *args, **options| __skip__ = new(*args, **options) do From 8aaa9cfc59888740526237e3ee235868c6d962be Mon Sep 17 00:00:00 2001 From: myronmarston-toast Date: Thu, 14 May 2026 18:14:43 -0700 Subject: [PATCH 10/14] Fix OptionTags yard-lint offenses Add @option tags for methods that accept keyword options: - HasTypeInfo#mapping: document all CUSTOMIZABLE_DATASTORE_PARAMS - HasTypeInfo#json_schema: document common JSON schema keywords - Field#json_schema: document :nullable option - Field#mapping, ScalarType#mapping: note forwarding to HasTypeInfo - HasIndices#initialize: note forwarding to super Co-Authored-By: Claude Opus 4.6 (1M context) --- .yard-lint-todo.yml | 7 ------ .../schema_definition/mixins/has_indices.rb | 2 ++ .../schema_definition/mixins/has_type_info.rb | 23 ++++++++++++++++++- .../schema_elements/field.rb | 5 ++++ .../schema_elements/scalar_type.rb | 2 ++ 5 files changed, 31 insertions(+), 8 deletions(-) diff --git a/.yard-lint-todo.yml b/.yard-lint-todo.yml index 29005b05d..a2e12e373 100644 --- a/.yard-lint-todo.yml +++ b/.yard-lint-todo.yml @@ -117,13 +117,6 @@ Tags/CollectionType: - "elasticgraph-support/lib/elastic_graph/support/json_schema/validator_factory.rb" - "elasticgraph-warehouse/lib/elastic_graph/warehouse/schema_definition/results_extension.rb" -Tags/OptionTags: - Exclude: - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb" - Tags/Order: Exclude: - "elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/apollo_directives.rb" diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb index be07ebc66..0445db4fe 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb @@ -30,6 +30,8 @@ module HasIndices # @dynamic default_graphql_resolver # @private + # @param options [Hash] forwarded to the including class's `initialize` + # @option options [Object] :** all keyword arguments are passed through to `super` def initialize(*args, **options) super(*args, **options) initialize_has_indices { yield self } diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb index 454093ff6..16d058a00 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb @@ -64,6 +64,17 @@ def json_schema_options # [geo_point type](https://www.elastic.co/guide/en/elasticsearch/reference/7.10/geo-point.html). # # @param options [Hash] mapping options--must be limited to {CUSTOMIZABLE_DATASTORE_PARAMS} + # @option options [String] :type mapping field type (e.g. `"keyword"`, `"text"`, `"integer"`) + # @option options [String] :analyzer analyzer to use for `text` fields + # @option options [Boolean] :eager_global_ordinals whether to eagerly load global ordinals + # @option options [Boolean] :enabled whether the field is enabled for indexing + # @option options [Hash] :fields multi-field mappings + # @option options [String] :format date format string + # @option options [Boolean] :index whether the field value should be indexed + # @option options [Hash] :meta arbitrary metadata attached to the field mapping + # @option options [Boolean] :norms whether field-length normalization is enabled + # @option options [Object] :null_value value to substitute for `null` at index time + # @option options [String] :search_analyzer analyzer to use at search time (overrides `:analyzer`) # @return [void] # # @example Define the mapping of a custom scalar type @@ -135,7 +146,17 @@ def mapping(**options) # validations than the source system itself has. We recommend limiting your JSON schema validations to situations where # violations would prevent ElasticGraph from operating correctly. # - # @param options [Hash] JSON schema options + # @param options [Hash] JSON schema options. Any + # [JSON schema validation keyword](https://json-schema.org/understanding-json-schema/reference) is accepted. + # In addition, `nullable: false` is supported to disallow `null` values. Common options are shown below. + # @option options [String] :type JSON type (e.g. `"string"`, `"integer"`, `"number"`) + # @option options [String] :format format hint (e.g. `"date-time"`, `"uri"`) + # @option options [String] :pattern regex pattern for string validation + # @option options [Integer] :maxLength maximum string length + # @option options [Integer] :minLength minimum string length + # @option options [Numeric] :minimum minimum numeric value + # @option options [Numeric] :maximum maximum numeric value + # @option options [Array] :enum allowed values # @return [void] # # @example Define the JSON schema validations of a custom scalar type diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb index 8dd38c6d9..a1214ed98 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb @@ -469,6 +469,10 @@ def on_each_generated_schema_element(&customization_block) end # (see Mixins::HasTypeInfo#json_schema) + # @param options [Hash] JSON schema options forwarded to {Mixins::HasTypeInfo#json_schema} + # @option options [Boolean] :nullable when `false`, disallows `null` values in JSON schema + # without changing the GraphQL nullability of the field. `true` is not allowed--use a + # nullable GraphQL type (no `!` suffix) instead. def json_schema(nullable: nil, **options) if options.key?(:type) raise Errors::SchemaError, "Cannot override JSON schema type of field `#{name}` with `#{options.fetch(:type)}`" @@ -485,6 +489,7 @@ def json_schema(nullable: nil, **options) end # (see Mixins::HasTypeInfo#mapping) + # @param options [Hash] mapping options forwarded to {Mixins::HasTypeInfo#mapping} def mapping(**options) # ElasticGraph has special handling for the nested type (e.g. we generate sub-aggregation types in the GraphQL schema for # nested fields), and that special handling requires that `nested` only be used on list-of-objects fields; otherwise diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb index 8e2703cd2..ecac092d3 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb @@ -98,6 +98,8 @@ def name end # (see Mixins::HasTypeInfo#mapping) + # @param options [Hash] mapping options forwarded to {Mixins::HasTypeInfo#mapping}. + # Must include `:type` for scalar types. def mapping(**options) self.mapping_type = options.fetch(:type) do raise Errors::SchemaError, "Must specify a mapping `type:` on custom scalars but was missing on the `#{name}` type." From 13ef61f8d8b7682887c61e58a1bd9203e95e4f88 Mon Sep 17 00:00:00 2001 From: myronmarston-toast Date: Thu, 14 May 2026 18:26:13 -0700 Subject: [PATCH 11/14] Fix Tags/Order yard-lint offenses MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reorder YARD tags to match enforced order: param, option, yield, yieldparam, yieldreturn, return, raise, see, example, note, todo. The most common fix was moving @note after @example — most methods had @note before @example. Also removed redundant @param/@option tags on methods using `(see ...)` cross-references, since those inherit all tags from the referenced method. Co-Authored-By: Claude Opus 4.6 (1M context) --- .yard-lint-todo.yml | 19 ------ .../schema_definition/apollo_directives.rb | 5 +- .../schema_definition/field_extension.rb | 5 +- .../object_and_interface_extension.rb | 14 +++-- .../lib/elastic_graph/local/rake_tasks.rb | 34 +++++------ .../schema_artifacts/from_disk.rb | 10 ++-- .../elastic_graph/schema_definition/api.rb | 42 ++++++------- .../schema_definition/indexing/index.rb | 36 +++++------ .../mixins/has_directives.rb | 6 +- .../schema_definition/mixins/has_indices.rb | 14 ++--- .../schema_definition/mixins/has_type_info.rb | 14 ++--- .../mixins/implements_interfaces.rb | 8 +-- .../schema_elements/field.rb | 59 +++++++++---------- .../schema_elements/scalar_type.rb | 18 +++--- .../schema_elements/type_with_subfields.rb | 50 ++++++++-------- .../lib/elastic_graph/support/config.rb | 2 +- .../support/json_schema/validator.rb | 5 +- 17 files changed, 157 insertions(+), 184 deletions(-) diff --git a/.yard-lint-todo.yml b/.yard-lint-todo.yml index a2e12e373..8a7556e2c 100644 --- a/.yard-lint-todo.yml +++ b/.yard-lint-todo.yml @@ -117,22 +117,3 @@ Tags/CollectionType: - "elasticgraph-support/lib/elastic_graph/support/json_schema/validator_factory.rb" - "elasticgraph-warehouse/lib/elastic_graph/warehouse/schema_definition/results_extension.rb" -Tags/Order: - Exclude: - - "elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/apollo_directives.rb" - - "elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/field_extension.rb" - - "elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/object_and_interface_extension.rb" - - "elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/index.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_directives.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/implements_interfaces.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_with_subfields.rb" - - "elasticgraph-support/lib/elastic_graph/support/config.rb" - - "elasticgraph-support/lib/elastic_graph/support/json_schema/validator.rb" - diff --git a/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/apollo_directives.rb b/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/apollo_directives.rb index 7fb988dd5..37268e7c2 100644 --- a/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/apollo_directives.rb +++ b/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/apollo_directives.rb @@ -267,6 +267,8 @@ module Tag # to the schema element. # # @return [void] + # @see APIExtension#tag_built_in_types_with + # @see FieldExtension#tag_with # # @example Add `@tag` to a type # ElasticGraph.define_schema do |schema| @@ -274,9 +276,6 @@ module Tag # t.apollo_tag name: "public" # end # end - # - # @see APIExtension#tag_built_in_types_with - # @see FieldExtension#tag_with def apollo_tag(name:) directive "tag", name: name end diff --git a/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/field_extension.rb b/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/field_extension.rb index ba6ea09eb..6703c0a33 100644 --- a/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/field_extension.rb +++ b/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/field_extension.rb @@ -32,6 +32,8 @@ module FieldExtension # # @param tag_name [String] tag to add to schema elements generated for this field # @return [void] + # @see ApolloDirectives::Tag + # @see APIExtension#tag_built_in_types_with # # @example Tag a field (and its derived elements) with "public" # ElasticGraph.define_schema do |schema| @@ -41,9 +43,6 @@ module FieldExtension # end # end # end - # - # @see ApolloDirectives::Tag - # @see APIExtension#tag_built_in_types_with def tag_with(tag_name) on_each_generated_schema_element do |element| needs_tagging = diff --git a/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/object_and_interface_extension.rb b/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/object_and_interface_extension.rb index 67a1d9a0d..c5fe5e032 100644 --- a/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/object_and_interface_extension.rb +++ b/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/object_and_interface_extension.rb @@ -37,9 +37,6 @@ module ObjectAndInterfaceExtension # @param type [String] Name of the entity reference type (which must be defined separately) # @param id_field_name_in_index [String] Name of the backing ID field in the datastore index # @return [void] - # @note This can be used for either a singleton or list reference, based on if `type` is a list. - # @note The resulting field will be only be available for clients to request as a return field. It will not support filtering, - # sorting, grouping, aggregated values, or highlights. # @see #apollo_entity_ref_paginated_collection_field # # @example Expose `Review.product` and `Review.comments` entity reference fields @@ -71,6 +68,10 @@ module ObjectAndInterfaceExtension # t.index "reviews" # end # end + # + # @note This can be used for either a singleton or list reference, based on if `type` is a list. + # @note The resulting field will be only be available for clients to request as a return field. It will not support filtering, + # sorting, grouping, aggregated values, or highlights. def apollo_entity_ref_field(name, type, id_field_name_in_index:) field( name, @@ -114,9 +115,6 @@ def apollo_entity_ref_field(name, type, id_field_name_in_index:) # @param element_type [String] Name of the entity reference type (which must be defined separately) # @param id_field_name_in_index [String] Name of the backing ID field in the datastore index # @return [void] - # @note This requires `id_field_name_in_index` to be a list or paginated collection field. - # @note The resulting field will be only be available for clients to request as a return field. It will not support filtering, - # sorting, grouping, aggregated values, or highlights. # @see #apollo_entity_ref_field # @see ElasticGraph::SchemaDefinition::SchemaElements::TypeWithSubfields#paginated_collection_field # @@ -140,6 +138,10 @@ def apollo_entity_ref_field(name, type, id_field_name_in_index:) # t.index "reviews" # end # end + # + # @note This requires `id_field_name_in_index` to be a list or paginated collection field. + # @note The resulting field will be only be available for clients to request as a return field. It will not support filtering, + # sorting, grouping, aggregated values, or highlights. def apollo_entity_ref_paginated_collection_field(name, element_type, id_field_name_in_index:) paginated_collection_field( name, diff --git a/elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb b/elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb index 044465c40..e971d0d71 100644 --- a/elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb +++ b/elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb @@ -33,10 +33,6 @@ class RakeTasks < ::Rake::TaskLib # # Defaults to `false` since it requires a plugin. # - # @note Enabling this requires the [mapper-size plugin](https://www.elastic.co/guide/en/elasticsearch/plugins/8.15/mapper-size.html) - # to be installed on your datastore cluster. You are responsible for ensuring that is installed if you enable this feature. If you - # enable this and the plugin is not installed, you will get errors! - # # @return [Boolean] whether or not the `_size` field should be indexed on each indexed type # # @example Enable indexing document sizes @@ -47,6 +43,10 @@ class RakeTasks < ::Rake::TaskLib # tasks.index_document_sizes = true # end # + # @note Enabling this requires the [mapper-size plugin](https://www.elastic.co/guide/en/elasticsearch/plugins/8.15/mapper-size.html) + # to be installed on your datastore cluster. You are responsible for ensuring that is installed if you enable this feature. If you + # enable this and the plugin is not installed, you will get errors! + # # @dynamic index_document_sizes, index_document_sizes= attr_accessor :index_document_sizes @@ -216,15 +216,6 @@ class RakeTasks < ::Rake::TaskLib # Whether or not to enforce the requirement that the JSON schema version is incremented every time # dumping the JSON schemas results in a changed artifact. Defaults to `true`. # - # @note Generally speaking, you will want this to be `true` for any ElasticGraph application that is in - # production as the versioning of JSON schemas is what supports safe schema evolution as it allows - # ElasticGraph to identify which version of the JSON schema the publishing system was operating on - # when it published an event. - # - # It can be useful to set it to `false` before your application is in production, as you do not want - # to be forced to bump the version after every single schema change while you are building an initial - # prototype. - # # @return [Boolean] whether to require `json_schema_version` to be incremented on changes that impact `json_schemas.yaml` # @see SchemaDefinition::API#json_schema_version # @@ -237,6 +228,15 @@ class RakeTasks < ::Rake::TaskLib # tasks.enforce_json_schema_version = false # end # + # @note Generally speaking, you will want this to be `true` for any ElasticGraph application that is in + # production as the versioning of JSON schemas is what supports safe schema evolution as it allows + # ElasticGraph to identify which version of the JSON schema the publishing system was operating on + # when it published an event. + # + # It can be useful to set it to `false` before your application is in production, as you do not want + # to be forced to bump the version after every single schema change while you are building an initial + # prototype. + # # @dynamic enforce_json_schema_version, enforce_json_schema_version= attr_accessor :enforce_json_schema_version @@ -285,9 +285,6 @@ class RakeTasks < ::Rake::TaskLib # Hash mapping environments (e.g. `:test`, `:dev`, etc) to port numbers for use when booting Elasticsearch or OpenSearch. The hash # automatically includes an entry for the `:local` environment, using a port number extracted from `local_config_yaml`. # - # @note When booting Elasticsearch/OpenSearch, Kibana (or its OpenSearch equivalent, "OpenSearch Dashboards") will also get booted, - # selecting the port by adding `10000` to the configured port. - # # @return [Hash] mapping from environment name to port number # # @example Define what port to use to boot the datastore for the `:test` environment @@ -298,6 +295,9 @@ class RakeTasks < ::Rake::TaskLib # tasks.env_port_mapping = {test: 9999} # end # + # @note When booting Elasticsearch/OpenSearch, Kibana (or its OpenSearch equivalent, "OpenSearch Dashboards") will also get booted, + # selecting the port by adding `10000` to the configured port. + # # @dynamic env_port_mapping, env_port_mapping= attr_accessor :env_port_mapping @@ -345,13 +345,13 @@ def define_fake_data_batch_for(type, &block) @fake_data_batch_generator_by_type[type] = block end - # @note This method uses keyword args for all required arguments. Optional task settings are instead specified using the block. # @param local_config_yaml [String, Pathname] path to the settings YAML file for the local/development environment # @param path_to_schema [String, Pathname] path to the Ruby schema definition file--either the only file that defines the schema # (using `ElasticGraph.define_schema`) or the "main" schema definition file, which loads other files which further define parts of # the schema. # @yield [RakeTasks] instance for further configuration # @yieldreturn [void] + # @note This method uses keyword args for all required arguments. Optional task settings are instead specified using the block. def initialize(local_config_yaml:, path_to_schema:) @local_config_yaml = local_config_yaml.to_s diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb index ac5fb7866..ed7e0defd 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb @@ -48,11 +48,6 @@ def graphql_schema_string # # In addition, they are used by `elasticgraph-indexer` to validate data before indexing it. # - # @note ElasticGraph supports multiple JSON schema versions in order to support safe, seamless schema evolution. - # Each event will be validated using the version specified in the event itself, allowing data publishers to be - # updated to the latest JSON schema at a later time after `elasticgraph-indexer` is deployed with a new JSON - # schema version. - # # @param version [Integer] the desired JSON schema version # @return [Hash] # @raise [Errors::MissingSchemaArtifactError] when the provided version does not exist within the `artifacts_dir`. @@ -62,6 +57,11 @@ def graphql_schema_string # @example Get the JSON schema for a `Widget` type at version 1 # artifacts = ElasticGraph::SchemaArtifacts::FromDisk.new(schema_artifacts_dir) # widget_v1_json_schema = artifacts.json_schemas_for(1).fetch("$defs").fetch("Widget") + # + # @note ElasticGraph supports multiple JSON schema versions in order to support safe, seamless schema evolution. + # Each event will be validated using the version specified in the event itself, allowing data publishers to be + # updated to the latest JSON schema at a later time after `elasticgraph-indexer` is deployed with a new JSON + # schema version. def json_schemas_for(version) unless available_json_schema_versions.include?(version) raise Errors::MissingSchemaArtifactError, "The requested json schema version (#{version}) is not available. " \ diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb index 6762b468f..3c758975f 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb @@ -175,10 +175,6 @@ def namespace_type(name, &block) # one or more fields that concrete implementations of the interface must also define. Each implementation can be an # {SchemaElements::ObjectType} or {SchemaElements::InterfaceType}. # - # @note An interface type can declare an index with {Mixins::HasIndices#index}. This creates a _mixed-type index_ in - # the datastore where concrete types that implement the interface coexist. A subtype may opt out of this shared - # index inheritance and use a dedicated index by declaring its own with {Mixins::HasIndices#index}. - # # @param name [String] name of the interface # @yield [SchemaElements::InterfaceType] interface type object # @return [void] @@ -204,6 +200,10 @@ def namespace_type(name, &block) # t.field "pointsPerGame", "Float" # end # end + # + # @note An interface type can declare an index with {Mixins::HasIndices#index}. This creates a _mixed-type index_ in + # the datastore where concrete types that implement the interface coexist. A subtype may opt out of this shared + # index inheritance and use a dedicated index by declaring its own with {Mixins::HasIndices#index}. def interface_type(name, &block) @state.register_object_interface_or_union_type @factory.new_interface_type(name.to_s, &block) nil @@ -243,10 +243,6 @@ def enum_type(name, &block) # Defines a [GraphQL union type](https://graphql.org/learn/schema/#union-types). Use it to define an abstract supertype with one or # more concrete subtypes. Each subtype must be an {SchemaElements::ObjectType}, but they do not have to share any fields in common. # - # @note A union type can declare an index with {Mixins::HasIndices#index}. This creates a _mixed-type index_ in - # the datastore where the union members coexist. A subtype may opt out of this shared index inheritance and use - # a dedicated index by declaring its own with {Mixins::HasIndices#index}. - # # @param name [String] name of the union type # @yield [SchemaElements::UnionType] union type object # @return [void] @@ -270,6 +266,10 @@ def enum_type(name, &block) # t.subtypes "BankAccount", "BitcoinWallet" # end # end + # + # @note A union type can declare an index with {Mixins::HasIndices#index}. This creates a _mixed-type index_ in + # the datastore where the union members coexist. A subtype may opt out of this shared index inheritance and use + # a dedicated index by declaring its own with {Mixins::HasIndices#index}. def union_type(name, &block) @state.register_object_interface_or_union_type @factory.new_union_type(name.to_s, &block) nil @@ -296,10 +296,6 @@ def scalar_type(name, &block) # Registers the name of a type that existed in a prior version of the schema but has been deleted. # - # @note In situations where this API applies, ElasticGraph will give you an error message indicating that you need to use this API - # or {SchemaElements::TypeWithSubfields#renamed_from}. Likewise, when ElasticGraph no longer needs to know about this, it'll give you a warning - # indicating the call to this method can be removed. - # # @param name [String] name of type that used to exist but has been deleted # @return [void] # @@ -307,6 +303,10 @@ def scalar_type(name, &block) # ElasticGraph.define_schema do |schema| # schema.deleted_type "Widget" # end + # + # @note In situations where this API applies, ElasticGraph will give you an error message indicating that you need to use this API + # or {SchemaElements::TypeWithSubfields#renamed_from}. Likewise, when ElasticGraph no longer needs to know about this, it'll give you a warning + # indicating the call to this method can be removed. def deleted_type(name) @state.register_deleted_type( name, @@ -450,10 +450,6 @@ def results # version number. The publisher will then include this version number in published events to identify the version of the schema it # was using. This avoids the need to deploy the publisher and ElasticGraph indexer at the same time to keep them in sync. # - # @note While this is an important part of how ElasticGraph is designed to support schema evolution, it can be annoying constantly - # have to increment this while rapidly changing the schema during prototyping. You can disable the requirement to increment this - # on every JSON schema change by setting `enforce_json_schema_version` to `false` in your `Rakefile`. - # # @param version [Integer] current version number of the JSON schema artifact # @return [void] # @see Local::RakeTasks#enforce_json_schema_version @@ -462,6 +458,10 @@ def results # ElasticGraph.define_schema do |schema| # schema.json_schema_version 1 # end + # + # @note While this is an important part of how ElasticGraph is designed to support schema evolution, it can be annoying constantly + # have to increment this while rapidly changing the schema during prototyping. You can disable the requirement to increment this + # on every JSON schema change by setting `enforce_json_schema_version` to `false` in your `Rakefile`. def json_schema_version(version) if !version.is_a?(Integer) || version < 1 raise Errors::SchemaError, "`json_schema_version` must be a positive integer. Specified version: #{version}" @@ -484,16 +484,16 @@ def json_schema_version(version) # @param allow_extra_fields [Boolean] Whether extra fields (e.g. beyond fields defined in the schema) can be included in indexing events. # @return [void] # + # @example Allow omitted fields and disallow extra fields + # ElasticGraph.define_schema do |schema| + # schema.json_schema_strictness allow_omitted_fields: true, allow_extra_fields: false + # end + # # @note If you allow both omitted fields and extra fields, ElasticGraph's JSON schema validation will allow (and ignore) misspelled # field names in indexing events. For example, if the ElasticGraph schema has a nullable field named `parentId` but the publisher # accidentally provides it as `parent_id`, ElasticGraph would happily ignore the `parent_id` field entirely, because `parentId` # is allowed to be omitted and `parent_id` would be treated as an extra field. Therefore, we recommend that you only set one of # these to `true` (or none). - # - # @example Allow omitted fields and disallow extra fields - # ElasticGraph.define_schema do |schema| - # schema.json_schema_strictness allow_omitted_fields: true, allow_extra_fields: false - # end def json_schema_strictness(allow_omitted_fields: false, allow_extra_fields: true) unless [true, false].include?(allow_omitted_fields) raise Errors::SchemaError, "`allow_omitted_fields` must be true or false" diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/index.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/index.rb index a6400db64..bac10d1e2 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/index.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/index.rb @@ -73,9 +73,6 @@ def initialize(name, settings, schema_def_state, indexed_type) # Specifies how documents in this index should sort by default, when no `orderBy` argument is provided to the GraphQL query. # - # @note the field name strings can be a dot-separated nested fields, but all referenced - # fields must exist when this is called. - # # @param field_name_direction_pairs [Array<(String, Symbol)>] pairs of field names and `:asc` or `:desc` # @return [void] # @@ -91,6 +88,9 @@ def initialize(name, settings, schema_def_state, indexed_type) # end # end # end + # + # @note the field name strings can be a dot-separated nested fields, but all referenced + # fields must exist when this is called. def default_sort(*field_name_direction_pairs) self.default_sort_pairs = field_name_direction_pairs end @@ -101,13 +101,6 @@ def default_sort(*field_name_direction_pairs) # Elasticsearch/OpenSearch limitations on the number of shards in one index. In addition, ElasticGraph optimizes queries which # filter on the timestamp field to target the subset of the indices in which matching documents could reside. # - # @note the timestamp field specified here **must be immutable**. To understand why, consider a `:yearly` rollover - # index used for data based on `createdAt`; if ElasticGraph ingests record `123` with a createdAt of `2023-12-31T23:59:59Z`, it - # will be indexed in the `2023` index. Later if it receives an update event for record `123` with a `createdAt` of - # `2024-01-01T00:00:00Z` (a mere one second later!), ElasticGraph will store the new version of the payment in the `2024` index, - # and leave the old copy of the payment in the `2023` index unchanged. It’ll have duplicates for that document. - # @note changing the `rollover` configuration on an existing index that already has data will result in duplicate documents - # # @param frequency [:yearly, :monthly, :daily, :hourly] how often to rollover the index # @param timestamp_field_path_name [String] dot-separated path to the timestamp field used for rollover. Note: all referenced # fields must exist when this is called. @@ -125,6 +118,13 @@ def default_sort(*field_name_direction_pairs) # end # end # end + # + # @note the timestamp field specified here **must be immutable**. To understand why, consider a `:yearly` rollover + # index used for data based on `createdAt`; if ElasticGraph ingests record `123` with a createdAt of `2023-12-31T23:59:59Z`, it + # will be indexed in the `2023` index. Later if it receives an update event for record `123` with a `createdAt` of + # `2024-01-01T00:00:00Z` (a mere one second later!), ElasticGraph will store the new version of the payment in the `2024` index, + # and leave the old copy of the payment in the `2023` index unchanged. It’ll have duplicates for that document. + # @note changing the `rollover` configuration on an existing index that already has data will result in duplicate documents def rollover(frequency, timestamp_field_path_name) schema_def_state.after_user_definition_complete do timestamp_field_path = public_field_path(timestamp_field_path_name, explanation: "it is referenced as an index `rollover` field") @@ -153,13 +153,6 @@ def rollover(frequency, timestamp_field_path_name) # field. Using an appropriate field for shard routing is often essential for horizontal scaling, as it avoids having every query # hit every node, allowing additional nodes to increase query throughput. # - # @note it is essential that the shards are well-balanced. If the data’s distribution is lopsided, using this feature can make - # performance worse. - # @note the routing field specified here **must be immutable**. If ElasticGraph receives an updated version of a document with a - # different routing value, it’ll write the new version of the document to a different shard and leave the copy on the old shard - # unchanged, leading to duplicates. - # @note changing the shard routing configuration on an existing index that already has data will result in duplicate documents - # # @param routing_field_path_name [String] dot-separated path to the field used for shard routing. Note: all referenced # fields must exist when this is called. # @return [void] @@ -176,6 +169,13 @@ def rollover(frequency, timestamp_field_path_name) # end # end # end + # + # @note it is essential that the shards are well-balanced. If the data’s distribution is lopsided, using this feature can make + # performance worse. + # @note the routing field specified here **must be immutable**. If ElasticGraph receives an updated version of a document with a + # different routing value, it’ll write the new version of the document to a different shard and leave the copy on the old shard + # unchanged, leading to duplicates. + # @note changing the shard routing configuration on an existing index that already has data will result in duplicate documents def route_with(routing_field_path_name) schema_def_state.after_user_definition_complete do routing_field_path = public_field_path(routing_field_path_name, explanation: "it is referenced as an index `route_with` field") @@ -224,8 +224,8 @@ def has_had_multiple_sources! self.has_had_multiple_sources_flag = true end - # @see #route_with # @return [Boolean] whether or not this index uses custom shard routing + # @see #route_with def uses_custom_routing? routing_field_path.path_in_index != "id" end diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_directives.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_directives.rb index e5ba2b01c..a46c81728 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_directives.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_directives.rb @@ -13,9 +13,6 @@ module Mixins module HasDirectives # Adds a GraphQL directive to the current schema element. # - # @note If you’re using a custom directive rather than a standard GraphQL directive like `@deprecated`, you’ll also need to use - # {API#raw_sdl} to define the custom directive. - # # @param name [String] name of the directive # @param arguments [Hash] arguments for the directive # @return [void] @@ -39,6 +36,9 @@ module HasDirectives # t.directive "sourcedFrom", system: "campaigns" # end # end + # + # @note If you’re using a custom directive rather than a standard GraphQL directive like `@deprecated`, you’ll also need to use + # {API#raw_sdl} to define the custom directive. def directive(name, arguments = {}) directives << schema_def_state.factory.new_directive(name, arguments) end diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb index 0445db4fe..e804e2185 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb @@ -43,13 +43,6 @@ def initialize(*args, **options) # needing to call `t.index` themselves. A subtype can opt out of this shared index inheritance by calling # `t.index` with a different name to use a dedicated index instead. # - # @note Use {#root_query_fields} on indexed types to name the field that will be exposed on `Query`. - # @note Indexed types must also define an `id` field, which ElasticGraph will use as the primary key. - # When an abstract type declares the index, each concrete subtype must also define `id`. - # @note Datastore index settings can also be defined (or overridden) in an environment-specific settings YAML file. Index settings - # that you want to configure differently for different environments (such as `index.number_of_shards`—-production and staging - # will probably need different numbers!) should be configured in the per-environment YAML configuration files rather than here. - # # @param name [String] name of the index. See the [Elasticsearch docs](https://www.elastic.co/guide/en/elasticsearch/reference/8.15/indices-create-index.html#indices-create-api-path-params) # for restrictions. # @param settings [Hash] datastore index settings you want applied to every environment. See the [Elasticsearch docs](https://www.elastic.co/guide/en/elasticsearch/reference/8.15/index-modules.html#index-modules-settings) @@ -99,6 +92,13 @@ def initialize(*args, **options) # t.index "motorcycles" # end # end + # + # @note Use {#root_query_fields} on indexed types to name the field that will be exposed on `Query`. + # @note Indexed types must also define an `id` field, which ElasticGraph will use as the primary key. + # When an abstract type declares the index, each concrete subtype must also define `id`. + # @note Datastore index settings can also be defined (or overridden) in an environment-specific settings YAML file. Index settings + # that you want to configure differently for different environments (such as `index.number_of_shards`—-production and staging + # will probably need different numbers!) should be configured in the per-environment YAML configuration files rather than here. def index(name, **settings, &block) unless @can_configure_index raise Errors::SchemaError, "Cannot define an index on `#{self.name}` after initialization is complete. " \ diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb index 16d058a00..6c17fb4fd 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb @@ -139,13 +139,6 @@ def mapping(**options) # GraphQL schema. If you think you might want to make a field non-nullable in the GraphQL schema some day, it’s a good idea to use # `json_schema nullable: false` now to ensure every indexed record has a non-null value for the field. # - # @note We recommend using JSON schema validations in a limited fashion. Validations that are appropriate to apply when data is - # entering the system-of-record are often not appropriate on a secondary index like ElasticGraph. Events that violate a JSON - # schema validation will fail to index (typically they will be sent to the dead letter queue and page an oncall engineer). If an - # ElasticGraph instance is meant to contain all the data of some source system, you probably don’t want it applying stricter - # validations than the source system itself has. We recommend limiting your JSON schema validations to situations where - # violations would prevent ElasticGraph from operating correctly. - # # @param options [Hash] JSON schema options. Any # [JSON schema validation keyword](https://json-schema.org/understanding-json-schema/reference) is accepted. # In addition, `nullable: false` is supported to disallow `null` values. Common options are shown below. @@ -187,6 +180,13 @@ def mapping(**options) # t.index "cards" # end # end + # + # @note We recommend using JSON schema validations in a limited fashion. Validations that are appropriate to apply when data is + # entering the system-of-record are often not appropriate on a secondary index like ElasticGraph. Events that violate a JSON + # schema validation will fail to index (typically they will be sent to the dead letter queue and page an oncall engineer). If an + # ElasticGraph instance is meant to contain all the data of some source system, you probably don't want it applying stricter + # validations than the source system itself has. We recommend limiting your JSON schema validations to situations where + # violations would prevent ElasticGraph from operating correctly. def json_schema(**options) validatable_json_schema = Support::HashUtil.stringify_keys(options) diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/implements_interfaces.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/implements_interfaces.rb index b218060c9..a5c8d9e97 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/implements_interfaces.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/implements_interfaces.rb @@ -16,10 +16,6 @@ module ImplementsInterfaces # Declares that the current type implements the specified interface, making the current type a subtype of the interface. The # current type must define all of the fields of the named interface, with the exact same field types. # - # @note If the named interface has declared an index (via {Mixins::HasIndices#index}), calling `implements` - # causes this type to automatically inherit that index — it will be stored in the same datastore index as all other - # implementations of the named interface. To use a dedicated index instead, call {Mixins::HasIndices#index} on this type. - # # @param interface_names [Array] names of interface types implemented by this type # @return [void] # @@ -44,6 +40,10 @@ module ImplementsInterfaces # t.field "pointsPerGame", "Float" # end # end + # + # @note If the named interface has declared an index (via {Mixins::HasIndices#index}), calling `implements` + # causes this type to automatically inherit that index — it will be stored in the same datastore index as all other + # implementations of the named interface. To use a dedicated index instead, call {Mixins::HasIndices#index} on this type. def implements(*interface_names) interface_refs = interface_names.map do |interface_name| schema_def_state.type_ref(interface_name).to_final_form.tap do |interface_ref| diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb index a1214ed98..6165224ac 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb @@ -200,9 +200,6 @@ def type_for_derived_types original_type_for_derived_types.to_final_form(as_input: as_input) end - # @note For each field defined in your schema that is filterable, a corresponding filtering field will be created on the - # `*FilterInput` type derived from the parent object type. - # # Registers a customization callback that will be applied to the corresponding filtering field that will be generated for this # field. # @@ -229,13 +226,13 @@ def type_for_derived_types # t.index "campaigns" # end # end + # + # @note For each field defined in your schema that is filterable, a corresponding filtering field will be created on the + # `*FilterInput` type derived from the parent object type. def customize_filter_field(&customization_block) filter_customizations << customization_block end - # @note For each field defined in your schema that is aggregatable, a corresponding `aggregatedValues` field will be created on the - # `*AggregatedValues` type derived from the parent object type. - # # Registers a customization callback that will be applied to the corresponding `aggregatedValues` field that will be generated for # this field. # @@ -262,13 +259,13 @@ def customize_filter_field(&customization_block) # t.index "campaigns" # end # end + # + # @note For each field defined in your schema that is aggregatable, a corresponding `aggregatedValues` field will be created on the + # `*AggregatedValues` type derived from the parent object type. def customize_aggregated_values_field(&customization_block) aggregated_values_customizations << customization_block end - # @note For each field defined in your schema that is groupable, a corresponding `groupedBy` field will be created on the - # `*AggregationGroupedBy` type derived from the parent object type. - # # Registers a customization callback that will be applied to the corresponding `groupedBy` field that will be generated for this # field. # @@ -295,13 +292,13 @@ def customize_aggregated_values_field(&customization_block) # t.index "campaigns" # end # end + # + # @note For each field defined in your schema that is groupable, a corresponding `groupedBy` field will be created on the + # `*AggregationGroupedBy` type derived from the parent object type. def customize_grouped_by_field(&customization_block) grouped_by_customizations << customization_block end - # @note For each field defined in your schema that is highlightable, a corresponding highlights field will be created on the - # `*Highlights` type derived from the parent object type. - # # Registers a customization callback that will be applied to the corresponding highlights field that will be generated for this # field. # @@ -328,13 +325,13 @@ def customize_grouped_by_field(&customization_block) # t.index "campaigns" # end # end + # + # @note For each field defined in your schema that is highlightable, a corresponding highlights field will be created on the + # `*Highlights` type derived from the parent object type. def customize_highlights_field(&customization_block) highlights_customizations << customization_block end - # @note For each field defined in your schema that is sub-aggregatable (e.g. list fields indexed using the `nested` mapping type), - # a corresponding field will be created on the `*AggregationSubAggregations` type derived from the parent object type. - # # Registers a customization callback that will be applied to the corresponding `subAggregations` field that will be generated for # this field. # @@ -370,13 +367,13 @@ def customize_highlights_field(&customization_block) # t.field "currency", "String" # end # end + # + # @note For each field defined in your schema that is sub-aggregatable (e.g. list fields indexed using the `nested` mapping type), + # a corresponding field will be created on the `*AggregationSubAggregations` type derived from the parent object type. def customize_sub_aggregations_field(&customization_block) sub_aggregations_customizations << customization_block end - # @note for each sortable field, enum values will be generated on the derived sort order enum type allowing you to - # sort by the field `ASC` or `DESC`. - # # Registers a customization callback that will be applied to the corresponding enum values that will be generated for this field # on the derived `SortOrder` enum type. # @@ -403,6 +400,9 @@ def customize_sub_aggregations_field(&customization_block) # t.index "campaigns" # end # end + # + # @note for each sortable field, enum values will be generated on the derived sort order enum type allowing you to + # sort by the field `ASC` or `DESC`. def customize_sort_order_enum_values(&customization_block) sort_order_enum_value_customizations << customization_block end @@ -469,10 +469,6 @@ def on_each_generated_schema_element(&customization_block) end # (see Mixins::HasTypeInfo#json_schema) - # @param options [Hash] JSON schema options forwarded to {Mixins::HasTypeInfo#json_schema} - # @option options [Boolean] :nullable when `false`, disallows `null` values in JSON schema - # without changing the GraphQL nullability of the field. `true` is not allowed--use a - # nullable GraphQL type (no `!` suffix) instead. def json_schema(nullable: nil, **options) if options.key?(:type) raise Errors::SchemaError, "Cannot override JSON schema type of field `#{name}` with `#{options.fetch(:type)}`" @@ -489,7 +485,6 @@ def json_schema(nullable: nil, **options) end # (see Mixins::HasTypeInfo#mapping) - # @param options [Hash] mapping options forwarded to {Mixins::HasTypeInfo#mapping} def mapping(**options) # ElasticGraph has special handling for the nested type (e.g. we generate sub-aggregation types in the GraphQL schema for # nested fields), and that special handling requires that `nested` only be used on list-of-objects fields; otherwise @@ -594,10 +589,6 @@ def runtime_script(script) # Registers an old name that this field used to have in a prior version of the schema. # - # @note In situations where this API applies, ElasticGraph will give you an error message indicating that you need to use this API - # or {TypeWithSubfields#deleted_field}. Likewise, when ElasticGraph no longer needs to know about this, it'll give you a warning - # indicating the call to this method can be removed. - # # @param old_name [String] old name this field used to have in a prior version of the schema # @return [void] # @@ -609,6 +600,10 @@ def runtime_script(script) # end # end # end + # + # @note In situations where this API applies, ElasticGraph will give you an error message indicating that you need to use this API + # or {TypeWithSubfields#deleted_field}. Likewise, when ElasticGraph no longer needs to know about this, it'll give you a warning + # indicating the call to this method can be removed. def renamed_from(old_name) schema_def_state.register_renamed_field( parent_type.name, @@ -795,11 +790,6 @@ def type_is_namespace? # Defines an argument on the field. # - # @note ElasticGraph takes care of defining arguments for all the query features it supports, so there is generally no need to use - # this API, and it has no way to interpret arbitrary arguments defined on a field. However, it can be useful for extensions that - # extend the {ElasticGraph::GraphQL} query engine. For example, {ElasticGraph::Apollo} uses this API to satisfy the [Apollo - # federation subgraph spec](https://www.apollographql.com/docs/federation/federation-spec/). - # # @param name [String] name of the argument # @param value_type [String] type of the argument in GraphQL SDL syntax # @yield [Argument] for further customization @@ -812,6 +802,11 @@ def type_is_namespace? # end # end # end + # + # @note ElasticGraph takes care of defining arguments for all the query features it supports, so there is generally no need to use + # this API, and it has no way to interpret arbitrary arguments defined on a field. However, it can be useful for extensions that + # extend the {ElasticGraph::GraphQL} query engine. For example, {ElasticGraph::Apollo} uses this API to satisfy the [Apollo + # federation subgraph spec](https://www.apollographql.com/docs/federation/federation-spec/). def argument(name, value_type, &block) args[name] = schema_def_state.factory.new_argument( self, diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb index ecac092d3..95aa4d644 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb @@ -98,8 +98,6 @@ def name end # (see Mixins::HasTypeInfo#mapping) - # @param options [Hash] mapping options forwarded to {Mixins::HasTypeInfo#mapping}. - # Must include `:type` for scalar types. def mapping(**options) self.mapping_type = options.fetch(:type) do raise Errors::SchemaError, "Must specify a mapping `type:` on custom scalars but was missing on the `#{name}` type." @@ -111,10 +109,6 @@ def mapping(**options) # Specifies the scalar coercion adapter that should be used for this scalar type. The scalar coercion adapter is responsible # for validating and coercing scalar input values, and converting scalar return values to a form suitable for JSON serialization. # - # @note For examples of scalar coercion adapters, see `ElasticGraph::GraphQL::ScalarCoercionAdapters`. - # @note If the `defined_at` require path requires any directories be put on the Ruby `$LOAD_PATH`, you are responsible for doing - # that before booting {ElasticGraph::GraphQL}. - # # @param adapter_name [String] fully qualified Ruby class name of the adapter # @param defined_at [String] the `require` path of the adapter # @return [void] @@ -127,6 +121,10 @@ def mapping(**options) # t.coerce_with "CoercionAdapters::PhoneNumber", defined_at: "./coercion_adapters/phone_number" # end # end + # + # @note For examples of scalar coercion adapters, see `ElasticGraph::GraphQL::ScalarCoercionAdapters`. + # @note If the `defined_at` require path requires any directories be put on the Ruby `$LOAD_PATH`, you are responsible for doing + # that before booting {ElasticGraph::GraphQL}. def coerce_with(adapter_name, defined_at:) self.runtime_metadata = runtime_metadata.with(coercion_adapter_ref: { "name" => adapter_name, @@ -137,10 +135,6 @@ def coerce_with(adapter_name, defined_at:) # Specifies an indexing preparer that should be used for this scalar type. The indexing preparer is responsible for preparing # scalar values before indexing them, performing any desired formatting or normalization. # - # @note For examples of scalar coercion adapters, see `ElasticGraph::Indexer::IndexingPreparers`. - # @note If the `defined_at` require path requires any directories be put on the Ruby `$LOAD_PATH`, you are responsible for doing - # that before booting {ElasticGraph::GraphQL}. - # # @param preparer_name [String] fully qualified Ruby class name of the indexing preparer # @param defined_at [String] the `require` path of the preparer # @return [void] @@ -155,6 +149,10 @@ def coerce_with(adapter_name, defined_at:) # defined_at: "./indexing_preparers/phone_number" # end # end + # + # @note For examples of scalar coercion adapters, see `ElasticGraph::Indexer::IndexingPreparers`. + # @note If the `defined_at` require path requires any directories be put on the Ruby `$LOAD_PATH`, you are responsible for doing + # that before booting {ElasticGraph::GraphQL}. def prepare_for_indexing_with(preparer_name, defined_at:) self.runtime_metadata = runtime_metadata.with(indexing_preparer_ref: { "name" => preparer_name, diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_with_subfields.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_with_subfields.rb index 4fc5f9c2f..55be1003b 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_with_subfields.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_with_subfields.rb @@ -152,19 +152,6 @@ def name # @see #relates_to_many # @see #relates_to_one # - # @note Be careful about defining non-nullable fields. Changing a field’s type from non-nullable (e.g. `Int!`) to nullable (e.g. - # `Int`) is a breaking change for clients. Making a field non-nullable may also prevent you from applying permissioning to a field - # via an AuthZ layer (as such a layer would have no way to force a field value to `null` for a client denied field access). - # Therefore, we recommend limiting your use of `!` to only a few situations such as defining a type’s primary key (e.g. - # `t.field "id", "ID!"`) or defining a list field (e.g. `t.field "authors", "[String!]!"`) since empty lists already provide a - # "no data" representation. You can still configure the ElasticGraph indexer to require a non-null value for a field using - # `f.json_schema nullable: false`. - # - # @note ElasticGraph’s understanding of datastore capabilities may override your configured - # `aggregatable`/`filterable`/`groupable`/`sortable` options. For example, a field indexed as `text` for full text search will - # not be sortable or groupable even if you pass `sortable: true, groupable: true` when defining the field, because [text fields - # cannot be efficiently sorted by or grouped on](https://www.elastic.co/guide/en/elasticsearch/reference/8.15/text.html#text). - # # @example Define a field with documentation # ElasticGraph.define_schema do |schema| # schema.object_type "Campaign" do |t| @@ -199,6 +186,19 @@ def name # t.field "endDate", "Date", name_in_index: "endOn", graphql_only: true # end # end + # + # @note Be careful about defining non-nullable fields. Changing a field's type from non-nullable (e.g. `Int!`) to nullable (e.g. + # `Int`) is a breaking change for clients. Making a field non-nullable may also prevent you from applying permissioning to a field + # via an AuthZ layer (as such a layer would have no way to force a field value to `null` for a client denied field access). + # Therefore, we recommend limiting your use of `!` to only a few situations such as defining a type's primary key (e.g. + # `t.field "id", "ID!"`) or defining a list field (e.g. `t.field "authors", "[String!]!"`) since empty lists already provide a + # "no data" representation. You can still configure the ElasticGraph indexer to require a non-null value for a field using + # `f.json_schema nullable: false`. + # + # @note ElasticGraph's understanding of datastore capabilities may override your configured + # `aggregatable`/`filterable`/`groupable`/`sortable` options. For example, a field indexed as `text` for full text search will + # not be sortable or groupable even if you pass `sortable: true, groupable: true` when defining the field, because [text fields + # cannot be efficiently sorted by or grouped on](https://www.elastic.co/guide/en/elasticsearch/reference/8.15/text.html#text). def field(name, type, graphql_only: false, indexing_only: false, **options) if reserved_field_names.include?(name) raise Errors::SchemaError, "Invalid field name: `#{self.name}.#{name}`. `#{name}` is reserved for use by " \ @@ -230,10 +230,6 @@ def field(name, type, graphql_only: false, indexing_only: false, **options) # Registers the name of a field that existed in a prior version of the schema but has been deleted. # - # @note In situations where this API applies, ElasticGraph will give you an error message indicating that you need to use this API - # or {Field#renamed_from}. Likewise, when ElasticGraph no longer needs to know about this, it'll give you a warning indicating - # the call to this method can be removed. - # # @param field_name [String] name of field that used to exist but has been deleted # @return [void] # @@ -243,6 +239,10 @@ def field(name, type, graphql_only: false, indexing_only: false, **options) # t.deleted_field "description" # end # end + # + # @note In situations where this API applies, ElasticGraph will give you an error message indicating that you need to use this API + # or {Field#renamed_from}. Likewise, when ElasticGraph no longer needs to know about this, it'll give you a warning indicating + # the call to this method can be removed. def deleted_field(field_name) schema_def_state.register_deleted_field( name, @@ -254,10 +254,6 @@ def deleted_field(field_name) # Registers an old name that this type used to have in a prior version of the schema. # - # @note In situations where this API applies, ElasticGraph will give you an error message indicating that you need to use this API - # or {API#deleted_type}. Likewise, when ElasticGraph no longer needs to know about this, it'll give you a warning indicating - # the call to this method can be removed. - # # @param old_name [String] old name this field used to have in a prior version of the schema # @return [void] # @@ -267,6 +263,10 @@ def deleted_field(field_name) # t.renamed_from "Component" # end # end + # + # @note In situations where this API applies, ElasticGraph will give you an error message indicating that you need to use this API + # or {API#deleted_type}. Likewise, when ElasticGraph no longer needs to know about this, it'll give you a warning indicating + # the call to this method can be removed. def renamed_from(old_name) schema_def_state.register_renamed_type( name, @@ -279,10 +279,6 @@ def renamed_from(old_name) # An alternative to {#field} for when you have a list field that you want exposed as a [paginated Relay # connection](https://relay.dev/graphql/connections.htm) rather than as a simple list. # - # @note Bear in mind that pagination does not have much efficiency benefit in this case: all elements of the collection will be - # retrieved when fetching this field from the datastore. The pagination implementation will just trim down the collection before - # returning it. - # # @param name [String] name of the field # @param element_type [String] name of the type of element in the collection # @param name_in_index [String] the name of the field in the datastore index. Can be used to back a GraphQL field with a @@ -313,6 +309,10 @@ def renamed_from(old_name) # t.index "authors" # end # end + # + # @note Bear in mind that pagination does not have much efficiency benefit in this case: all elements of the collection will be + # retrieved when fetching this field from the datastore. The pagination implementation will just trim down the collection before + # returning it. def paginated_collection_field( name, element_type, diff --git a/elasticgraph-support/lib/elastic_graph/support/config.rb b/elasticgraph-support/lib/elastic_graph/support/config.rb index b7e057629..86c316301 100644 --- a/elasticgraph-support/lib/elastic_graph/support/config.rb +++ b/elasticgraph-support/lib/elastic_graph/support/config.rb @@ -19,8 +19,8 @@ module Config # Defines a configuration class with the given attributes. # # @param attrs [::Symbol] attribute names - # @return [::Class] the defined configuration class # @yield [::Data] the body of the class (similar to `::Data.define`) + # @return [::Class] the defined configuration class # # @example Define a configuration class # require "elastic_graph/support/config" diff --git a/elasticgraph-support/lib/elastic_graph/support/json_schema/validator.rb b/elasticgraph-support/lib/elastic_graph/support/json_schema/validator.rb index 04aef7352..e60f4c9bd 100644 --- a/elasticgraph-support/lib/elastic_graph/support/json_schema/validator.rb +++ b/elasticgraph-support/lib/elastic_graph/support/json_schema/validator.rb @@ -52,11 +52,10 @@ def validate(data) # # @param data [Object] JSON data to validate # @return [nil, String] a validation error message, if the data is invalid - # - # @note The returned error message may contain PII unless {#sanitize_pii} has not been set. - # # @see #valid? # @see #validate + # + # @note The returned error message may contain PII unless {#sanitize_pii} has not been set. def validate_with_error_message(data) errors = validate(data) return if errors.empty? From 8fb652377bc08f14a2a2f9d0550e6cb946a703b8 Mon Sep 17 00:00:00 2001 From: myronmarston-toast Date: Thu, 14 May 2026 18:30:26 -0700 Subject: [PATCH 12/14] Fix UndocumentedOptions yard-lint offenses Add @option tags and improve @param descriptions for methods with **kwargs. Methods with enumerable options (enum_value, type_namer, namespace_type, graphql_formatter) got specific @option tags. Methods with open-ended pass-through kwargs (api, has_indices, field, config) got improved @param descriptions explaining where the options are forwarded. 7 files remain in the todo for open-ended kwargs where @option tags would be impractical/misleading. Co-Authored-By: Claude Opus 4.6 (1M context) --- .yard-lint-todo.yml | 3 --- .../lib/elastic_graph/schema_definition/api.rb | 4 ++-- .../elastic_graph/schema_definition/mixins/has_indices.rb | 7 ++++--- .../schema_definition/schema_elements/enum_value.rb | 4 ++++ .../schema_definition/schema_elements/field.rb | 2 +- .../schema_definition/schema_elements/namespace_type.rb | 2 ++ .../schema_definition/schema_elements/type_namer.rb | 2 ++ elasticgraph-support/lib/elastic_graph/support/config.rb | 3 ++- .../lib/elastic_graph/support/graphql_formatter.rb | 3 +++ 9 files changed, 20 insertions(+), 10 deletions(-) diff --git a/.yard-lint-todo.yml b/.yard-lint-todo.yml index 8a7556e2c..235e5a863 100644 --- a/.yard-lint-todo.yml +++ b/.yard-lint-todo.yml @@ -72,11 +72,8 @@ Documentation/UndocumentedOptions: Exclude: - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb" - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb" - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb" - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/namespace_type.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb" - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb" - "elasticgraph-support/lib/elastic_graph/support/config.rb" - "elasticgraph-support/lib/elastic_graph/support/graphql_formatter.rb" diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb index 3c758975f..94dae1fd3 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb @@ -324,7 +324,7 @@ def deleted_type(name) # # @param extension_module [Module] GraphQL extension module # @param defined_at [String] the `require` path of the extension module - # @param config [Hash] configuration options for the extension module + # @param config [Hash] extension-specific configuration forwarded to the extension module's `initialize` method # @return [void] # # @example Register `elasticgraph-query_registry` extension module @@ -348,7 +348,7 @@ def register_graphql_extension(extension_module, defined_at:, **config) # @param defined_at [String] the `require` path of the resolver # @param built_in [Boolean] Whether this resolver is built-in to ElasticGraph or one of its extensions. # Built-in resolvers that are unused in a schema will not trigger a warning. - # @param resolver_config [Hash{Symbol => Object}] configuration options for the resolver, to support parameterized resolvers + # @param resolver_config [Hash{Symbol => Object}] resolver-specific configuration forwarded to the resolver's `initialize` method within the `config` parameter # @return [void] # @see Mixins::HasIndices#resolve_fields_with # @see SchemaElements::Field#resolve_with diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb index e804e2185..886e2c990 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb @@ -45,8 +45,7 @@ def initialize(*args, **options) # # @param name [String] name of the index. See the [Elasticsearch docs](https://www.elastic.co/guide/en/elasticsearch/reference/8.15/indices-create-index.html#indices-create-api-path-params) # for restrictions. - # @param settings [Hash] datastore index settings you want applied to every environment. See the [Elasticsearch docs](https://www.elastic.co/guide/en/elasticsearch/reference/8.15/index-modules.html#index-modules-settings) - # for a list of valid settings, but be sure to omit the `index.` prefix here. + # @param settings [Hash] datastore index settings (without the `index.` prefix) forwarded to the index definition. See the [Elasticsearch docs](https://www.elastic.co/guide/en/elasticsearch/reference/8.15/index-modules.html#index-modules-settings) for available settings. # @yield [Indexing::Index] the index, so it can be customized further # @return [void] # @@ -118,7 +117,7 @@ def index(name, **settings, &block) # can override this using {SchemaElements::Field#resolve_with}. # # @param default_resolver_name [Symbol] name of the GraphQL resolver to use as the default for fields of this type - # @param config [Hash] configuration parameters for the resolver + # @param config [Hash] resolver-specific configuration forwarded to the resolver's `initialize` method within the `config` parameter # @return [void] # @see API#register_graphql_resolver def resolve_fields_with(default_resolver_name, **config) @@ -253,6 +252,8 @@ def derived_indexed_types # `runtime_metadata.yaml` schema artifact and made available at runtime to `elasticgraph-graphql` and # `elasticgraph-indexer`. # + # @param overrides [Hash] runtime metadata attributes to override, corresponding to + # {SchemaArtifacts::RuntimeMetadata::ObjectType} fields (e.g. `:elasticgraph_category`, `:source_type`) # @return [void] def override_runtime_metadata(**overrides) @runtime_metadata_overrides.merge!(overrides) diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb index 5e171d0a9..2e9176b6c 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_value.rb @@ -61,6 +61,10 @@ def duplicate_on(other_enum_type) # Updates the runtime metadata. # # @param updates [Hash{Symbol => Object}] to apply to the runtime metadata + # @option updates [Object] :sort_field sort field metadata for this enum value + # @option updates [Object] :datastore_value custom value stored in the datastore for this enum value + # @option updates [Symbol] :datastore_abbreviation abbreviated form stored in the datastore + # @option updates [String] :alternate_original_name alternate original name (set when the enum value was renamed) # @return [void] def update_runtime_metadata(**updates) self.runtime_metadata = runtime_metadata.with(**updates) diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb index 6165224ac..09c2ea499 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb @@ -546,7 +546,7 @@ def sourced_from(relationship, field_path) # via {Mixins::HasIndices#resolve_fields_with} will be used. # # @param resolver_name [Symbol] name of the GraphQL resolver - # @param config [Hash] configuration parameters for the resolver + # @param config [Hash] resolver-specific configuration forwarded to the resolver's `initialize` method within the `config` parameter # @return [void] # @see API#register_graphql_resolver # diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/namespace_type.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/namespace_type.rb index c0d257d36..6ebae8f65 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/namespace_type.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/namespace_type.rb @@ -40,6 +40,8 @@ def initialize(schema_def_state, name) end # Namespace types cannot be indexed. + # @param name [String] index name (unused; raises before processing) + # @param settings [Hash{Symbol => Object}] index settings (unused; raises before processing) # @raise [Errors::SchemaError] always # @private def index(name, **settings, &block) diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb index 462bd378e..fb39a5080 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb @@ -63,6 +63,8 @@ def revert_override_for(potentially_overriden_name) # # Note: this does not apply any configured `name_overrides`. It's up to the caller to apply that when desired. # + # @param format_name [Symbol] key from {DEFAULT_FORMATS} identifying the format to use + # @param args [Hash] placeholder values required by the chosen format (e.g. `:base`, `:parent_types`, `:parent_agg_type`, `:field_path`) # @private def generate_name_for(format_name, **args) format = formats.fetch(format_name) do diff --git a/elasticgraph-support/lib/elastic_graph/support/config.rb b/elasticgraph-support/lib/elastic_graph/support/config.rb index 86c316301..d63f54274 100644 --- a/elasticgraph-support/lib/elastic_graph/support/config.rb +++ b/elasticgraph-support/lib/elastic_graph/support/config.rb @@ -109,7 +109,7 @@ module ClassMethods # # @param at [::String] path from the global configuration root to where this configuration resides # @param optional [::Boolean] whether configuration at the provided `path` is optional - # @param schema [::Hash<::Symbol, ::Object>] JSON schema definition + # @param schema [::Hash<::Symbol, ::Object>] JSON Schema definition keywords (e.g. `properties`, `required`, `type`) forwarded to the draft-07 JSON Schema validator # @return [void] # # @example Define a configuration class @@ -177,6 +177,7 @@ def raise_invalid_config(error) # Like `new`, but avoids applying JSON schema validation. This is needed so that we can make # `#with` work correctly with the validation and conversion features we offer. # + # @param data [Hash] attribute values matching the members declared by `Data.define` # @private def new_without_validation(**data) instance = allocate diff --git a/elasticgraph-support/lib/elastic_graph/support/graphql_formatter.rb b/elasticgraph-support/lib/elastic_graph/support/graphql_formatter.rb index 3f660ef50..4c12dfd63 100644 --- a/elasticgraph-support/lib/elastic_graph/support/graphql_formatter.rb +++ b/elasticgraph-support/lib/elastic_graph/support/graphql_formatter.rb @@ -18,6 +18,9 @@ module GraphQLFormatter # Otherwise, wraps the args list in parens. This allows the returned string to be appended # to a field or directive, and it'll correctly use parens (or not) based on if there are args # or not. + # + # @param args [Hash{Symbol => Object}] GraphQL argument names mapped to their values, serialized into GraphQL syntax + # @return [String] the formatted argument list (e.g. `"(foo: 1, bar: \"hi\")"`) or `""` if empty def self.format_args(**args) return "" if args.empty? "(#{serialize(args, wrap_hash_with_braces: false)})" From 7867263422fa4c7b7a15b6de0cb0107aa16a2c67 Mon Sep 17 00:00:00 2001 From: myronmarston-toast Date: Thu, 14 May 2026 18:31:58 -0700 Subject: [PATCH 13/14] Fix CollectionType yard-lint offenses Replace `Hash` with `Hash{K => V}` in all YARD type annotations per YARD's standard collection type syntax. Co-Authored-By: Claude Opus 4.6 (1M context) --- .yard-lint-todo.yml | 36 ------------------- .../lib/elastic_graph/local/rake_tasks.rb | 10 +++--- .../elastic_graph/rack/graphql_endpoint.rb | 4 +-- .../lib/elastic_graph/schema_artifacts.rb | 2 +- .../artifacts_helper_methods.rb | 8 ++--- .../schema_artifacts/from_disk.rb | 4 +-- .../runtime_metadata/schema.rb | 4 +-- .../elastic_graph/schema_definition/api.rb | 2 +- .../indexing/event_envelope.rb | 2 +- .../schema_definition/indexing/field.rb | 6 ++-- .../indexing/field_type/enum.rb | 10 +++--- .../indexing/field_type/object.rb | 14 ++++---- .../indexing/field_type/scalar.rb | 10 +++--- .../indexing/field_type/union.rb | 12 +++---- .../schema_definition/indexing/index.rb | 8 ++--- .../indexing/json_schema_field_metadata.rb | 2 +- .../mixins/has_directives.rb | 2 +- .../schema_definition/mixins/has_indices.rb | 6 ++-- .../schema_definition/mixins/has_type_info.rb | 12 +++---- .../schema_definition/rake_tasks.rb | 8 ++--- .../schema_definition/results.rb | 8 ++--- .../schema_elements/directive.rb | 2 +- .../schema_elements/enum_type.rb | 2 +- .../schema_elements/field.rb | 2 +- .../schema_elements/object_type.rb | 2 +- .../schema_elements/relationship.rb | 2 +- .../schema_elements/type_namer.rb | 4 +-- .../lib/elastic_graph/support/config.rb | 8 ++--- .../json_schema/meta_schema_validator.rb | 2 +- .../support/json_schema/validator.rb | 4 +-- .../support/json_schema/validator_factory.rb | 2 +- .../schema_definition/results_extension.rb | 4 +-- 32 files changed, 84 insertions(+), 120 deletions(-) diff --git a/.yard-lint-todo.yml b/.yard-lint-todo.yml index 235e5a863..754dd4ad2 100644 --- a/.yard-lint-todo.yml +++ b/.yard-lint-todo.yml @@ -78,39 +78,3 @@ Documentation/UndocumentedOptions: - "elasticgraph-support/lib/elastic_graph/support/config.rb" - "elasticgraph-support/lib/elastic_graph/support/graphql_formatter.rb" -# Tags validators -Tags/CollectionType: - Exclude: - - "elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb" - - "elasticgraph-rack/lib/elastic_graph/rack/graphql_endpoint.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/artifacts_helper_methods.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/schema.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/event_envelope.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/enum.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/object.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/scalar.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/union.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/index.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/json_schema_field_metadata.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_directives.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/rake_tasks.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/results.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/directive.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_type.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/object_type.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/relationship.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/scalar_type.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb" - - "elasticgraph-support/lib/elastic_graph/support/config.rb" - - "elasticgraph-support/lib/elastic_graph/support/json_schema/meta_schema_validator.rb" - - "elasticgraph-support/lib/elastic_graph/support/json_schema/validator.rb" - - "elasticgraph-support/lib/elastic_graph/support/json_schema/validator_factory.rb" - - "elasticgraph-warehouse/lib/elastic_graph/warehouse/schema_definition/results_extension.rb" - diff --git a/elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb b/elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb index e971d0d71..7f3a79952 100644 --- a/elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb +++ b/elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb @@ -74,7 +74,7 @@ class RakeTasks < ::Rake::TaskLib # # Defaults to an empty hash. # - # @return [Hash] overrides for specific field, argument, or directive names + # @return [Hash{Symbol => String}] overrides for specific field, argument, or directive names # # @example Spell out comparison operators instead of using shortened forms # ElasticGraph::Local::RakeTasks.new( @@ -115,7 +115,7 @@ class RakeTasks < ::Rake::TaskLib # # Defaults to an empty hash. # - # @return [Hash] overrides for specific type names + # @return [Hash{Symbol => String}] overrides for specific type names # # @example Rename `JsonSafeLong` to `BigInt` # ElasticGraph::Local::RakeTasks.new( @@ -133,7 +133,7 @@ class RakeTasks < ::Rake::TaskLib # # Defaults to an empty hash. # - # @return [Hash>] overrides for the names of specific enum values for specific enum types + # @return [Hash{Symbol => Hash{Symbol => String}}] overrides for the names of specific enum values for specific enum types # # @example Shorten the names of the `DayOfWeek` enum values # ElasticGraph::Local::RakeTasks.new( @@ -285,7 +285,7 @@ class RakeTasks < ::Rake::TaskLib # Hash mapping environments (e.g. `:test`, `:dev`, etc) to port numbers for use when booting Elasticsearch or OpenSearch. The hash # automatically includes an entry for the `:local` environment, using a port number extracted from `local_config_yaml`. # - # @return [Hash] mapping from environment name to port number + # @return [Hash{Symbol => Integer}] mapping from environment name to port number # # @example Define what port to use to boot the datastore for the `:test` environment # ElasticGraph::Local::RakeTasks.new( @@ -330,7 +330,7 @@ class RakeTasks < ::Rake::TaskLib # registered callback. # # @param type [Symbol] type of data batch. Can be the name of a GraphQL type or any other name you want to give a batch of fake data - # @yieldreturn [Array>] generated data + # @yieldreturn [Array Object}>] generated data # # @example Register a callback to generate fake `campaigns` data # ElasticGraph::Local::RakeTasks.new( diff --git a/elasticgraph-rack/lib/elastic_graph/rack/graphql_endpoint.rb b/elasticgraph-rack/lib/elastic_graph/rack/graphql_endpoint.rb index f3a283988..4bf9845f9 100644 --- a/elasticgraph-rack/lib/elastic_graph/rack/graphql_endpoint.rb +++ b/elasticgraph-rack/lib/elastic_graph/rack/graphql_endpoint.rb @@ -30,8 +30,8 @@ def initialize(graphql) # Responds to a Rack request. # - # @param env [Hash] Rack env - # @return [Array(Integer, Hash, Array)] + # @param env [Hash{String => Object}] Rack env + # @return [Array(Integer, Hash{String => String}, Array)] def call(env) rack_request = ::Rack::Request.new(env) diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts.rb index 7fa07892d..359b6fa27 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts.rb @@ -20,7 +20,7 @@ module SchemaArtifacts # Builds a `SchemaArtifacts::FromDisk` instance using the provided YAML settings. # - # @param parsed_yaml [Hash] hash parsed from a settings YAML file + # @param parsed_yaml [Hash{String => Object}] hash parsed from a settings YAML file # @return [FromDisk] def self.from_parsed_yaml(parsed_yaml) config = Config.from_parsed_yaml(parsed_yaml) || Config.new diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/artifacts_helper_methods.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/artifacts_helper_methods.rb index 8f5b1fb3c..95f2d3c33 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/artifacts_helper_methods.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/artifacts_helper_methods.rb @@ -15,7 +15,7 @@ module ArtifactsHelperMethods # Provides accesses to the datastore scripts, typically written using the [painless scripting # language](https://www.elastic.co/docs/explore-analyze/scripting/modules-scripting-painless). # - # @return [Hash>] + # @return [Hash{String => Hash{String => Object}}] def datastore_scripts datastore_config.fetch("scripts") end @@ -23,14 +23,14 @@ def datastore_scripts # Provides accesses to the datastore index templates, which are used for a rollover index defined using # {SchemaDefinition::Indexing::Index#rollover}. # - # @return [Hash>] + # @return [Hash{String => Hash{String => Object}}] def index_templates datastore_config.fetch("index_templates") end # Provides accesses to the datastore indices, used for an index that does not rollover. # - # @return [Hash>] + # @return [Hash{String => Hash{String => Object}}] def indices datastore_config.fetch("indices") end @@ -38,7 +38,7 @@ def indices # Provides access to the [mappings](https://www.elastic.co/docs/manage-data/data-store/mapping) of both the # {#index_templates} and {#indices}. # - # @return [Hash>] + # @return [Hash{String => Hash{String => Object}}] def index_mappings_by_index_def_name @index_mappings_by_index_def_name ||= index_templates .transform_values { |config| config.fetch("template").fetch("mappings") } diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb index ed7e0defd..31189fbf6 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/from_disk.rb @@ -49,7 +49,7 @@ def graphql_schema_string # In addition, they are used by `elasticgraph-indexer` to validate data before indexing it. # # @param version [Integer] the desired JSON schema version - # @return [Hash] + # @return [Hash{String => Object}] # @raise [Errors::MissingSchemaArtifactError] when the provided version does not exist within the `artifacts_dir`. # @see #available_json_schema_versions # @see #latest_json_schema_version @@ -114,7 +114,7 @@ def latest_json_schema_version # # `elasticgraph-admin` uses this artifact to administer the datastore. # - # @return [Hash] + # @return [Hash{String => Object}] # @raise [Errors::MissingSchemaArtifactError] when `datastore_config.yaml` does not exist within the `artifacts_dir`. # # @example Print the current list of indices diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/schema.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/schema.rb index 6167c5376..37e284f0e 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/schema.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/schema.rb @@ -57,7 +57,7 @@ class Schema < ::Data.define( # Loads a {RuntimeMetadata::Schema} from the given hash. # - # @param hash [Hash>] runtime metadata hash loaded from YAML + # @param hash [Hash{String => Hash{String => Object}}] runtime metadata hash loaded from YAML # @return [Schema] the runtime metadata schema instance def self.from_hash(hash) elasticgraph_version = hash.fetch(ELASTICGRAPH_VERSION) do @@ -114,7 +114,7 @@ def self.from_hash(hash) # Converts to a hash that is suitable for dumping to disk as YAML. # - # @return [Hash>] runtime metadata hash ready to dump to YAML + # @return [Hash{String => Hash{String => Object}}] runtime metadata hash ready to dump to YAML def to_dumpable_hash Support::HashUtil.recursively_prune_nils_and_empties_from({ # Keys here are ordered alphabetically; please keep them that way. diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb index 94dae1fd3..63ee460f6 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb @@ -324,7 +324,7 @@ def deleted_type(name) # # @param extension_module [Module] GraphQL extension module # @param defined_at [String] the `require` path of the extension module - # @param config [Hash] extension-specific configuration forwarded to the extension module's `initialize` method + # @param config [Hash{Symbol => Object}] extension-specific configuration forwarded to the extension module's `initialize` method # @return [void] # # @example Register `elasticgraph-query_registry` extension module diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/event_envelope.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/event_envelope.rb index 605024146..dd7868c37 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/event_envelope.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/event_envelope.rb @@ -17,7 +17,7 @@ module Indexing module EventEnvelope # @param indexed_type_names [Array] names of the indexed types # @param json_schema_version [Integer] the version of the JSON schema - # @return [Hash] the JSON schema for the ElasticGraph event envelope for the given `indexed_type_names`. + # @return [Hash{String => Object}] the JSON schema for the ElasticGraph event envelope for the given `indexed_type_names`. def self.json_schema(indexed_type_names, json_schema_version) { "type" => "object", diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field.rb index 51cf47b32..5c1ea37a8 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field.rb @@ -44,7 +44,7 @@ class Field < Support::MemoizableData.define( "text" => {"maxLength" => DEFAULT_MAX_TEXT_LENGTH} } - # @return [Hash] the mapping for this field. The returned hash should be composed entirely + # @return [Hash{String => Object}] the mapping for this field. The returned hash should be composed entirely # of Ruby primitives that, when converted to a JSON string, match the structure required by # [Elasticsearch](https://www.elastic.co/guide/en/elasticsearch/reference/current/mapping.html). def mapping @@ -63,7 +63,7 @@ def mapping end end - # @return [Hash] the JSON schema definition for this field. The returned object should + # @return [Hash{String => Object}] the JSON schema definition for this field. The returned object should # be composed entirely of Ruby primitives that, when converted to a JSON string, match the # requirements of [the JSON schema spec](https://json-schema.org/). def json_schema @@ -85,7 +85,7 @@ def json_schema_metadata # work properly. # # @param fields [Array] fields to generate a mapping hash from - # @return [Hash] generated mapping hash + # @return [Hash{String => Object}] generated mapping hash def self.normalized_mapping_hash_for(fields) # When an object field has `properties`, the datastore normalizes the mapping by dropping # the `type => object` (it's implicit, as `properties` are only valid on an object...). diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/enum.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/enum.rb index d2f72fb6f..2ac1cd1a7 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/enum.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/enum.rb @@ -23,23 +23,23 @@ module FieldType # # @api private class Enum < ::Data - # @return [Hash] the JSON schema for this enum type. + # @return [Hash{String => ::Object}] the JSON schema for this enum type. def to_json_schema {"type" => "string", "enum" => enum_value_names} end - # @return [Hash] the datastore mapping for this enum type. + # @return [Hash{String => ::Object}] the datastore mapping for this enum type. def to_mapping {"type" => "keyword"} end - # @return [Hash] additional ElasticGraph metadata to put in the JSON schema for this enum type. + # @return [Hash{String => ::Object}] additional ElasticGraph metadata to put in the JSON schema for this enum type. def json_schema_field_metadata_by_field_name {} end - # @param customizations [Hash] JSON schema customizations - # @return [Hash] formatted customizations. + # @param customizations [Hash{String => ::Object}] JSON schema customizations + # @return [Hash{String => ::Object}] formatted customizations. def format_field_json_schema_customizations(customizations) # Since an enum type already restricts the values to a small set of allowed values, we do not need to keep # other customizations (such as the `maxLength` field customization EG automatically applies to fields diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/object.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/object.rb index c01fcbd4e..d62f6e32c 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/object.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/object.rb @@ -21,15 +21,15 @@ module FieldType # @!attribute [r] subfields # @return [Array] the subfields of this object type # @!attribute [r] mapping_options - # @return [Hash] options to be included in the mapping + # @return [Hash{String => ::Object}] options to be included in the mapping # @!attribute [r] json_schema_options - # @return [Hash] options to be included in the JSON schema + # @return [Hash{String => ::Object}] options to be included in the JSON schema # @!attribute [r] doc_comment # @return [String, nil] documentation for the type # # @api private class Object < Support::MemoizableData.define(:schema_def_state, :type_name, :subfields, :mapping_options, :json_schema_options, :doc_comment) - # @return [Hash] the datastore mapping for this object type. + # @return [Hash{String => ::Object}] the datastore mapping for this object type. def to_mapping @to_mapping ||= begin base_mapping = Field.normalized_mapping_hash_for(subfields) @@ -41,7 +41,7 @@ def to_mapping end end - # @return [Hash] the JSON schema for this object type. + # @return [Hash{String => ::Object}] the JSON schema for this object type. def to_json_schema @to_json_schema ||= if json_schema_options.empty? @@ -68,13 +68,13 @@ def to_json_schema end end - # @return [Hash] additional ElasticGraph metadata to put in the JSON schema for this object type. + # @return [Hash{String => ::Object}] additional ElasticGraph metadata to put in the JSON schema for this object type. def json_schema_field_metadata_by_field_name subfields.to_h { |f| [f.name, f.json_schema_metadata] } end - # @param customizations [Hash] JSON schema customizations - # @return [Hash] formatted customizations. + # @param customizations [Hash{String => ::Object}] JSON schema customizations + # @return [Hash{String => ::Object}] formatted customizations. def format_field_json_schema_customizations(customizations) customizations end diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/scalar.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/scalar.rb index cb9c3132e..f39a54993 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/scalar.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/scalar.rb @@ -22,23 +22,23 @@ module FieldType # # @api private class Scalar < ::Data - # @return [Hash] the datastore mapping for this scalar type. + # @return [Hash{String => ::Object}] the datastore mapping for this scalar type. def to_mapping Support::HashUtil.stringify_keys(scalar_type.mapping_options) end - # @return [Hash] the JSON schema for this scalar type. + # @return [Hash{String => ::Object}] the JSON schema for this scalar type. def to_json_schema Support::HashUtil.stringify_keys(scalar_type.json_schema_options) end - # @return [Hash] additional ElasticGraph metadata to put in the JSON schema for this scalar type. + # @return [Hash{String => ::Object}] additional ElasticGraph metadata to put in the JSON schema for this scalar type. def json_schema_field_metadata_by_field_name {} end - # @param customizations [Hash] JSON schema customizations - # @return [Hash] formatted customizations. + # @param customizations [Hash{String => ::Object}] JSON schema customizations + # @return [Hash{String => ::Object}] formatted customizations. def format_field_json_schema_customizations(customizations) customizations end diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/union.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/union.rb index e4d6e634f..5c49e99e9 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/union.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/field_type/union.rb @@ -20,11 +20,11 @@ module FieldType # of the subtypes (and also a `__typename` keyword field). # # @!attribute [r] subtypes_by_name - # @return [Hash] the subtypes of the union, keyed by name. + # @return [Hash{String => Object}] the subtypes of the union, keyed by name. # # @api private class Union < ::Data.define(:subtypes_by_name) - # @return [Hash] the JSON schema for this union type. + # @return [Hash{String => ::Object}] the JSON schema for this union type. def to_json_schema subtype_json_schemas = subtypes_by_name.keys.map { |name| {"$ref" => "#/$defs/#{name}"} } @@ -43,7 +43,7 @@ def to_json_schema } end - # @return [Hash] the datastore mapping for this union type. + # @return [Hash{String => ::Object}] the datastore mapping for this union type. def to_mapping mapping_subfields = subtypes_by_name.values.map(&:subfields).reduce([], :union) @@ -53,13 +53,13 @@ def to_mapping ) end - # @return [Hash] additional ElasticGraph metadata to put in the JSON schema for this union type. + # @return [Hash{String => ::Object}] additional ElasticGraph metadata to put in the JSON schema for this union type. def json_schema_field_metadata_by_field_name {} end - # @param customizations [Hash] JSON schema customizations - # @return [Hash] formatted customizations. + # @param customizations [Hash{String => ::Object}] JSON schema customizations + # @return [Hash{String => ::Object}] formatted customizations. def format_field_json_schema_customizations(customizations) customizations end diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/index.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/index.rb index bac10d1e2..536d15a11 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/index.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/index.rb @@ -27,7 +27,7 @@ module Indexing # @!attribute [r] default_sort_pairs # @return [Array<(String, Symbol)>] (field name, direction) pairs for the default sort # @!attribute [r] settings - # @return [Hash<(String, Object)>] datastore settings for the index + # @return [Hash{String => Object}] datastore settings for the index # @!attribute [r] schema_def_state # @return [State] schema definition state # @!attribute [r] indexed_type @@ -42,7 +42,7 @@ class Index < Struct.new(:name, :default_sort_pairs, :settings, :schema_def_stat include Mixins::HasReadableToSAndInspect.new { |i| i.name } # @param name [String] name of the index - # @param settings [Hash<(String, Object)>] datastore settings for the index + # @param settings [Hash{String => Object}] datastore settings for the index # @param schema_def_state [State] schema definition state # @param indexed_type [SchemaElements::ObjectType, SchemaElements::InterfaceType, SchemaElements::UnionType] type backed by this index # @yield [Index] the index, for further customization @@ -230,7 +230,7 @@ def uses_custom_routing? routing_field_path.path_in_index != "id" end - # @return [Hash] datastore configuration for this index for when it does not use rollover + # @return [Hash{String => Object}] datastore configuration for this index for when it does not use rollover def to_index_config { "aliases" => {}, @@ -239,7 +239,7 @@ def to_index_config }.compact end - # @return [Hash] datastore configuration for the index template that will be defined if rollover is used + # @return [Hash{String => Object}] datastore configuration for the index template that will be defined if rollover is used def to_index_template_config { "index_patterns" => ["#{name}#{ROLLOVER_INDEX_INFIX_MARKER}*"], diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/json_schema_field_metadata.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/json_schema_field_metadata.rb index 535d11b2d..ad7f3dfc0 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/json_schema_field_metadata.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/json_schema_field_metadata.rb @@ -22,7 +22,7 @@ module Indexing # # @api private class JSONSchemaFieldMetadata < ::Data - # @return [Hash] hash form of the metadata that can be dumped in JSON schema + # @return [Hash{String => String}] hash form of the metadata that can be dumped in JSON schema def to_dumpable_hash {"type" => type, "nameInIndex" => name_in_index} end diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_directives.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_directives.rb index a46c81728..eea970237 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_directives.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_directives.rb @@ -14,7 +14,7 @@ module HasDirectives # Adds a GraphQL directive to the current schema element. # # @param name [String] name of the directive - # @param arguments [Hash] arguments for the directive + # @param arguments [Hash{String => Object}] arguments for the directive # @return [void] # # @example Add a standard GraphQL directive to a field diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb index 886e2c990..df78cb4b6 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb @@ -45,7 +45,7 @@ def initialize(*args, **options) # # @param name [String] name of the index. See the [Elasticsearch docs](https://www.elastic.co/guide/en/elasticsearch/reference/8.15/indices-create-index.html#indices-create-api-path-params) # for restrictions. - # @param settings [Hash] datastore index settings (without the `index.` prefix) forwarded to the index definition. See the [Elasticsearch docs](https://www.elastic.co/guide/en/elasticsearch/reference/8.15/index-modules.html#index-modules-settings) for available settings. + # @param settings [Hash{Symbol => Object}] datastore index settings (without the `index.` prefix) forwarded to the index definition. See the [Elasticsearch docs](https://www.elastic.co/guide/en/elasticsearch/reference/8.15/index-modules.html#index-modules-settings) for available settings. # @yield [Indexing::Index] the index, so it can be customized further # @return [void] # @@ -117,7 +117,7 @@ def index(name, **settings, &block) # can override this using {SchemaElements::Field#resolve_with}. # # @param default_resolver_name [Symbol] name of the GraphQL resolver to use as the default for fields of this type - # @param config [Hash] resolver-specific configuration forwarded to the resolver's `initialize` method within the `config` parameter + # @param config [Hash{Symbol => Object}] resolver-specific configuration forwarded to the resolver's `initialize` method within the `config` parameter # @return [void] # @see API#register_graphql_resolver def resolve_fields_with(default_resolver_name, **config) @@ -252,7 +252,7 @@ def derived_indexed_types # `runtime_metadata.yaml` schema artifact and made available at runtime to `elasticgraph-graphql` and # `elasticgraph-indexer`. # - # @param overrides [Hash] runtime metadata attributes to override, corresponding to + # @param overrides [Hash{Symbol => Object}] runtime metadata attributes to override, corresponding to # {SchemaArtifacts::RuntimeMetadata::ObjectType} fields (e.g. `:elasticgraph_category`, `:source_type`) # @return [void] def override_runtime_metadata(**overrides) diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb index 6c17fb4fd..a068495ec 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_type_info.rb @@ -19,12 +19,12 @@ module Mixins # - {SchemaElements::TypeWithSubfields}: allows customization of how an object type is represented in JSON schema and the index. # - {SchemaElements::Field}: allows customization of a specific field over the field type's standard JSON schema and the index mapping. module HasTypeInfo - # @return [Hash] datastore mapping options + # @return [Hash{Symbol => Object}] datastore mapping options def mapping_options @mapping_options ||= {} end - # @return [Hash] JSON schema options + # @return [Hash{Symbol => Object}] JSON schema options def json_schema_options @json_schema_options ||= {} end @@ -63,15 +63,15 @@ def json_schema_options # modeled as an object in GraphQL. For example, we use it for the `GeoLocation` type so they get indexed in Elasticsearch using the # [geo_point type](https://www.elastic.co/guide/en/elasticsearch/reference/7.10/geo-point.html). # - # @param options [Hash] mapping options--must be limited to {CUSTOMIZABLE_DATASTORE_PARAMS} + # @param options [Hash{Symbol => Object}] mapping options--must be limited to {CUSTOMIZABLE_DATASTORE_PARAMS} # @option options [String] :type mapping field type (e.g. `"keyword"`, `"text"`, `"integer"`) # @option options [String] :analyzer analyzer to use for `text` fields # @option options [Boolean] :eager_global_ordinals whether to eagerly load global ordinals # @option options [Boolean] :enabled whether the field is enabled for indexing - # @option options [Hash] :fields multi-field mappings + # @option options [Hash{String => Object}] :fields multi-field mappings # @option options [String] :format date format string # @option options [Boolean] :index whether the field value should be indexed - # @option options [Hash] :meta arbitrary metadata attached to the field mapping + # @option options [Hash{String => Object}] :meta arbitrary metadata attached to the field mapping # @option options [Boolean] :norms whether field-length normalization is enabled # @option options [Object] :null_value value to substitute for `null` at index time # @option options [String] :search_analyzer analyzer to use at search time (overrides `:analyzer`) @@ -139,7 +139,7 @@ def mapping(**options) # GraphQL schema. If you think you might want to make a field non-nullable in the GraphQL schema some day, it’s a good idea to use # `json_schema nullable: false` now to ensure every indexed record has a non-null value for the field. # - # @param options [Hash] JSON schema options. Any + # @param options [Hash{Symbol => Object}] JSON schema options. Any # [JSON schema validation keyword](https://json-schema.org/understanding-json-schema/reference) is accepted. # In addition, `nullable: false` is supported to disallow `null` values. Common options are shown below. # @option options [String] :type JSON type (e.g. `"string"`, `"integer"`, `"number"`) diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/rake_tasks.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/rake_tasks.rb index 58fbe7517..4307bb0b1 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/rake_tasks.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/rake_tasks.rb @@ -29,15 +29,15 @@ class RakeTasks < ::Rake::TaskLib # @param schema_artifacts_directory [String, Pathname] Directory to dump the schema artifacts in # @param schema_element_name_form [:camelCase, :snake_case] the form of names for schema elements (fields, arguments, directives) # generated by ElasticGraph. - # @param schema_element_name_overrides [Hash] overrides for specific names of schema elements (fields, arguments, + # @param schema_element_name_overrides [Hash{Symbol => String}] overrides for specific names of schema elements (fields, arguments, # directives) generated by ElasticGraph. For example, to rename the `gt` filter field to `greaterThan`, pass `{gt: "greaterThan"}`. - # @param derived_type_name_formats [Hash] overrides for the naming formats used by ElasticGraph for derived GraphQL + # @param derived_type_name_formats [Hash{Symbol => String}] overrides for the naming formats used by ElasticGraph for derived GraphQL # type names. For example, to use `Metrics` instead of `AggregatedValues` as the suffix for the generated types supporting # getting aggregated metrid values, pass `{AggregatedValues: "%{base}Metrics"}`. See {SchemaElements::TypeNamer::DEFAULT_FORMATS} # for the available formats. - # @param type_name_overrides [Hash] overrides for the names of specific GraphQL types. For example, to rename the + # @param type_name_overrides [Hash{Symbol => String}] overrides for the names of specific GraphQL types. For example, to rename the # `DateTime` scalar to `Timestamp`, pass `{DateTime: "Timestamp}`. - # @param enum_value_overrides_by_type [Hash>] overrides for the names of specific enum values for + # @param enum_value_overrides_by_type [Hash{Symbol => Hash{Symbol => String}}] overrides for the names of specific enum values for # specific enum types. For example, to rename the `DayOfWeek.MONDAY` enum to `DayOfWeek.MON`, pass `{DayOfWeek: {MONDAY: "MON"}}`. # @param extension_modules [Array] List of Ruby modules to extend onto the `SchemaDefinition::API` instance. Designed to # support ElasticGraph extension gems (such as `elasticgraph-apollo`). diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/results.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/results.rb index 7010f7720..32f39f98c 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/results.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/results.rb @@ -36,18 +36,18 @@ def graphql_schema_string @graphql_schema_string ||= generate_sdl end - # @return [Hash] the Elasticsearch/OpenSearch configuration dumped as `datastore_config.yaml` + # @return [Hash{String => Object}] the Elasticsearch/OpenSearch configuration dumped as `datastore_config.yaml` def datastore_config @datastore_config ||= generate_datastore_config end - # @return [Hash] runtime metadata used by other parts of ElasticGraph and dumped as `runtime_metadata.yaml` + # @return [Hash{String => Object}] runtime metadata used by other parts of ElasticGraph and dumped as `runtime_metadata.yaml` def runtime_metadata @runtime_metadata ||= build_runtime_metadata end # @param version [Integer] desired JSON schema version - # @return [Hash] the JSON schema for the requested version, if available + # @return [Hash{String => Object}] the JSON schema for the requested version, if available # @raise [Errors::NotFoundError] if the requested JSON schema version is not available def json_schemas_for(version) unless available_json_schema_versions.include?(version) @@ -62,7 +62,7 @@ def available_json_schema_versions @available_json_schema_versions ||= Set[latest_json_schema_version] end - # @return [Hash] the newly generated JSON schema + # @return [Hash{String => Object}] the newly generated JSON schema def latest_json_schema_version current_public_json_schema[JSON_SCHEMA_VERSION_KEY] end diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/directive.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/directive.rb index 77e872607..dbe555157 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/directive.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/directive.rb @@ -17,7 +17,7 @@ module SchemaElements # @!attribute [r] name # @return [String] name of the directive # @!attribute [r] arguments - # @return [Hash] directive arguments + # @return [Hash{Symbol => Object}] directive arguments # @!parse class Directive < ::Data; end class Directive < ::Data.define(:name, :arguments) prepend Mixins::VerifiesGraphQLName diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_type.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_type.rb index 0bdb27b60..27969d454 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_type.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_type.rb @@ -35,7 +35,7 @@ module SchemaElements # @!attribute [rw] for_output # @return [Boolean] `true` if this enum is used for both input and output; `false` if it is for input only # @!attribute [r] values_by_name - # @return [Hash] map of enum values, keyed by name + # @return [Hash{String => EnumValue}] map of enum values, keyed by name class EnumType < Struct.new(:schema_def_state, :type_ref, :for_output, :values_by_name) # @dynamic type_ref, graphql_only? prepend Mixins::VerifiesGraphQLName diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb index 09c2ea499..18832bcd8 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb @@ -546,7 +546,7 @@ def sourced_from(relationship, field_path) # via {Mixins::HasIndices#resolve_fields_with} will be used. # # @param resolver_name [Symbol] name of the GraphQL resolver - # @param config [Hash] resolver-specific configuration forwarded to the resolver's `initialize` method within the `config` parameter + # @param config [Hash{Symbol => Object}] resolver-specific configuration forwarded to the resolver's `initialize` method within the `config` parameter # @return [void] # @see API#register_graphql_resolver # diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/object_type.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/object_type.rb index 057d27394..3eaa9ca4e 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/object_type.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/object_type.rb @@ -38,7 +38,7 @@ class ObjectType < DelegateClass(TypeWithSubfields) include Mixins::ImplementsInterfaces include Mixins::HasReadableToSAndInspect.new { |t| t.name } - # @return [Hash] fields that will be indexed, including __typename for mixed-type indices (types + # @return [Hash{String => Field}] fields that will be indexed, including __typename for mixed-type indices (types # that inherit an index from an abstract supertype) # @private def indexing_fields_by_name_in_index diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/relationship.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/relationship.rb index 29c7ec2f0..76a25d2b4 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/relationship.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/relationship.rb @@ -59,7 +59,7 @@ def initialize(field, cardinality:, related_type:, foreign_key:, direction:) # Adds additional filter conditions to a relationship beyond the foreign key. # - # @param filter [Hash, Hash] additional filter conditions for this relationship + # @param filter [Hash{Symbol => Object}, Hash{String => Object}] additional filter conditions for this relationship # @return [void] # # @example Define additional filter conditions on a `relates_to_one` relationship diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb index fb39a5080..3402a0cd6 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb @@ -64,7 +64,7 @@ def revert_override_for(potentially_overriden_name) # Note: this does not apply any configured `name_overrides`. It's up to the caller to apply that when desired. # # @param format_name [Symbol] key from {DEFAULT_FORMATS} identifying the format to use - # @param args [Hash] placeholder values required by the chosen format (e.g. `:base`, `:parent_types`, `:parent_agg_type`, `:field_path`) + # @param args [Hash{Symbol => String}] placeholder values required by the chosen format (e.g. `:base`, `:parent_types`, `:parent_agg_type`, `:field_path`) # @private def generate_name_for(format_name, **args) format = formats.fetch(format_name) do @@ -140,7 +140,7 @@ def self.placeholders_in(format) # The default formats used for derived GraphQL type names. These formats can be customized by providing `derived_type_name_formats` # to {RakeTasks} or {Local::RakeTasks}. # - # @return [Hash] + # @return [Hash{Symbol => String}] DEFAULT_FORMATS = { AggregatedValues: "%{base}AggregatedValues", Aggregation: "%{base}Aggregation", diff --git a/elasticgraph-support/lib/elastic_graph/support/config.rb b/elasticgraph-support/lib/elastic_graph/support/config.rb index d63f54274..83e8dc7e5 100644 --- a/elasticgraph-support/lib/elastic_graph/support/config.rb +++ b/elasticgraph-support/lib/elastic_graph/support/config.rb @@ -109,7 +109,7 @@ module ClassMethods # # @param at [::String] path from the global configuration root to where this configuration resides # @param optional [::Boolean] whether configuration at the provided `path` is optional - # @param schema [::Hash<::Symbol, ::Object>] JSON Schema definition keywords (e.g. `properties`, `required`, `type`) forwarded to the draft-07 JSON Schema validator + # @param schema [::Hash{::Symbol => ::Object}] JSON Schema definition keywords (e.g. `properties`, `required`, `type`) forwarded to the draft-07 JSON Schema validator # @return [void] # # @example Define a configuration class @@ -147,7 +147,7 @@ def json_schema(at:, optional:, **schema) # Instantiates a config instance from the given parsed YAML class, returning `nil` if there is no config. # In addition, this (along with `Support::FromYamlFile`) makes `from_yaml_file(path_to_file)` available. # - # @param parsed_yaml [::Hash<::String, ::Object>] config hash parsed from YAML + # @param parsed_yaml [::Hash{::String => ::Object}] config hash parsed from YAML # @return [::Data, nil] the instantiated config object or `nil` if there is nothing at the specified path def from_parsed_yaml(parsed_yaml) value_at_path = Support::HashUtil.fetch_value_at_path(parsed_yaml, path.split(".")) { return nil } @@ -162,7 +162,7 @@ def from_parsed_yaml(parsed_yaml) # Instantiates a config instance from the given parsed YAML class, raising an error if there is no config. # - # @param parsed_yaml [::Hash<::String, ::Object>] config hash parsed from YAML + # @param parsed_yaml [::Hash{::String => ::Object}] config hash parsed from YAML # @return [::Data] the instantiated config object # @raise [Errors::ConfigError] if there is no config at the specified path. def from_parsed_yaml!(parsed_yaml) @@ -177,7 +177,7 @@ def raise_invalid_config(error) # Like `new`, but avoids applying JSON schema validation. This is needed so that we can make # `#with` work correctly with the validation and conversion features we offer. # - # @param data [Hash] attribute values matching the members declared by `Data.define` + # @param data [Hash{Symbol => Object}] attribute values matching the members declared by `Data.define` # @private def new_without_validation(**data) instance = allocate diff --git a/elasticgraph-support/lib/elastic_graph/support/json_schema/meta_schema_validator.rb b/elasticgraph-support/lib/elastic_graph/support/json_schema/meta_schema_validator.rb index 17e8bc9d3..4ecc843b1 100644 --- a/elasticgraph-support/lib/elastic_graph/support/json_schema/meta_schema_validator.rb +++ b/elasticgraph-support/lib/elastic_graph/support/json_schema/meta_schema_validator.rb @@ -49,7 +49,7 @@ def self.elastic_graph_internal_meta_schema_validator module MetaSchemaLoader # Builds a validator to validate a JSON schema definition according to the JSON schema meta schema. # - # @param overrides [Hash] meta schema overrides + # @param overrides [Hash{String => Object}] meta schema overrides def self.load_strict_validator(overrides = {}) schema = ::JSONSchemer::Draft7::SCHEMA schema = ::ElasticGraph::Support::HashUtil.deep_merge(schema, overrides) unless overrides.empty? diff --git a/elasticgraph-support/lib/elastic_graph/support/json_schema/validator.rb b/elasticgraph-support/lib/elastic_graph/support/json_schema/validator.rb index e60f4c9bd..1319e7943 100644 --- a/elasticgraph-support/lib/elastic_graph/support/json_schema/validator.rb +++ b/elasticgraph-support/lib/elastic_graph/support/json_schema/validator.rb @@ -15,7 +15,7 @@ module JSONSchema # Responsible for validating JSON data against the ElasticGraph JSON schema for a particular type. # # @!attribute [r] schema - # @return [Hash] a JSON schema + # @return [Hash{String => Object}] a JSON schema # @!attribute [r] sanitize_pii # @return [Boolean] whether to omit data that may contain PII from error messages class Validator < MemoizableData.define(:schema, :sanitize_pii) @@ -34,7 +34,7 @@ def valid?(data) # any validation errors. # # @param data [Object] JSON data to validate - # @return [Array>] validation errors; will be empty if `data` is valid + # @return [Array Object}>] validation errors; will be empty if `data` is valid # # @see #valid? # @see #validate_with_error_message diff --git a/elasticgraph-support/lib/elastic_graph/support/json_schema/validator_factory.rb b/elasticgraph-support/lib/elastic_graph/support/json_schema/validator_factory.rb index 28b40c8ed..b74303d78 100644 --- a/elasticgraph-support/lib/elastic_graph/support/json_schema/validator_factory.rb +++ b/elasticgraph-support/lib/elastic_graph/support/json_schema/validator_factory.rb @@ -18,7 +18,7 @@ class ValidatorFactory # @private attr_reader :root_schema - # @param schema [Hash] the JSON schema for an entire ElasticGraph schema + # @param schema [Hash{String => Object}] the JSON schema for an entire ElasticGraph schema # @param sanitize_pii [Boolean] whether to omit data that may contain PII from error messages def initialize(schema:, sanitize_pii:) @raw_schema = schema diff --git a/elasticgraph-warehouse/lib/elastic_graph/warehouse/schema_definition/results_extension.rb b/elasticgraph-warehouse/lib/elastic_graph/warehouse/schema_definition/results_extension.rb index 09a643da9..218fd9bc2 100644 --- a/elasticgraph-warehouse/lib/elastic_graph/warehouse/schema_definition/results_extension.rb +++ b/elasticgraph-warehouse/lib/elastic_graph/warehouse/schema_definition/results_extension.rb @@ -17,7 +17,7 @@ module SchemaDefinition module ResultsExtension # Returns the warehouse configuration generated from the schema definition. # - # @return [Hash] a hash mapping table names to their configuration + # @return [Hash{String => Hash}] a hash mapping table names to their configuration def warehouse_config @warehouse_config ||= generate_warehouse_config end @@ -26,7 +26,7 @@ def warehouse_config # Generates warehouse configuration from indices that have warehouse table definitions. # - # @return [Hash] a hash mapping table names to their configuration + # @return [Hash{String => Hash}] a hash mapping table names to their configuration def generate_warehouse_config tables = all_types .filter_map { |type| (_ = type).own_index_def if type.respond_to?(:own_index_def) } From ce18a716ba66340deb06a907924163bf93dcf5dc Mon Sep 17 00:00:00 2001 From: myronmarston-toast Date: Fri, 15 May 2026 07:13:22 -0700 Subject: [PATCH 14/14] Fix UndocumentedMethodArguments yard-lint offenses Add @param tags to 52 files where methods had doc comments but were missing parameter documentation. This was the largest category (106 non-@private offenses). Co-Authored-By: Claude Opus 4.6 (1M context) --- .yard-lint-todo.yml | 54 +--------------- .../admin_lambda/rake_adapter.rb | 1 + .../apollo/graphql/engine_extension.rb | 1 + .../apollo/graphql/entities_field_resolver.rb | 1 + .../apollo/schema_definition/api_extension.rb | 1 + .../schema_definition/apollo_directives.rb | 1 + .../schema_definition/state_extension.rb | 1 + .../lib/elastic_graph/graphiql.rb | 1 + .../indexer_autoscaler_lambda.rb | 7 +++ .../lib/elastic_graph/local/docker_runner.rb | 1 + .../lib/elastic_graph/local/rake_tasks.rb | 1 + .../runtime_metadata/computation_detail.rb | 1 + .../configured_graphql_resolver.rb | 1 + .../schema_artifacts/runtime_metadata/enum.rb | 2 + .../runtime_metadata/extension.rb | 9 +++ .../runtime_metadata/graphql_extension.rb | 1 + .../runtime_metadata/graphql_field.rb | 5 ++ .../runtime_metadata/graphql_resolver.rb | 14 +++++ .../runtime_metadata/hash_dumper.rb | 2 + .../runtime_metadata/index_definition.rb | 8 +++ .../runtime_metadata/index_field.rb | 1 + .../runtime_metadata/interface_verifier.rb | 6 ++ .../runtime_metadata/object_type.rb | 7 +++ .../runtime_metadata/params.rb | 11 ++++ .../runtime_metadata/relation.rb | 1 + .../runtime_metadata/scalar_type.rb | 6 ++ .../runtime_metadata/schema_element_names.rb | 3 + .../runtime_metadata/sort_field.rb | 3 + .../runtime_metadata/update_target.rb | 4 ++ .../elastic_graph/schema_definition/api.rb | 23 ++++--- .../schema_definition/factory.rb | 61 +++++++++++++++++++ .../field_initializer_support.rb | 4 ++ .../indexing/list_counts_mapping.rb | 2 + .../indexing/update_target_factory.rb | 6 ++ .../indexing/update_target_resolver.rb | 14 +++++ .../schema_definition/json_schema_pruner.rb | 4 ++ ...has_derived_graphql_type_customizations.rb | 4 ++ .../schema_definition/mixins/has_indices.rb | 10 ++- .../mixins/implements_interfaces.rb | 3 +- .../schema_elements/enum_type.rb | 4 ++ .../schema_elements/field.rb | 57 +++++++++++++++++ .../schema_elements/list_counts_state.rb | 4 ++ .../schema_elements/sub_aggregation_path.rb | 5 ++ .../schema_elements/type_namer.rb | 15 +++++ .../schema_elements/type_with_subfields.rb | 18 ++++++ .../elastic_graph/schema_definition/state.rb | 34 +++++++++++ .../lib/elastic_graph/support/config.rb | 3 + .../support/graphql_formatter.rb | 3 + .../lib/elastic_graph/support/hash_util.rb | 24 ++++++++ .../lib/elastic_graph/support/logger.rb | 8 +++ .../lib/elastic_graph/support/threading.rb | 1 + .../lib/elastic_graph/support/time_set.rb | 22 +++++++ .../lib/elastic_graph/support/time_util.rb | 3 + .../elastic_graph/support/untyped_encoder.rb | 4 ++ .../schema_definition/factory_extension.rb | 1 + .../lib/elastic_graph/warehouse_lambda.rb | 1 + 56 files changed, 428 insertions(+), 65 deletions(-) diff --git a/.yard-lint-todo.yml b/.yard-lint-todo.yml index 754dd4ad2..faa6108da 100644 --- a/.yard-lint-todo.yml +++ b/.yard-lint-todo.yml @@ -10,63 +10,13 @@ # Documentation validators Documentation/BlankLineBeforeDefinition: Exclude: + - "elasticgraph-apollo/lib/elastic_graph/apollo/graphql/engine_extension.rb" - "elasticgraph-elasticsearch/lib/elastic_graph/elasticsearch/client.rb" - "elasticgraph-opensearch/lib/elastic_graph/opensearch/client.rb" -Documentation/UndocumentedMethodArguments: +Tags/OptionTags: Exclude: - - "elasticgraph-admin_lambda/lib/elastic_graph/admin_lambda/rake_adapter.rb" - - "elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/api_extension.rb" - - "elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/apollo_directives.rb" - - "elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/state_extension.rb" - - "elasticgraph-graphiql/lib/elastic_graph/graphiql.rb" - - "elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda.rb" - - "elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/computation_detail.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/configured_graphql_resolver.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/enum.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/extension.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/graphql_extension.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/graphql_field.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/graphql_resolver.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/hash_dumper.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/index_definition.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/index_field.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/interface_verifier.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/object_type.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/params.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/relation.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/scalar_type.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/schema_element_names.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/sort_field.rb" - - "elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/update_target.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/factory.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/derived_fields/field_initializer_support.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/list_counts_mapping.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_factory.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_resolver.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/json_schema_pruner.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_derived_graphql_type_customizations.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/implements_interfaces.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_type.rb" - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/list_counts_state.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/sub_aggregation_path.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_with_subfields.rb" - - "elasticgraph-schema_definition/lib/elastic_graph/schema_definition/state.rb" - - "elasticgraph-support/lib/elastic_graph/support/config.rb" - - "elasticgraph-support/lib/elastic_graph/support/graphql_formatter.rb" - - "elasticgraph-support/lib/elastic_graph/support/hash_util.rb" - - "elasticgraph-support/lib/elastic_graph/support/logger.rb" - - "elasticgraph-support/lib/elastic_graph/support/threading.rb" - - "elasticgraph-support/lib/elastic_graph/support/time_set.rb" - - "elasticgraph-support/lib/elastic_graph/support/time_util.rb" - - "elasticgraph-support/lib/elastic_graph/support/untyped_encoder.rb" - - "elasticgraph-warehouse/lib/elastic_graph/warehouse/schema_definition/factory_extension.rb" - - "elasticgraph-warehouse_lambda/lib/elastic_graph/warehouse_lambda.rb" Documentation/UndocumentedOptions: Exclude: diff --git a/elasticgraph-admin_lambda/lib/elastic_graph/admin_lambda/rake_adapter.rb b/elasticgraph-admin_lambda/lib/elastic_graph/admin_lambda/rake_adapter.rb index 2766a1370..014a0db22 100644 --- a/elasticgraph-admin_lambda/lib/elastic_graph/admin_lambda/rake_adapter.rb +++ b/elasticgraph-admin_lambda/lib/elastic_graph/admin_lambda/rake_adapter.rb @@ -15,6 +15,7 @@ module AdminLambda class RakeAdapter RAKEFILE = File.expand_path("../Rakefile", __FILE__) + # @param argv [Array] command-line arguments to pass to Rake def self.run_rake(argv) capture_output do # We need to instantiate a new application on each invocation, because Rake is normally diff --git a/elasticgraph-apollo/lib/elastic_graph/apollo/graphql/engine_extension.rb b/elasticgraph-apollo/lib/elastic_graph/apollo/graphql/engine_extension.rb index 8bad79226..e798195c1 100644 --- a/elasticgraph-apollo/lib/elastic_graph/apollo/graphql/engine_extension.rb +++ b/elasticgraph-apollo/lib/elastic_graph/apollo/graphql/engine_extension.rb @@ -5,6 +5,7 @@ # https://opensource.org/licenses/MIT. # # frozen_string_literal: true + module ElasticGraph module Apollo # Namespace for all Apollo GraphQL engine logic. diff --git a/elasticgraph-apollo/lib/elastic_graph/apollo/graphql/entities_field_resolver.rb b/elasticgraph-apollo/lib/elastic_graph/apollo/graphql/entities_field_resolver.rb index 5c7b629bc..195effd7b 100644 --- a/elasticgraph-apollo/lib/elastic_graph/apollo/graphql/entities_field_resolver.rb +++ b/elasticgraph-apollo/lib/elastic_graph/apollo/graphql/entities_field_resolver.rb @@ -302,6 +302,7 @@ def customize_query(query, representations) def index_search_hits(response) nil end + # :nocov: def identify_matching_hit(indexed_search_hits, representation, context:, index:) representation.representation_hash diff --git a/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/api_extension.rb b/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/api_extension.rb index 5b2db4351..ff5cfe591 100644 --- a/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/api_extension.rb +++ b/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/api_extension.rb @@ -103,6 +103,7 @@ def target_apollo_federation_version(version) end end + # @param api [ElasticGraph::SchemaDefinition::API] schema definition API instance to extend def self.extended(api) api.factory.extend FactoryExtension api.state.extend StateExtension diff --git a/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/apollo_directives.rb b/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/apollo_directives.rb index 37268e7c2..941215f4b 100644 --- a/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/apollo_directives.rb +++ b/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/apollo_directives.rb @@ -266,6 +266,7 @@ module Tag # Adds the [`@tag` directive](https://www.apollographql.com/docs/federation/federated-types/federated-directives/#tag) # to the schema element. # + # @param name [String] tag name to apply # @return [void] # @see APIExtension#tag_built_in_types_with # @see FieldExtension#tag_with diff --git a/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/state_extension.rb b/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/state_extension.rb index a8258e724..a7059cb77 100644 --- a/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/state_extension.rb +++ b/elasticgraph-apollo/lib/elastic_graph/apollo/schema_definition/state_extension.rb @@ -16,6 +16,7 @@ module StateExtension # @dynamic apollo_directive_definitions, apollo_directive_definitions= attr_accessor :apollo_directive_definitions + # @param state [ElasticGraph::SchemaDefinition::State] state instance to extend def self.extended(state) state.apollo_directive_definitions = [] # Ensure it's never `nil`. end diff --git a/elasticgraph-graphiql/lib/elastic_graph/graphiql.rb b/elasticgraph-graphiql/lib/elastic_graph/graphiql.rb index 71faa54ed..536bc140a 100644 --- a/elasticgraph-graphiql/lib/elastic_graph/graphiql.rb +++ b/elasticgraph-graphiql/lib/elastic_graph/graphiql.rb @@ -29,6 +29,7 @@ module GraphiQL # and a [GraphiQL IDE](https://github.com/graphql/graphiql). # # @param graphql [ElasticGraph::GraphQL] ElasticGraph GraphQL instance + # @param output [IO] where to print status messages (defaults to stdout) # @return [Rack::Builder] built Rack application def self.new(graphql, output: $stdout) tarball_path = ::File.join(__dir__.to_s, "graphiql/assets.tar.gz") diff --git a/elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda.rb b/elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda.rb index a52f03633..ca114e9d5 100644 --- a/elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda.rb +++ b/elasticgraph-indexer_autoscaler_lambda/lib/elastic_graph/indexer_autoscaler_lambda.rb @@ -22,6 +22,9 @@ def self.from_env # A factory method that builds a IndexerAutoscalerLambda instance from the given parsed YAML config. # `from_yaml_file(file_name, &block)` is also available (via `Support::FromYamlFile`). + # + # @param parsed_yaml [Hash{String => Object}] parsed YAML configuration + # @param datastore_client_customization_block [Proc, nil] optional block for customizing the datastore client def self.from_parsed_yaml(parsed_yaml, &datastore_client_customization_block) new(datastore_core: DatastoreCore.from_parsed_yaml(parsed_yaml, &datastore_client_customization_block)) end @@ -29,6 +32,10 @@ def self.from_parsed_yaml(parsed_yaml, &datastore_client_customization_block) # @dynamic datastore_core attr_reader :datastore_core + # @param datastore_core [ElasticGraph::DatastoreCore] core datastore instance + # @param sqs_client [Aws::SQS::Client, nil] optional SQS client override + # @param lambda_client [Aws::Lambda::Client, nil] optional Lambda client override + # @param cloudwatch_client [Aws::CloudWatch::Client, nil] optional CloudWatch client override def initialize( datastore_core:, sqs_client: nil, diff --git a/elasticgraph-local/lib/elastic_graph/local/docker_runner.rb b/elasticgraph-local/lib/elastic_graph/local/docker_runner.rb index 6c1d902f6..c911a3b64 100644 --- a/elasticgraph-local/lib/elastic_graph/local/docker_runner.rb +++ b/elasticgraph-local/lib/elastic_graph/local/docker_runner.rb @@ -31,6 +31,7 @@ def boot exec(command) # we use `exec` so that our process is replaced with that one. end end + # :nocov: def halt prepare_docker_compose_run "down --volumes" do |command| diff --git a/elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb b/elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb index 7f3a79952..fa3be5acc 100644 --- a/elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb +++ b/elasticgraph-local/lib/elastic_graph/local/rake_tasks.rb @@ -330,6 +330,7 @@ class RakeTasks < ::Rake::TaskLib # registered callback. # # @param type [Symbol] type of data batch. Can be the name of a GraphQL type or any other name you want to give a batch of fake data + # @param block [Proc] generates fake data for the given type # @yieldreturn [Array Object}>] generated data # # @example Register a callback to generate fake `campaigns` data diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/computation_detail.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/computation_detail.rb index 0e013abe5..8d61e4e81 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/computation_detail.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/computation_detail.rb @@ -16,6 +16,7 @@ class ComputationDetail < ::Data.define(:empty_bucket_value, :function) FUNCTION = "function" EMPTY_BUCKET_VALUE = "empty_bucket_value" + # @param hash [Hash{String => Object}] serialized computation detail def self.from_hash(hash) new( empty_bucket_value: hash[EMPTY_BUCKET_VALUE], diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/configured_graphql_resolver.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/configured_graphql_resolver.rb index 0e45fa852..974ec64ee 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/configured_graphql_resolver.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/configured_graphql_resolver.rb @@ -17,6 +17,7 @@ class ConfiguredGraphQLResolver < ::Data.define(:name, :config) NAME = "name" CONFIG = "config" + # @param hash [Hash{String => Object}] serialized configured resolver def self.from_hash(hash) new( name: hash.fetch(NAME).to_sym, diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/enum.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/enum.rb index b5525083c..7506d0fa9 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/enum.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/enum.rb @@ -20,6 +20,7 @@ module Enum class Type < ::Data.define(:values_by_name) VALUES_BY_NAME = "values_by_name" + # @param hash [Hash{String => Object}] serialized enum type def self.from_hash(hash) values_by_name = hash[VALUES_BY_NAME]&.transform_values do |value_hash| Value.from_hash(value_hash) @@ -45,6 +46,7 @@ class Value < ::Data.define(:sort_field, :datastore_value, :datastore_abbreviati SORT_FIELD = "sort_field" ALTERNATE_ORIGINAL_NAME = "alternate_original_name" + # @param hash [Hash{String => Object}] serialized enum value def self.from_hash(hash) new( sort_field: hash[SORT_FIELD]&.then { |h| SortField.from_hash(h) }, diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/extension.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/extension.rb index 8f67fa365..65c3b4fa0 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/extension.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/extension.rb @@ -27,11 +27,18 @@ module RuntimeMetadata # @private Extension = ::Data.define(:extension_class, :require_path, :config, :name) do # @implements Extension + # @param extension_class [Class, Module] loaded extension class or module + # @param require_path [String] file path to require to load the extension + # @param config [Hash{Symbol => Object}] extension configuration + # @param name [String] Ruby constant name of the extension def initialize(extension_class:, require_path:, config:, name: extension_class.name.to_s) super(extension_class:, require_path:, config:, name:) end # Loads an extension using a serialized hash, via the provided `ExtensionLoader`. + # + # @param hash [Hash{String => Object}] serialized extension + # @param via [ExtensionLoader] loader to use for resolving the extension def self.load_from_hash(hash, via:) config = Support::HashUtil.symbolize_keys(hash["config"] || {}) # : ::Hash[::Symbol, untyped] via.load(hash.fetch("name"), from: hash.fetch("require_path"), config: config) @@ -47,10 +54,12 @@ def to_dumpable_hash }.reject { |_, v| v.empty? } end + # @param interface_def [Class] interface definition to verify against def verify_against!(interface_def) InterfaceVerifier.verify!(extension_class, against: interface_def, constant_name: name) end + # @param interface_def [Class] interface definition to verify against def verify_against(interface_def) InterfaceVerifier.verify(extension_class, against: interface_def, constant_name: name) end diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/graphql_extension.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/graphql_extension.rb index 673f88b02..92bea5057 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/graphql_extension.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/graphql_extension.rb @@ -23,6 +23,7 @@ def load_extension Extension.load_from_hash(extension_ref, via: GraphQLExtension.loader) end + # @param hash [Hash{String => Object}] serialized GraphQL extension def self.from_hash(hash) new( extension_ref: hash.fetch(EXTENSION_REF) diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/graphql_field.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/graphql_field.rb index ed7f43ee5..fe733e336 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/graphql_field.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/graphql_field.rb @@ -21,6 +21,7 @@ class GraphQLField < ::Data.define(:name_in_index, :relation, :computation_detai AGGREGATION_DETAIL = "computation_detail" RESOLVER = "resolver" + # @param hash [Hash{String => Object}] serialized GraphQL field def self.from_hash(hash) new( name_in_index: hash[NAME_IN_INDEX], @@ -43,6 +44,8 @@ def to_dumpable_hash # Indicates if we need this field in our dumped runtime metadata, when it has the given # `name_in_graphql`. Fields that have not been customized in some way do not need to be # included in the dumped runtime metadata. + # + # @param name_in_graphql [String] field name as it appears in the GraphQL schema def needed?(name_in_graphql) !!relation || !!computation_detail || @@ -51,6 +54,8 @@ def needed?(name_in_graphql) false end + # @param empty_bucket_value [Object, nil] default value for empty aggregation buckets + # @param function [Symbol] aggregation function name def with_computation_detail(empty_bucket_value:, function:) with(computation_detail: ComputationDetail.new( empty_bucket_value: empty_bucket_value, diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/graphql_resolver.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/graphql_resolver.rb index 559c84172..2012b3bc0 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/graphql_resolver.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/graphql_resolver.rb @@ -29,6 +29,7 @@ def load_resolver Extension.load_from_hash(resolver_ref, via: loader) end + # @param hash [Hash{String => Object}] serialized GraphQL resolver def self.from_hash(hash) new( needs_lookahead: hash.fetch(NEEDS_LOOKAHEAD), @@ -46,20 +47,33 @@ def to_dumpable_hash # @private class InterfaceWithLookahead + # @param elasticgraph_graphql [ElasticGraph::GraphQL] GraphQL instance + # @param config [Hash{Symbol => Object}] resolver configuration def initialize(elasticgraph_graphql:, config:) # must be defined, but nothing to do end + # @param field [Object] GraphQL field being resolved + # @param object [Object] parent object + # @param args [Hash{Symbol => Object}] field arguments + # @param context [Object] GraphQL context + # @param lookahead [Object] lookahead into sub-selections def resolve(field:, object:, args:, context:, lookahead:) end end # @private class InterfaceWithoutLookahead + # @param elasticgraph_graphql [ElasticGraph::GraphQL] GraphQL instance + # @param config [Hash{Symbol => Object}] resolver configuration def initialize(elasticgraph_graphql:, config:) # must be defined, but nothing to do end + # @param field [Object] GraphQL field being resolved + # @param object [Object] parent object + # @param args [Hash{Symbol => Object}] field arguments + # @param context [Object] GraphQL context def resolve(field:, object:, args:, context:) end end diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/hash_dumper.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/hash_dumper.rb index 7423047b3..fca982934 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/hash_dumper.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/hash_dumper.rb @@ -11,6 +11,8 @@ module SchemaArtifacts module RuntimeMetadata # @private module HashDumper + # @param hash [Hash{String => Object}] hash to dump in sorted order + # @yield [value] transforms each value for dumping def self.dump_hash(hash) hash.sort_by(&:first).to_h do |key, value| [key, yield(value)] diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/index_definition.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/index_definition.rb index 9e4f26eb0..98ea4e418 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/index_definition.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/index_definition.rb @@ -24,6 +24,12 @@ class IndexDefinition < ::Data.define(:route_with, :rollover, :default_sort_fiel FIELDS_BY_PATH = "fields_by_path" HAS_HAD_MULTIPLE_SOURCES = "has_had_multiple_sources" + # @param route_with [String, nil] field path used for routing + # @param rollover [Rollover, nil] rollover configuration + # @param default_sort_fields [Array] default sort fields for queries + # @param current_sources [Array] current source event types + # @param fields_by_path [Hash{String => IndexField}] index field metadata keyed by path + # @param has_had_multiple_sources [Boolean] whether this index has ever had multiple sources def initialize(route_with:, rollover:, default_sort_fields:, current_sources:, fields_by_path:, has_had_multiple_sources:) super( route_with: route_with, @@ -35,6 +41,7 @@ def initialize(route_with:, rollover:, default_sort_fields:, current_sources:, f ) end + # @param hash [Hash{String => Object}] serialized index definition def self.from_hash(hash) new( route_with: hash[ROUTE_WITH], @@ -64,6 +71,7 @@ class Rollover < ::Data.define(:frequency, :timestamp_field_path) TIMESTAMP_FIELD_PATH = "timestamp_field_path" # @implements Rollover + # @param hash [Hash{String => Object}] serialized rollover configuration def self.from_hash(hash) new( frequency: hash.fetch(FREQUENCY).to_sym, diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/index_field.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/index_field.rb index 9c5d4fe18..3c52306fc 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/index_field.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/index_field.rb @@ -17,6 +17,7 @@ module RuntimeMetadata class IndexField < ::Data.define(:source) SOURCE = "source" + # @param hash [Hash{String => Object}] serialized index field def self.from_hash(hash) new( source: hash[SOURCE] || SELF_RELATIONSHIP_NAME diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/interface_verifier.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/interface_verifier.rb index d57bb7004..f54e582b1 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/interface_verifier.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/interface_verifier.rb @@ -24,6 +24,9 @@ module RuntimeMetadata # @private module InterfaceVerifier class << self + # @param extension [Module] module whose method signatures will be checked + # @param against [Module] interface definition to verify against + # @param constant_name [String] fully qualified name of the extension constant def verify!(extension, against:, constant_name:) problems = verify(extension, against:, constant_name:) @@ -34,6 +37,9 @@ def verify!(extension, against:, constant_name:) end end + # @param extension [Module] module whose method signatures will be checked + # @param against [Module] interface definition to verify against + # @param constant_name [String] fully qualified name of the extension constant def verify(extension, against:, constant_name:) problems = [] # : ::Array[::String] problems.concat(verify_methods("class", extension.singleton_class, against.singleton_class)) diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/object_type.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/object_type.rb index f5ddcf1a8..d5338e586 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/object_type.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/object_type.rb @@ -34,6 +34,12 @@ class ObjectType < ::Data.define( SOURCE_TYPE = "source_type" GRAPHQL_ONLY_RETURN_TYPE = "graphql_only_return_type" + # @param update_targets [Array] targets for datastore update calls + # @param index_definition_names [Array] names of associated index definitions + # @param graphql_fields_by_name [Hash{String => GraphQLField}] GraphQL field metadata keyed by field name + # @param elasticgraph_category [Symbol, nil] category tag for this object type + # @param source_type [String, nil] name of the GraphQL type from which this type was generated + # @param graphql_only_return_type [Boolean] whether this type exists only as a GraphQL return type def initialize(update_targets:, index_definition_names:, graphql_fields_by_name:, elasticgraph_category:, source_type:, graphql_only_return_type:) graphql_fields_by_name = graphql_fields_by_name.select { |name, field| field.needed?(name) } @@ -47,6 +53,7 @@ def initialize(update_targets:, index_definition_names:, graphql_fields_by_name: ) end + # @param hash [Hash{String => Object}] serialized form of an ObjectType def self.from_hash(hash) update_targets = hash[UPDATE_TARGETS]&.map do |update_target_hash| UpdateTarget.from_hash(update_target_hash) diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/params.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/params.rb index 52e312cbf..c5de6eb5b 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/params.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/params.rb @@ -14,14 +14,18 @@ module SchemaArtifacts module RuntimeMetadata # @private module Param + # @param hash_of_params [Hash{String => DynamicParam, StaticParam}] params keyed by name def self.dump_params_hash(hash_of_params) hash_of_params.sort_by(&:first).to_h { |name, param| [name, param.to_dumpable_hash(name)] } end + # @param hash_of_hashes [Hash{String => Hash{String => Object}}] serialized params keyed by name def self.load_params_hash(hash_of_hashes) hash_of_hashes.to_h { |name, hash| [name, from_hash(hash, name)] } end + # @param hash [Hash{String => Object}] serialized param data + # @param name [String] param name, used as default source path for dynamic params def self.from_hash(hash, name) if hash.key?(StaticParam::VALUE) StaticParam.from_hash(hash) @@ -38,6 +42,8 @@ class DynamicParam < ::Data.define(:source_path, :cardinality) SOURCE_PATH = "source_path" CARDINALITY = "cardinality" + # @param hash [Hash{String => Object}] serialized form of a DynamicParam + # @param name [String] param name, used as default source path def self.from_hash(hash, name) new( source_path: hash[SOURCE_PATH] || name, @@ -45,6 +51,7 @@ def self.from_hash(hash, name) ) end + # @param param_name [String] name of this param, used to omit redundant source path def to_dumpable_hash(param_name) { # Keys here are ordered alphabetically; please keep them that way. @@ -53,6 +60,7 @@ def to_dumpable_hash(param_name) } end + # @param event_or_prepared_record [Hash{String => Object}] event or prepared record to extract value from def value_for(event_or_prepared_record) case cardinality when :many then Support::HashUtil.fetch_leaf_values_at_path(event_or_prepared_record, source_path.split(".")) { [] } @@ -65,10 +73,12 @@ def value_for(event_or_prepared_record) class StaticParam < ::Data.define(:value) VALUE = "value" + # @param hash [Hash{String => Object}] serialized form of a StaticParam def self.from_hash(hash) new(value: hash.fetch(VALUE)) end + # @param param_name [String] name of this param (unused for static params, present for interface consistency) def to_dumpable_hash(param_name) { # Keys here are ordered alphabetically; please keep them that way. @@ -76,6 +86,7 @@ def to_dumpable_hash(param_name) } end + # @param event_or_prepared_record [Hash{String => Object}] event or prepared record (ignored; static value is always returned) def value_for(event_or_prepared_record) value end diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/relation.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/relation.rb index 035c06edc..1fa0562ef 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/relation.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/relation.rb @@ -16,6 +16,7 @@ class Relation < ::Data.define(:foreign_key, :direction, :additional_filter, :fo ADDITIONAL_FILTER = "additional_filter" FOREIGN_KEY_NESTED_PATHS = "foreign_key_nested_paths" + # @param hash [Hash{String => Object}] serialized form of a Relation def self.from_hash(hash) new( foreign_key: hash[FOREIGN_KEY], diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/scalar_type.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/scalar_type.rb index 704706d45..2e234a782 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/scalar_type.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/scalar_type.rb @@ -37,6 +37,7 @@ def self.indexing_preparer_extension_loader # serialized hash form (matching what `to_dumpable_hash` returns). We expose a method # this way because we want to use a single loader for all `ScalarType`s that # need to get loaded, as it performs some caching for efficiency. + # @param scalar_type_hashes_by_name [Hash{String => Hash{String => Object}}] serialized scalar types keyed by type name def self.load_many(scalar_type_hashes_by_name) scalar_type_hashes_by_name.transform_values do |hash| new( @@ -79,15 +80,20 @@ def to_dumpable_hash # @private class ScalarCoercionAdapterInterface + # @param value [Object] scalar value to coerce + # @param ctx [Object] GraphQL context def self.coerce_input(value, ctx) end + # @param value [Object] scalar value to coerce + # @param ctx [Object] GraphQL context def self.coerce_result(value, ctx) end end # @private class ScalarIndexingPreparerInterface + # @param value [Object] scalar value to prepare for indexing def self.prepare_for_indexing(value) end end diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/schema_element_names.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/schema_element_names.rb index 316da3382..74859a42f 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/schema_element_names.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/schema_element_names.rb @@ -16,6 +16,7 @@ module RuntimeMetadata # # @private class SchemaElementNamesDefinition + # @param element_names [Array] canonical names of the schema elements def self.new(*element_names) ::Data.define(:form, :overrides, :exposed_name_by_canonical_name, :canonical_name_by_exposed_name) do const_set(:ELEMENT_NAMES, element_names) @@ -118,6 +119,7 @@ def validate_no_name_collisions(canonical_name_by_exposed_name, exposed_name_by_ module SnakeCaseConverter extend self + # @param name [String] name to convert to snake_case def normalize_case(name) name.gsub(/([[:upper:]])/) { "_#{$1.downcase}" } end @@ -127,6 +129,7 @@ def normalize_case(name) module CamelCaseConverter extend self + # @param name [String] name to convert to camelCase def normalize_case(name) name.gsub(/(?<=\w)_(\w)/) { $1.upcase } end diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/sort_field.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/sort_field.rb index 7e5c20c35..f4fcd115b 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/sort_field.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/sort_field.rb @@ -13,6 +13,8 @@ module SchemaArtifacts module RuntimeMetadata # @private class SortField < ::Data.define(:field_path, :direction) + # @param field_path [String] dot-separated path to the field in the index + # @param direction [Symbol] sort direction (`:asc` or `:desc`) def initialize(field_path:, direction:) unless direction == :asc || direction == :desc raise Errors::SchemaError, "Sort direction `#{direction.inspect}` is invalid; it must be `:asc` or `:desc`" @@ -24,6 +26,7 @@ def initialize(field_path:, direction:) FIELD_PATH = "field_path" DIRECTION = "direction" + # @param hash [Hash{String => Object}] serialized form of a SortField def self.from_hash(hash) new( field_path: hash[FIELD_PATH], diff --git a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/update_target.rb b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/update_target.rb index 2e8fd0653..fed2ae596 100644 --- a/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/update_target.rb +++ b/elasticgraph-schema_artifacts/lib/elastic_graph/schema_artifacts/runtime_metadata/update_target.rb @@ -34,6 +34,7 @@ class UpdateTarget < ::Data.define( DATA_PARAMS = "data_params" METADATA_PARAMS = "metadata_params" + # @param hash [Hash{String => Object}] serialized form of an UpdateTarget def self.from_hash(hash) new( type: hash[TYPE], @@ -65,6 +66,9 @@ def for_normal_indexing? script_id == INDEX_DATA_UPDATE_SCRIPT_ID end + # @param doc_id [String] document ID for the update + # @param event [Hash{String => Object}] source event containing metadata + # @param prepared_record [Hash{String => Object}] prepared record containing data fields def params_for(doc_id:, event:, prepared_record:) data = data_params.to_h do |name, param| [name, param.value_for(prepared_record)] diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb index 63ee460f6..68baabe9f 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/api.rb @@ -56,6 +56,13 @@ class API attr_reader :factory # @private + # @param schema_elements [SchemaArtifacts::RuntimeMetadata::SchemaElementNamesDefinition] schema element name configuration + # @param index_document_sizes [Boolean] whether to index document sizes + # @param extension_modules [Array] modules to extend onto this API instance + # @param derived_type_name_formats [Hash{Symbol => String}] format strings for derived type names + # @param type_name_overrides [Hash{String => String}] overrides for generated type names + # @param enum_value_overrides_by_type [Hash{String => Hash{String => String}}] overrides for generated enum values, keyed by type + # @param output [IO] output stream for warnings and messages def initialize( schema_elements, index_document_sizes, @@ -111,7 +118,7 @@ def raw_sdl(string) # root `Query` object) or _embedded_ in other indexed types. # # @param name [String] name of the object type - # @yield [SchemaElements::ObjectType] object type object + # @param block [Proc] block yielding the object type for customization # @return [void] # # @example Define embedded and indexed object types @@ -151,7 +158,7 @@ def object_type(name, &block) # intermediate namespace fields. # # @param name [String] name of the namespace type - # @yield [SchemaElements::NamespaceType] namespace type object, for further customization + # @param block [Proc] block yielding the namespace type for customization # @return [void] # # @example Define an `OlapQuery` namespace type and hang it off `Query` @@ -176,7 +183,7 @@ def namespace_type(name, &block) # {SchemaElements::ObjectType} or {SchemaElements::InterfaceType}. # # @param name [String] name of the interface - # @yield [SchemaElements::InterfaceType] interface type object + # @param block [Proc] block yielding the interface type for customization # @return [void] # # @example Define an interface and implement it @@ -217,7 +224,7 @@ def interface_type(name, &block) # enum and an output enum). # # @param name [String] name of the enum type - # @yield [SchemaElements::EnumType] enum type object + # @param block [Proc] block yielding the enum type for customization # @return [void] # # @example Define an enum type @@ -244,7 +251,7 @@ def enum_type(name, &block) # more concrete subtypes. Each subtype must be an {SchemaElements::ObjectType}, but they do not have to share any fields in common. # # @param name [String] name of the union type - # @yield [SchemaElements::UnionType] union type object + # @param block [Proc] block yielding the union type for customization # @return [void] # # @example Define a union type @@ -279,7 +286,7 @@ def union_type(name, &block) # common scalar types (e.g. `Date` and `DateTime`), but it is also available to you to use to define your own custom scalar types. # # @param name [String] name of the scalar type - # @yield [SchemaElements::ScalarType] scalar type object + # @param block [Proc] block yielding the scalar type for customization # @return [void] # # @example Define a scalar type @@ -511,7 +518,7 @@ def json_schema_strictness(allow_omitted_fields: false, allow_extra_fields: true # Registers a customization callback that will be applied to every built-in type automatically provided by ElasticGraph. Provides # an opportunity to customize the built-in types (e.g. to add directives to them or whatever). # - # @yield [SchemaElements::EnumType, SchemaElements::InputType, SchemaElements::InterfaceType, SchemaElements::ObjectType, SchemaElements::ScalarType, SchemaElements::UnionType] built in type + # @param customization_block [Proc] block that receives each built-in type for customization # @return [void] # # @example Customize documentation of built-in types @@ -527,7 +534,7 @@ def on_built_in_types(&customization_block) # Registers a customization callback that will be applied to the root `Query` type when it is generated. # - # @yield [SchemaElements::ObjectType] the root `Query` type + # @param customization_block [Proc] block that receives the root `Query` type for customization # @return [void] # # @example Customize documentation of built-in types diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/factory.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/factory.rb index cd1bf8a8f..4b72f0054 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/factory.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/factory.rb @@ -59,6 +59,7 @@ module SchemaDefinition class Factory include Mixins::HasReadableToSAndInspect.new + # @param state [State] schema definition state def initialize(state) @state = state end @@ -67,17 +68,24 @@ def initialize(state) # element classes to happen via this factory method provided here. To enforce that, this helper returns # the `new` method (as a `Method` object) after removing it from the given class. That makes it impossible # for `new` to be called by anyone except from the factory using the captured method object. + # @param klass [Class] class whose `new` method should be captured and removed def self.prevent_non_factory_instantiation_of(klass) klass.method(:new).tap do klass.singleton_class.undef_method :new end end + # @param name [String] name of the deprecated element + # @param defined_at [Thread::Backtrace::Location] source location of the definition + # @param defined_via [String] code snippet that defined this element def new_deprecated_element(name, defined_at:, defined_via:) @@deprecated_element_new.call(schema_def_state: @state, name: name, defined_at: defined_at, defined_via: defined_via) end @@deprecated_element_new = prevent_non_factory_instantiation_of(SchemaElements::DeprecatedElement) + # @param field [SchemaElements::Field] parent field + # @param name [String] + # @param value_type [String] GraphQL type of the argument def new_argument(field, name, value_type) @@argument_new.call(@state, field, name, value_type).tap do |argument| yield argument if block_given? @@ -85,21 +93,28 @@ def new_argument(field, name, value_type) end @@argument_new = prevent_non_factory_instantiation_of(SchemaElements::Argument) + # @param api [API] schema definition API instance def new_built_in_types(api) @@built_in_types_new.call(api, @state) end @@built_in_types_new = prevent_non_factory_instantiation_of(SchemaElements::BuiltInTypes) + # @param name [String] directive name + # @param arguments [Hash{Symbol => Object}] directive arguments def new_directive(name, arguments) @@directive_new.call(name, arguments) end @@directive_new = prevent_non_factory_instantiation_of(SchemaElements::Directive) + # @param name [String] enum type name + # @param block [Proc] block yielding the enum type for customization def new_enum_type(name, &block) @@enum_type_new.call(@state, name, &block) end @@enum_type_new = prevent_non_factory_instantiation_of(SchemaElements::EnumType) + # @param name [String] exposed enum value name + # @param original_name [String] original (canonical) enum value name def new_enum_value(name, original_name) @@enum_value_new.call(@state, name, original_name) do |enum_value| yield enum_value if block_given? @@ -119,6 +134,7 @@ def new_enums_for_directly_queryable_types end @@field_new = prevent_non_factory_instantiation_of(SchemaElements::Field) + # @param all_types [Hash{String => Object}] map of all registered types def new_graphql_sdl_enumerator(all_types) @@graphql_sdl_enumerator_new.call(@state, all_types) end @@ -133,6 +149,7 @@ def new_graphql_sdl_enumerator(all_types) end @@input_field_new = prevent_non_factory_instantiation_of(SchemaElements::InputField) + # @param name [String] input type name def new_input_type(name) @@input_type_new.call(@state, name) do |input_type| yield input_type @@ -140,6 +157,9 @@ def new_input_type(name) end @@input_type_new = prevent_non_factory_instantiation_of(SchemaElements::InputType) + # @param source_type [String] GraphQL type name being filtered + # @param name_prefix [String] prefix for the derived filter input type name + # @param category [Symbol] category of the filter input type def new_filter_input_type(source_type, name_prefix: source_type, category: :filter_input) all_of = @state.schema_elements.all_of any_of = @state.schema_elements.any_of @@ -190,6 +210,9 @@ def new_filter_input_type(source_type, name_prefix: source_type, category: :filt # All GraphQL leaf types (enums and scalars) are indexing leaf types, but some GraphQL object types are # as well. For example, `GeoLocation` is an object type in GraphQL (with separate lat/long fields) but is # an indexing leaf type because we use the datastore `geo_point` type for it. + # @param source_type [String] GraphQL type name being filtered + # @param name_prefix [String] prefix for derived filter input type names + # @param define_filter_fields [Proc] block that defines filter fields on the input type def build_standard_filter_input_types_for_index_leaf_type(source_type, name_prefix: source_type, &define_filter_fields) single_value_filter = new_filter_input_type(source_type, name_prefix: name_prefix, &define_filter_fields) list_filter = new_list_filter_input_type(source_type, name_prefix: name_prefix, any_satisfy_type_category: :list_element_filter_input) @@ -203,6 +226,9 @@ def build_standard_filter_input_types_for_index_leaf_type(source_type, name_pref # Most GraphQL object types are indexing object types as well, but not all. # For example, `GeoLocation` is an object type in GraphQL (with separate lat/long fields) but is # an indexing leaf type because we use the datastore `geo_point` type for it. + # @param source_type [String] GraphQL type name being filtered + # @param name_prefix [String] prefix for derived filter input type names + # @param define_filter_fields [Proc] block that defines filter fields on the input type def build_standard_filter_input_types_for_index_object_type(source_type, name_prefix: source_type, &define_filter_fields) single_value_filter = new_filter_input_type(source_type, name_prefix: name_prefix, &define_filter_fields) list_filter = new_list_filter_input_type(source_type, name_prefix: name_prefix, any_satisfy_type_category: :filter_input) @@ -211,6 +237,11 @@ def build_standard_filter_input_types_for_index_object_type(source_type, name_pr [single_value_filter, list_filter, fields_list_filter] end + # @param type_name [String] GraphQL type name to build pagination types for + # @param include_total_edge_count [Boolean] whether to include a `totalEdgeCount` field + # @param derived_indexed_types [Array] derived indexed types for the connection + # @param support_pagination [Boolean] whether to generate full pagination support (edges, cursors) + # @param customize_connection [Proc] optional block for customizing the connection type def build_relay_pagination_types(type_name, include_total_edge_count: false, derived_indexed_types: [], support_pagination: true, &customize_connection) [ (edge_type_for(type_name) if support_pagination), @@ -218,6 +249,7 @@ def build_relay_pagination_types(type_name, include_total_edge_count: false, der ].compact end + # @param name [String] interface type name def new_interface_type(name) @@interface_type_new.call(@state, name.to_s) do |interface_type| yield interface_type @@ -225,11 +257,14 @@ def new_interface_type(name) end @@interface_type_new = prevent_non_factory_instantiation_of(SchemaElements::InterfaceType) + # @param name [String] namespace type name + # @param block [Proc] block yielding the namespace type for customization def new_namespace_type(name, &block) @@namespace_type_new.call(@state, name.to_s, &block) end @@namespace_type_new = prevent_non_factory_instantiation_of(SchemaElements::NamespaceType) + # @param name [String] object type name def new_object_type(name) @@object_type_new.call(@state, name.to_s) do |object_type| yield object_type if block_given? @@ -237,6 +272,7 @@ def new_object_type(name) end @@object_type_new = prevent_non_factory_instantiation_of(SchemaElements::ObjectType) + # @param name [String] scalar type name def new_scalar_type(name) @@scalar_type_new.call(@state, name.to_s) do |scalar_type| yield scalar_type @@ -244,16 +280,23 @@ def new_scalar_type(name) end @@scalar_type_new = prevent_non_factory_instantiation_of(SchemaElements::ScalarType) + # @param enum_value [SchemaElements::EnumValue] enum value to wrap + # @param sort_order_field_path [String] dot-separated field path for sort ordering def new_sort_order_enum_value(enum_value, sort_order_field_path) @@sort_order_enum_value_new.call(enum_value, sort_order_field_path) end @@sort_order_enum_value_new = prevent_non_factory_instantiation_of(SchemaElements::SortOrderEnumValue) + # @param name [String] GraphQL type name def new_type_reference(name) @@type_reference_new.call(name, @state) end @@type_reference_new = prevent_non_factory_instantiation_of(SchemaElements::TypeReference) + # @param schema_kind [Symbol] kind of schema type (e.g. `:object`, `:input_object`) + # @param name [String] type name + # @param wrapping_type [Object] wrapping type for fields + # @param field_factory [Symbol] factory method name to use for creating fields def new_type_with_subfields(schema_kind, name, wrapping_type:, field_factory:) @@type_with_subfields_new.call(schema_kind, @state, name, wrapping_type: wrapping_type, field_factory: field_factory) do |type_with_subfields| yield type_with_subfields @@ -261,6 +304,7 @@ def new_type_with_subfields(schema_kind, name, wrapping_type:, field_factory:) end @@type_with_subfields_new = prevent_non_factory_instantiation_of(SchemaElements::TypeWithSubfields) + # @param name [String] union type name def new_union_type(name) @@union_type_new.call(@state, name.to_s) do |union_type| yield union_type @@ -268,11 +312,18 @@ def new_union_type(name) end @@union_type_new = prevent_non_factory_instantiation_of(SchemaElements::UnionType) + # @param relationship_name [String] name of the relationship + # @param field_path [String] dot-separated path to the source field def new_field_source(relationship_name:, field_path:) @@field_source_new.call(relationship_name, field_path) end @@field_source_new = prevent_non_factory_instantiation_of(SchemaElements::FieldSource) + # @param field [SchemaElements::Field] field that holds this relationship + # @param cardinality [Symbol] relationship cardinality (`:one` or `:many`) + # @param related_type [String] name of the related GraphQL type + # @param foreign_key [String] foreign key field name + # @param direction [Symbol] relationship direction (`:in` or `:out`) def new_relationship(field, cardinality:, related_type:, foreign_key:, direction:) @@relationship_new.call( field, @@ -284,6 +335,10 @@ def new_relationship(field, cardinality:, related_type:, foreign_key:, direction end @@relationship_new = prevent_non_factory_instantiation_of(SchemaElements::Relationship) + # @param name [String] index name + # @param settings [Hash{Symbol => Object}] index settings + # @param type [Object] type that owns this index + # @param block [Proc] optional block for further index customization def new_index(name, settings, type, &block) @@index_new.call(name, settings, @state, type, &block) end @@ -294,6 +349,11 @@ def new_results end @@results_new = prevent_non_factory_instantiation_of(Results) + # @param schema_definition_results [Results] schema definition results + # @param schema_artifacts_directory [String] path to the schema artifacts output directory + # @param enforce_json_schema_version [Boolean] whether to enforce JSON schema version incrementing + # @param output [IO] output stream for messages + # @param max_diff_lines [Integer] maximum diff lines to display def new_schema_artifact_manager( schema_definition_results:, schema_artifacts_directory:, @@ -318,6 +378,7 @@ def new_schema_artifact_manager( # rarely (but sometimes) are. For example, the `GeoLocation` object type has two subfields # (`latitude` and `longitude`) but is backed by a single `geo_point` field in the index, # so it is an index leaf type. + # @param index_leaf_type [String] name of the index leaf type to aggregate def new_aggregated_values_type_for_index_leaf_type(index_leaf_type) new_object_type @state.type_ref(index_leaf_type).as_aggregated_values.name do |type| type.graphql_only true diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/derived_fields/field_initializer_support.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/derived_fields/field_initializer_support.rb index d3fa192fe..64a8e0137 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/derived_fields/field_initializer_support.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/derived_fields/field_initializer_support.rb @@ -23,6 +23,8 @@ module FieldInitializerSupport # Painless literal for an empty map, from [the docs](https://www.elastic.co/guide/en/elasticsearch/painless/8.15/painless-operators-reference.html#map-initialization-operator). EMPTY_PAINLESS_MAP = "[:]" + # @param destination_field [String] dot-separated path to the destination field + # @param leaf_value [Symbol, String] empty value for the leaf field (e.g. `EMPTY_PAINLESS_LIST`, `:leave_unset`) # @return [Array] a list of painless statements that will initialize a given `destination_field` path to an empty value. def self.build_empty_value_initializers(destination_field, leaf_value:) snippets = [] # : ::Array[::String] @@ -44,6 +46,8 @@ def self.build_empty_value_initializers(destination_field, leaf_value:) snippets end + # @param field_path [String] dot-separated path to the field + # @param empty_value [String] painless expression for the empty value # @return [String] a painless statement that will default a single field to an empty value. def self.default_source_field_to_empty(field_path, empty_value) <<~EOS.strip diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/list_counts_mapping.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/list_counts_mapping.rb index 43c929650..a590559fd 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/list_counts_mapping.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/list_counts_mapping.rb @@ -20,6 +20,8 @@ module Indexing module ListCountsMapping # Builds the `__counts` field mapping for the given `for_type`. Returns a new `mapping_hash` with # the extra `__counts` field merged into it. + # @param mapping_hash [Hash{String => Object}] existing mapping hash to merge into + # @param for_type [Object] type whose list fields determine the counts properties def self.merged_into(mapping_hash, for_type:) counts_properties = for_type.indexing_fields_by_name_in_index.values.flat_map do |field| field.paths_to_lists_for_count_indexing.map do |path| diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_factory.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_factory.rb index 3017267d4..9829148b7 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_factory.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_factory.rb @@ -12,6 +12,12 @@ module Indexing # Helper class that contains common logic for instantiating `UpdateTargets`. # @private module UpdateTargetFactory + # @param type [String] name of the target type + # @param relationship [String] name of the relationship + # @param id_source [String] source path for the document ID + # @param data_params [Hash{String => SchemaArtifacts::RuntimeMetadata::DynamicParam}] data parameters for the update script + # @param routing_value_source [String, nil] source path for the routing value + # @param rollover_timestamp_value_source [String, nil] source path for the rollover timestamp def self.new_normal_indexing_update_target( type:, relationship:, diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_resolver.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_resolver.rb index a0ef72f22..0099a00ee 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_resolver.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/indexing/update_target_resolver.rb @@ -18,6 +18,10 @@ module Indexing # # @private class UpdateTargetResolver + # @param object_type [Object] type that owns the sourced fields + # @param resolved_relationship [Object] resolved relationship metadata + # @param sourced_fields [Array] fields that source their data from the relationship + # @param field_path_resolver [Object] resolves field paths on types def initialize( object_type:, resolved_relationship:, @@ -165,10 +169,15 @@ def resolve_field_source(adapter) # # @private module RoutingSourceAdapter + # @param relationship [Object] relationship to get routing source from + # @param index [Indexing::Index] index definition + # @param block [Proc] block called when routing source cannot be determined def self.get_field_source(relationship, index, &block) relationship.routing_value_source_for_index(index, &block) end + # @param object_type [Object] type that needs routing + # @param relationship_name [String] name of the relationship def self.cannot_update_reason(object_type, relationship_name) "`#{object_type.name}` uses custom shard routing but we don't know what `#{relationship_name}` field to use " \ "to route the `#{object_type.name}` update requests" @@ -179,10 +188,15 @@ def self.cannot_update_reason(object_type, relationship_name) # # @private module RolloverTimestampSourceAdapter + # @param relationship [Object] relationship to get rollover timestamp source from + # @param index [Indexing::Index] index definition + # @param block [Proc] block called when rollover timestamp source cannot be determined def self.get_field_source(relationship, index, &block) relationship.rollover_timestamp_value_source_for_index(index, &block) end + # @param object_type [Object] type that uses rollover + # @param relationship_name [String] name of the relationship def self.cannot_update_reason(object_type, relationship_name) "`#{object_type.name}` uses a rollover index but we don't know what `#{relationship_name}` timestamp field to use " \ "to select an index for the `#{object_type.name}` update requests" diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/json_schema_pruner.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/json_schema_pruner.rb index 7a8323fa6..02fbf16a0 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/json_schema_pruner.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/json_schema_pruner.rb @@ -14,6 +14,7 @@ module SchemaDefinition # # @private class JSONSchemaPruner + # @param original_json_schema [Hash{String => Object}] JSON schema to prune def self.prune(original_json_schema) initial_type_names = [EVENT_ENVELOPE_JSON_SCHEMA_NAME] + original_json_schema .dig("$defs", EVENT_ENVELOPE_JSON_SCHEMA_NAME, "properties", "type", "enum") @@ -30,6 +31,8 @@ def self.prune(original_json_schema) # Returns a list of type names indicating all types referenced from any type in source_type_names. private_class_method + # @param source_type_names [Array] type names to find references from + # @param original_defs [Hash{String => Object}] all type definitions from the JSON schema def self.referenced_type_names(source_type_names, original_defs) return Set.new if source_type_names.empty? @@ -40,6 +43,7 @@ def self.referenced_type_names(source_type_names, original_defs) end private_class_method + # @param hash [Hash{String => Object}] hash to search for `$ref` entries def self.collect_ref_names(hash) hash.flat_map do |key, value| case value diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_derived_graphql_type_customizations.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_derived_graphql_type_customizations.rb index 34b42ae0f..aef0e712a 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_derived_graphql_type_customizations.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_derived_graphql_type_customizations.rb @@ -18,6 +18,7 @@ module HasDerivedGraphQLTypeCustomizations # types, allowing them to be customized. # # @param type_names [Array, :all] names of the derived types to customize, or `:all` to customize all derived types + # @param customization_block [Proc] block receiving each matching derived type for customization # @return [void] # # @example Customize named derived GraphQL types @@ -61,6 +62,7 @@ def customize_derived_types(*type_names, &customization_block) # # @param type_name [String] name of the derived type containing fields you want to customize # @param field_names [Array] names of the fields on the derived types that you wish to customize + # @param customization_block [Proc] block receiving each matching field for customization # @return [void] # # @example Customize named fields of a derived GraphQL type @@ -85,12 +87,14 @@ def customize_derived_type_fields(type_name, *field_names, &customization_block) end # @private + # @param type [Object] derived type to get customizations for def derived_type_customizations_for_type(type) derived_type_customizations = derived_type_customizations_by_name[type.name] # : ::Array[^(::ElasticGraph::SchemaDefinition::_Type) -> void] derived_type_customizations + derived_type_customizations_for_all_types end # @private + # @param type [Object] derived type to get field customizations for def derived_field_customizations_by_name_for_type(type) derived_field_customizations_by_type_and_field_name[type.name] # : ::Hash[::String, ::Array[^(SchemaElements::Field) -> void]] end diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb index df78cb4b6..e676cf0db 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/has_indices.rb @@ -30,6 +30,7 @@ module HasIndices # @dynamic default_graphql_resolver # @private + # @param args [Array] positional arguments forwarded to `super` # @param options [Hash] forwarded to the including class's `initialize` # @option options [Object] :** all keyword arguments are passed through to `super` def initialize(*args, **options) @@ -46,7 +47,7 @@ def initialize(*args, **options) # @param name [String] name of the index. See the [Elasticsearch docs](https://www.elastic.co/guide/en/elasticsearch/reference/8.15/indices-create-index.html#indices-create-api-path-params) # for restrictions. # @param settings [Hash{Symbol => Object}] datastore index settings (without the `index.` prefix) forwarded to the index definition. See the [Elasticsearch docs](https://www.elastic.co/guide/en/elasticsearch/reference/8.15/index-modules.html#index-modules-settings) for available settings. - # @yield [Indexing::Index] the index, so it can be customized further + # @param block [Proc] optional block yielding the index for further customization # @return [void] # # @example Define a `campaigns` index on a concrete type @@ -190,7 +191,7 @@ def abstract? # @param from_id [String] path to the source type field with `id` values for the derived type # @param route_with [String, nil] path to the source type field with values for shard routing on the derived type # @param rollover_with [String, nil] path to the source type field with values for index rollover on the derived type - # @yield [Indexing::DerivedIndexedType] configuration object for field derivations + # @param block [Proc] block yielding the derived indexed type configuration # @return [void] # # @example Derive a `Course` type from `StudentCourseEnrollment` events @@ -260,6 +261,7 @@ def override_runtime_metadata(**overrides) end # @private + # @param extra_update_targets [Array] additional update targets from relationships def runtime_metadata(extra_update_targets) SchemaArtifacts::RuntimeMetadata::ObjectType.new( update_targets: derived_indexed_types.map(&:runtime_metadata_for_source_type) + [self_update_target].compact + extra_update_targets, @@ -278,7 +280,7 @@ def runtime_metadata(extra_update_targets) # @param singular [String, nil] the singular name of the entity; used for the root `Query` field (with an `Aggregations` suffix) that # queries aggregations of this indexed type. If not provided, will derive it from the type name (e.g. converting it to `camelCase` # or `snake_case`, depending on configuration). - # @yield [SchemaElements::Field] field on the root `Query` type used to query this indexed type, to support customization + # @param customization_block [Proc] optional block yielding the root query field for customization # @return [void] # # @example Set `plural` and `singular` names @@ -344,6 +346,8 @@ def fields_with_sources # through interface/union subtype cycles. # # @private + # @param path_prefix [String] dot-separated prefix prepended to field names + # @param under_non_returnable_parent [Boolean] whether an ancestor field is non-returnable def source_excludes_paths(path_prefix = "", under_non_returnable_parent = false) indexing_fields_by_name_in_index.flat_map do |name, field| path = path_prefix + name diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/implements_interfaces.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/implements_interfaces.rb index a5c8d9e97..bfde57fb5 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/implements_interfaces.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/mixins/implements_interfaces.rb @@ -108,8 +108,7 @@ def verify_graphql_correctness! end end - # @yield [SchemaElements::Argument] an argument - # @yieldreturn [Boolean] whether or not to include the argument in the generated GraphQL SDL + # @param field_arg_selector [Proc] block that selects which arguments to include in SDL # @return [String] SDL string of the type def to_sdl(&field_arg_selector) name_section = diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_type.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_type.rb index 27969d454..5ae50b7eb 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_type.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/enum_type.rb @@ -46,6 +46,9 @@ class EnumType < Struct.new(:schema_def_state, :type_ref, :for_output, :values_b include Mixins::HasReadableToSAndInspect.new { |e| e.name } # @private + # + # @param schema_def_state [State] schema definition state + # @param name [String] name of the enum type def initialize(schema_def_state, name) # @type var values_by_name: ::Hash[::String, EnumValue] values_by_name = {} @@ -69,6 +72,7 @@ def aggregated_values_type # Defines an enum value for the current enum type. # # @param value_name [String] name of the enum value + # @param block [Proc] enum value so it can be further customized # @yield [EnumValue] enum value so it can be further customized # @return [void] # diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb index 18832bcd8..895b4fe9f 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/field.rb @@ -104,6 +104,24 @@ class Field < Struct.new( include Mixins::HasReadableToSAndInspect.new(&:to_qualified_sdl) # @private + # + # @param name [String] name of the field + # @param type [String] GraphQL type reference + # @param parent_type [TypeWithSubfields] the type that owns this field + # @param schema_def_state [State] schema definition state + # @param accuracy_confidence [Symbol] how confident we are in this field's accuracy + # @param name_in_index [String] the name of this field in the datastore index + # @param type_for_derived_types [String, nil] optional type override for derived types + # @param graphql_only [Boolean, nil] whether this field exists only in GraphQL + # @param singular [String, nil] singular form of a list field name + # @param sortable [Boolean, nil] whether this field is sortable + # @param filterable [Boolean, nil] whether this field is filterable + # @param aggregatable [Boolean, nil] whether this field is aggregatable + # @param groupable [Boolean, nil] whether this field is groupable + # @param highlightable [Boolean, nil] whether this field supports highlighting + # @param returnable [Boolean, nil] whether this field is returnable in responses + # @param as_input [Boolean] whether this field is used as input + # @param resolver [Symbol, nil] name of the GraphQL resolver def initialize( name:, type:, parent_type:, schema_def_state:, accuracy_confidence: :high, name_in_index: name, @@ -203,6 +221,7 @@ def type_for_derived_types # Registers a customization callback that will be applied to the corresponding filtering field that will be generated for this # field. # + # @param customization_block [Proc] callback applied to the derived filtering field # @yield [Field] derived filtering field # @return [void] # @see #customize_aggregated_values_field @@ -236,6 +255,7 @@ def customize_filter_field(&customization_block) # Registers a customization callback that will be applied to the corresponding `aggregatedValues` field that will be generated for # this field. # + # @param customization_block [Proc] callback applied to the derived aggregated values field # @yield [Field] derived aggregated values field # @return [void] # @see #customize_filter_field @@ -269,6 +289,7 @@ def customize_aggregated_values_field(&customization_block) # Registers a customization callback that will be applied to the corresponding `groupedBy` field that will be generated for this # field. # + # @param customization_block [Proc] callback applied to the derived grouped by field # @yield [Field] derived grouped by field # @return [void] # @see #customize_aggregated_values_field @@ -302,6 +323,7 @@ def customize_grouped_by_field(&customization_block) # Registers a customization callback that will be applied to the corresponding highlights field that will be generated for this # field. # + # @param customization_block [Proc] callback applied to the derived highlights field # @yield [Field] derived highlights field # @return [void] # @see #customize_aggregated_values_field @@ -335,6 +357,7 @@ def customize_highlights_field(&customization_block) # Registers a customization callback that will be applied to the corresponding `subAggregations` field that will be generated for # this field. # + # @param customization_block [Proc] callback applied to the derived sub-aggregations field # @yield [Field] derived sub-aggregations field # @return [void] # @see #customize_aggregated_values_field @@ -377,6 +400,7 @@ def customize_sub_aggregations_field(&customization_block) # Registers a customization callback that will be applied to the corresponding enum values that will be generated for this field # on the derived `SortOrder` enum type. # + # @param customization_block [Proc] callback applied to the derived sort order enum values # @yield [SortOrderEnumValue] derived sort order enum value # @return [void] # @see #customize_aggregated_values_field @@ -427,6 +451,7 @@ def customize_sort_order_enum_values(&customization_block) # # This method registers a customization callback which is applied to every element that is generated for this field. # + # @param customization_block [Proc] callback applied to every generated schema element for this field # @yield [Field, EnumValue] the schema element # @return [void] # @see #customize_aggregated_values_field @@ -468,6 +493,8 @@ def on_each_generated_schema_element(&customization_block) customize_sort_order_enum_values(&customization_block) end + # @param nullable [Boolean, nil] when `false`, disallows `null` in JSON schema without changing GraphQL nullability + # @param options [Hash{Symbol => Object}] JSON schema options forwarded to {Mixins::HasTypeInfo#json_schema} # (see Mixins::HasTypeInfo#json_schema) def json_schema(nullable: nil, **options) if options.key?(:type) @@ -583,6 +610,8 @@ def resolve_with(resolver_name, **config) end # @private + # + # @param script [Object] the runtime field script def runtime_script(script) self.runtime_field_script = script end @@ -615,6 +644,10 @@ def renamed_from(old_name) end # @private + # + # @param type_structure_only [Boolean] whether to emit only the type structure (no docs/directives) + # @param default_value_sdl [String, nil] optional default value SDL suffix + # @param arg_selector [Proc] optional block to filter which arguments to include def to_sdl(type_structure_only: false, default_value_sdl: nil, &arg_selector) if type_structure_only "#{name}#{args_sdl(joiner: ", ", &arg_selector)}: #{type.name}" @@ -792,6 +825,7 @@ def type_is_namespace? # # @param name [String] name of the argument # @param value_type [String] type of the argument in GraphQL SDL syntax + # @param block [Proc] optional block for further customization # @yield [Argument] for further customization # # @example Define an argument on a field @@ -829,6 +863,8 @@ def list_field_groupable_by_single_values? end # @private + # + # @param parent_type [TypeWithSubfields] the type to define the aggregated values field on def define_aggregated_values_field(parent_type) return unless aggregatable? @@ -847,6 +883,8 @@ def define_aggregated_values_field(parent_type) end # @private + # + # @param parent_type [TypeWithSubfields] the type to define the grouped by field on def define_grouped_by_field(parent_type) return unless (field_name = grouped_by_field_name) @@ -858,6 +896,8 @@ def define_grouped_by_field(parent_type) end # @private + # + # @param parent_type [TypeWithSubfields] the type to define the highlights field on def define_highlights_field(parent_type) return unless highlightable? @@ -888,6 +928,8 @@ def grouped_by_field_type_name end # @private + # + # @param field [Field] the grouped by field to add documentation to def add_grouped_by_field_documentation(field) text = if list_field_groupable_by_single_values? derived_documentation( @@ -915,6 +957,9 @@ def grouped_by_field_name end # @private + # + # @param parent_type [TypeWithSubfields] the type to define the sub-aggregations field on + # @param type [String] GraphQL type name for the sub-aggregations field def define_sub_aggregations_field(parent_type:, type:) parent_type.field name, type, name_in_index: name_in_index, graphql_only: true do |f| f.documentation derived_documentation("Used to perform a sub-aggregation of `#{name}`") @@ -925,6 +970,9 @@ def define_sub_aggregations_field(parent_type:, type:) end # @private + # + # @param parent_type [TypeWithSubfields] the parent type for the filter field + # @param for_single_value [Boolean] whether the filter is for a single value vs a list def to_filter_field(parent_type:, for_single_value: !type_for_derived_types.list?) type_prefix = text? ? "Text" : type_for_derived_types.fully_unwrapped.name filter_type = schema_def_state @@ -1039,6 +1087,8 @@ def resolve_mapping # We do this to support the ability to filter on the size of a list. # # @private + # + # @param has_list_ancestor [Boolean] whether an ancestor field is a list type def paths_to_lists_for_count_indexing(has_list_ancestor: false) self_path = (has_list_ancestor || type.list?) ? [name_in_index] : [] @@ -1096,6 +1146,10 @@ def index_leaf? # are exactly equal (in which case we can return either). # # @private + # + # @param field1 [Field] first candidate field + # @param field2 [Field] second candidate field + # @param to_comparable [Proc] converts a field to a comparable representation def self.pick_most_accurate_from(field1, field2, to_comparable: ->(value) { value }) return field1 if to_comparable.call(field1) == to_comparable.call(field2) yield if field1.accuracy_confidence == field2.accuracy_confidence @@ -1115,6 +1169,9 @@ def nested? # Records the `ComputationDetail` that should be on the `runtime_metadata_graphql_field`. # # @private + # + # @param empty_bucket_value [Object] value to use when an aggregation bucket is empty + # @param function [Symbol] the aggregation function def runtime_metadata_computation_detail(empty_bucket_value:, function:) self.computation_detail = SchemaArtifacts::RuntimeMetadata::ComputationDetail.new( empty_bucket_value: empty_bucket_value, diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/list_counts_state.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/list_counts_state.rb index c22104889..a1c019d4b 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/list_counts_state.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/list_counts_state.rb @@ -19,16 +19,20 @@ class ListCountsState < ::Data.define( :path_from_list_counts ) # @dynamic path_to_list_counts, path_from_list_counts, with + # + # @param at [String] path from the root to the list counts field def self.new_list_counts_field(at:) new(path_to_list_counts: at, path_from_list_counts: "") end INITIAL = new_list_counts_field(at: LIST_COUNTS_FIELD) + # @param subpath [String] subpath to append to the current path def [](subpath) with(path_from_list_counts: "#{path_from_list_counts}#{subpath}.") end + # @param subpath [String] subpath to the count subfield def path_to_count_subfield(subpath) count_subfield = (path_from_list_counts + subpath).gsub(".", LIST_COUNTS_FIELD_PATH_KEY_SEPARATOR) "#{path_to_list_counts}.#{count_subfield}" diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/sub_aggregation_path.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/sub_aggregation_path.rb index 0ab06358c..2c3c93a8c 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/sub_aggregation_path.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/sub_aggregation_path.rb @@ -27,6 +27,9 @@ module SchemaElements # @implements SubAggregationPath # Determines the set of sub aggregation paths for the given type. + # + # @param type [SchemaElements::TypeWithSubfields] the type to find paths for + # @param schema_def_state [State] schema definition state def self.paths_for(type, schema_def_state:) root_paths = type.root_document_type? ? [SubAggregationPath.new([type.name], [])] : [] # : ::Array[SubAggregationPath] @@ -49,10 +52,12 @@ def self.paths_for(type, schema_def_state:) end end + # @param parent [String] name of the parent document type to add def plus_parent(parent) with(parent_doc_types: parent_doc_types + [parent], field_path: []) end + # @param field [Indexing::FieldReference] field reference to append to the path def plus_field(field) with(field_path: field_path + [field]) end diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb index 3402a0cd6..94de1bb61 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_namer.rb @@ -21,6 +21,9 @@ class TypeNamer < ::Struct.new(:formats, :regexes, :name_overrides, :reverse_ove # the same placeholders as are present in the default formats. # # @private + # + # @param format_overrides [Hash{Symbol => String}] overrides for the default derived type name formats + # @param name_overrides [Hash{String => String}] specific type name overrides def initialize(format_overrides: {}, name_overrides: {}) @used_names = [] name_overrides = name_overrides.transform_keys(&:to_s) @@ -42,6 +45,8 @@ def initialize(format_overrides: {}, name_overrides: {}) # returned instead. # # @private + # + # @param standard_name [String, Symbol] the standard name to look up def name_for(standard_name) string_name = standard_name.to_s @used_names << string_name @@ -54,6 +59,8 @@ def name_for(standard_name) # be used without any `name_overrides`. # # @private + # + # @param potentially_overriden_name [String] a name that may have been overridden def revert_override_for(potentially_overriden_name) reverse_overrides.fetch(potentially_overriden_name, potentially_overriden_name) end @@ -93,6 +100,9 @@ def generate_name_for(format_name, **args) # Returns `nil` if the given `format` does support `base` extraction but `name` does not match the `format`. # # @private + # + # @param name [String] the generated name to extract the base from + # @param format [Symbol] the format key to match against def extract_base_from(name, format:) unless REQUIRED_PLACEHOLDERS.fetch(format) == [:base] raise Errors::InvalidArgumentValueError, "The `#{format}` format does not support base extraction." @@ -107,6 +117,9 @@ def extract_base_from(name, format:) # fact that a name matches a format does not guarantee it was generated by that format. # # @private + # + # @param name [String] the name to check + # @param format_name [Symbol] the format key to match against def matches_format?(name, format_name) regexes.fetch(format_name).match?(name) end @@ -133,6 +146,8 @@ def used_names # Extracts the names of the placeholders from the provided format. # # @private + # + # @param format [String] a format string containing `%{placeholder}` tokens def self.placeholders_in(format) format.scan(PLACEHOLDER_REGEX).flatten.map(&:to_sym) end diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_with_subfields.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_with_subfields.rb index 55be1003b..c9d761b94 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_with_subfields.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/schema_elements/type_with_subfields.rb @@ -72,6 +72,12 @@ class TypeWithSubfields < Struct.new( # @dynamic graphql_only? # @private + # + # @param schema_kind [String] the GraphQL schema kind (e.g. `"type"`, `"input"`, `"interface"`) + # @param schema_def_state [State] schema definition state + # @param name [String] name of the type + # @param wrapping_type [TypeWithSubfields] the type that wraps this one (for registering fields) + # @param field_factory [Proc] factory used to create fields def initialize(schema_kind, schema_def_state, name, wrapping_type:, field_factory:) # `any_satisfy`, `any_of`/`all_of`, and `not` are "reserved" field names. They are reserved for usage by # ElasticGraph itself in the `*FilterInput` types it generates. If we allow them to be used as field @@ -283,6 +289,7 @@ def renamed_from(old_name) # @param element_type [String] name of the type of element in the collection # @param name_in_index [String] the name of the field in the datastore index. Can be used to back a GraphQL field with a # differently named field in the index. + # @param graphql_only [Boolean] if `true`, ElasticGraph will define the field only in the GraphQL schema, omitting it from indexing artifacts. # @param singular [String] indicates what the singular form of a field's name is. When provided, ElasticGraph will define a # `groupedBy` field (using the singular form) allowing clients to group by individual values from the field. # @param aggregatable [Boolean] force-enables or disables the ability for aggregation queries to aggregate over this field. @@ -293,6 +300,7 @@ def renamed_from(old_name) # not provided, ElasticGraph will infer field groupability based on the field's GraphQL type and mapping type. # @param highlightable [Boolean] force-enables or disables the ability to request search highlights for this field. When # not provided, ElasticGraph will infer field highlightable based on the field's mapping type. + # @param block [Proc] optional block for further field customization # @yield [Field] the field for further customization # @return [void] # @@ -363,6 +371,7 @@ def paginated_collection_field( # the related type. # @param indexing_only [Boolean] when true, the relationship is used only for indexing purposes (e.g. `sourced_from`) and will not # generate a GraphQL field. + # @param block [Proc] optional block for further relationship customization # @yield [Relationship] the generated relationship fields, for further customization # @return [void] # @@ -471,11 +480,16 @@ def relates_to_many(field_name, type, via:, dir:, singular: nil, indexing_only: # Converts the type to GraphQL SDL syntax. # # @private + # + # @param field_arg_selector [Proc] optional block to filter field arguments def to_sdl(&field_arg_selector) generate_sdl(name_section: name, &field_arg_selector) end # @private + # + # @param name_section [String] the name portion of the SDL definition + # @param field_arg_selector [Proc] optional block to filter field arguments def generate_sdl(name_section:, &field_arg_selector) <<~SDL #{formatted_documentation}#{schema_kind} #{name_section} #{directives_sdl(suffix_with: " ")}{ @@ -510,6 +524,10 @@ def current_sources end # @private + # + # @param path_prefix [String] path from the overall document root + # @param parent_source [String] the source of the parent field + # @param list_counts_state [ListCountsState] tracks the state of the list counts field def index_field_runtime_metadata_tuples( # path from the overall document root path_prefix: "", diff --git a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/state.rb b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/state.rb index ed1994f25..f21d9fbcd 100644 --- a/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/state.rb +++ b/elasticgraph-schema_definition/lib/elastic_graph/schema_definition/state.rb @@ -61,6 +61,13 @@ class State < Struct.new( ) include Mixins::HasReadableToSAndInspect.new + # @param api [API] the public schema definition API + # @param schema_elements [SchemaElements::SchemaElements] configured schema element names + # @param index_document_sizes [Boolean] whether to index document sizes + # @param derived_type_name_formats [Hash{Symbol => String}] overrides for derived type name formats + # @param type_name_overrides [Hash{String => String}] specific type name overrides + # @param enum_value_overrides_by_type [Hash{String => Hash{String => String}}] enum value overrides keyed by type name + # @param output [IO] output stream for warnings def self.with( api:, schema_elements:, @@ -117,28 +124,35 @@ def self.with( # @dynamic index_document_sizes? alias_method :index_document_sizes?, :index_document_sizes + # @param name [String] the type name def type_ref(name) # Type references are immutable and can be safely cached. Here we cache them because we've observed # it having a noticeable impact on our test suite runtime. type_refs_by_name[name] ||= factory.new_type_reference(name) end + # @param type [Object] the type to register def register_object_interface_or_union_type(type) register_type(type, object_types_by_name) end + # @param type [SchemaElements::EnumType] the enum type to register def register_enum_type(type) register_type(type, enum_types_by_name) end + # @param type [SchemaElements::ScalarType] the scalar type to register def register_scalar_type(type) register_type(type, scalar_types_by_name) end + # @param type [SchemaElements::InputType] the input type to register def register_input_type(type) register_type(type) end + # @param name [String] name of the index + # @param type [Object] the type this index belongs to def register_index(name, type) if (existing_type = indexed_types_by_index_name[name]) raise Errors::SchemaError, "Duplicate index name `#{name}` defined on `#{type.name}` and `#{existing_type.name}`. Each index can only be defined once." @@ -146,6 +160,10 @@ def register_index(name, type) indexed_types_by_index_name[name] = type end + # @param type_name [String] the current name of the type + # @param from [String] the old name of the type + # @param defined_at [Thread::Backtrace::Location] location where the rename was defined + # @param defined_via [String] the DSL call that defined the rename def register_renamed_type(type_name, from:, defined_at:, defined_via:) renamed_types_by_old_name[from] = factory.new_deprecated_element( type_name, @@ -154,6 +172,9 @@ def register_renamed_type(type_name, from:, defined_at:, defined_via:) ) end + # @param type_name [String] the name of the deleted type + # @param defined_at [Thread::Backtrace::Location] location where the deletion was defined + # @param defined_via [String] the DSL call that defined the deletion def register_deleted_type(type_name, defined_at:, defined_via:) deleted_types_by_old_name[type_name] = factory.new_deprecated_element( type_name, @@ -162,6 +183,11 @@ def register_deleted_type(type_name, defined_at:, defined_via:) ) end + # @param type_name [String] the name of the type containing the renamed field + # @param from [String] the old field name + # @param to [String] the new field name + # @param defined_at [Thread::Backtrace::Location] location where the rename was defined + # @param defined_via [String] the DSL call that defined the rename def register_renamed_field(type_name, from:, to:, defined_at:, defined_via:) renamed_fields_by_old_field_name = renamed_fields_by_type_name_and_old_field_name[type_name] # : ::Hash[::String, SchemaElements::DeprecatedElement] renamed_fields_by_old_field_name[from] = factory.new_deprecated_element( @@ -171,6 +197,10 @@ def register_renamed_field(type_name, from:, to:, defined_at:, defined_via:) ) end + # @param type_name [String] the name of the type containing the deleted field + # @param field_name [String] the name of the deleted field + # @param defined_at [Thread::Backtrace::Location] location where the deletion was defined + # @param defined_via [String] the DSL call that defined the deletion def register_deleted_field(type_name, field_name, defined_at:, defined_via:) deleted_fields_by_old_field_name = deleted_fields_by_type_name_and_old_field_name[type_name] # : ::Hash[::String, SchemaElements::DeprecatedElement] deleted_fields_by_old_field_name[field_name] = factory.new_deprecated_element( @@ -181,6 +211,8 @@ def register_deleted_field(type_name, field_name, defined_at:, defined_via:) end # Registers the given `field` as a user-defined field, unless the user definitions are complete. + # + # @param field [SchemaElements::Field] the field to register def register_user_defined_field(field) user_defined_fields << field end @@ -203,6 +235,7 @@ def enums_for_directly_queryable_types @enums_for_directly_queryable_types ||= factory.new_enums_for_directly_queryable_types end + # @param type [Object] the type to find sub-aggregation paths for def sub_aggregation_paths_for(type) sub_aggregation_paths_by_type.fetch(type) do SchemaElements::SubAggregationPath.paths_for(type, schema_def_state: self).uniq.tap do |paths| @@ -214,6 +247,7 @@ def sub_aggregation_paths_for(type) end end + # @param block [Proc] callback to invoke after user definition is complete def after_user_definition_complete(&block) user_definition_complete_callbacks << block end diff --git a/elasticgraph-support/lib/elastic_graph/support/config.rb b/elasticgraph-support/lib/elastic_graph/support/config.rb index 83e8dc7e5..708b9a0ba 100644 --- a/elasticgraph-support/lib/elastic_graph/support/config.rb +++ b/elasticgraph-support/lib/elastic_graph/support/config.rb @@ -19,6 +19,7 @@ module Config # Defines a configuration class with the given attributes. # # @param attrs [::Symbol] attribute names + # @param block [Proc] class body block (similar to `::Data.define`) # @yield [::Data] the body of the class (similar to `::Data.define`) # @return [::Class] the defined configuration class # @@ -170,6 +171,8 @@ def from_parsed_yaml!(parsed_yaml) end # @private + # + # @param error [String] error message describing the validation failure def raise_invalid_config(error) raise Errors::ConfigError, "Invalid configuration for `#{name}` at `#{path}`: #{error}" end diff --git a/elasticgraph-support/lib/elastic_graph/support/graphql_formatter.rb b/elasticgraph-support/lib/elastic_graph/support/graphql_formatter.rb index 4c12dfd63..0ea2470bc 100644 --- a/elasticgraph-support/lib/elastic_graph/support/graphql_formatter.rb +++ b/elasticgraph-support/lib/elastic_graph/support/graphql_formatter.rb @@ -44,6 +44,9 @@ def self.format_args(**args) # callers to pass them for GraphQL enums. # - We've removed the `quirks_mode: true` flag passed to `JSON.generate` since it has been # deprecated for a while: https://github.com/flori/json/issues/309 + # + # @param value [Object] the value to serialize into GraphQL syntax + # @param wrap_hash_with_braces [Boolean] whether to wrap hash output with curly braces def self.serialize(value, wrap_hash_with_braces: true) case value when ::Hash diff --git a/elasticgraph-support/lib/elastic_graph/support/hash_util.rb b/elasticgraph-support/lib/elastic_graph/support/hash_util.rb index 846f4149b..5a3c1fe28 100644 --- a/elasticgraph-support/lib/elastic_graph/support/hash_util.rb +++ b/elasticgraph-support/lib/elastic_graph/support/hash_util.rb @@ -12,6 +12,9 @@ module Support class HashUtil # Fetches a key from a hash (just like `Hash#fetch`) but with a more verbose error message when the key is not found. # The error message indicates the available keys unlike `Hash#fetch`. + # + # @param hash [Hash] the hash to fetch from + # @param key [Object] the key to fetch def self.verbose_fetch(hash, key) hash.fetch(key) do raise ::KeyError, "key not found: #{key.inspect}. Available keys: #{hash.keys.inspect}." @@ -20,6 +23,8 @@ def self.verbose_fetch(hash, key) # Like `Hash#to_h`, but strict. When the given input has conflicting keys, `Hash#to_h` will happily let # the last pair when. This method instead raises an exception. + # + # @param pairs [Array] key-value pairs to convert to a hash def self.strict_to_h(pairs) hash = pairs.to_h @@ -33,6 +38,9 @@ def self.strict_to_h(pairs) # Like `Hash#merge`, but verifies that the hashes were strictly disjoint (e.g. had no keys in common). # An error is raised if they do have any keys in common. + # + # @param hash1 [Hash] first hash + # @param hash2 [Hash] second hash to merge into the first def self.disjoint_merge(hash1, hash2) conflicting_keys = [] # : ::Array[untyped] merged = hash1.merge(hash2) do |key, v1, _v2| @@ -49,6 +57,8 @@ def self.disjoint_merge(hash1, hash2) # Recursively transforms any hash keys in the given object to string keys, without # mutating the provided argument. + # + # @param object [Object] the object whose hash keys should be stringified def self.stringify_keys(object) transform_keys(object, :to_s) end @@ -58,6 +68,7 @@ def self.stringify_keys(object) # # Important note: this should never be used on untrusted input. Symbols are not GCd in # Ruby in the same way as strings. + # @param object [Object] the object whose hash keys should be symbolized def self.symbolize_keys(object) transform_keys(object, :to_sym) end @@ -65,6 +76,8 @@ def self.symbolize_keys(object) # Recursively prunes nil values from the hash, at any level of its structure, without # mutating the provided argument. Key paths that are pruned are yielded to the caller # to allow the caller to have awareness of what was pruned. + # @param object [Object] the object to prune nil values from + # @param block [Proc] callback invoked with the key path of each pruned entry def self.recursively_prune_nils_from(object, &block) recursively_prune_if(object, block, &:nil?) end @@ -72,6 +85,8 @@ def self.recursively_prune_nils_from(object, &block) # Recursively prunes nil values or empty hash/array values from the hash, at any level # of its structure, without mutating the provided argument. Key paths that are pruned # are yielded to the caller to allow the caller to have awareness of what was pruned. + # @param object [Object] the object to prune nil and empty values from + # @param block [Proc] callback invoked with the key path of each pruned entry def self.recursively_prune_nils_and_empties_from(object, &block) recursively_prune_if(object, block) do |value| if value.is_a?(::Hash) || value.is_a?(::Array) @@ -87,6 +102,8 @@ def self.recursively_prune_nils_and_empties_from(object, &block) # # flatten_and_stringify_keys({ a: { b: 3 }, c: 5 }, prefix: "foo") returns: # { "foo.a.b" => 3, "foo.c" => 5 } + # @param source_hash [Hash] the hash to flatten + # @param prefix [String, nil] optional prefix prepended to all keys def self.flatten_and_stringify_keys(source_hash, prefix: nil) # @type var flat_hash: ::Hash[::String, untyped] flat_hash = {} @@ -98,6 +115,8 @@ def self.flatten_and_stringify_keys(source_hash, prefix: nil) # Recursively merges the values from `hash2` into `hash1`, without mutating either `hash1` or `hash2`. # When a key is in both `hash2` and `hash1`, takes the value from `hash2` just like `Hash#merge` does. + # @param hash1 [Hash] base hash + # @param hash2 [Hash] hash whose values take precedence on conflict def self.deep_merge(hash1, hash2) # `_ =` needed to satisfy steep--the types here are quite complicated. _ = hash1.merge(hash2) do |key, hash1_value, hash2_value| @@ -116,6 +135,9 @@ def self.deep_merge(hash1, hash2) # Raises an error if the key is not found unless a default block is provided. # Raises an error if any parent value is not a hash as expected. # Raises an error if the provided path is not a full path to a leaf in the nested structure. + # @param hash [Hash] the hash to fetch from + # @param key_path [Array] ordered list of keys forming the path to the leaf + # @param default [Proc] optional block providing a default when a key is missing def self.fetch_leaf_values_at_path(hash, key_path, &default) do_fetch_leaf_values_at_path(hash, key_path, 0, &default) end @@ -129,6 +151,8 @@ def self.fetch_leaf_values_at_path(hash, key_path, &default) # Note: this is a somewhat lengthy implementation, but it was chosen based on benchmarking. This method # needs to be fast because it gets used repeatedly when resolving GraphQL queries at all levels of the # response structure. + # @param hash [Hash] the hash to fetch from + # @param path_parts [Array] ordered list of keys forming the path def self.fetch_value_at_path(hash, path_parts) # We expect the most common case to be a single path part. Benchmarks have shown that special casing it # is quite worthwhile, as it is much faster than the general purpose implementation further below. diff --git a/elasticgraph-support/lib/elastic_graph/support/logger.rb b/elasticgraph-support/lib/elastic_graph/support/logger.rb index 740550938..a01530d69 100644 --- a/elasticgraph-support/lib/elastic_graph/support/logger.rb +++ b/elasticgraph-support/lib/elastic_graph/support/logger.rb @@ -17,6 +17,8 @@ module Support # @private module Logger # Builds a logger instance from the given parsed YAML config. + # + # @param parsed_yaml [Hash{String => Object}] parsed YAML configuration def self.from_parsed_yaml(parsed_yaml) Factory.build(config: Config.from_parsed_yaml(parsed_yaml) || Config.new) end @@ -76,6 +78,10 @@ def initialize @original_formatter = ::Logger::Formatter.new end + # @param severity [String] log severity level + # @param datetime [Time] timestamp of the log entry + # @param progname [String, nil] program name + # @param msg [String, Hash] log message or hash to be JSON-formatted def call(severity, datetime, progname, msg) msg = msg.is_a?(::Hash) ? ::JSON.generate(msg, space: " ") : msg @original_formatter.call(severity, datetime, progname, msg) @@ -84,6 +90,8 @@ def call(severity, datetime, progname, msg) # @private module Factory + # @param config [Config] logger configuration + # @param device [IO, nil] optional IO device override def self.build(config:, device: nil) ::Logger.new( device || config.prepared_device, diff --git a/elasticgraph-support/lib/elastic_graph/support/threading.rb b/elasticgraph-support/lib/elastic_graph/support/threading.rb index 2bdec1e2e..dd5adf5bf 100644 --- a/elasticgraph-support/lib/elastic_graph/support/threading.rb +++ b/elasticgraph-support/lib/elastic_graph/support/threading.rb @@ -17,6 +17,7 @@ module Threading # quite helpful when dealing with blocking I/O. However, the cost of threads is # such that this method should not be used when you have a large list of items to # map over (say, hundreds or thousands of items or more). + # @param items [Array] collection of items to map over in parallel def self.parallel_map(items) return _ = items.map { |item| yield item } if items.size < 2 diff --git a/elasticgraph-support/lib/elastic_graph/support/time_set.rb b/elasticgraph-support/lib/elastic_graph/support/time_set.rb index 0fc5ab430..a7e26a36e 100644 --- a/elasticgraph-support/lib/elastic_graph/support/time_set.rb +++ b/elasticgraph-support/lib/elastic_graph/support/time_set.rb @@ -24,6 +24,11 @@ module Support # @private class TimeSet < ::Data.define(:ranges) # Factory method to construct a `TimeSet` using a range with the given bounds. + # + # @param gt [Time, nil] exclusive lower bound + # @param gte [Time, nil] inclusive lower bound + # @param lt [Time, nil] exclusive upper bound + # @param lte [Time, nil] inclusive upper bound def self.of_range(gt: nil, gte: nil, lt: nil, lte: nil) if gt && gte raise ArgumentError, "TimeSet got two lower bounds, but can have only one (gt: #{gt.inspect}, gte: #{gte.inspect})" @@ -48,12 +53,16 @@ def self.of_range(gt: nil, gte: nil, lt: nil, lte: nil) # Factory method to construct a `TimeSet` from a collection of `::Time` objects. # Internally we convert it to a set of `::Range` objects, one per unique time. + # + # @param times [Array