[Groonga-commit] ranguba/groonga-client at bbcdd32 [master] select: support command version 3

Back to archive index

Kouhei Sutou null+****@clear*****
Mon May 30 12:13:54 JST 2016


Kouhei Sutou	2016-05-30 12:13:54 +0900 (Mon, 30 May 2016)

  New Revision: bbcdd324787e3f4199c7d2a22e1efd26ff4a91c7
  https://github.com/ranguba/groonga-client/commit/bbcdd324787e3f4199c7d2a22e1efd26ff4a91c7

  Message:
    select: support command version 3

  Added files:
    test/response/test-select-command-version3.rb
  Modified files:
    lib/groonga/client/response/base.rb
    lib/groonga/client/response/select.rb
    test/response/test-select-command-version1.rb

  Modified: lib/groonga/client/response/base.rb (+5 -1)
===================================================================
--- lib/groonga/client/response/base.rb    2016-05-30 10:56:29 +0900 (5226446)
+++ lib/groonga/client/response/base.rb    2016-05-30 12:13:54 +0900 (3d2722b)
@@ -61,22 +61,26 @@ module Groonga
       class Base
         class << self
           def parse(command, raw_response)
+            return_code = nil
             case command.output_type
             when :json
               response = JSON.parse(raw_response)
               if response.is_a?(::Array)
                 header, body = response
+                return_code = header[0] if header
               else
                 header = response["header"]
                 body = response["body"]
+                return_code = header["return_code"] if header
               end
             when :xml
               header, body = parse_xml(raw_response)
+              return_code = header[0] if header
             else
               header = nil
               body = raw_response
             end
-            if header.nil? or header[0].zero?
+            if header.nil? or return_code == 0
               response = new(command, header, body)
             else
               response = Error.new(command, header, body)

  Modified: lib/groonga/client/response/select.rb (+51 -23)
===================================================================
--- lib/groonga/client/response/select.rb    2016-05-30 10:56:29 +0900 (61ae899)
+++ lib/groonga/client/response/select.rb    2016-05-30 12:13:54 +0900 (27d7a65)
@@ -36,33 +36,42 @@ module Groonga
 
         private
         def parse_body(body)
-          @n_hits, @records = parse_match_records(body.first)
-          @drilldowns = parse_drilldowns(body[1..-1])
+          if body.is_a?(::Array)
+            @n_hits, @records = parse_match_records_v1(body.first)
+            @drilldowns = parse_drilldowns_v1(body[1..-1])
+          else
+            @n_hits, @records = parse_match_records_v3(body)
+            @drilldowns = parse_drilldowns_v3(body["drilldowns"])
+          end
           body
         end
 
-        def parse_result(raw_result)
-          n_hits = raw_result.first.first
+        def parse_records(raw_columns, raw_records)
           column_names = {}
-          properties = raw_result[1].collect do |column_name, column_type|
-            base_column_name = column_name
+          columns = raw_columns.collect do |column|
+            if column.is_a?(::Array)
+              name, type = column
+            else
+              name = column["name"]
+              type = column["type"]
+            end
+            base_column_name = name
             suffix = 2
-            while column_names.key?(column_name)
-              column_name = "#{base_column_name}#{suffix}"
+            while column_names.key?(name)
+              name = "#{base_column_name}#{suffix}"
               suffix += 1
             end
-            column_names[column_name] = true
-            [column_name, column_type]
+            column_names[name] = true
+            [name, type]
           end
-          infos = raw_result[2..-1] || []
-          items = infos.collect do |info|
-            item = {}
-            properties.each_with_index do |(name, type), i|
-              item[name] = convert_value(info[i], type)
+
+          (raw_records || []).collect do |raw_record|
+            record = {}
+            columns.each_with_index do |(name, type), i|
+              record[name] = convert_value(raw_record[i], type)
             end
-            item
+            record
           end
-          [n_hits, items]
         end
 
         def convert_value(value, type)
@@ -74,19 +83,38 @@ module Groonga
           end
         end
 
-        def parse_match_records(raw_records)
-          parse_result(raw_records)
+        def parse_match_records_v1(raw_records)
+          [
+            raw_records.first.first,
+            parse_records(raw_records[1], raw_records[2..-1]),
+          ]
         end
 
-        def parse_drilldowns(raw_drilldowns)
+        def parse_match_records_v3(raw_records)
+          [
+            raw_records["n_hits"],
+            parse_records(raw_records["columns"], raw_records["records"]),
+          ]
+        end
+
+        def parse_drilldowns_v1(raw_drilldowns)
           (raw_drilldowns || []).collect.with_index do |raw_drilldown, i|
             key =****@comma*****[i]
-            n_hits, items = parse_result(raw_drilldown)
-            Drilldown.new(key, n_hits, items)
+            n_hits, records = parse_match_records_v1(raw_drilldown)
+            Drilldown.new(key, n_hits, records)
+          end
+        end
+
+        def parse_drilldowns_v3(raw_drilldowns)
+          (raw_drilldowns || {}).collect do |(key, raw_drilldown)|
+            n_hits, records = parse_match_records_v3(raw_drilldown)
+            Drilldown.new(key, n_hits, records)
           end
         end
 
-        class Drilldown < Struct.new(:key, :n_hits, :items)
+        class Drilldown < Struct.new(:key, :n_hits, :records)
+          # @deprecated since 0.2.6. Use {#records} instead.
+          alias_method :items, :records
         end
       end
     end

  Modified: test/response/test-select-command-version1.rb (+2 -2)
===================================================================
--- test/response/test-select-command-version1.rb    2016-05-30 10:56:29 +0900 (710abd5)
+++ test/response/test-select-command-version1.rb    2016-05-30 12:13:54 +0900 (b08c66c)
@@ -88,7 +88,7 @@ class TestResponseSelectCommandVersion1 < Test::Unit::TestCase
     class TestDrilldowns < self
       def setup
         pair_arguments = {
-          "drilldown" => "_key",
+          "drilldown" => "tag",
           "drilldown_output_columns" => "_key,_nsubrecs",
         }
         @command = Groonga::Command::Select.new("select", pair_arguments)
@@ -108,7 +108,7 @@ class TestResponseSelectCommandVersion1 < Test::Unit::TestCase
             ["rroonga",  9],
           ],
         ]
-        assert_equal(["_key"],
+        assert_equal(["tag"],
                      drilldowns(body).collect(&:key))
       end
 

  Added: test/response/test-select-command-version3.rb (+247 -0) 100644
===================================================================
--- /dev/null
+++ test/response/test-select-command-version3.rb    2016-05-30 12:13:54 +0900 (56ab249)
@@ -0,0 +1,247 @@
+# Copyright (C) 2013-2016  Kouhei Sutou <kou �� clear-code.com>
+# Copyright (C) 2013  Kosuke Asami
+#
+# This library is free software; you can redistribute it and/or
+# modify it under the terms of the GNU Lesser General Public
+# License as published by the Free Software Foundation; either
+# version 2.1 of the License, or (at your option) any later version.
+#
+# This library is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+# Lesser General Public License for more details.
+#
+# You should have received a copy of the GNU Lesser General Public
+# License along with this library; if not, write to the Free Software
+# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
+
+require "response/helper"
+
+class TestResponseSelectCommandVersion3 < Test::Unit::TestCase
+  class TestParseRawResponse < self
+    include TestResponseHelper
+
+    def test_select
+      header = {
+        "return_code"  => 0,
+        "start_time"   => 1372430096.70991,
+        "elapsed_time" => 0.000522851943969727,
+      }
+      body = {
+        "n_hits" => 1,
+        "columns" => [
+          {
+            "name" => "_id",
+            "type" => "UInt32",
+          },
+        ],
+        "records" => [
+          1,
+        ],
+      }
+      raw_response = {
+        "header" => header,
+        "body"   => body,
+      }.to_json
+
+      response = parse_raw_response("select", raw_response)
+      assert_equal(Groonga::Client::Response::Select, response.class)
+    end
+  end
+
+  class TestBody < self
+    def setup
+      @command = Groonga::Command::Select.new("select", {})
+    end
+
+    def test_n_hits
+      response = create_response({
+                                   "n_hits" => 29,
+                                   "columns" => [
+                                     {
+                                       "name" => "_id",
+                                       "type" => "UInt32",
+                                     },
+                                   ],
+                                   "records" => [
+                                   ],
+                                 })
+      assert_equal(29, response.n_hits)
+    end
+
+    private
+    def create_response(body)
+      header = {
+        "return_code"  => 0,
+        "start_time"   => 1372430096.70991,
+        "elapsed_time" => 0.000522851943969727,
+      }
+      Groonga::Client::Response::Select.new(@command, header, body)
+    end
+
+    class TestRecords < self
+      def test_time
+        updated_at = 1379040474
+        assert_equal([{"updated_at" => Time.at(updated_at)}],
+                     records({
+                               "n_hits" => 1,
+                               "columns" => [
+                                 {
+                                   "name" => "updated_at",
+                                   "type" => "Time",
+                                 },
+                               ],
+                               "records" => [
+                                 [updated_at],
+                               ],
+                             }))
+      end
+
+      def test_duplicated_column_name
+        assert_equal([
+                       {
+                         "html_escape"  => "content1",
+                         "html_escape2" => "content2",
+                         "html_escape3" => "content3",
+                       }
+                     ],
+                     records({
+                               "n_hits" => 1,
+                               "columns" => [
+                                 {
+                                   "name" => "html_escape",
+                                   "type" => nil,
+                                 },
+                                 {
+                                   "name" => "html_escape",
+                                   "type" => nil,
+                                 },
+                                 {
+                                   "name" => "html_escape",
+                                   "type" => nil,
+                                 }
+                               ],
+                               "records" => [
+                                 ["content1", "content2", "content3"],
+                               ],
+                             }))
+      end
+
+      private
+      def records(body)
+        create_response(body).records
+      end
+    end
+
+    class TestDrilldowns < self
+      def setup
+        pair_arguments = {
+          "drilldown" => "tag",
+          "drilldown_output_columns" => "_key,_nsubrecs",
+        }
+        @command = Groonga::Command::Select.new("select", pair_arguments)
+      end
+
+      def test_key
+        body = {
+          "n_hits" => 0,
+          "columns" => [],
+          "records" => [],
+          "drilldowns" => {
+            "tag" => {
+              "n_hits" => 29,
+              "columns" => [
+                {
+                  "name" => "_key",
+                  "type" => "ShortText",
+                },
+                {
+                  "name" => "_nsubrecs",
+                  "type" => "Int32",
+                },
+              ],
+              "records" => [
+                ["groonga", 29],
+                ["Ruby",    19],
+                ["rroonga",  9],
+              ],
+            },
+          },
+        }
+        assert_equal(["tag"],
+                     drilldowns(body).collect(&:key))
+      end
+
+      def test_n_hits
+        body = {
+          "n_hits" => 0,
+          "columns" => [],
+          "records" => [],
+          "drilldowns" => {
+            "tag" => {
+              "n_hits" => 29,
+              "columns" => [
+                {
+                  "name" => "_key",
+                  "type" => "ShortText",
+                },
+                {
+                  "name" => "_nsubrecs",
+                  "type" => "Int32",
+                },
+              ],
+              "records" => [
+                ["groonga", 29],
+                ["Ruby",    19],
+                ["rroonga",  9],
+              ],
+            },
+          },
+        }
+        assert_equal([29],
+                     drilldowns(body).collect(&:n_hits))
+      end
+
+      def test_items
+        body = {
+          "n_hits" => 0,
+          "columns" => [],
+          "records" => [],
+          "drilldowns" => {
+            "tag" => {
+              "n_hits" => 29,
+              "columns" => [
+                {
+                  "name" => "_key",
+                  "type" => "ShortText",
+                },
+                {
+                  "name" => "_nsubrecs",
+                  "type" => "Int32",
+                },
+              ],
+              "records" => [
+                ["groonga", 29],
+                ["Ruby",    19],
+                ["rroonga",  9],
+              ],
+            },
+          },
+        }
+        assert_equal([
+                       [
+                         {"_key" => "groonga", "_nsubrecs" => 29},
+                         {"_key" => "Ruby",    "_nsubrecs" => 19},
+                         {"_key" => "rroonga", "_nsubrecs" =>  9},
+                       ],
+                     ],
+                     drilldowns(body).collect(&:items))
+      end
+
+      private
+      def drilldowns(body)
+        create_response(body).drilldowns
+      end
+    end
+  end
+end
-------------- next part --------------
HTML����������������������������...
下載 



More information about the Groonga-commit mailing list
Back to archive index