{"record":{"id":"3e43ccefceebc604","repo":"puppetlabs/puppet","slug":"a-block-is-required","errorCode":null,"errorMessage":"A block is required","messagePattern":"A block is required","errorType":"validation","errorClass":"ArgumentError","httpStatus":null,"severity":"error","filePath":"lib/puppet/http/response_net_http.rb","lineNumber":24,"sourceCode":"class Puppet::HTTP::ResponseNetHTTP < Puppet::HTTP::Response\n  # Create a response associated with the URL.\n  #\n  # @param [URI] url\n  # @param [Net::HTTPResponse] nethttp The response\n  def initialize(url, nethttp)\n    super(url, nethttp.code.to_i, nethttp.message)\n\n    @nethttp = nethttp\n  end\n\n  # (see Puppet::HTTP::Response#body)\n  def body\n    @nethttp.body\n  end\n\n  # (see Puppet::HTTP::Response#read_body)\n  def read_body(&block)\n    raise ArgumentError, \"A block is required\" unless block_given?\n\n    @nethttp.read_body(&block)\n  end\n\n  # (see Puppet::HTTP::Response#success?)\n  def success?\n    @nethttp.is_a?(Net::HTTPSuccess)\n  end\n\n  # (see Puppet::HTTP::Response#[])\n  def [](name)\n    @nethttp[name]\n  end\n\n  # (see Puppet::HTTP::Response#each_header)\n  def each_header(&block)\n    @nethttp.each_header(&block)\n  end","sourceCodeStart":6,"sourceCodeEnd":42,"githubUrl":"https://github.com/puppetlabs/puppet/blob/e227c27540975c25aa22d533a52424a9d2fc886a/lib/puppet/http/response_net_http.rb#L6-L42","documentation":"Puppet::HTTP::ResponseNetHTTP#read_body streams the response body by yielding decoded chunks to a block (it delegates to Net::HTTP's read_body). Calling it without a block cannot stream anything, so it raises ArgumentError; to get the whole body as a String use Response#body instead.","triggerScenarios":"response.read_body with no block (e.g. assigning its result: body = response.read_body); forwarding &block when block is nil; code ported from Net::HTTP where read_body without a block returns the full body string.","commonSituations":"Developers used to net/http semantics calling read_body expecting a String return; partial refactors where the consumer callback was removed but the call kept; block passed as &nil via an optional kwarg default.","solutions":["Pass a block: response.read_body { |chunk| out.write(chunk) }.","If you want the full body, call response.body instead.","When forwarding, guard with block_given? before calling read_body."],"exampleFix":"# before\nbody = response.read_body\n\n# after (streaming)\nresponse.read_body { |chunk| socket.write(chunk) }\n\n# after (full body)\nbody = response.body","handlingStrategy":"validation","validationCode":"if block\n  response.read_body(&block)\nelse\n  response.body\nend","typeGuard":"has_block = ->(&b) { !b.nil? }\nraise ArgumentError, 'pass a block or use #body' unless has_block { |&blk| blk }","tryCatchPattern":null,"preventionTips":["Use response.body for the full string; read_body is streaming-only.","When forwarding optional blocks, check block_given? before delegating."],"tags":["puppet","http","response","streaming","ruby"],"backgroundTag":"missing-block-argument","analyzedSha":"e227c27540975c25aa22d533a52424a9d2fc886a","analyzedAt":"2026-08-21T20:49:46.650Z","schemaVersion":2},"datasetVersion":"2026-08-21T23:17:16.201Z"}