protobuf-cucumber 3.10.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/.gitignore +21 -0
- data/.rubocop.yml +70 -0
- data/.rubocop_todo.yml +145 -0
- data/.travis.yml +40 -0
- data/.yardopts +5 -0
- data/CHANGES.md +344 -0
- data/CONTRIBUTING.md +16 -0
- data/Gemfile +3 -0
- data/LICENSE.txt +22 -0
- data/README.md +33 -0
- data/Rakefile +64 -0
- data/bin/protoc-gen-ruby +22 -0
- data/bin/rpc_server +5 -0
- data/install-protobuf.sh +28 -0
- data/lib/protobuf.rb +129 -0
- data/lib/protobuf/cli.rb +257 -0
- data/lib/protobuf/code_generator.rb +120 -0
- data/lib/protobuf/decoder.rb +28 -0
- data/lib/protobuf/deprecation.rb +117 -0
- data/lib/protobuf/descriptors.rb +3 -0
- data/lib/protobuf/descriptors/google/protobuf/compiler/plugin.pb.rb +62 -0
- data/lib/protobuf/descriptors/google/protobuf/descriptor.pb.rb +301 -0
- data/lib/protobuf/encoder.rb +11 -0
- data/lib/protobuf/enum.rb +365 -0
- data/lib/protobuf/exceptions.rb +9 -0
- data/lib/protobuf/field.rb +74 -0
- data/lib/protobuf/field/base_field.rb +380 -0
- data/lib/protobuf/field/base_field_object_definitions.rb +504 -0
- data/lib/protobuf/field/bool_field.rb +64 -0
- data/lib/protobuf/field/bytes_field.rb +78 -0
- data/lib/protobuf/field/double_field.rb +25 -0
- data/lib/protobuf/field/enum_field.rb +61 -0
- data/lib/protobuf/field/field_array.rb +104 -0
- data/lib/protobuf/field/field_hash.rb +122 -0
- data/lib/protobuf/field/fixed32_field.rb +25 -0
- data/lib/protobuf/field/fixed64_field.rb +28 -0
- data/lib/protobuf/field/float_field.rb +43 -0
- data/lib/protobuf/field/int32_field.rb +21 -0
- data/lib/protobuf/field/int64_field.rb +34 -0
- data/lib/protobuf/field/integer_field.rb +23 -0
- data/lib/protobuf/field/message_field.rb +51 -0
- data/lib/protobuf/field/sfixed32_field.rb +27 -0
- data/lib/protobuf/field/sfixed64_field.rb +28 -0
- data/lib/protobuf/field/signed_integer_field.rb +29 -0
- data/lib/protobuf/field/sint32_field.rb +21 -0
- data/lib/protobuf/field/sint64_field.rb +21 -0
- data/lib/protobuf/field/string_field.rb +51 -0
- data/lib/protobuf/field/uint32_field.rb +21 -0
- data/lib/protobuf/field/uint64_field.rb +21 -0
- data/lib/protobuf/field/varint_field.rb +77 -0
- data/lib/protobuf/generators/base.rb +85 -0
- data/lib/protobuf/generators/enum_generator.rb +39 -0
- data/lib/protobuf/generators/extension_generator.rb +27 -0
- data/lib/protobuf/generators/field_generator.rb +193 -0
- data/lib/protobuf/generators/file_generator.rb +262 -0
- data/lib/protobuf/generators/group_generator.rb +122 -0
- data/lib/protobuf/generators/message_generator.rb +104 -0
- data/lib/protobuf/generators/option_generator.rb +17 -0
- data/lib/protobuf/generators/printable.rb +160 -0
- data/lib/protobuf/generators/service_generator.rb +50 -0
- data/lib/protobuf/lifecycle.rb +33 -0
- data/lib/protobuf/logging.rb +39 -0
- data/lib/protobuf/message.rb +260 -0
- data/lib/protobuf/message/fields.rb +233 -0
- data/lib/protobuf/message/serialization.rb +85 -0
- data/lib/protobuf/optionable.rb +70 -0
- data/lib/protobuf/rpc/buffer.rb +78 -0
- data/lib/protobuf/rpc/client.rb +140 -0
- data/lib/protobuf/rpc/connectors/base.rb +221 -0
- data/lib/protobuf/rpc/connectors/ping.rb +89 -0
- data/lib/protobuf/rpc/connectors/socket.rb +78 -0
- data/lib/protobuf/rpc/connectors/zmq.rb +319 -0
- data/lib/protobuf/rpc/dynamic_discovery.pb.rb +50 -0
- data/lib/protobuf/rpc/env.rb +60 -0
- data/lib/protobuf/rpc/error.rb +28 -0
- data/lib/protobuf/rpc/error/client_error.rb +31 -0
- data/lib/protobuf/rpc/error/server_error.rb +43 -0
- data/lib/protobuf/rpc/middleware.rb +25 -0
- data/lib/protobuf/rpc/middleware/exception_handler.rb +40 -0
- data/lib/protobuf/rpc/middleware/logger.rb +95 -0
- data/lib/protobuf/rpc/middleware/request_decoder.rb +79 -0
- data/lib/protobuf/rpc/middleware/response_encoder.rb +83 -0
- data/lib/protobuf/rpc/middleware/runner.rb +18 -0
- data/lib/protobuf/rpc/rpc.pb.rb +64 -0
- data/lib/protobuf/rpc/rpc_method.rb +16 -0
- data/lib/protobuf/rpc/server.rb +39 -0
- data/lib/protobuf/rpc/servers/socket/server.rb +121 -0
- data/lib/protobuf/rpc/servers/socket/worker.rb +56 -0
- data/lib/protobuf/rpc/servers/socket_runner.rb +46 -0
- data/lib/protobuf/rpc/servers/zmq/broker.rb +194 -0
- data/lib/protobuf/rpc/servers/zmq/server.rb +321 -0
- data/lib/protobuf/rpc/servers/zmq/util.rb +48 -0
- data/lib/protobuf/rpc/servers/zmq/worker.rb +105 -0
- data/lib/protobuf/rpc/servers/zmq_runner.rb +70 -0
- data/lib/protobuf/rpc/service.rb +172 -0
- data/lib/protobuf/rpc/service_directory.rb +261 -0
- data/lib/protobuf/rpc/service_dispatcher.rb +45 -0
- data/lib/protobuf/rpc/service_filters.rb +250 -0
- data/lib/protobuf/rpc/stat.rb +119 -0
- data/lib/protobuf/socket.rb +21 -0
- data/lib/protobuf/tasks.rb +1 -0
- data/lib/protobuf/tasks/compile.rake +80 -0
- data/lib/protobuf/varint.rb +20 -0
- data/lib/protobuf/varint_pure.rb +31 -0
- data/lib/protobuf/version.rb +3 -0
- data/lib/protobuf/wire_type.rb +10 -0
- data/lib/protobuf/zmq.rb +21 -0
- data/profile.html +5103 -0
- data/proto/dynamic_discovery.proto +44 -0
- data/proto/google/protobuf/compiler/plugin.proto +147 -0
- data/proto/google/protobuf/descriptor.proto +779 -0
- data/proto/rpc.proto +69 -0
- data/protobuf-cucumber.gemspec +57 -0
- data/spec/benchmark/tasks.rb +143 -0
- data/spec/bin/protoc-gen-ruby_spec.rb +23 -0
- data/spec/encoding/all_types_spec.rb +103 -0
- data/spec/encoding/extreme_values_spec.rb +0 -0
- data/spec/functional/class_inheritance_spec.rb +52 -0
- data/spec/functional/code_generator_spec.rb +58 -0
- data/spec/functional/socket_server_spec.rb +59 -0
- data/spec/functional/zmq_server_spec.rb +105 -0
- data/spec/lib/protobuf/cli_spec.rb +317 -0
- data/spec/lib/protobuf/code_generator_spec.rb +87 -0
- data/spec/lib/protobuf/enum_spec.rb +307 -0
- data/spec/lib/protobuf/field/bool_field_spec.rb +91 -0
- data/spec/lib/protobuf/field/double_field_spec.rb +9 -0
- data/spec/lib/protobuf/field/enum_field_spec.rb +44 -0
- data/spec/lib/protobuf/field/field_array_spec.rb +105 -0
- data/spec/lib/protobuf/field/field_hash_spec.rb +168 -0
- data/spec/lib/protobuf/field/fixed32_field_spec.rb +7 -0
- data/spec/lib/protobuf/field/fixed64_field_spec.rb +7 -0
- data/spec/lib/protobuf/field/float_field_spec.rb +90 -0
- data/spec/lib/protobuf/field/int32_field_spec.rb +120 -0
- data/spec/lib/protobuf/field/int64_field_spec.rb +7 -0
- data/spec/lib/protobuf/field/message_field_spec.rb +132 -0
- data/spec/lib/protobuf/field/sfixed32_field_spec.rb +9 -0
- data/spec/lib/protobuf/field/sfixed64_field_spec.rb +9 -0
- data/spec/lib/protobuf/field/sint32_field_spec.rb +9 -0
- data/spec/lib/protobuf/field/sint64_field_spec.rb +9 -0
- data/spec/lib/protobuf/field/string_field_spec.rb +79 -0
- data/spec/lib/protobuf/field/uint32_field_spec.rb +7 -0
- data/spec/lib/protobuf/field/uint64_field_spec.rb +7 -0
- data/spec/lib/protobuf/field_spec.rb +192 -0
- data/spec/lib/protobuf/generators/base_spec.rb +154 -0
- data/spec/lib/protobuf/generators/enum_generator_spec.rb +82 -0
- data/spec/lib/protobuf/generators/extension_generator_spec.rb +42 -0
- data/spec/lib/protobuf/generators/field_generator_spec.rb +197 -0
- data/spec/lib/protobuf/generators/file_generator_spec.rb +119 -0
- data/spec/lib/protobuf/generators/message_generator_spec.rb +0 -0
- data/spec/lib/protobuf/generators/service_generator_spec.rb +99 -0
- data/spec/lib/protobuf/lifecycle_spec.rb +94 -0
- data/spec/lib/protobuf/message_spec.rb +944 -0
- data/spec/lib/protobuf/optionable_spec.rb +265 -0
- data/spec/lib/protobuf/rpc/client_spec.rb +66 -0
- data/spec/lib/protobuf/rpc/connectors/base_spec.rb +226 -0
- data/spec/lib/protobuf/rpc/connectors/ping_spec.rb +69 -0
- data/spec/lib/protobuf/rpc/connectors/socket_spec.rb +34 -0
- data/spec/lib/protobuf/rpc/connectors/zmq_spec.rb +110 -0
- data/spec/lib/protobuf/rpc/middleware/exception_handler_spec.rb +62 -0
- data/spec/lib/protobuf/rpc/middleware/logger_spec.rb +49 -0
- data/spec/lib/protobuf/rpc/middleware/request_decoder_spec.rb +115 -0
- data/spec/lib/protobuf/rpc/middleware/response_encoder_spec.rb +91 -0
- data/spec/lib/protobuf/rpc/servers/socket_server_spec.rb +38 -0
- data/spec/lib/protobuf/rpc/servers/zmq/server_spec.rb +43 -0
- data/spec/lib/protobuf/rpc/servers/zmq/util_spec.rb +55 -0
- data/spec/lib/protobuf/rpc/servers/zmq/worker_spec.rb +35 -0
- data/spec/lib/protobuf/rpc/service_directory_spec.rb +293 -0
- data/spec/lib/protobuf/rpc/service_dispatcher_spec.rb +35 -0
- data/spec/lib/protobuf/rpc/service_filters_spec.rb +517 -0
- data/spec/lib/protobuf/rpc/service_spec.rb +162 -0
- data/spec/lib/protobuf/rpc/stat_spec.rb +101 -0
- data/spec/lib/protobuf/varint_spec.rb +29 -0
- data/spec/lib/protobuf_spec.rb +105 -0
- data/spec/spec_helper.rb +42 -0
- data/spec/support/all.rb +6 -0
- data/spec/support/packed_field.rb +23 -0
- data/spec/support/protos/all_types.data.bin +0 -0
- data/spec/support/protos/all_types.data.txt +119 -0
- data/spec/support/protos/enum.pb.rb +63 -0
- data/spec/support/protos/enum.proto +37 -0
- data/spec/support/protos/extreme_values.data.bin +0 -0
- data/spec/support/protos/google_unittest.bin +0 -0
- data/spec/support/protos/google_unittest.pb.rb +798 -0
- data/spec/support/protos/google_unittest.proto +884 -0
- data/spec/support/protos/google_unittest_custom_options.bin +0 -0
- data/spec/support/protos/google_unittest_custom_options.pb.rb +361 -0
- data/spec/support/protos/google_unittest_custom_options.proto +424 -0
- data/spec/support/protos/google_unittest_import.pb.rb +55 -0
- data/spec/support/protos/google_unittest_import.proto +73 -0
- data/spec/support/protos/google_unittest_import_public.pb.rb +31 -0
- data/spec/support/protos/google_unittest_import_public.proto +41 -0
- data/spec/support/protos/map-test.bin +157 -0
- data/spec/support/protos/map-test.pb.rb +85 -0
- data/spec/support/protos/map-test.proto +68 -0
- data/spec/support/protos/multi_field_extensions.pb.rb +59 -0
- data/spec/support/protos/multi_field_extensions.proto +35 -0
- data/spec/support/protos/resource.pb.rb +172 -0
- data/spec/support/protos/resource.proto +137 -0
- data/spec/support/resource_service.rb +23 -0
- data/spec/support/server.rb +65 -0
- data/spec/support/test_app_file.rb +2 -0
- data/varint_prof.rb +82 -0
- metadata +579 -0
| @@ -0,0 +1,33 @@ | |
| 1 | 
            +
            module Protobuf
         | 
| 2 | 
            +
              class Lifecycle
         | 
| 3 | 
            +
                class << self
         | 
| 4 | 
            +
                  def register(event_name)
         | 
| 5 | 
            +
                    fail "Lifecycle register must have a block" unless block_given?
         | 
| 6 | 
            +
                    event_name = normalized_event_name(event_name)
         | 
| 7 | 
            +
             | 
| 8 | 
            +
                    ::ActiveSupport::Notifications.subscribe(event_name) do |_name, _start, _finish, _id, args|
         | 
| 9 | 
            +
                      yield(*args)
         | 
| 10 | 
            +
                    end
         | 
| 11 | 
            +
                  end
         | 
| 12 | 
            +
                  alias :on register
         | 
| 13 | 
            +
             | 
| 14 | 
            +
                  def trigger(event_name, *args)
         | 
| 15 | 
            +
                    event_name = normalized_event_name(event_name)
         | 
| 16 | 
            +
             | 
| 17 | 
            +
                    ::ActiveSupport::Notifications.instrument(event_name, args)
         | 
| 18 | 
            +
                  end
         | 
| 19 | 
            +
             | 
| 20 | 
            +
                  replacement = ::ActiveSupport::Notifications
         | 
| 21 | 
            +
             | 
| 22 | 
            +
                  ::Protobuf.deprecator.deprecate_methods(
         | 
| 23 | 
            +
                    self,
         | 
| 24 | 
            +
                    :register => "#{replacement}.#{replacement.method(:subscribe).name}".to_sym,
         | 
| 25 | 
            +
                    :trigger => "#{replacement}.#{replacement.method(:instrument).name}".to_sym,
         | 
| 26 | 
            +
                  )
         | 
| 27 | 
            +
             | 
| 28 | 
            +
                  def normalized_event_name(event_name)
         | 
| 29 | 
            +
                    event_name.to_s.downcase
         | 
| 30 | 
            +
                  end
         | 
| 31 | 
            +
                end
         | 
| 32 | 
            +
              end
         | 
| 33 | 
            +
            end
         | 
| @@ -0,0 +1,39 @@ | |
| 1 | 
            +
            require 'logger'
         | 
| 2 | 
            +
             | 
| 3 | 
            +
            module Protobuf
         | 
| 4 | 
            +
              module Logging
         | 
| 5 | 
            +
                def self.initialize_logger(log_target = $stdout, log_level = ::Logger::INFO)
         | 
| 6 | 
            +
                  @logger = Logger.new(log_target)
         | 
| 7 | 
            +
                  @logger.level = log_level
         | 
| 8 | 
            +
                  @logger
         | 
| 9 | 
            +
                end
         | 
| 10 | 
            +
             | 
| 11 | 
            +
                def self.logger
         | 
| 12 | 
            +
                  defined?(@logger) ? @logger : initialize_logger
         | 
| 13 | 
            +
                end
         | 
| 14 | 
            +
             | 
| 15 | 
            +
                class << self
         | 
| 16 | 
            +
                  attr_writer :logger
         | 
| 17 | 
            +
                end
         | 
| 18 | 
            +
             | 
| 19 | 
            +
                def logger
         | 
| 20 | 
            +
                  ::Protobuf::Logging.logger
         | 
| 21 | 
            +
                end
         | 
| 22 | 
            +
             | 
| 23 | 
            +
                def log_exception(ex)
         | 
| 24 | 
            +
                  logger.error { ex.message }
         | 
| 25 | 
            +
                  logger.error { ex.backtrace[0..5].join("\n") }
         | 
| 26 | 
            +
                  logger.debug { ex.backtrace.join("\n") }
         | 
| 27 | 
            +
                end
         | 
| 28 | 
            +
             | 
| 29 | 
            +
                def log_signature
         | 
| 30 | 
            +
                  @_log_signature ||= "[#{self.class == Class ? name : self.class.name}]"
         | 
| 31 | 
            +
                end
         | 
| 32 | 
            +
             | 
| 33 | 
            +
                def sign_message(message)
         | 
| 34 | 
            +
                  "#{log_signature} #{message}"
         | 
| 35 | 
            +
                end
         | 
| 36 | 
            +
              end
         | 
| 37 | 
            +
            end
         | 
| 38 | 
            +
             | 
| 39 | 
            +
            # Inspired by [mperham](https://github.com/mperham/sidekiq)
         | 
| @@ -0,0 +1,260 @@ | |
| 1 | 
            +
            require 'protobuf/message/fields'
         | 
| 2 | 
            +
            require 'protobuf/message/serialization'
         | 
| 3 | 
            +
            require 'protobuf/varint'
         | 
| 4 | 
            +
             | 
| 5 | 
            +
            module Protobuf
         | 
| 6 | 
            +
              class Message
         | 
| 7 | 
            +
             | 
| 8 | 
            +
                ##
         | 
| 9 | 
            +
                # Includes & Extends
         | 
| 10 | 
            +
                #
         | 
| 11 | 
            +
             | 
| 12 | 
            +
                extend ::Protobuf::Message::Fields
         | 
| 13 | 
            +
                include ::Protobuf::Message::Serialization
         | 
| 14 | 
            +
                ::Protobuf::Optionable.inject(self) { ::Google::Protobuf::MessageOptions }
         | 
| 15 | 
            +
             | 
| 16 | 
            +
                ##
         | 
| 17 | 
            +
                # Class Methods
         | 
| 18 | 
            +
                #
         | 
| 19 | 
            +
             | 
| 20 | 
            +
                def self.to_json
         | 
| 21 | 
            +
                  name
         | 
| 22 | 
            +
                end
         | 
| 23 | 
            +
             | 
| 24 | 
            +
                def self.from_json(json)
         | 
| 25 | 
            +
                  fields = normalize_json(JSON.parse(json))
         | 
| 26 | 
            +
                  new(fields)
         | 
| 27 | 
            +
                end
         | 
| 28 | 
            +
             | 
| 29 | 
            +
                def self.normalize_json(ob)
         | 
| 30 | 
            +
                  case ob
         | 
| 31 | 
            +
                  when Array
         | 
| 32 | 
            +
                    ob.map { |value| normalize_json(value) }
         | 
| 33 | 
            +
                  when Hash
         | 
| 34 | 
            +
                    Hash[*ob.flat_map { |key, value| [key.underscore, normalize_json(value)] }]
         | 
| 35 | 
            +
                  else
         | 
| 36 | 
            +
                    ob
         | 
| 37 | 
            +
                  end
         | 
| 38 | 
            +
                end
         | 
| 39 | 
            +
             | 
| 40 | 
            +
                ##
         | 
| 41 | 
            +
                # Constructor
         | 
| 42 | 
            +
                #
         | 
| 43 | 
            +
             | 
| 44 | 
            +
                def initialize(fields = {})
         | 
| 45 | 
            +
                  @values = {}
         | 
| 46 | 
            +
                  fields.to_hash.each do |name, value|
         | 
| 47 | 
            +
                    set_field(name, value, true)
         | 
| 48 | 
            +
                  end
         | 
| 49 | 
            +
             | 
| 50 | 
            +
                  yield self if block_given?
         | 
| 51 | 
            +
                end
         | 
| 52 | 
            +
             | 
| 53 | 
            +
                ##
         | 
| 54 | 
            +
                # Public Instance Methods
         | 
| 55 | 
            +
                #
         | 
| 56 | 
            +
             | 
| 57 | 
            +
                def clear!
         | 
| 58 | 
            +
                  @values.delete_if do |_, value|
         | 
| 59 | 
            +
                    if value.is_a?(::Protobuf::Field::FieldArray) || value.is_a?(::Protobuf::Field::FieldHash)
         | 
| 60 | 
            +
                      value.clear
         | 
| 61 | 
            +
                      false
         | 
| 62 | 
            +
                    else
         | 
| 63 | 
            +
                      true
         | 
| 64 | 
            +
                    end
         | 
| 65 | 
            +
                  end
         | 
| 66 | 
            +
                  self
         | 
| 67 | 
            +
                end
         | 
| 68 | 
            +
             | 
| 69 | 
            +
                def clone
         | 
| 70 | 
            +
                  copy_to(super, :clone)
         | 
| 71 | 
            +
                end
         | 
| 72 | 
            +
             | 
| 73 | 
            +
                def dup
         | 
| 74 | 
            +
                  copy_to(super, :dup)
         | 
| 75 | 
            +
                end
         | 
| 76 | 
            +
             | 
| 77 | 
            +
                # Iterate over every field, invoking the given block
         | 
| 78 | 
            +
                #
         | 
| 79 | 
            +
                def each_field
         | 
| 80 | 
            +
                  return to_enum(:each_field) unless block_given?
         | 
| 81 | 
            +
             | 
| 82 | 
            +
                  self.class.all_fields.each do |field|
         | 
| 83 | 
            +
                    value = self[field.name]
         | 
| 84 | 
            +
                    yield(field, value)
         | 
| 85 | 
            +
                  end
         | 
| 86 | 
            +
                end
         | 
| 87 | 
            +
             | 
| 88 | 
            +
                def each_field_for_serialization
         | 
| 89 | 
            +
                  _protobuf_message_unset_required_field_tags.each do |tag|
         | 
| 90 | 
            +
                    fail ::Protobuf::SerializationError, "Required field #{self.class.name}##{_protobuf_message_field[tag].name} does not have a value."
         | 
| 91 | 
            +
                  end
         | 
| 92 | 
            +
             | 
| 93 | 
            +
                  @values.each_key do |fully_qualified_name|
         | 
| 94 | 
            +
                    field = _protobuf_message_field[fully_qualified_name]
         | 
| 95 | 
            +
                    yield(field, field.value_from_values_for_serialization(@values))
         | 
| 96 | 
            +
                  end
         | 
| 97 | 
            +
                end
         | 
| 98 | 
            +
             | 
| 99 | 
            +
                def field?(name)
         | 
| 100 | 
            +
                  field = _protobuf_message_field[name]
         | 
| 101 | 
            +
             | 
| 102 | 
            +
                  if field
         | 
| 103 | 
            +
                    field.field?(@values)
         | 
| 104 | 
            +
                  else
         | 
| 105 | 
            +
                    false
         | 
| 106 | 
            +
                  end
         | 
| 107 | 
            +
                end
         | 
| 108 | 
            +
                alias :respond_to_has? field?
         | 
| 109 | 
            +
                ::Protobuf.deprecator.define_deprecated_methods(self, :has_field? => :field?)
         | 
| 110 | 
            +
             | 
| 111 | 
            +
                def inspect
         | 
| 112 | 
            +
                  attrs = self.class.fields.map do |field|
         | 
| 113 | 
            +
                    [field.name, self[field.name].inspect].join('=')
         | 
| 114 | 
            +
                  end.join(' ')
         | 
| 115 | 
            +
             | 
| 116 | 
            +
                  "#<#{self.class} #{attrs}>"
         | 
| 117 | 
            +
                end
         | 
| 118 | 
            +
             | 
| 119 | 
            +
                def respond_to_has_and_present?(key)
         | 
| 120 | 
            +
                  field = _protobuf_message_field[key]
         | 
| 121 | 
            +
             | 
| 122 | 
            +
                  if field
         | 
| 123 | 
            +
                    field.field_and_present?(@values)
         | 
| 124 | 
            +
                  else
         | 
| 125 | 
            +
                    false
         | 
| 126 | 
            +
                  end
         | 
| 127 | 
            +
                end
         | 
| 128 | 
            +
             | 
| 129 | 
            +
                # Return a hash-representation of the given fields for this message type.
         | 
| 130 | 
            +
                def to_hash
         | 
| 131 | 
            +
                  result = {}
         | 
| 132 | 
            +
             | 
| 133 | 
            +
                  @values.each_key do |field_name|
         | 
| 134 | 
            +
                    field = _protobuf_message_field[field_name]
         | 
| 135 | 
            +
                    field.to_message_hash(@values, result)
         | 
| 136 | 
            +
                  end
         | 
| 137 | 
            +
             | 
| 138 | 
            +
                  result
         | 
| 139 | 
            +
                end
         | 
| 140 | 
            +
             | 
| 141 | 
            +
                def to_hash_with_string_keys
         | 
| 142 | 
            +
                  result = {}
         | 
| 143 | 
            +
             | 
| 144 | 
            +
                  @values.each_key do |field_name|
         | 
| 145 | 
            +
                    field = _protobuf_message_field[field_name]
         | 
| 146 | 
            +
                    field.to_message_hash_with_string_key(@values, result)
         | 
| 147 | 
            +
                  end
         | 
| 148 | 
            +
             | 
| 149 | 
            +
                  result
         | 
| 150 | 
            +
                end
         | 
| 151 | 
            +
             | 
| 152 | 
            +
                def to_json(options = {})
         | 
| 153 | 
            +
                  to_json_hash(options).to_json(options)
         | 
| 154 | 
            +
                end
         | 
| 155 | 
            +
             | 
| 156 | 
            +
                # Return a hash-representation of the given fields for this message type that
         | 
| 157 | 
            +
                # is safe to convert to JSON.
         | 
| 158 | 
            +
                def to_json_hash(options = {})
         | 
| 159 | 
            +
                  result = {}
         | 
| 160 | 
            +
             | 
| 161 | 
            +
                  lower_camel_case = options[:lower_camel_case]
         | 
| 162 | 
            +
             | 
| 163 | 
            +
                  @values.each_key do |field_name|
         | 
| 164 | 
            +
                    value = self[field_name]
         | 
| 165 | 
            +
                    field = self.class.get_field(field_name, true)
         | 
| 166 | 
            +
             | 
| 167 | 
            +
                    # NB: to_json_hash_value should come before json_encode so as to handle
         | 
| 168 | 
            +
                    # repeated fields without extra logic.
         | 
| 169 | 
            +
                    hashed_value = if value.respond_to?(:to_json_hash_value) && !field.is_a?(::Protobuf::Field::EnumField)
         | 
| 170 | 
            +
                                     value.to_json_hash_value(options)
         | 
| 171 | 
            +
                                   elsif field.respond_to?(:json_encode)
         | 
| 172 | 
            +
                                     field.json_encode(value)
         | 
| 173 | 
            +
                                   else
         | 
| 174 | 
            +
                                     value
         | 
| 175 | 
            +
                                   end
         | 
| 176 | 
            +
             | 
| 177 | 
            +
                    key = lower_camel_case ? field.name.to_s.camelize(:lower).to_sym : field.name
         | 
| 178 | 
            +
                    result[key] = hashed_value
         | 
| 179 | 
            +
                  end
         | 
| 180 | 
            +
             | 
| 181 | 
            +
                  result
         | 
| 182 | 
            +
                end
         | 
| 183 | 
            +
             | 
| 184 | 
            +
                def to_proto
         | 
| 185 | 
            +
                  self
         | 
| 186 | 
            +
                end
         | 
| 187 | 
            +
             | 
| 188 | 
            +
                def ==(other)
         | 
| 189 | 
            +
                  return false unless other.is_a?(self.class)
         | 
| 190 | 
            +
                  each_field do |field, value|
         | 
| 191 | 
            +
                    return false unless value == other[field.name]
         | 
| 192 | 
            +
                  end
         | 
| 193 | 
            +
                  true
         | 
| 194 | 
            +
                end
         | 
| 195 | 
            +
             | 
| 196 | 
            +
                def [](name)
         | 
| 197 | 
            +
                  field = _protobuf_message_field[name]
         | 
| 198 | 
            +
                  field.value_from_values(@values)
         | 
| 199 | 
            +
                rescue # not having a field should be the exceptional state
         | 
| 200 | 
            +
                  raise if field
         | 
| 201 | 
            +
                  fail ArgumentError, "invalid field name=#{name.inspect}"
         | 
| 202 | 
            +
                end
         | 
| 203 | 
            +
             | 
| 204 | 
            +
                def []=(name, value)
         | 
| 205 | 
            +
                  set_field(name, value, true)
         | 
| 206 | 
            +
                end
         | 
| 207 | 
            +
             | 
| 208 | 
            +
                def set_field(name, value, ignore_nil_for_repeated, field = nil)
         | 
| 209 | 
            +
                  field ||= _protobuf_message_field[name]
         | 
| 210 | 
            +
             | 
| 211 | 
            +
                  if field
         | 
| 212 | 
            +
                    field.set_field(@values, value, ignore_nil_for_repeated, self)
         | 
| 213 | 
            +
                  else
         | 
| 214 | 
            +
                    fail(::Protobuf::FieldNotDefinedError, name) unless ::Protobuf.ignore_unknown_fields?
         | 
| 215 | 
            +
                  end
         | 
| 216 | 
            +
                end
         | 
| 217 | 
            +
             | 
| 218 | 
            +
                ##
         | 
| 219 | 
            +
                # Instance Aliases
         | 
| 220 | 
            +
                #
         | 
| 221 | 
            +
                alias :to_hash_value to_hash
         | 
| 222 | 
            +
                alias :to_json_hash_value to_json_hash
         | 
| 223 | 
            +
                alias :to_proto_hash to_hash
         | 
| 224 | 
            +
                alias :responds_to_has? respond_to_has?
         | 
| 225 | 
            +
                alias :respond_to_and_has? respond_to_has?
         | 
| 226 | 
            +
                alias :responds_to_and_has? respond_to_has?
         | 
| 227 | 
            +
                alias :respond_to_has_present? respond_to_has_and_present?
         | 
| 228 | 
            +
                alias :respond_to_and_has_present? respond_to_has_and_present?
         | 
| 229 | 
            +
                alias :respond_to_and_has_and_present? respond_to_has_and_present?
         | 
| 230 | 
            +
                alias :responds_to_has_present? respond_to_has_and_present?
         | 
| 231 | 
            +
                alias :responds_to_and_has_present? respond_to_has_and_present?
         | 
| 232 | 
            +
                alias :responds_to_and_has_and_present? respond_to_has_and_present?
         | 
| 233 | 
            +
             | 
| 234 | 
            +
                ##
         | 
| 235 | 
            +
                # Private Instance Methods
         | 
| 236 | 
            +
                #
         | 
| 237 | 
            +
             | 
| 238 | 
            +
                private
         | 
| 239 | 
            +
             | 
| 240 | 
            +
                def copy_to(object, method)
         | 
| 241 | 
            +
                  duplicate = proc do |obj|
         | 
| 242 | 
            +
                    case obj
         | 
| 243 | 
            +
                    when Message, String then obj.__send__(method)
         | 
| 244 | 
            +
                    else                      obj
         | 
| 245 | 
            +
                    end
         | 
| 246 | 
            +
                  end
         | 
| 247 | 
            +
             | 
| 248 | 
            +
                  object.__send__(:initialize)
         | 
| 249 | 
            +
                  @values.each do |name, value|
         | 
| 250 | 
            +
                    if value.is_a?(::Protobuf::Field::FieldArray)
         | 
| 251 | 
            +
                      object[name].replace(value.map { |v| duplicate.call(v) })
         | 
| 252 | 
            +
                    else
         | 
| 253 | 
            +
                      object[name] = duplicate.call(value)
         | 
| 254 | 
            +
                    end
         | 
| 255 | 
            +
                  end
         | 
| 256 | 
            +
                  object
         | 
| 257 | 
            +
                end
         | 
| 258 | 
            +
             | 
| 259 | 
            +
              end
         | 
| 260 | 
            +
            end
         | 
| @@ -0,0 +1,233 @@ | |
| 1 | 
            +
            require "set"
         | 
| 2 | 
            +
             | 
| 3 | 
            +
            module Protobuf
         | 
| 4 | 
            +
              class Message
         | 
| 5 | 
            +
                module Fields
         | 
| 6 | 
            +
             | 
| 7 | 
            +
                  ACCESSOR_SUFFIXES = ["", "=", "!", "?"].freeze
         | 
| 8 | 
            +
             | 
| 9 | 
            +
                  def self.extended(other)
         | 
| 10 | 
            +
                    other.extend(ClassMethods)
         | 
| 11 | 
            +
                    ::Protobuf.deprecator.define_deprecated_methods(
         | 
| 12 | 
            +
                      other.singleton_class,
         | 
| 13 | 
            +
                      :get_ext_field_by_name => :get_extension_field,
         | 
| 14 | 
            +
                      :get_ext_field_by_tag => :get_extension_field,
         | 
| 15 | 
            +
                      :get_field_by_name => :get_field,
         | 
| 16 | 
            +
                      :get_field_by_tag => :get_field,
         | 
| 17 | 
            +
                    )
         | 
| 18 | 
            +
                  end
         | 
| 19 | 
            +
             | 
| 20 | 
            +
                  module ClassMethods
         | 
| 21 | 
            +
                    def inherited(subclass)
         | 
| 22 | 
            +
                      inherit_fields!(subclass)
         | 
| 23 | 
            +
                      subclass.const_set("PROTOBUF_MESSAGE_REQUIRED_FIELD_TAGS", subclass.required_field_tags)
         | 
| 24 | 
            +
                      subclass.const_set("PROTOBUF_MESSAGE_GET_FIELD", subclass.field_store)
         | 
| 25 | 
            +
                      subclass.class_eval <<-RUBY, __FILE__, __LINE__
         | 
| 26 | 
            +
                        def _protobuf_message_field
         | 
| 27 | 
            +
                          PROTOBUF_MESSAGE_GET_FIELD
         | 
| 28 | 
            +
                        end
         | 
| 29 | 
            +
             | 
| 30 | 
            +
                        def _protobuf_message_unset_required_field_tags
         | 
| 31 | 
            +
                          @_protobuf_message_unset_required_field_tags ||= PROTOBUF_MESSAGE_REQUIRED_FIELD_TAGS.dup
         | 
| 32 | 
            +
                        end
         | 
| 33 | 
            +
                      RUBY
         | 
| 34 | 
            +
                    end
         | 
| 35 | 
            +
             | 
| 36 | 
            +
                    ##
         | 
| 37 | 
            +
                    # Field Definition Methods
         | 
| 38 | 
            +
                    #
         | 
| 39 | 
            +
             | 
| 40 | 
            +
                    # Define an optional field.
         | 
| 41 | 
            +
                    #
         | 
| 42 | 
            +
                    def optional(type_class, name, tag, options = {})
         | 
| 43 | 
            +
                      define_field(:optional, type_class, name, tag, options)
         | 
| 44 | 
            +
                    end
         | 
| 45 | 
            +
             | 
| 46 | 
            +
                    # Define a repeated field.
         | 
| 47 | 
            +
                    #
         | 
| 48 | 
            +
                    def repeated(type_class, name, tag, options = {})
         | 
| 49 | 
            +
                      define_field(:repeated, type_class, name, tag, options)
         | 
| 50 | 
            +
                    end
         | 
| 51 | 
            +
             | 
| 52 | 
            +
                    # Define a required field.
         | 
| 53 | 
            +
                    #
         | 
| 54 | 
            +
                    def required(type_class, name, tag, options = {})
         | 
| 55 | 
            +
                      required_field_tags << tag
         | 
| 56 | 
            +
                      define_field(:required, type_class, name, tag, options)
         | 
| 57 | 
            +
                    end
         | 
| 58 | 
            +
             | 
| 59 | 
            +
                    # Define a map field.
         | 
| 60 | 
            +
                    #
         | 
| 61 | 
            +
                    def map(key_type_class, value_type_class, name, tag, options = {})
         | 
| 62 | 
            +
                      # manufacture a message that represents the map entry, used for
         | 
| 63 | 
            +
                      # serialization and deserialization
         | 
| 64 | 
            +
                      entry_type = Class.new(::Protobuf::Message) do
         | 
| 65 | 
            +
                        set_option :map_entry, true
         | 
| 66 | 
            +
                        optional key_type_class, :key, 1
         | 
| 67 | 
            +
                        optional value_type_class, :value, 2
         | 
| 68 | 
            +
                      end
         | 
| 69 | 
            +
                      define_field(:repeated, entry_type, name, tag, options)
         | 
| 70 | 
            +
                    end
         | 
| 71 | 
            +
             | 
| 72 | 
            +
                    # Define an extension range.
         | 
| 73 | 
            +
                    #
         | 
| 74 | 
            +
                    def extensions(range)
         | 
| 75 | 
            +
                      extension_ranges << range
         | 
| 76 | 
            +
                    end
         | 
| 77 | 
            +
             | 
| 78 | 
            +
                    ##
         | 
| 79 | 
            +
                    # Field Access Methods
         | 
| 80 | 
            +
                    #
         | 
| 81 | 
            +
                    def all_fields
         | 
| 82 | 
            +
                      @all_fields ||= field_store.values.uniq.sort_by(&:tag)
         | 
| 83 | 
            +
                    end
         | 
| 84 | 
            +
             | 
| 85 | 
            +
                    def extension_fields
         | 
| 86 | 
            +
                      @extension_fields ||= all_fields.select(&:extension?)
         | 
| 87 | 
            +
                    end
         | 
| 88 | 
            +
             | 
| 89 | 
            +
                    def extension_ranges
         | 
| 90 | 
            +
                      @extension_ranges ||= []
         | 
| 91 | 
            +
                    end
         | 
| 92 | 
            +
             | 
| 93 | 
            +
                    def required_field_tags
         | 
| 94 | 
            +
                      @required_field_tags ||= []
         | 
| 95 | 
            +
                    end
         | 
| 96 | 
            +
             | 
| 97 | 
            +
                    def extension_tag?(tag)
         | 
| 98 | 
            +
                      tag.respond_to?(:to_i) && get_extension_field(tag).present?
         | 
| 99 | 
            +
                    end
         | 
| 100 | 
            +
             | 
| 101 | 
            +
                    def field_store
         | 
| 102 | 
            +
                      @field_store ||= {}
         | 
| 103 | 
            +
                    end
         | 
| 104 | 
            +
             | 
| 105 | 
            +
                    def fields
         | 
| 106 | 
            +
                      @fields ||= all_fields.reject(&:extension?)
         | 
| 107 | 
            +
                    end
         | 
| 108 | 
            +
             | 
| 109 | 
            +
                    def field_tag?(tag, allow_extension = false)
         | 
| 110 | 
            +
                      tag.respond_to?(:to_i) && get_field(tag, allow_extension).present?
         | 
| 111 | 
            +
                    end
         | 
| 112 | 
            +
             | 
| 113 | 
            +
                    def get_extension_field(name_or_tag)
         | 
| 114 | 
            +
                      field = field_store[name_or_tag]
         | 
| 115 | 
            +
                      field if field.try(:extension?) { false }
         | 
| 116 | 
            +
                    end
         | 
| 117 | 
            +
             | 
| 118 | 
            +
                    def get_field(name_or_tag, allow_extension = false)
         | 
| 119 | 
            +
                      field = field_store[name_or_tag]
         | 
| 120 | 
            +
             | 
| 121 | 
            +
                      if field && (allow_extension || !field.extension?)
         | 
| 122 | 
            +
                        field
         | 
| 123 | 
            +
                      else
         | 
| 124 | 
            +
                        nil
         | 
| 125 | 
            +
                      end
         | 
| 126 | 
            +
                    end
         | 
| 127 | 
            +
             | 
| 128 | 
            +
                    def define_field(rule, type_class, fully_qualified_field_name, tag, options)
         | 
| 129 | 
            +
                      raise_if_tag_collision(tag, fully_qualified_field_name)
         | 
| 130 | 
            +
                      raise_if_name_collision(fully_qualified_field_name)
         | 
| 131 | 
            +
             | 
| 132 | 
            +
                      # Determine appropirate accessor for fields depending on name collisions via extensions:
         | 
| 133 | 
            +
             | 
| 134 | 
            +
                      # Case 1: Base field = "string_field" and no extensions of the same name
         | 
| 135 | 
            +
                      # Result:
         | 
| 136 | 
            +
                      #   message.string_field #=> @values["string_field"]
         | 
| 137 | 
            +
                      #   message[:string_field] #=> @values["string_field"]
         | 
| 138 | 
            +
                      #   message['string_field'] #=> @values["string_field"]
         | 
| 139 | 
            +
             | 
| 140 | 
            +
                      # Case 2: Base field = "string_field" and extension 1 = ".my_package.string_field", extension N = ".package_N.string_field"...
         | 
| 141 | 
            +
                      # Result:
         | 
| 142 | 
            +
                      #   message.string_field #=> @values["string_field"]
         | 
| 143 | 
            +
                      #   message[:string_field] #=> @values["string_field"]
         | 
| 144 | 
            +
                      #   message['string_field'] #=> @values["string_field"]
         | 
| 145 | 
            +
                      #   message[:'.my_package.string_field'] #=> @values[".my_package.string_field"]
         | 
| 146 | 
            +
                      #   message['.my_package.string_field']  #=> @values[".my_package.string_field"]
         | 
| 147 | 
            +
             | 
| 148 | 
            +
                      # Case 3: No base field, extension 1 = ".my_package.string_field", extension 2 = ".other_package.string_field", extension N...
         | 
| 149 | 
            +
                      # Result:
         | 
| 150 | 
            +
                      #   message.string_field #=> raise NoMethodError (no simple accessor allowed)
         | 
| 151 | 
            +
                      #   message[:string_field] #=> raise NoMethodError (no simple accessor allowed)
         | 
| 152 | 
            +
                      #   message['string_field'] #=> raise NoMethodError (no simple accessor allowed)
         | 
| 153 | 
            +
                      #   message[:'.my_package.string_field'] #=> @values[".my_package.string_field"]
         | 
| 154 | 
            +
                      #   message['.my_package.string_field']  #=> @values[".my_package.string_field"]
         | 
| 155 | 
            +
                      #   message[:'.other_package.string_field'] #=> @values[".other_package.string_field"]
         | 
| 156 | 
            +
                      #   message['.other_package.string_field']  #=> @values[".other_package.string_field"]
         | 
| 157 | 
            +
             | 
| 158 | 
            +
                      # Case 4: No base field, extension = ".my_package.string_field", no other extensions
         | 
| 159 | 
            +
                      # Result:
         | 
| 160 | 
            +
                      #   message.string_field #=> @values[".my_package.string_field"]
         | 
| 161 | 
            +
                      #   message[:string_field] #=> @values[".my_package.string_field"]
         | 
| 162 | 
            +
                      #   message['string_field'] #=> @values[".my_package.string_field"]
         | 
| 163 | 
            +
                      #   message[:'.my_package.string_field'] #=> @values[".my_package.string_field"]
         | 
| 164 | 
            +
                      #   message[:'.my_package.string_field'] #=> @values[".my_package.string_field"]
         | 
| 165 | 
            +
             | 
| 166 | 
            +
                      simple_name =
         | 
| 167 | 
            +
                        if options[:extension]
         | 
| 168 | 
            +
                          base_name = fully_qualified_field_name.to_s.split('.').last.to_sym
         | 
| 169 | 
            +
                          if field_store[base_name]
         | 
| 170 | 
            +
                            # Case 3
         | 
| 171 | 
            +
                            if field_store[base_name].extension?
         | 
| 172 | 
            +
                              remove_existing_accessors(base_name)
         | 
| 173 | 
            +
                            end
         | 
| 174 | 
            +
                            nil
         | 
| 175 | 
            +
                          # Case 4
         | 
| 176 | 
            +
                          else
         | 
| 177 | 
            +
                            base_name
         | 
| 178 | 
            +
                          end
         | 
| 179 | 
            +
                        else
         | 
| 180 | 
            +
                          # Case 1
         | 
| 181 | 
            +
                          fully_qualified_field_name
         | 
| 182 | 
            +
                        end
         | 
| 183 | 
            +
             | 
| 184 | 
            +
                      field = ::Protobuf::Field.build(self, rule, type_class, fully_qualified_field_name,
         | 
| 185 | 
            +
                                                      tag, simple_name, options)
         | 
| 186 | 
            +
                      field_store[tag] = field
         | 
| 187 | 
            +
                      field_store[fully_qualified_field_name.to_sym] = field
         | 
| 188 | 
            +
                      field_store[fully_qualified_field_name.to_s] = field
         | 
| 189 | 
            +
                      if simple_name && simple_name != fully_qualified_field_name
         | 
| 190 | 
            +
                        field_store[simple_name.to_sym] = field
         | 
| 191 | 
            +
                        field_store[simple_name.to_s] = field
         | 
| 192 | 
            +
                      end
         | 
| 193 | 
            +
                      # defining a new field for the message will cause cached @all_fields, @extension_fields,
         | 
| 194 | 
            +
                      # and @fields to be incorrect; reset them
         | 
| 195 | 
            +
                      @all_fields = @extension_fields = @fields = nil
         | 
| 196 | 
            +
                    end
         | 
| 197 | 
            +
             | 
| 198 | 
            +
                    def remove_existing_accessors(accessor)
         | 
| 199 | 
            +
                      field_store.delete(accessor.to_sym).try(:fully_qualified_name_only!)
         | 
| 200 | 
            +
                      field_store.delete(accessor.to_s)
         | 
| 201 | 
            +
                      ACCESSOR_SUFFIXES.each do |modifier|
         | 
| 202 | 
            +
                        begin
         | 
| 203 | 
            +
                          remove_method("#{accessor}#{modifier}")
         | 
| 204 | 
            +
                        # rubocop: disable Lint/HandleExceptions
         | 
| 205 | 
            +
                        rescue NameError
         | 
| 206 | 
            +
                          # Do not remove the method
         | 
| 207 | 
            +
                        end
         | 
| 208 | 
            +
                      end
         | 
| 209 | 
            +
                    end
         | 
| 210 | 
            +
             | 
| 211 | 
            +
                    def raise_if_tag_collision(tag, field_name)
         | 
| 212 | 
            +
                      if get_field(tag, true)
         | 
| 213 | 
            +
                        fail TagCollisionError, %(Field number #{tag} has already been used in "#{name}" by field "#{field_name}".)
         | 
| 214 | 
            +
                      end
         | 
| 215 | 
            +
                    end
         | 
| 216 | 
            +
             | 
| 217 | 
            +
                    def raise_if_name_collision(field_name)
         | 
| 218 | 
            +
                      if get_field(field_name, true)
         | 
| 219 | 
            +
                        fail DuplicateFieldNameError, %(Field name #{field_name} has already been used in "#{name}".)
         | 
| 220 | 
            +
                      end
         | 
| 221 | 
            +
                    end
         | 
| 222 | 
            +
             | 
| 223 | 
            +
                    def inherit_fields!(subclass)
         | 
| 224 | 
            +
                      instance_variables.each do |iv|
         | 
| 225 | 
            +
                        subclass.instance_variable_set(iv, instance_variable_get(iv))
         | 
| 226 | 
            +
                      end
         | 
| 227 | 
            +
                    end
         | 
| 228 | 
            +
                    private :inherit_fields!
         | 
| 229 | 
            +
             | 
| 230 | 
            +
                  end
         | 
| 231 | 
            +
                end
         | 
| 232 | 
            +
              end
         | 
| 233 | 
            +
            end
         |